Oauth2密碼模式+JWT+Oracle

1.Oauth2 相關Maven依賴
 

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-security</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.security.oauth.boot</groupId>
            <artifactId>spring-security-oauth2-autoconfigure</artifactId>
            <version>2.1.3.RELEASE</version>
        </dependency>

2.Oauth2 使用的表(表明固定)OAUTH_CLIENT_DETAILS

  CREATE TABLE "OAUTH_CLIENT_DETAILS" 
   (	"CLIENT_ID" VARCHAR2(256 BYTE) NOT NULL ENABLE, 
	"RESOURCE_IDS" VARCHAR2(256 BYTE) DEFAULT NULL, 
	"CLIENT_SECRET" VARCHAR2(256 BYTE) DEFAULT NULL, 
	"SCOPE" VARCHAR2(256 BYTE) DEFAULT NULL, 
	"AUTHORIZED_GRANT_TYPES" VARCHAR2(256 BYTE) DEFAULT NULL, 
	"WEB_SERVER_REDIRECT_URI" VARCHAR2(256 BYTE) DEFAULT NULL, 
	"AUTHORITIES" VARCHAR2(256 BYTE) DEFAULT NULL, 
	"ACCESS_TOKEN_VALIDITY" NUMBER(11,0) DEFAULT NULL, 
	"REFRESH_TOKEN_VALIDITY" NUMBER(11,0) DEFAULT NULL, 
	"ADDITIONAL_INFORMATION" VARCHAR2(1000 BYTE) DEFAULT NULL, 
	"AUTOAPPROVE" VARCHAR2(256 BYTE) DEFAULT NULL, 
	 PRIMARY KEY ("CLIENT_ID")
  USING INDEX PCTFREE 10 INITRANS 2 MAXTRANS 255 COMPUTE STATISTICS 
  STORAGE(INITIAL 5242880 NEXT 5242880 MINEXTENTS 1 MAXEXTENTS 2147483645
  PCTINCREASE 0 FREELISTS 1 FREELIST GROUPS 1
  BUFFER_POOL DEFAULT FLASH_CACHE DEFAULT CELL_FLASH_CACHE DEFAULT)
  TABLESPACE "LOG_DATA"  ENABLE
   )

3.Oauth2相關配置文件

a.token自定義載荷

import java.util.HashMap;
import java.util.Map;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.security.oauth2.common.DefaultOAuth2AccessToken;
import org.springframework.security.oauth2.common.OAuth2AccessToken;
import org.springframework.security.oauth2.provider.OAuth2Authentication;
import org.springframework.security.oauth2.provider.token.TokenEnhancer;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;

public class JwtTokenEnhancer  implements TokenEnhancer {
    private static final Logger logger = LoggerFactory.getLogger(JwtTokenEnhancer.class);

	@Override
    public OAuth2AccessToken enhance(OAuth2AccessToken oAuth2AccessToken, 
    		OAuth2Authentication oAuth2Authentication) {

        Map<String,Object> info = new HashMap<>();
        info.put("provider","Fant.J");
        //设置附加信息
        ((DefaultOAuth2AccessToken)oAuth2AccessToken).setAdditionalInformation(info);
        logger.debug("debug");
        return oAuth2AccessToken;
    }

}

b.授權服務器配置

import javax.sql.DataSource;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.security.oauth2.config.annotation.configurers.ClientDetailsServiceConfigurer;
import org.springframework.security.oauth2.config.annotation.web.configuration.AuthorizationServerConfigurerAdapter;
import org.springframework.security.oauth2.config.annotation.web.configuration.EnableAuthorizationServer;
import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerEndpointsConfigurer;
import org.springframework.security.oauth2.config.annotation.web.configurers.AuthorizationServerSecurityConfigurer;
import org.springframework.security.oauth2.provider.ClientDetailsService;
import org.springframework.security.oauth2.provider.client.JdbcClientDetailsService;
import org.springframework.security.oauth2.provider.token.DefaultTokenServices;
import org.springframework.security.oauth2.provider.token.TokenStore;
import org.springframework.security.oauth2.provider.token.store.JwtAccessTokenConverter;

import com.foxconn.provider.service.MyUserDetailsService;

@Configuration
@EnableAuthorizationServer
public class MyAuthorizationServerConfig extends AuthorizationServerConfigurerAdapter{
	
    private static final Logger logger = LoggerFactory.getLogger(MyAuthorizationServerConfig.class);

	    @Autowired
	    private AuthenticationManager authenticationManager;

	    @Autowired
	    private  MyUserDetailsService userDetailsService;
	    
	    @Autowired
	    private PasswordEncoder passwordEncoder;
	    
