Getting Scope Validating error in Identity Server 4 using JavaScript Client in asp.net core

37,670

Solution 1

While your client (application) is configured or allowed to request the openid resource (or scope), your identity server is not configured for the openid identity resource

You need to add it as an identity resource similar to how its done here and have a method that returns all your identity resources that you want to use like its done here.

In short add a new method to your Config.cs that looks like this:

public static List<IdentityResource> GetIdentityResources()
{
    return new List<IdentityResource>
    {
        new IdentityResources.OpenId(),
        new IdentityResources.Profile() // <-- usefull
    };
}

And then to your identityservers service container add your identity resource configuration like this:

 services.AddIdentityServer()
    .AddTemporarySigningCredential()
    .AddInMemoryApiResources(Config.GetApiResources())
    .AddInMemoryClients(Config.GetClients())
    .AddInMemoryIdentityResources(Config.GetIdentityResources()); // <-- adding identity resources/scopes

Solution 2

In my particular case, this was caused by a missing call to .AddInMemoryApiScopes(), as shown by inspecting the return value of the below under the debugger (in particular, the Error and HttpStatusCode fields indicated invalid scope as you reported) from a simple console application.

await client.RequestClientCredentialsTokenAsync(new ClientCredentialsTokenRequest { ... });

To resolve this, I added the below to method to my custom configuration class

public static IEnumerable<ApiScope> Scopes
{
    get
    {
        return new List<ApiScope> 
        { 
            new ApiScope("my-scope-name", "Friendly scope name") 
        };
    }
}

And then called this as such from within Startup.ConfigureServices()

    services.AddIdentityServer()
        .AddInMemoryApiResources(Configuration.Apis)
        .AddInMemoryClients(Configuration.Clients)
        .AddInMemoryApiScopes(Configuration.Scopes);
Share:
37,670
maxspan
Author by

maxspan

Always trying to learn better and efficient ways to write code.

Updated on July 06, 2021

Comments

  • maxspan
    maxspan almost 3 years

    I am getting the below error while making a request to my Identity Server application from my Javascript Client Application.

    fail: IdentityServer4.Validation.ScopeValidator[0] Invalid scope: openid

    I have made sure I add the scope in my Identity Server application. Below is my code.

    IdentityServer Application ( the Host) Config.cs

      public class Config
    {
        public static IEnumerable<ApiResource> GetApiResources()
        {
            return new List<ApiResource>
            {
                new ApiResource("api1","My API")
            };
        }
    
        public static IEnumerable<Client> GetClients()
        {
            return new List<Client>
            {
                new Client
                {
                     ClientId = "js",
                     ClientName = "javaScript Client",
                     AllowedGrantTypes = GrantTypes.Implicit,
                     AllowAccessTokensViaBrowser = true,
                     RedirectUris = { "http://localhost:5003/callback.html" },
                     PostLogoutRedirectUris = { "http://localhost:5003/index.html" },
                     AllowedCorsOrigins = { "http://localhost:5003" },
                     AllowedScopes =
                        {
                            IdentityServerConstants.StandardScopes.OpenId,
                            IdentityServerConstants.StandardScopes.Profile,
                            "api1"
                        }
                }
            };
        }
    }
    

    Startup.cs

      public class Startup
    {
        // This method gets called by the runtime. Use this method to add services to the container.
        // For more information on how to configure your application, visit http://go.microsoft.com/fwlink/?LinkID=398940
        public void ConfigureServices(IServiceCollection services)
        {
    
            services.AddIdentityServer()
                .AddTemporarySigningCredential()
                .AddInMemoryApiResources(Config.GetApiResources())
                .AddInMemoryClients(Config.GetClients());
        }
    
        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
        {
            loggerFactory.AddConsole();
    
            if (env.IsDevelopment())
            {
                app.UseDeveloperExceptionPage();
                app.UseIdentityServer();
            }
    
            app.Run(async (context) =>
            {
                await context.Response.WriteAsync("Hello World!");
            });
        }
    }
    

    Web API Startup.cs

     public class Startup
    {
        public Startup(IHostingEnvironment env)
        {
            var builder = new ConfigurationBuilder()
                .SetBasePath(env.ContentRootPath)
                .AddJsonFile("appsettings.json", optional: true, reloadOnChange: true)
                .AddJsonFile($"appsettings.{env.EnvironmentName}.json", optional: true);
    
            if (env.IsEnvironment("Development"))
            {
                // This will push telemetry data through Application Insights pipeline faster, allowing you to view results immediately.
                builder.AddApplicationInsightsSettings(developerMode: true);
            }
    
            builder.AddEnvironmentVariables();
            Configuration = builder.Build();
        }
    
        public IConfigurationRoot Configuration { get; }
    
        // This method gets called by the runtime. Use this method to add services to the container
        public void ConfigureServices(IServiceCollection services)
        {
            // Add framework services.
            services.AddApplicationInsightsTelemetry(Configuration);
    
            services.AddCors(option =>
            {
                option.AddPolicy("dafault", policy =>
                {
                    policy.WithOrigins("http://localhost:5003")
                          .AllowAnyHeader()
                          .AllowAnyMethod();
                });
            });
            services.AddMvcCore()
                    .AddAuthorization()
                    .AddJsonFormatters();
        }
    
        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline
        public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
        {
            loggerFactory.AddConsole(Configuration.GetSection("Logging"));
            loggerFactory.AddDebug();
    
            //this uses the policy called "default"
            app.UseCors("default");
    
            app.UseIdentityServerAuthentication(new IdentityServerAuthenticationOptions
            {
                Authority = "http://localhost:5000",
                AllowedScopes = { "api1" },
                RequireHttpsMetadata = false
            });
    
            app.UseApplicationInsightsRequestTelemetry();
    
            app.UseApplicationInsightsExceptionTelemetry();
    
            app.UseMvc();
        }
    }
    
  • maxspan
    maxspan over 7 years
    Its working now, But now its showing Showing login: User is not authenticated
  • Lutando
    Lutando over 7 years
    Logs are your friend, is your console logging on trace level?
  • maxspan
    maxspan over 7 years
    yes. It showing IdentityServer4.ResponseHandling.AuthorizeInteractionRespons‌​eGenerator[0] User is not authenticated. How do I authenticate user
  • Lutando
    Lutando over 7 years
    When does this happen? after entering user credentials into the login page?
  • maxspan
    maxspan over 7 years
    I dont have a login page. Its a javascript client application
  • Lutando
    Lutando over 7 years
    The login page of the identityserver. You are using a javascript application and your client is implicit flow === youre doing a single sign on example?
  • maxspan
    maxspan over 7 years
  • maxspan
    maxspan over 7 years
    Yes I am using javascript application. The sample in the documentation
  • maxspan
    maxspan over 7 years
  • Adam Mendoza
    Adam Mendoza almost 5 years
    All links are now invalid.
  • Phil
    Phil almost 5 years
    @Lutando thank you!!! You made me realise I hadn't added an IdentityResource to the GetIdentityResources() method.
  • Lutando
    Lutando almost 5 years
    @AdamMendoza i fixed the links
  • Lutando
    Lutando almost 5 years
    @Phil anytime :)
  • Alejandro B.
    Alejandro B. over 3 years
    I was having a similar error and fixed it in a similar manner exept that I added AddInMemoryApiScopes on ConfigureServices