首页 > 解决方案 > 无法使用身份服务器访问客户端应用程序

问题描述

我正在尝试使用身份服务器对客户端 mvc 应用程序进行身份验证。

我的应用程序有身份服务器 mvc 应用程序、MVC 应用程序、API

我在客户端 MVC 应用程序中使用了 4 个范围(OpenId、电子邮件、配置文件、办公室——办公室是自定义声明类型)。

我正在使用此代码创建具有身份验证 mvc 应用程序的身份服务器。

1 identity server run 

2 MVC application run 

3 Login link click using MVC application 

图片1

4 Login the identity server using TestUser details

图片2

5 after login success always display this screen (not show my all scope to check in client application)

图3

身份服务器 - ( http://localhost:61632 )

public class Startup
    {
        public Startup(IConfiguration configuration)
        {
            Configuration = configuration;
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {
            services.AddMvc();

            services.AddIdentityServer()
               .AddTestUsers(TestUsers.Users)
               .AddInMemoryClients(Config.GetClients())
               .AddInMemoryIdentityResources(Config.GetIdentityResources())
               .AddInMemoryApiResources(Config.GetApiResources());

        }

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IHostingEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseBrowserLink();
                app.UseDeveloperExceptionPage();
            }
            else
            {
                app.UseExceptionHandler("/Home/Error");
            }

            app.UseStaticFiles();

            app.UseIdentityServer();

            app.UseMvc(routes =>
            {
                routes.MapRoute(
                    name: "default",
                    template: "{controller=Home}/{action=Index}/{id?}");
            });
        }
    }

测试用户类

 public class TestUsers
    {
        public static List<TestUser> Users = new List<TestUser>
        {
            new TestUser{SubjectId = "818727", Username = "Kasunjith", Password = "kasunjith", 
                Claims = 
                {
                    new Claim("office_Id","23"),
                    new Claim(JwtClaimTypes.Name, "Alice Smith"),
                    new Claim(JwtClaimTypes.GivenName, "Alice"),
                    new Claim(JwtClaimTypes.FamilyName, "Smith"),
                    new Claim(JwtClaimTypes.Email, "AliceSmith@email.com"),
                    new Claim(JwtClaimTypes.EmailVerified, "true", ClaimValueTypes.Boolean),
                    new Claim(JwtClaimTypes.WebSite, "http://alice.com"),
                    new Claim(JwtClaimTypes.Address, @"{ 'street_address': 'One Hacker Way', 'locality': 'Heidelberg', 'postal_code': 69118, 'country': 'Germany' }", IdentityServer4.IdentityServerConstants.ClaimValueTypes.Json)
                }
            },
            new TestUser{SubjectId = "88421113", Username = "bimal", Password = "bimal", 
                Claims = 
                {
                    new Claim("office_Id","24"),
                    new Claim(JwtClaimTypes.Name, "Bob Smith"),
                    new Claim(JwtClaimTypes.GivenName, "Bob"),
                    new Claim(JwtClaimTypes.FamilyName, "Smith"),
                    new Claim(JwtClaimTypes.Email, "BobSmith@email.com"),
                    new Claim(JwtClaimTypes.EmailVerified, "true", ClaimValueTypes.Boolean),
                    new Claim(JwtClaimTypes.WebSite, "http://bob.com"),
                    new Claim(JwtClaimTypes.Address, @"{ 'street_address': 'One Hacker Way', 'locality': 'Heidelberg', 'postal_code': 69118, 'country': 'Germany' }", IdentityServer4.IdentityServerConstants.ClaimValueTypes.Json),
                    new Claim("location", "somewhere")
                }
            }
        };
    }

配置类

 public class Config
    {
        public static IEnumerable<Client> GetClients()
        {
            return new Client[]
            {
                new Client
                {
                    ClientId ="mvc",
                    ClientName="MVC Demo",
                    AllowedGrantTypes = GrantTypes.Implicit,
                    RedirectUris ={ "http://localhost:62104/signin-oidc" },
                    AllowedScopes={ "openid","email", "profile","office"},
                    AllowRememberConsent = true,

                }

            };
        }

        public static IEnumerable<IdentityResource> GetIdentityResources()
        {
            return new IdentityResource[]
            {
                new IdentityResources.OpenId(),
                new IdentityResources.Email(),
                new IdentityResources.Profile(),
                new IdentityResource
                {
                    Name="office",
                    DisplayName ="office details",
                    UserClaims = {"office_Id"}
                }


            };
        }


        public static IEnumerable<ApiResource> GetApiResources()
        {
            return new ApiResource[]
            {

            };
        }
    }

