今天的内容很简单,1分钟就能看完,5分钟就能学会,但是却是在我们平时开发中必须要学会的一个小知识点,我就不让大家走弯路了,直接看操作。
在平时的IdentityServer4开发中呢,我们都是根据官方的Demo来操作一遍,或者是根据那个快速启动页面跑一跑,也就没有做其他的扩展,本文说的是登录,大家肯定认为这个是最简单的了,直接跳转,然后提交表单即可,但是就在要睡觉的时候,我想到了QQ或者其他登录页都是有一个oauth的字样,看着很专业的样子😀,我也想换掉,目前的太程序员化了,说干就干,坐起来打开了电脑,需求如下:
目前的登录地址是: https://ids.neters.club/Account/Login?ReturnUrl=%2Fgrants 我想要换成这样的效果:
https://ids.neters.club/oauth2/authorize?ReturnUrl=%2Fgrants
如果说你已经会了呢,可以不用看了;
如果说自己想先动手实践一下,先关掉本文窗口;
如果两者都不是,就跟着我往下走吧,很简单。
这个其实不是本文的内容,但是和登录页有关系,我还是说一下吧,登录页的自定义样式很简单,甚至整个页面的布局也可以改变,别说css文件了,就是很普通的MVC操作,甚至也可以搞成前后端分离的形式,你没有听错,就是用前后端分离来设计Ids4认证中心项目。
不过这个感觉不是很有必要,还是把精力放到业务上吧,我这里简单的做了下样式处理,可以和原版的坐下对比:
(官方默认版本)
(我自定义模板样式)
(群内网友的项目,挺好)
为什么要说这个呢,是因为我们既然要做统一的授权认证中心,一个好看的登录页是很有必要的,毕竟以后很多个项目都要共用这一个,安全是第一位,美貌也不能丢,我的审美就不行,等春节在家优化优化。
刚刚我们说完了登录样式,那就到了重头戏,自定义登录路由地址,官方给我们的地址是:
/Account/Login
这个看着也真的有点儿硬了,而且我看很多的公司认证项目都是自定义的,那路径肯定我们也要修改修改,翻看了下官方资料,发现很简单,还记得我们上一篇说到的自定义跳转域名么,本来是localhost,后来我们配置了ids.neters.club,没错,还是那个地方:
services.AddIdentityServer(options =>
{
options.Events.RaiseErrorEvents = true;
options.Events.RaiseInformationEvents = true;
options.Events.RaiseFailureEvents = true;
options.Events.RaiseSuccessEvents = true;
options.IssuerUri = "https://ids.neters.club";
options.PublicOrigin = "https://ids.neters.club";
// 就是这里,自定义用户交互选项
options.UserInteraction = new UserInteractionOptions
{
LoginUrl = "/oauth2/authorize",//登录地址
LogoutUrl = "/Account/Logout",//退出地址
ConsentUrl = "/Account/Consent",//允许授权同意页面地址
ErrorUrl = "/Account/Error", //错误页面地址
LoginReturnUrlParameter = "ReturnUrl",//设置传递给登录页面的返回URL参数的名称。默认为returnUrl
LogoutIdParameter = "logoutId", //设置传递给注销页面的注销消息ID参数的名称。缺省为logoutId
ConsentReturnUrlParameter = "ReturnUrl", //设置传递给同意页面的返回URL参数的名称。默认为returnUrl
ErrorIdParameter = "errorId", //设置传递给错误页面的错误消息ID参数的名称。缺省为errorId
CustomRedirectReturnUrlParameter = "ReturnUrl", //设置从授权端点传递给自定义重定向的返回URL参数的名称。默认为returnUrl
CookieMessageThreshold = 5 //由于浏览器对Cookie的大小有限制,设置Cookies数量的限制,有效的保证了浏览器打开多个选项卡,一旦超出了Cookies限制就会清除以前的Cookies值
};
})
这里的配置是没有走数据库的,只有config.cs里的会配置到数据,从这里我们可以看出他们的一贯套路,就是走配置,不过如果不了解,配置多了就会乱,这不,说来就来了:
用这种办法,在InMemory模式下很正常,我使用是内存模式的,然后也跳转到了指定的登陆页面:oauth2/authorize,欣喜雀跃,替换到我的正式项目,不!!行!!。
然后看官网也没错呀,大约时间过去了十多分钟,我想到了一个问题。
这个是个小知识点,如果你对Aspnet core的Identity不熟悉的话,可能不会来得及考虑这个问题,因为我的项目是用的Identity来处理应用数据这一块的,如果你公司的项目是自定义的话,那就不用考虑这个问题了,我也打算在公司尝试使用自定义仓储的模式,替换掉微软官方推荐的Identity类来操作用户应用数据。
直接修改代码吧:
services.ConfigureApplicationCookie(options =>
{
options.AccessDeniedPath = new PathString("/Account/AccessDenied");
options.Cookie.Name = "Cookie";
options.Cookie.HttpOnly = true;
options.ExpireTimeSpan = TimeSpan.FromMinutes(720);
options.LoginPath = new PathString("/oauth2/authorize");
options.ReturnUrlParameter = CookieAuthenticationDefaults.ReturnUrlParameter;
options.SlidingExpiration = true;
});
具体的每一个啥意思,从字面意思上我们也能看的出来,我这里只用到了LoginPath这一个属性操作,这下应该没有问题了吧。
既然我们新设计了登录页,那我们就必须创建一个新的控制器OAuth2Controller,当然你可以直接修改下原来的AccountController进行重命名,我采用的还是新增,现在开发基本都是对内修改禁止的思路,不过我新增这个也不能直接粘贴复制,要重构封装,还需要进一步优化中,优化这一块以后就不写到文章了,这里一笔带过了:
public class Oauth2Controller : Controller
{
private readonly UserManager<ApplicationUser> _userManager;
private readonly RoleManager<ApplicationRole> _roleManager;
private readonly SignInManager<ApplicationUser> _signInManager;
private readonly IIdentityServerInteractionService _interaction;
private readonly IClientStore _clientStore;
private readonly IAuthenticationSchemeProvider _schemeProvider;
private readonly IEventService _events;
public Oauth2Controller(
UserManager<ApplicationUser> userManager,
RoleManager<ApplicationRole> roleManager,
SignInManager<ApplicationUser> signInManager,
IIdentityServerInteractionService interaction,
IClientStore clientStore,
IAuthenticationSchemeProvider schemeProvider,
IEventService events)
{
_userManager = userManager;
_roleManager = roleManager;
_signInManager = signInManager;
_interaction = interaction;
_clientStore = clientStore;
_schemeProvider = schemeProvider;
_events = events;
}
/// <summary>
/// Show login page
/// </summary>
[HttpGet]
public async Task<IActionResult> authorize(string returnUrl)
{
// build a model so we know what to show on the login page
var vm = await BuildLoginViewModelAsync(returnUrl);
if (vm.IsExternalLoginOnly)
{
// we only have one option for logging in and it's an external provider
return await ExternalLogin(vm.ExternalLoginScheme, returnUrl);
}
return View(vm);
}
}
具体的和之前的是一样的,只不过拷贝过去了而已,这里不多说,发布查看效果吧。
修改了上面三个小地方以后,我们提交我们的代码,最终实现了目的,登录页跳转看着专业了一丢丢:
打完手工,其实说白了,整篇文章就是一个小技巧,看看就明白了,但是这里要说一下,修改完以后,一定要多多的做测试,联调,或者让群里小伙伴一起检验。
本文分享自 NetCore 从壹开始 微信公众号,前往查看
如有侵权,请联系 cloudcommunity@tencent.com 删除。
本文参与 腾讯云自媒体同步曝光计划 ,欢迎热爱写作的你一起参与!