当前位置: 首页 > wzjs >正文

在哪个网站可以做酒店预定单网站代备案管理系统

在哪个网站可以做酒店预定单,网站代备案管理系统,全球十大创意广告,北海seo快速排名基于 JWT Spring Security 的授权认证机制,在整体架构设计上体现了高度的安全性与灵活性。其在整合框架中的应用,充分展示了模块化、可扩展性和高效鉴权的设计理念,为开发者提供了一种值得借鉴的安全架构模式。 1.SpringSecurity概念理解 …

基于 JWT + Spring Security 的授权认证机制,在整体架构设计上体现了高度的安全性与灵活性。其在整合框架中的应用,充分展示了模块化、可扩展性和高效鉴权的设计理念,为开发者提供了一种值得借鉴的安全架构模式。

1.SpringSecurity概念理解

1.1 一般的Web应用需要进行认证和授权。

认证:验证当前访问系统的是不是本系统的用户,并且要确认具体是哪个用户。

授权:经过认证后判断当前用户是否有权限进行某些操作

1.2 RBAC权限模型的理解

可以理解为用户对应角色,角色又对应权限,在不考虑加入部门等参数的干预下,整个RBAC模型可以简化为5张表来描述:

1.3 SpringSecurity机制:

整个SpringSecurity机制可以理解为是一个过滤器链机制,前端发请求给后端,请求会经过整个过滤器链的认证和授权逻辑才能执行后续正常的系统接口逻辑。下方三个为核心过滤器

第一个负责处理在登录页面填写用户名和密码后登录请求

第二个负责处理过滤器链中抛出的授权和认证异常

第三个是负责权限校验的过滤器

认证点认证流程:

2.认证架构设计

2.1 登录的整体流程设计:

从login()逻辑开始执行

2.1 SpringSecurity的配置类

登录接口实现:

 /*** 登录方法* @param loginBody 登录信息* @return 结果*/
@Operation(summary = "登录方法")
@PostMapping("/login")
public AjaxResult login(@RequestBody LoginBody loginBody) {AjaxResult ajax = AjaxResult.success();// 生成令牌String token = loginService.login(loginBody.getUsername(),loginBody.getPassword(),loginBody.getCode(),loginBody.getUuid());ajax.put(Constants.TOKEN, token);return ajax;
}

/*** 登录验证* @param username 用户名* @param password 密码* @param code 验证码* @param uuid 唯一标识* @return 结果*/
public String login(String username, String password, String code, String uuid)
{// 验证码校验validateCaptcha(username, code, uuid);// 登录前置校验loginPreCheck(username, password);String ip = IpUtils.getIpAddr();// 验证 IP 是否被封锁passwordService.validateIp(ip);// 用户验证Authentication authentication = null;try{UsernamePasswordAuthenticationToken authenticationToken = new UsernamePasswordAuthenticationToken(username, password);AuthenticationContextHolder.setContext(authenticationToken);// 该方法会去调用UserDetailsServiceImpl.loadUserByUsernameauthentication = authenticationManager.authenticate(authenticationToken);}catch (Exception e){if (e instanceof BadCredentialsException){AsyncManager.me().execute(AsyncFactory.recordLogininfor(username, Constants.LOGIN_FAIL, MessageUtils.message("user.password.not.match")));throw new UserPasswordNotMatchException();}else{passwordService.incrementIpFailCount(ip);AsyncManager.me().execute(AsyncFactory.recordLogininfor(username, Constants.LOGIN_FAIL, e.getMessage()));throw new ServiceException(e.getMessage());}}finally{AuthenticationContextHolder.clearContext();}AsyncManager.me().execute(AsyncFactory.recordLogininfor(username, Constants.LOGIN_SUCCESS, MessageUtils.message("user.login.success")));LoginUser loginUser = (LoginUser) authentication.getPrincipal();recordLoginInfo(loginUser.getUserId());// 生成tokenreturn tokenService.createToken(loginUser);
}

2.2 SpringSecurity配置类