客户端 - Mvc 应用程序 ( http://localhost:62104 )

public class Startup
    {
        public Startup(IConfiguration configuration)
        {
            Configuration = configuration;
        }

        public IConfiguration Configuration { get; }

        // This method gets called by the runtime. Use this method to add services to the container.
        public void ConfigureServices(IServiceCollection services)
        {
            services.AddMvc();

            services.AddAuthentication(options =>
            {
                options.DefaultScheme = "Cookies";
                options.DefaultChallengeScheme = "oidc";
                //options.DefaultAuthenticateScheme = "Cookies";
            }).AddCookie("Cookies")
             .AddOpenIdConnect("oidc", options =>
             {

                 options.SignInScheme = "Cookies";
                 options.RequireHttpsMetadata = false;
                 options.Authority = "http://localhost:61632";
                 options.ClientId = "mvc";
                 options.ResponseType = "id_token";
                 //options.CallbackPath = new PathString("...")
                 //options.SignedOutCallbackPath = new PathString("...")
                 options.Scope.Add("openid");
                 options.Scope.Add("email");
                 options.Scope.Add("profile");
                 options.Scope.Add("office");




             });
        }

        // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
        public void Configure(IApplicationBuilder app, IHostingEnvironment env)
        {
            if (env.IsDevelopment())
            {
                app.UseBrowserLink();
                app.UseDeveloperExceptionPage();
            }
            else
            {
                app.UseExceptionHandler("/Home/Error");
            }

            app.UseStaticFiles();


            app.UseAuthentication();

            app.UseMvc(routes =>
            {
                routes.MapRoute(
                    name: "default",
                    template: "{controller=Home}/{action=Index}/{id?}");
            });
        }
    }

标签: asp.net-corecookiesidentityserver4openid-connectidentityserver3

解决方案


发现问题(这很难!)

代码工作得很好。不起作用的部分是在Consent视图中显示范围。问题归结为这一行:

意见/同意/Index.cshtml

<partial name="_ScopeListItem" model="@scope" />

这使用了在 ASP.NET 2.1 中引入的Partial Tag Helper 。

您在评论中链接的项目(您的项目)使用 ASP.NET 2.0,但您从IdentityServerQuickStart UI复制的项目使用 ASP.NET Core 2.1,因此基本上它们是不兼容的。要修复,请为您的版本使用正确的标记帮助程序,或者(我建议)升级到 ASP.NET Core 2.2。为此,您可以:

更改项目文件:

<Project Sdk="Microsoft.NET.Sdk.Web">

  <!-- Upgrade the project to .NET Core 2.2-->
  <PropertyGroup>
    <TargetFramework>netcoreapp2.2</TargetFramework>
  </PropertyGroup>

  <ItemGroup>
    <PackageReference Include="IdentityServer4" Version="2.3.2" />

    <!-- Change the ASP.NET Core from All to App. -->
    <PackageReference Include="Microsoft.AspNetCore.App" />
  </ItemGroup>

  <ItemGroup>
    <DotNetCliToolReference Include="Microsoft.VisualStudio.Web.CodeGeneration.Tools" Version="2.0.2" />
  </ItemGroup>

</Project>

Startup.cs

public IConfiguration Configuration { get; }
public IHostingEnvironment Environment { get; }

public Startup(IConfiguration configuration, IHostingEnvironment environment)
{
    Configuration = configuration;
    Environment = environment;
}

public void ConfigureServices(IServiceCollection services)
{
    services.AddMvc().SetCompatibilityVersion(Microsoft.AspNetCore.Mvc.CompatibilityVersion.Version_2_1);

    var builder = services.AddIdentityServer()
       .AddTestUsers(TestUsers.Users)
       .AddInMemoryClients(Config.GetClients())
       .AddInMemoryIdentityResources(Config.GetIdentityResources())
       .AddInMemoryApiResources(Config.GetApiResources());

    // without this you can't sign jwt tokens in dev. still need to configure for prod.
    if (Environment.IsDevelopment())
    {
        builder.AddDeveloperSigningCredential();
    }
    else
    {
        throw new Exception("need to configure key material");
    }

}

既然你喜欢它,我还建议升级 MVC(客户端)应用程序。我在您的 GitHub 存储库上发送了一个 PR,其中包含上述更改以及在您的用户登录后列出范围/声明的视图。


推荐阅读