• Spring Boot 集成 Shiro实现权限控制,亲测可用,附带sql


    前提:

    本文主要讲解Spring Boot 与 Shiro的集成 与权限控制的实现方式(主要以代码实现功能为主),主要用到的技术Spring Boot+Shiro+Jpa(通过Maven构建),并不会涉及到Shiro框架的源码分析

    如果有想要学习Shiro框架的小伙伴可以去http://shiro.apache.org/官网自行学习,并推荐一个中文学习Shiro的网站https://www.sojson.com/shiro(感觉挺不错的)

    需求说明:

    通过SpringBoot+Shiro实现用户登录验证,授权,对不同用户角色访问资源进行验证,对用户权限访问资源验证,通过迭代加密方式提高用户密码的安全性

    用户 and 角色表关系 多对多

    角色 and 权限表关系 多对多

    废话不多说直接上代码:

    此项目是Maven多模块项目 码云地址 https://gitee.com/h-java/springboot-parent-demo

    小伙伴们代码里的注释我已经写的很详细了,所以博客里不做讲解,直接看代码注释讲解就可以了

    SQL文件

    /*
    Navicat MySQL Data Transfer
    
    Source Server         : localhost
    Source Server Version : 50520
    Source Host           : localhost:3306
    Source Database       : shiro-demo
    
    Target Server Type    : MYSQL
    Target Server Version : 50520
    File Encoding         : 65001
    
    Date: 2018-11-15 16:59:02
    */
    
    SET FOREIGN_KEY_CHECKS=0;
    
    -- ----------------------------
    -- Table structure for hibernate_sequence
    -- ----------------------------
    DROP TABLE IF EXISTS `hibernate_sequence`;
    CREATE TABLE `hibernate_sequence` (
      `next_val` bigint(20) DEFAULT NULL
    ) ENGINE=MyISAM DEFAULT CHARSET=utf8;
    
    -- ----------------------------
    -- Records of hibernate_sequence
    -- ----------------------------
    INSERT INTO `hibernate_sequence` VALUES ('4');
    INSERT INTO `hibernate_sequence` VALUES ('4');
    INSERT INTO `hibernate_sequence` VALUES ('4');
    
    -- ----------------------------
    -- Table structure for permission_t
    -- ----------------------------
    DROP TABLE IF EXISTS `permission_t`;
    CREATE TABLE `permission_t` (
      `id` int(11) NOT NULL,
      `name` varchar(255) DEFAULT NULL,
      PRIMARY KEY (`id`)
    ) ENGINE=MyISAM DEFAULT CHARSET=utf8;
    
    -- ----------------------------
    -- Records of permission_t
    -- ----------------------------
    INSERT INTO `permission_t` VALUES ('1', 'Retrieve');
    INSERT INTO `permission_t` VALUES ('2', 'Create');
    INSERT INTO `permission_t` VALUES ('3', 'Update');
    INSERT INTO `permission_t` VALUES ('4', 'Delete');
    
    -- ----------------------------
    -- Table structure for role
    -- ----------------------------
    DROP TABLE IF EXISTS `role`;
    CREATE TABLE `role` (
      `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
      `role` varchar(255) DEFAULT NULL,
      PRIMARY KEY (`id`)
    ) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8;
    
    -- ----------------------------
    -- Records of role
    -- ----------------------------
    INSERT INTO `role` VALUES ('1', 'user');
    INSERT INTO `role` VALUES ('2', 'admin');
    
    -- ----------------------------
    -- Table structure for role_permission_t
    -- ----------------------------
    DROP TABLE IF EXISTS `role_permission_t`;
    CREATE TABLE `role_permission_t` (
      `pid` int(11) NOT NULL,
      `rid` int(11) NOT NULL,
      KEY `FKt2l638rvh84yplqqu7odiwhdx` (`rid`),
      KEY `FKh946y0ynuov5ynnrn024vapg9` (`pid`)
    ) ENGINE=MyISAM DEFAULT CHARSET=utf8;
    
    -- ----------------------------
    -- Records of role_permission_t
    -- ----------------------------
    INSERT INTO `role_permission_t` VALUES ('1', '1');
    INSERT INTO `role_permission_t` VALUES ('1', '2');
    INSERT INTO `role_permission_t` VALUES ('2', '2');
    INSERT INTO `role_permission_t` VALUES ('3', '2');
    INSERT INTO `role_permission_t` VALUES ('1', '3');
    INSERT INTO `role_permission_t` VALUES ('2', '3');
    INSERT INTO `role_permission_t` VALUES ('3', '3');
    INSERT INTO `role_permission_t` VALUES ('4', '3');
    
    -- ----------------------------
    -- Table structure for role_t
    -- ----------------------------
    DROP TABLE IF EXISTS `role_t`;
    CREATE TABLE `role_t` (
      `id` int(11) NOT NULL,
      `role` varchar(255) DEFAULT NULL,
      PRIMARY KEY (`id`)
    ) ENGINE=MyISAM DEFAULT CHARSET=utf8;
    
    -- ----------------------------
    -- Records of role_t
    -- ----------------------------
    INSERT INTO `role_t` VALUES ('1', 'guest');
    INSERT INTO `role_t` VALUES ('2', 'user');
    INSERT INTO `role_t` VALUES ('3', 'admin');
    
    -- ----------------------------
    -- Table structure for user
    -- ----------------------------
    DROP TABLE IF EXISTS `user`;
    CREATE TABLE `user` (
      `id` int(11) unsigned NOT NULL AUTO_INCREMENT,
      `username` varchar(255) DEFAULT NULL,
      `password` varchar(255) DEFAULT NULL,
      `role` varchar(255) DEFAULT NULL,
      PRIMARY KEY (`id`)
    ) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8;
    
    -- ----------------------------
    -- Records of user
    -- ----------------------------
    INSERT INTO `user` VALUES ('1', 'howie', '123456', 'user');
    INSERT INTO `user` VALUES ('2', 'swit', '123456789', 'admin');
    
    -- ----------------------------
    -- Table structure for user_role_t
    -- ----------------------------
    DROP TABLE IF EXISTS `user_role_t`;
    CREATE TABLE `user_role_t` (
      `rid` int(11) NOT NULL,
      `uid` bigint(20) NOT NULL,
      KEY `FKe6b6umcoegdbmjws9e9y0n2jj` (`uid`),
      KEY `FK8lhd80hb3gbdbvdmlkn2oyprl` (`rid`)
    ) ENGINE=MyISAM DEFAULT CHARSET=utf8;
    
    -- ----------------------------
    -- Records of user_role_t
    -- ----------------------------
    INSERT INTO `user_role_t` VALUES ('3', '2');
    INSERT INTO `user_role_t` VALUES ('2', '1');
    INSERT INTO `user_role_t` VALUES ('1', '3');
    
    -- ----------------------------
    -- Table structure for user_t
    -- ----------------------------
    DROP TABLE IF EXISTS `user_t`;
    CREATE TABLE `user_t` (
      `id` bigint(20) NOT NULL,
      `password` varchar(255) DEFAULT NULL,
      `salt` varchar(255) DEFAULT NULL,
      `username` varchar(255) DEFAULT NULL,
      PRIMARY KEY (`id`)
    ) ENGINE=MyISAM DEFAULT CHARSET=utf8;
    
    -- ----------------------------
    -- Records of user_t
    -- ----------------------------
    INSERT INTO `user_t` VALUES ('1', 'dd531568fac3d2338bdba66b46b39fd7', '73ee684dd5a07e3b9034b02dcebf4e7c', 'hly');
    INSERT INTO `user_t` VALUES ('2', '7f5e269e2f52955a0bbdfdef19281fd4', 'c6dc702282fd467c2c5481617c45a014', 'dxl');
    INSERT INTO `user_t` VALUES ('3', 'edec83e7318071af89c8811536fd0a68', 'be535103fe5f98c4cef83cf24ab0d11b', 'zy');
    View Code

    父POM文件:

     1 <?xml version="1.0" encoding="UTF-8"?>
     2 <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
     3     xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
     4     <modelVersion>4.0.0</modelVersion>
     5 
     6     <groupId>com.boot</groupId>
     7     <artifactId>springboot-parent-demo</artifactId>
     8     <version>0.0.1-SNAPSHOT</version>
     9     <packaging>pom</packaging>
    10 
    11     <name>springboot-parent-demo</name>
    12     <description>Spring Boot Parent Demo</description>
    13 
    14     <parent>
    15         <groupId>org.springframework.boot</groupId>
    16         <artifactId>spring-boot-starter-parent</artifactId>
    17         <version>2.0.5.RELEASE</version>
    18         <relativePath/> <!-- lookup parent from repository -->
    19     </parent>
    20 
    21     <!--编码-->
    22     <properties>
    23         <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
    24         <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
    25         <java.version>1.8</java.version>
    26     </properties>
    27 
    28     <!--子模块-->
    29     <modules>
    30         <module>sb-listener</module>
    31         <module>sb-configration-file</module>
    32         <module>sb-shiro</module>
    33         <module>sb-shiro2</module>
    34     </modules>
    35 
    36     <!-- 版本说明:这里统一管理依赖的版本号 -->
    37     <dependencyManagement>
    38         <dependencies>
    39             <dependency>
    40                 <groupId>com.example</groupId>
    41                 <artifactId>sb-listener</artifactId>
    42                 <version>0.0.1-SNAPSHOT</version>
    43             </dependency>
    44         </dependencies>
    45     </dependencyManagement>
    46 
    47     <!--父依赖-->
    48     <dependencies>
    49         <dependency>
    50             <groupId>org.springframework.boot</groupId>
    51             <artifactId>spring-boot-starter-thymeleaf</artifactId>
    52         </dependency>
    53         <dependency>
    54             <groupId>org.springframework.boot</groupId>
    55             <artifactId>spring-boot-starter-web</artifactId>
    56         </dependency>
    57 
    58         <dependency>
    59             <groupId>org.projectlombok</groupId>
    60             <artifactId>lombok</artifactId>
    61             <optional>true</optional>
    62         </dependency>
    63         <dependency>
    64             <groupId>org.springframework.boot</groupId>
    65             <artifactId>spring-boot-starter-test</artifactId>
    66             <scope>test</scope>
    67         </dependency>
    68     </dependencies>
    69 
    70     <!--插件依赖-->
    71     <build>
    72         <plugins>
    73             <plugin>
    74                 <groupId>org.springframework.boot</groupId>
    75                 <artifactId>spring-boot-maven-plugin</artifactId>
    76             </plugin>
    77         </plugins>
    78     </build>
    79 
    80 
    81 </project>

    子模块项目sb-shiro2的POM文件:

    <?xml version="1.0" encoding="UTF-8"?>
    <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
        <modelVersion>4.0.0</modelVersion>
    
        <groupId>com.example</groupId>
        <artifactId>sb-shiro2</artifactId>
        <version>0.0.1-SNAPSHOT</version>
        <packaging>jar</packaging>
    
        <name>sb-shiro2</name>
        <description>Spring Boot Shiro Demo 2</description>
    
        <parent>
            <groupId>com.boot</groupId>
            <artifactId>springboot-parent-demo</artifactId>
            <version>0.0.1-SNAPSHOT</version>
        </parent>
        
        <dependencies>
            <dependency>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-data-jpa</artifactId>
            </dependency>
            <dependency>
                <groupId>org.apache.shiro</groupId>
                <artifactId>shiro-spring</artifactId>
                <version>1.4.0</version>
            </dependency>
    
            <dependency>
                <groupId>com.alibaba</groupId>
                <artifactId>druid</artifactId>
                <version>1.0.19</version>
            </dependency>
    
            <dependency>
                <groupId>mysql</groupId>
                <artifactId>mysql-connector-java</artifactId>
            </dependency>
        </dependencies>
    
        <build>
            <plugins>
                <plugin>
                    <groupId>org.springframework.boot</groupId>
                    <artifactId>spring-boot-maven-plugin</artifactId>
                </plugin>
            </plugins>
        </build>
    
    
    </project>

     整体项目结构:

    application.yml

    server:
       port: 8088
    spring:
       application:
          name: shiro
       datasource:
          url: jdbc:mysql://localhost:3306/shiro-demo
          username: root
          password: 123456
          driver-class-name: com.mysql.jdbc.Driver
       jpa:
          database: mysql
          showSql: true
          hibernate:
             ddlAuto: update
          properties:
             hibernate:
                dialect: org.hibernate.dialect.MySQL5Dialect
                format_sql: true
    View Code

    entity包

    通过Jpa生成数据库表

    User类

    package com.example.demo.entity;
    
    import lombok.Data;
    
    import javax.persistence.*;
    import java.io.Serializable;
    import java.util.List;
    
    /**
     * Created by hly on 20181114 0014.
     */
    @Data
    @Entity
    @Table(name = "user_t") //数据库生成的表名
    public class User implements Serializable{
    
        private static final long serialVersionUID = 6469007496170509665L;
        /**
         * 用户id
         */
        @Id
        @GeneratedValue
        private long id;
        /**
         * 用户名
         */
        private String username;
        /**
         * 用户密码
         */
        private String password;
        /**
         * yan
         */
        private String salt;
        /**
         * 用户表和角色表的多对多关联
         */
        @ManyToMany(fetch = FetchType.EAGER)
        @JoinTable(name = "user_role_t",joinColumns = {@JoinColumn(name = "uid")},
                inverseJoinColumns = {@JoinColumn(name = "rid")})
        private List<SysRole> roles;
    
        /**
         * 对盐进行再次加密
         * @return
         */
        public String getCredentialsSalt() {
            return username + salt + salt;
        }
    
    }
    View Code

    SysRole类 

    package com.example.demo.entity;
    
    import lombok.Data;
    
    import javax.persistence.*;
    import java.io.Serializable;
    import java.util.List;
    
    /**
     * Created by hly on 20181114 0014.
     */
    @Data
    @Entity
    @Table(name = "role_t")
    public class SysRole implements Serializable {
    
        private static final long serialVersionUID = 8215278487246865520L;
        /**
         * 角色id
         */
        @Id
        @GeneratedValue
        private Integer id;
        /**
         * 角色名称
         */
        private String role;
    
        /**
         * 权限与用户的多对多关联
         */
        @ManyToMany
        @JoinTable(name = "user_role_t",joinColumns = {@JoinColumn(name = "rid")},
                inverseJoinColumns = {@JoinColumn(name = "uid")})
        List<User> users;
    
        /**
         * 角色与权限的多对多关联
         */
        @ManyToMany(fetch = FetchType.EAGER)
        @JoinTable(name = "role_permission_t",joinColumns = {@JoinColumn(name = "rid")},
                inverseJoinColumns = {@JoinColumn(name = "pid")})
        List<SysPermission> permissions ;
    
    }
    View Code

    SysPermission类

    package com.example.demo.entity;
    
    import lombok.Data;
    
    import javax.persistence.*;
    import java.io.Serializable;
    import java.util.List;
    
    /**
     * Created by hly on 20181114 0014.
     */
    @Data
    @Entity
    @Table(name = "role_t")
    public class SysRole implements Serializable {
    
        private static final long serialVersionUID = 8215278487246865520L;
        /**
         * 角色id
         */
        @Id
        @GeneratedValue
        private Integer id;
        /**
         * 角色名称
         */
        private String role;
    
        /**
         * 权限与用户的多对多关联
         */
        @ManyToMany
        @JoinTable(name = "user_role_t",joinColumns = {@JoinColumn(name = "rid")},
                inverseJoinColumns = {@JoinColumn(name = "uid")})
        List<User> users;
    
        /**
         * 角色与权限的多对多关联
         */
        @ManyToMany(fetch = FetchType.EAGER)
        @JoinTable(name = "role_permission_t",joinColumns = {@JoinColumn(name = "rid")},
                inverseJoinColumns = {@JoinColumn(name = "pid")})
        List<SysPermission> permissions ;
    
    }
    View Code

    mapper接口

    package com.example.demo.dao;
    
    import com.example.demo.entity.User;
    import org.springframework.data.jpa.repository.JpaRepository;
    
    /**
     * Created by hly on 20181114 0014.
     */
    public interface UserMapper extends JpaRepository<User,Long>{
        User findUserByUsername(String username);
    }
    View Code

    UserService

    package com.example.demo.service;
    
    import com.example.demo.dao.UserMapper;
    import com.example.demo.entity.User;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.stereotype.Service;
    
    /**
     * Created by hly on 20181114 0014.
     */
    @Service
    public class UserService {
    
        @Autowired
        private UserMapper userMapper;
    
        public User findUserByName(String username){
            return userMapper.findUserByUsername(username);
        }
    
        public User saveUser(User user){
            return userMapper.save(user);
        }
    }
    View Code

    Shiro包

    ShiroConfig

    package com.example.demo.shiro;
    
    import org.apache.shiro.authc.credential.HashedCredentialsMatcher;
    import org.apache.shiro.mgt.SecurityManager;
    import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
    import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
    import org.springframework.context.annotation.Bean;
    import org.springframework.context.annotation.Configuration;
    
    import java.util.HashMap;
    import java.util.Map;
    
    /**
     * Created by hly on 20181114 0014.
     */
    @Configuration
    public class ShiroConfig {
        // shiro filter
        @Bean
        public ShiroFilterFactoryBean shirFilter(SecurityManager securityManager) {
            ShiroFilterFactoryBean shiroFilterFactoryBean = new ShiroFilterFactoryBean();
            shiroFilterFactoryBean.setSecurityManager(securityManager);
    
            Map<String, String> filterChainDefinitionMap = new HashMap<String, String>();
            //登录界面,没有登录的用户访问授权的界面就会跳转到该界面
            shiroFilterFactoryBean.setLoginUrl("/login");
            //没有授权的资源,都可以访问,用户访问授权的资源无权限时跳转到该界面
            shiroFilterFactoryBean.setUnauthorizedUrl("/unauthc");
            shiroFilterFactoryBean.setSuccessUrl("/home/index");
            //所有路径都拦截
            filterChainDefinitionMap.put("/*", "anon");
            //授权资源,只有登录了才能访问,并且有该对应权限的用户才可以访问
            filterChainDefinitionMap.put("/authc/index", "authc");
            filterChainDefinitionMap.put("/authc/admin", "roles[admin]");
            filterChainDefinitionMap.put("/authc/renewable", "perms[Create,Update]");
            filterChainDefinitionMap.put("/authc/removable", "perms[Delete]");
            filterChainDefinitionMap.put("/authc/retrievable", "perms[Retrieve]");
            shiroFilterFactoryBean.setFilterChainDefinitionMap(filterChainDefinitionMap);
            System.out.println("shirFilter配置成功");
            return shiroFilterFactoryBean;
        }
    
        //授权管理者
        @Bean
        public SecurityManager securityManager() {
            DefaultWebSecurityManager  securityManager = new DefaultWebSecurityManager();
            securityManager.setRealm(shiroRealm());
            return securityManager;
        }
        //shiro realm
        @Bean
        public EnceladusShiroRealm shiroRealm() {
            EnceladusShiroRealm shiroRealm = new EnceladusShiroRealm();
            shiroRealm.setCredentialsMatcher(hashedCredentialsMatcher());
            return shiroRealm;
        }
        //设置算法和迭代
        @Bean
        public HashedCredentialsMatcher hashedCredentialsMatcher() {
            HashedCredentialsMatcher hashedCredentialsMatcher = new HashedCredentialsMatcher();
            hashedCredentialsMatcher.setHashAlgorithmName(PasswordHelper.ALGORITHM_NAME);// 散列算法
            hashedCredentialsMatcher.setHashIterations(PasswordHelper.HASH_ITERATIONS);// 散列次数
            return hashedCredentialsMatcher;
        }
        //密码加密
        @Bean
        public PasswordHelper passwordHelper() {
            return new PasswordHelper();
        }
    }
    View Code

    EnceladusShiroRealm

    package com.example.demo.shiro;
    
    import com.example.demo.entity.SysPermission;
    import com.example.demo.entity.SysRole;
    import com.example.demo.entity.User;
    import com.example.demo.service.UserService;
    import org.apache.shiro.authc.AuthenticationException;
    import org.apache.shiro.authc.AuthenticationInfo;
    import org.apache.shiro.authc.AuthenticationToken;
    import org.apache.shiro.authc.SimpleAuthenticationInfo;
    import org.apache.shiro.authz.AuthorizationInfo;
    import org.apache.shiro.authz.SimpleAuthorizationInfo;
    import org.apache.shiro.realm.AuthorizingRealm;
    import org.apache.shiro.subject.PrincipalCollection;
    import org.apache.shiro.util.ByteSource;
    import org.springframework.beans.factory.annotation.Autowired;
    
    /**
     * Created by hly on 20181114 0014.
     * shiro中用户自定义登录验证和授权认证的地方(realm)
     */
    public class EnceladusShiroRealm extends AuthorizingRealm{
    
        @Autowired
        private UserService userService;
    
        /**
         * 授权认证
         * @param principal
         * @return
         */
        @Override
        protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principal) {
            //负责装载role和permission的对象
            SimpleAuthorizationInfo authorizationInfo = new SimpleAuthorizationInfo();
            //获取用户名
            String username = (String) principal.getPrimaryPrincipal();
            //获取用户
            User user = userService.findUserByName(username);
            //遍历角色和权限,并把名称加入到authorizationInfo中
            for (SysRole role:user.getRoles()) {
                authorizationInfo.addRole(role.getRole());
                for(SysPermission permission:role.getPermissions()) {
                    authorizationInfo.addStringPermission(permission.getName());
                }
            }
            return authorizationInfo;
        }
    
        /**
         * 登录验证
         * @param token
         * @return
         * @throws AuthenticationException
         */
        @Override
        protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken token) throws AuthenticationException {
            //获取用户名
            String username = (String)token.getPrincipal();
            //查寻用户
            User user = userService.findUserByName(username);
            //逻辑
            if (user == null) {
                return null;
            }
            //包装对象(用户名、密码、用户Salt、抽象类CachingRealm的getName())
            SimpleAuthenticationInfo authenticationInfo = new SimpleAuthenticationInfo(user.getUsername(),user.getPassword(),
                    ByteSource.Util.bytes(user.getCredentialsSalt()),getName());
            System.out.println("getName():"+getName());
            //返回SimpleAuthenticationInfo对象
            return authenticationInfo;
        }
    }
    View Code

    PasswordHelper

    package com.example.demo.shiro;
    
    import com.example.demo.entity.User;
    import org.apache.shiro.crypto.RandomNumberGenerator;
    import org.apache.shiro.crypto.SecureRandomNumberGenerator;
    import org.apache.shiro.crypto.hash.SimpleHash;
    import org.apache.shiro.util.ByteSource;
    
    /**
     * Created by hly on 20181114 0014.
     * 对密码进行迭代加密,保证用户密码的安全
     */
    public class PasswordHelper {
        //安全的随机字符
        private RandomNumberGenerator randomNumberGenerator = new SecureRandomNumberGenerator();
        //算法名称
        public static final String ALGORITHM_NAME = "md5";
        //迭代次数
        public static final int HASH_ITERATIONS = 2;
    
        public void encryptPassword(User user) {
            //随机字符串作为用户的Salt
            user.setSalt(randomNumberGenerator.nextBytes().toHex());
            //算法、用户密码、用户Salt、迭代次数
            String newPassword = new SimpleHash(ALGORITHM_NAME,user.getPassword(),
                    ByteSource.Util.bytes(user.getCredentialsSalt()),HASH_ITERATIONS).toHex();
            //对用户设置新密码
            user.setPassword(newPassword);
        }
    
    
    }
    View Code

    Controller包

    AuthcController

    package com.example.demo.controller;
    
    import com.example.demo.entity.User;
    import org.apache.shiro.SecurityUtils;
    import org.apache.shiro.subject.Subject;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RestController;
    
    /**
     * 验证的接口
     */
    @RestController
    @RequestMapping("authc")
    public class AuthcController {
    
        @GetMapping("index")
        public Object index() {
            Subject subject = SecurityUtils.getSubject();
            User user = (User) subject.getSession().getAttribute("user");
            return user.toString();
        }
    
        @GetMapping("admin")
        public Object admin() {
            return "Welcome Admin";
        }
    
        // delete
        @GetMapping("removable")
        public Object removable() {
            return "removable";
        }
    
        // creat & update
        @GetMapping("renewable")
        public Object renewable() {
            return "renewable";
        }
    
        @GetMapping("retrievable")
        public Object retrievable() {return "retrievable";}
    
    }
    View Code

    HomeController

    package com.example.demo.controller;
    
    import com.example.demo.entity.User;
    import com.example.demo.service.UserService;
    import com.example.demo.shiro.PasswordHelper;
    import org.apache.shiro.SecurityUtils;
    import org.apache.shiro.authc.IncorrectCredentialsException;
    import org.apache.shiro.authc.UnknownAccountException;
    import org.apache.shiro.authc.UsernamePasswordToken;
    import org.apache.shiro.subject.Subject;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestParam;
    import org.springframework.web.bind.annotation.RestController;
    
    /**
     * 不验证的接口
     */
    @RestController
    @RequestMapping
    public class HomeController {
    
        @Autowired
        private UserService userService;
    
        @Autowired
        private PasswordHelper passwordHelper;
    
        @GetMapping("/login")
        public Object login() {
            return "Here is Login page";
        }
    
        @GetMapping("/unauthc")
        public Object unauthc() {
            return "Here is Unauthc page";
        }
    
        @GetMapping("doLogin")
        public Object doLogin(@RequestParam String username, @RequestParam String password) {
            UsernamePasswordToken token = new UsernamePasswordToken(username, password);
            Subject subject = SecurityUtils.getSubject();
            try {
                subject.login(token);
            } catch (IncorrectCredentialsException ice) {
                return "password error!";
            } catch (UnknownAccountException uae) {
                return "username error!";
            }
    
            User user = userService.findUserByName(username);
            subject.getSession().setAttribute("user", user);
            return "SUCCESS";
        }
    
        @GetMapping("/register")
        public Object register(@RequestParam String username, @RequestParam String password) {
            User user = new User();
            user.setUsername(username);
            user.setPassword(password);
            passwordHelper.encryptPassword(user);
    
            userService.saveUser(user);
            return "注册用户SUCCESS";
        }
    }
    View Code

    之后运行项目通过rest接口测试

    localhost:8088/login
    localhost:8088/unauthc
    localhost:8088/doLogin?username=hly&password=123
    等等通过controller里的接口进行运行测试就好了,看运行效果,我就不一一往下copy了
  • 相关阅读:
    大咖们如何评判优秀架构师?
    腾讯会议大规模任务调度系统架构设计
    计算压力倍增,携程度假起价引擎架构演变
    快手春节红包背后,高并发存储架构设计
    日均20亿流量:携程机票查询系统的架构升级
    我是如何一步步的在并行编程中将lock锁次数降到最低实现无锁编程
    OGRE
    CMake
    深入理解C++11【5】
    深入理解C++11【4】
  • 原文地址:https://www.cnblogs.com/h-java/p/9964994.html
走看看 - 开发者的网上家园