	    //数据源会自动配置
	    @Autowired
	    private DataSource dataSource;    
	    
	    @Autowired
	    private TokenStore tokenStore;
	    
	    @Autowired
	    private JwtAccessTokenConverter jwtAccessTokenConverter;

	    @Override
	    public void configure(AuthorizationServerSecurityConfigurer security) throws Exception {
//	        super.configure(security);
   	
	    	security.tokenKeyAccess("isAnonymous() || hasAuthority('ROLE_TRUSTED_CLIENT')")
            .checkTokenAccess("isAnonymous() || hasAuthority('ROLE_TRUSTED_CLIENT')");
	    	
	    }
    
	    @Override
	    public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
	    	clients.withClientDetails(jdbcClientDetailsService());
	     
	    }
	    	    
	    /**
	     * 配置通過 數據庫的方式 去 獲取 client 信息
	     * @return
	     */
	    @Bean
	    public ClientDetailsService  jdbcClientDetailsService(){
	        JdbcClientDetailsService  jdbcClientDetailsService = new JdbcClientDetailsService(dataSource);
	        jdbcClientDetailsService.setPasswordEncoder(passwordEncoder);
	        return  jdbcClientDetailsService;
	    }
	    
	    //把上面的各个组件组合在一起
	    @Override
	    public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
	    	    	
	        endpoints
	                .tokenStore(tokenStore)
	                .authenticationManager(authenticationManager)  // 认证管理器 - 在密码模式必须配置
	                .userDetailsService(userDetailsService)  // 自定义校验用户service
	                .accessTokenConverter(jwtAccessTokenConverter);
	        logger.debug("debug");
	        }
	    
}

c.使用JWT令牌配置

@Configuration
public class TokenConfig {
	/** JWT密钥 */
    private String signingKey = "fastboot";

    /**
     * 配置 token 如何生成
     * 1. InMemoryTokenStore 基于内存存储
     * 2. JdbcTokenStore 基于数据库存储
     * 3. JwtTokenStore 使用 JWT 存储 该方式可以让资源服务器自己校验令牌的有效性而不必远程连接认证服务器再进行认证
     */

    public String getSigningKey() {
        return signingKey;
    }

    public void setSigningKey(String signingKey) {
        this.signingKey = signingKey;
    }
    
    // 第二個 token config 類
    @Bean
    public TokenStore jwtTokenStore(){
        return new JwtTokenStore(jwtAccessTokenConverter());
    }

    /**
     * token生成处理:指定签名
     */
    @Bean
    public JwtAccessTokenConverter jwtAccessTokenConverter(){
        JwtAccessTokenConverter accessTokenConverter = new JwtAccessTokenConverter();
        accessTokenConverter.setSigningKey(signingKey);
        accessTokenConverter.setVerifierKey(signingKey);
        return accessTokenConverter;
    }

    @Bean
    public TokenEnhancer jwtTokenEnhancer(){
        return new JwtTokenEnhancer();
    }   
}

d.權限配置

@Configuration
@EnableWebSecurity
public class WebSecurityConfig  extends WebSecurityConfigurerAdapter{
 
    @Autowired
    private MyUserDetailsService  myuserDetailsService;
    /// 自己的 數據庫實現的  用戶詳情信息
 
    @Override
    protected void configure(AuthenticationManagerBuilder auth) throws Exception {
        ///auth.userDetailsService(userDetailsService()).passwordEncoder(passwordEncoder());
    	auth.userDetailsService(myuserDetailsService).passwordEncoder(passwordEncoder());
    }
 
    @Override
    public void configure(WebSecurity web) throws Exception {
        web.ignoring().antMatchers("/assets/**", "/css/**", "/images/**");
    }
 
    @Override
    protected void configure(HttpSecurity http) throws Exception {
        http.formLogin()
                .and()
                .authorizeRequests().antMatchers("/oauth/**").permitAll()
                .anyRequest()
                .authenticated()
                .and().csrf().disable().cors();
    }
    
 
    /**
     * 密碼的 加密方式 
     * @return
     */
    @Bean
    public PasswordEncoder passwordEncoder() {
        return  new BCryptPasswordEncoder();
    }
    
    /**
     * 密碼模式下必須注入的bean authenticationManagerBean
     * 認證是由 AuthenticationManager 來管理的,
     * 但是真正進行認證的是 AuthenticationManager 中定義的AuthenticationProvider。
     *  AuthenticationManager 中可以定義有多個 AuthenticationProvider
     */
    @Override
    @Bean
    public  AuthenticationManager authenticationManagerBean() throws Exception {
        return super.authenticationManagerBean();
    }

}

4.生成token、刷新token、校驗token

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值