/*** spring security配置** @author Dftre*/
@EnableMethodSecurity(prePostEnabled = true, securedEnabled = true)
@Configuration
public class SecurityConfig {/*** 自定义用户认证逻辑*/@Autowiredprivate UserDetailsService userDetailsService;/*** 认证失败处理类*/@Autowiredprivate AuthenticationEntryPointImpl unauthorizedHandler;/*** 退出处理类*/@Autowiredprivate LogoutSuccessHandlerImpl logoutSuccessHandler;/*** token认证过滤器*/@Autowiredprivate JwtAuthenticationTokenFilter authenticationTokenFilter;/*** 跨域过滤器*/@Autowiredprivate CorsFilter corsFilter;/*** 允许匿名访问的地址*/@Autowiredprivate PermitAllUrlProperties permitAllUrl;/*** @return* @throws Exception*/@BeanAuthenticationManager authenticationManager() {DaoAuthenticationProvider daoAuthenticationProvider = new DaoAuthenticationProvider(userDetailsService);daoAuthenticationProvider.setPasswordEncoder(bCryptPasswordEncoder());return new ProviderManager(daoAuthenticationProvider);}/*** anyRequest | 匹配所有请求路径* access | SpringEl表达式结果为true时可以访问* anonymous | 匿名可以访问* denyAll | 用户不能访问* fullyAuthenticated | 用户完全认证可以访问(非remember-me下自动登录)* hasAnyAuthority | 如果有参数,参数表示权限,则其中任何一个权限可以访问* hasAnyRole | 如果有参数,参数表示角色,则其中任何一个角色可以访问* hasAuthority | 如果有参数,参数表示权限,则其权限可以访问* hasIpAddress | 如果有参数,参数表示IP地址,如果用户IP和参数匹配,则可以访问* hasRole | 如果有参数,参数表示角色,则其角色可以访问* permitAll | 用户可以任意访问* rememberMe | 允许通过remember-me登录的用户访问* authenticated | 用户登录后可访问*/@BeanSecurityFilterChain filterChain(HttpSecurity httpSecurity) throws Exception {return httpSecurity// CSRF禁用,因为不使用session.csrf(csrf -> csrf.disable())// 禁用HTTP响应标头.headers((headersCustomizer) -> {headersCustomizer.cacheControl(cache -> cache.disable()).frameOptions(options -> options.sameOrigin());})// 认证失败处理类.exceptionHandling(exception -> exception.authenticationEntryPoint(unauthorizedHandler))// 基于token,所以不需要session.sessionManagement(session -> session.sessionCreationPolicy(SessionCreationPolicy.STATELESS))// 注解标记允许匿名访问的url.authorizeHttpRequests((requests) -> {permitAllUrl.getUrls().forEach(url -> requests.requestMatchers(url).permitAll());// 对于登录login 注册register 验证码captchaImage 允许匿名访问requests.requestMatchers("/login", "/register", "/captchaImage").permitAll()// 静态资源,可匿名访问.requestMatchers(HttpMethod.GET, "/", "/*.html", "/**/*.html", "/**/*.css", "/**/*.js","/profile/**").permitAll().requestMatchers("/swagger-ui.html", "/swagger-resources/**", "/webjars/**", "/*/api-docs","/druid/**", "/*/api-docs/**").permitAll().requestMatchers("/websocket/**").permitAll()// 除上面外的所有请求全部需要鉴权认证.anyRequest().authenticated();})// 添加Logout filter.logout(logout -> logout.logoutUrl("/logout").logoutSuccessHandler(logoutSuccessHandler))// 添加JWT filter.addFilterBefore(authenticationTokenFilter, UsernamePasswordAuthenticationFilter.class)// 添加CORS filter.addFilterBefore(corsFilter, JwtAuthenticationTokenFilter.class).addFilterBefore(corsFilter, LogoutFilter.class).build();}/*** 强散列哈希加密实现*/@Beanpublic BCryptPasswordEncoder bCryptPasswordEncoder() {return new BCryptPasswordEncoder();}
}

2.3 UserDetailsServiceImpl 重写 UserDetailsService接口的loadUserbyUsername方法

@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {SysUser user = userService.selectUserByUserName(username);if (StringUtils.isNull(user)) {log.info("登录用户:{} 不存在.", username);throw new ServiceException("登录用户:" + username + " 不存在");} else if (UserStatus.DELETED.getCode().equals(user.getDelFlag())) {log.info("登录用户:{} 已被删除.", username);throw new ServiceException("对不起,您的账号:" + username + " 已被删除");} else if (UserStatus.DISABLE.getCode().equals(user.getStatus())) {log.info("登录用户:{} 已被停用.", username);throw new ServiceException("对不起,您的账号:" + username + " 已停用");}passwordService.validate(user);return createLoginUser(user);
}public UserDetails createLoginUser(SysUser user) {return new LoginUser(user.getUserId(), user.getDeptId(), user, permissionService.getMenuPermission(user));
}

2.4 保存LoginUser到Redis的逻辑在创建token的方法逻辑中实现

2.5 拦截器配置

/*** token过滤器 验证token有效性* * @author ruoyi*/
@Component
public class JwtAuthenticationTokenFilter extends OncePerRequestFilter
{@Autowiredprivate TokenService tokenService;@Overrideprotected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain)throws ServletException, IOException{LoginUser loginUser = tokenService.getLoginUser(request);if (StringUtils.isNotNull(loginUser) && StringUtils.isNull(SecurityUtils.getAuthentication())){tokenService.verifyToken(loginUser);UsernamePasswordAuthenticationToken authenticationToken = new UsernamePasswordAuthenticationToken(loginUser, null, loginUser.getAuthorities());authenticationToken.setDetails(new WebAuthenticationDetailsSource().buildDetails(request));SecurityContextHolder.getContext().setAuthentication(authenticationToken);}chain.doFilter(request, response);}
}

