【发布时间】:2020-10-08 18:18:13
【问题描述】:
我正在尝试使用 .net core API 3.1 和 Identity server 4 创建一个小型电子商务演示应用程序。
Config.cs(Demo.Auth 项目)
public static class Config
{
public static IEnumerable<IdentityResource> Ids =>
new IdentityResource[]
{
new IdentityResources.Profile(),
};
public static IEnumerable<ApiResource> ApiResources => new[]
{
new ApiResource("Demo.Api", "Demo Api")
};
public static IEnumerable<Client> Clients => new[]
{
new Client()
{
ClientId = "mvc",
ClientName = "Demo.MvcClient",
AllowedGrantTypes = GrantTypes.ClientCredentials,
RequirePkce = true,
ClientSecrets =
{
new Secret("49C1A7E1-0C79-4A89-A3D6-A37998FB86B0".Sha256())
},
RedirectUris = {"http://localhost:5003/signin-oidc"},
FrontChannelLogoutUri = "http://localhost:5003/signout-oidc",
PostLogoutRedirectUris = {"http://localhost:5003/signout-callback-oidc"},
AllowOfflineAccess = true,
AllowedScopes = {"profile"}
}
};
}
Startup.cs(Demo.Auth 项目)
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 https://go.microsoft.com/fwlink/?LinkID=398940
public void ConfigureServices(IServiceCollection services)
{
services.AddControllersWithViews();
IConfigurationRoot config = new ConfigurationBuilder()
.SetBasePath(Directory.GetCurrentDirectory())
.AddJsonFile("appsettings.json")
.Build();
string identityConnectionString = config.GetSection("ConnectionStrings")
.Value;
var migratingAssembly = typeof(Startup).GetTypeInfo()
.Assembly.GetName()
.Name;
if (config.GetValue<bool>("UseInMemoryDatabase"))
{
services.AddIdentityServer(options =>
{
options.Events.RaiseErrorEvents = true;
options.Events.RaiseInformationEvents = true;
options.Events.RaiseFailureEvents = true;
options.Events.RaiseSuccessEvents = true;
})
.AddTestUsers(TestUsers.Users)
.AddInMemoryIdentityResources(Config.Ids)
.AddInMemoryApiResources(Config.ApiResources)
.AddInMemoryClients(Config.Clients)
.AddDeveloperSigningCredential();
}
else
{
services.AddIdentityServer(options =>
{
options.Events.RaiseErrorEvents = true;
options.Events.RaiseInformationEvents = true;
options.Events.RaiseFailureEvents = true;
options.Events.RaiseSuccessEvents = true;
})
.AddTestUsers(TestUsers.Users)
.AddDeveloperSigningCredential()
//This will store client and ApiResource
.AddConfigurationStore(options =>
{
options.ConfigureDbContext = b => b.UseSqlServer(identityConnectionString,
sql => sql.MigrationsAssembly(migratingAssembly));
})
//This will store token, consent or code
.AddOperationalStore(options =>
{
options.ConfigureDbContext = b => b.UseSqlServer(identityConnectionString,
sql => sql.MigrationsAssembly(migratingAssembly));
});
}
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app,
IWebHostEnvironment env)
{
// this will do the initial DB population
// InitializeDatabase(app);
if (env.IsDevelopment())
app.UseDeveloperExceptionPage();
app.UseRouting();
app.UseIdentityServer();
app.UseEndpoints(endpoints =>
{
endpoints.MapGet("/",
async context => { await context.Response.WriteAsync("Hello World!"); });
});
}
}
Startup.cs(API 项目)
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.AddAuthentication("Bearer").AddIdentityServerAuthentication(options =>
{
options.Authority = "http://localhost:5000";
options.RequireHttpsMetadata = false;
options.ApiName = "Demo.Api";
});
services.AddControllers();
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment()) app.UseDeveloperExceptionPage();
app.UseRouting();
app.UseAuthentication();
app.UseAuthorization();
app.UseEndpoints(endpoints => { endpoints.MapControllers(); });
}
}
WeatherForecastController(Demo.Api 项目的)
[Authorize]
[ApiController]
[Route("[controller]")]
public class WeatherForecastController : ControllerBase
{
private static readonly string[] Summaries = new[]
{
"Freezing", "Bracing", "Chilly", "Cool", "Mild", "Warm", "Balmy", "Hot", "Sweltering", "Scorching"
};
private readonly ILogger<WeatherForecastController> _logger;
public WeatherForecastController(ILogger<WeatherForecastController> logger)
{
_logger = logger;
}
[HttpGet]
public IEnumerable<WeatherForecast> Get()
{
var rng = new Random();
return Enumerable.Range(1, 5).Select(index => new WeatherForecast
{
Date = DateTime.Now.AddDays(index),
TemperatureC = rng.Next(-20, 55),
Summary = Summaries[rng.Next(Summaries.Length)]
})
.ToArray();
}
}
我在 postman 中测试了 API,它工作正常。 “Demo.Auth”项目正在生成令牌,我可以成功访问我的授权控制器。
这里的想法是:
MVC 客户端 ----> 身份服务器项目 ---> API
MVC 客户端想要访问 API。因此,我将在身份服务器项目上对 Mvc 客户端进行身份验证,如果他是有效用户,则生成令牌,然后我将调用我的 api。
注意:目前我正在使用 MVC 客户端,但稍后我会再添加一个客户端,可能是 Angular。
但我有一个问题。
如何将用户添加到我的数据库并验证数据库用户而不是测试用户。
我不明白的另一件事是我应该将登录和注册功能放在哪里以及该代码的外观。
我是身份服务器的新手,请原谅。
有人可以用一些代码指导我解决上述问题吗?提前致谢
【问题讨论】:
标签: .net asp.net-core-webapi identityserver4 openid-connect