Logical API for multi-API access, does not work

I’ve got as follows

“Client App” - this is a Winforms NET 6.0 desktop application. I’ve used Auth0.OidcClient.Core and built a web-based Auth0 login experience into this app. This works fine. I get an access token on a successful login, and a refresh token which my code uses to do a refresh and get a replacement access token at regular intervals.

“Api A” - this is an ASP NET Core 6.0 Web API which I have deployed to Azure. This uses the Microsoft.AspNetCore.Authentication.JwtBearer. The configuration code is shown below. This API is registered in Auth0 and I can use my Client App token to call the API. So far, so good.

Now I have created “Api B” and this is where the problem begins. I want to use my Client App access token to call both Api A and Api B. Api B is, like Api A, an ASP NET Core 6.0 Web API, and both APIs are configured to use JwtBearer authentication. Across both APIs, controllers have the [Authorize] attribute, but nothing more (no authentication “Policy”, for example).

I have reviewed this article, which appears to specifically address my scenario: Configure Logical API for Multiple APIs

So, I have taken the following steps:

  1. Registered API B in Auth0

  2. Registered a new logical API, let’s call it “API L”, in Auth0

  3. As I have no existing Scopes, but the article says I need them to support this scenario, I created new scopes as follows

-In the Permissions tab for API A, I created a new permission called “api:APIA”, intended to represent permission to access API A and all its actions and resources
-In the Permissions tab for API B, I created a new permission called “api:APIB”, intended to represent permission to access API B and all its actions and resources
-In the Permissions tab for API L, I created a new permission called “api:APIA”, matching the above
-In the Permissions tab for API L, I created a new permission called “api:APIB”, matching the above

  1. Modified my client code to send a login request with the audience for “API L”, and with the new Scopes “api:APIA api:APIB” included in the request.

I found the section of the article which talks about Scopes to be unclear. However My working assumption is that because I now have scopes in API L (“api:APIA”, “api:APIB”) which have identical names to the scopes declared for each of API A (“api:APIA”) and API B (“api:APIB”), Auth0 will then do the necessary magic that allows a token issued for the Logical API to be used to access the other two APIs.

I have not changed the Audience and Domain configuration on the ASP/Azure side of API A or API B. I presume I shouldn’t need to do so in order to make this work.

However, now, API A will not authorise a token issued to my Client App. It returns an “Unauthorised” error.

I am trying to work out what I’m missing.

I did wonder if the fact that the token includes any scope at all (whereas in my previous configuration, there were no scopes defined) might be enough to prevent my API A from authenticating successfully, without making some kind of configuration change to the API. Perhaps I have to instruct the API explicitly to disregard Scopes?

To be clear, I don’t need scopes at all. I just want my client to be able to authenticate to both APIs, using the same token, to access the full functionality of both APIs. However my presumption is that the scopes are necessary to create the magic glue between a “logical api” and a set of concrete APIs.

I would appreciate any pointers here about what i might be doing wrong??

Config code for API A

var builder = WebApplication.CreateBuilder(args);

var GoogleTextSpeechApiKey = builder.Configuration[“GoogleTextSpeech:apikey”];

builder.Services.AddAuthentication(options =>
options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
}).AddJwtBearer(options =>
options.Authority = $“https://{builder.Configuration[“Auth0:Domain”]}/”;
options.Audience = builder.Configuration[“Auth0:Audience”];
options.TokenValidationParameters = new TokenValidationParameters
NameClaimType = ClaimTypes.NameIdentifier



var app = builder.Build();

if (app.Environment.IsDevelopment())




It seems like you’re facing issues with implementing a logical API for multi-API access. To help you troubleshoot the problem, I’ll need more specific details about your setup, the technologies you’re using, and the issues you’re encountering. However, I can provide some general guidance on setting up a logical API for multiple API access:

  1. Design Your API Logic:

    • Plan the structure and endpoints of your logical API. Decide how you want to group and manage different APIs under this logical API. Determine how the logical API will route requests to the appropriate underlying APIs.
  2. API Gateway:

    • An API gateway acts as a central entry point for all your APIs. It can handle request routing, authentication, authorization, rate limiting, and other cross-cutting concerns. Popular API gateway solutions include Amazon API Gateway, Apigee, Kong, and more.
  3. Authentication and Authorization:

    • Implement a unified authentication and authorization mechanism for your logical API. This might involve using OAuth 2.0, JWT (JSON Web Tokens), API keys, or other authentication methods.
  4. Routing and Mapping:

    • Define rules for how requests to your logical API are mapped to specific underlying APIs. This could be based on request paths, headers, or other criteria. Ensure that the routing logic is correctly implemented.
  5. Error Handling and Logging:

    • Implement consistent error handling and logging across your logical API. This will help you troubleshoot issues and provide a better experience for developers using your API.
  6. Testing and Debugging:

    • Test your logical API thoroughly to ensure that requests are being correctly routed to the underlying APIs. Use tools like Postman or curl to make requests and examine the responses.
  7. Documentation:

    • Provide comprehensive documentation for developers using your logical API. Explain how to authenticate, access different APIs, and interpret responses.
  8. Monitor and Scale:

    • Set up monitoring to keep track of API usage, performance, and errors. Ensure that your infrastructure can handle the expected load and consider scaling options if necessary.
  9. Cross-Origin Resource Sharing (CORS):

    • If your logical API will be accessed by different client applications on different domains, ensure you configure CORS settings correctly to allow requests from authorized domains.
  10. Security Considerations:

    • Pay attention to security practices such as input validation, output encoding, and protection against common vulnerabilities like SQL injection and cross-site scripting.
      If you’re facing specific issues or errors, it would be helpful to provide more details about the technologies you’re using, the steps you’ve taken so far, and any error messages you’re encountering. This will enable me to provide more targeted guidance to help you troubleshoot and resolve the problem.

I have not changed the Audience and Domain configuration on the ASP/Azure side of API A or API B. I presume I shouldn’t need to do so in order to make this work.

@robertellisuk Why do you assume this? I thought that’s exactly what needs to be done in such a scenario. Could you elaborate, please? I’m facing a similar scenario at the moment.

I made that assumption because to my mind, if the inverse assumption held true, there would be no benefit in having a logical api as a single entity for implementation of multiple ‘concrete’ APIs. In other words, my thinking was, ‘if I have to update the configuration of all of the composite APIs, then what is the point of the Logical API to begin with?’

Anyway, as it turned out you are quite right to question this assumption, and my thinking must have been awry, because that was the key to making it work. I had to add the logical API audience to each of the discrete APIs.

I’m still not sure I fully understand much of this (OAuth) to be honest. It’s genuinely difficult stuff.

Good luck!

I think that’s the whole point of the Logical API - that you kind of merge the configuration of all your underlying APIs into one. To be fair, I also don’t see too many benefits of this approach. It seems it just solves the issue where you need to generate another access token (to access a different API, so you have different level of access basically) but you use refresh tokens at the same time. It looks like the refresh token is bound to single audience only, so every time you try to create another token, with different audience it will just fail.

I’m not 100% sure I’m making any sense now either, frankly. Maybe someone from Auth0 team will confirm.