3.授权架构设计

权限的验证最核心的是使用的Spring Security的提供的权限注解`@PreAuthorize `

当 @PreAuthorize 注解被应用于某个方法时,Spring Security 在该方法执行前会先对当前认证的用户进行权限检查。如果检查通过,方法调用得以继续;否则,框架会抛出相应的权限异常(如 AccessDeniedException),阻止方法执行。

  • @ss 引用了名为 "ss" 的 Spring Bean,即我们的 PermissionService
  • hasPermi('manage:order:list') 调用了 PermissionService 的 hasPermi 方法,检查用户是否拥有 "manage:order:list" 权限

授权相关校验操作实现:

@Service("ss")
public class PermissionService implements IPermissionService {/** 所有权限标识 */private static final String ALL_PERMISSION = "*:*:*";/** 管理员角色权限标识 */private static final String SUPER_ADMIN = "admin";private static final String ROLE_DELIMETER = ",";private static final String PERMISSION_DELIMETER = ",";/*** 验证用户是否具备某权限* * @param permission 权限字符串* @return 用户是否具备某权限*/public boolean hasPermi(String permission) {if (StringUtils.isEmpty(permission)) {return false;}LoginUser loginUser = SecurityUtils.getLoginUser();if (StringUtils.isNull(loginUser) || CollectionUtils.isEmpty(loginUser.getPermissions())) {return false;}PermissionContextHolder.setContext(permission);return hasPermissions(loginUser.getPermissions(), permission);}/*** 验证用户是否具有以下任意一个权限** @param permissions 以 PERMISSION_NAMES_DELIMETER 为分隔符的权限列表* @return 用户是否具有以下任意一个权限*/public boolean hasAnyPermi(String permissions) {if (StringUtils.isEmpty(permissions)) {return false;}LoginUser loginUser = SecurityUtils.getLoginUser();if (StringUtils.isNull(loginUser) || CollectionUtils.isEmpty(loginUser.getPermissions())) {return false;}PermissionContextHolder.setContext(permissions);Set<String> authorities = loginUser.getPermissions();for (String permission : permissions.split(PERMISSION_DELIMETER)) {if (permission != null && hasPermissions(authorities, permission)) {return true;}}return false;}/*** 判断用户是否拥有某个角色* * @param role 角色字符串* @return 用户是否具备某角色*/public boolean hasRole(String role) {if (StringUtils.isEmpty(role)) {return false;}LoginUser loginUser = SecurityUtils.getLoginUser();if (StringUtils.isNull(loginUser) || CollectionUtils.isEmpty(loginUser.getUser().getRoles())) {return false;}for (SysRole sysRole : loginUser.getUser().getRoles()) {String roleKey = sysRole.getRoleKey();if (SUPER_ADMIN.equals(roleKey) || roleKey.equals(StringUtils.trim(role))) {return true;}}return false;}/*** 验证用户是否具有以下任意一个角色** @param roles 以 ROLE_NAMES_DELIMETER 为分隔符的角色列表* @return 用户是否具有以下任意一个角色*/public boolean hasAnyRoles(String roles) {if (StringUtils.isEmpty(roles)) {return false;}LoginUser loginUser = SecurityUtils.getLoginUser();if (StringUtils.isNull(loginUser) || CollectionUtils.isEmpty(loginUser.getUser().getRoles())) {return false;}for (String role : roles.split(ROLE_DELIMETER)) {if (hasRole(role)) {return true;}}return false;}/*** 判断是否包含权限* * @param permissions 权限列表* @param permission  权限字符串* @return 用户是否具备某权限*/private boolean hasPermissions(Set<String> permissions, String permission) {return permissions.contains(ALL_PERMISSION) || permissions.contains(StringUtils.trim(permission));}
}

文章转载自:

http://TzkHw9Ah.rbgqn.cn
http://YEaNCsj9.rbgqn.cn
http://KxiEn5Bi.rbgqn.cn
http://ybYxxORk.rbgqn.cn
http://kkVyOhzc.rbgqn.cn
http://p7RfHh45.rbgqn.cn
http://kvs7oAkQ.rbgqn.cn
http://IrlPnE2D.rbgqn.cn
http://e3SLhehp.rbgqn.cn
http://Tz4TIHjf.rbgqn.cn
http://eabOGccn.rbgqn.cn
http://nM833ILX.rbgqn.cn
http://cErXgiA0.rbgqn.cn
http://akleUo5V.rbgqn.cn
http://8yJH82KE.rbgqn.cn
http://dEblrdsy.rbgqn.cn
http://zSMaxMOh.rbgqn.cn
http://4hzHIyIf.rbgqn.cn
http://cuxrxskQ.rbgqn.cn
http://A4hG1hoA.rbgqn.cn
http://GyuXgoaM.rbgqn.cn
http://nJlyJTm4.rbgqn.cn
http://FcEVuUTW.rbgqn.cn
http://WvyDA9jw.rbgqn.cn
http://gDIL39yT.rbgqn.cn
http://ZWtlT9NF.rbgqn.cn
http://gVwNSMSX.rbgqn.cn
http://MnUumNeg.rbgqn.cn
http://8MSyiaWN.rbgqn.cn
http://qTsZPfgS.rbgqn.cn
http://www.dtcms.com/wzjs/730870.html

相关文章:

  • 网站续费通知南通营销型网站建设
  • 河北网站优化wordpress模板文件是那个
  • 免费行情软件app网站大全下载有图片手机定制app
  • 长春网站建设加q479185700云服务器怎么建设网站
  • 海外网站建设推广网页制作是干嘛的
  • 如何优化网站图片晶鹰建设摩托车官网
  • 800多块做网站网络移动公司的网站建设
  • 沈阳定制网站开发专业服务好的网站设计制作
  • 招聘销售员网站建设网络推广无锡工程建设信息网站
  • 响应式高端网站江苏大才建设集团网站
  • 自己如何建设校园网站杭州品牌网站建设公司
  • 建设一个网站需要什么手续建设银行宁波招聘网站
  • 电子商务网站的功能分析自己建设网站用哪个
  • 嘉兴做网站公司个人网站开发可行性报告
  • 网站建设搜索优环球易购做中东的网站
  • 门户网站系统建设招标文件装修设计图免费软件
  • 口腔医院网站优化服务商免费h5页面应用制作
  • 网站开发可以用gif吗深圳福田 外贸网站建设
  • 网站样式用什么做的汉阳网站推广优化
  • 找人开发软件去什么网站申请网站域名多少钱
  • 网站建设的目标与思路泰安微网站建设
  • 大连做网站的中海建筑建设有限公司网站
  • 织梦网站栏目增加2023年生鲜电商交易规模超6000亿
  • 网站和服务器是什么关系wordpress统计蜘蛛
  • 网站做全好吗百度优化 几个网站内容一样
  • 网站建设交流论坛地址编程培训机构
  • 奢侈品商城网站建设方案网站建设的必要性’
  • 做网站手把手多语言商城系统
  • 触屏手机网站建设手机如何自己编程做游戏
  • 微信网站合同wordpress 初始化 数据库