最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

Spring Security基于JWT實(shí)現(xiàn)SSO單點(diǎn)登錄詳解

 更新時(shí)間:2019年09月06日 15:08:12   作者:ZhuPengWei_  
這篇文章主要介紹了Spring Security基于JWT實(shí)現(xiàn)SSO單點(diǎn)登錄詳解,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧

SSO :同一個(gè)帳號(hào)在同一個(gè)公司不同系統(tǒng)上登陸

這里寫(xiě)圖片描述 

使用SpringSecurity實(shí)現(xiàn)類似于SSO登陸系統(tǒng)是十分簡(jiǎn)單的 下面我就搭建一個(gè)DEMO

首先來(lái)看看目錄的結(jié)構(gòu)

這里寫(xiě)圖片描述 

其中sso-demo是父工程項(xiàng)目 sso-client 、sso-client2分別對(duì)應(yīng)2個(gè)資源服務(wù)器,sso-server是認(rèn)證服務(wù)器

引入的pom文件

sso-demo

<?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>study.security.sso</groupId>
  <artifactId>sso-demo</artifactId>
  <version>1.0.0-SNAPSHOT</version>
  <modules>
    <module>sso-server</module>
    <module>sso-client</module>
    <module>sso-client2</module>
  </modules>
  <packaging>pom</packaging>

  <dependencyManagement>
    <dependencies>
      <dependency>
        <groupId>io.spring.platform</groupId>
        <artifactId>platform-bom</artifactId>
        <version>Brussels-SR4</version>
        <type>pom</type>
        <scope>import</scope>
      </dependency>
      <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-dependencies</artifactId>
        <version>Dalston.SR2</version>
        <type>pom</type>
        <scope>import</scope>
      </dependency>
    </dependencies>
  </dependencyManagement>

  <build>
    <plugins>
      <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-compiler-plugin</artifactId>
        <version>2.3.2</version>
        <configuration>
          <source>1.8</source>
          <target>1.8</target>
          <encoding>UTF-8</encoding>
        </configuration>
      </plugin>
    </plugins>
  </build>

</project>

sso-server

<?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">
  <parent>
    <artifactId>sso-demo</artifactId>
    <groupId>study.security.sso</groupId>
    <version>1.0.0-SNAPSHOT</version>
  </parent>
  <modelVersion>4.0.0</modelVersion>

  <artifactId>sso-server</artifactId>

  <dependencies>
    <dependency>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-starter-security</artifactId>
    </dependency>
    <dependency>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
      <groupId>org.springframework.security.oauth</groupId>
      <artifactId>spring-security-oauth2</artifactId>
    </dependency>
    <dependency>
      <groupId>org.springframework.security</groupId>
      <artifactId>spring-security-jwt</artifactId>
    </dependency>

  </dependencies>

</project>

sso-client與sso-client2 pom 中的 是一樣的

1.sso-server

現(xiàn)在開(kāi)始搭建認(rèn)證服務(wù)器

認(rèn)證服務(wù)器的目錄結(jié)構(gòu)如下

這里寫(xiě)圖片描述

/**
 * 認(rèn)證服務(wù)器配置
 * Created by ZhuPengWei on 2018/1/11.
 */
@Configuration
@EnableAuthorizationServer
public class SsoAuthenticationServerConfig extends AuthorizationServerConfigurerAdapter {

  @Override
  public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
    clients.inMemory()
        .withClient("client1")
        .secret("client1")
        .authorizedGrantTypes("authorization_code", "refresh_token")
        .scopes("all")
        .and()
        .withClient("client2")
        .secret("client2")
        .authorizedGrantTypes("authorization_code", "refresh_token")
        .scopes("all");
  }

  @Override
  public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
    endpoints.tokenStore(jwtTokenStore()).accessTokenConverter(jwtAccessTokenConverter());
  }


  /**
   * 認(rèn)證服務(wù)器的安全配置
   *
   * @param security
   * @throws Exception
   */
  @Override
  public void configure(AuthorizationServerSecurityConfigurer security) throws Exception {
    // 要訪問(wèn)認(rèn)證服務(wù)器tokenKey的時(shí)候需要經(jīng)過(guò)身份認(rèn)證
    security.tokenKeyAccess("isAuthenticated()");
  }

  @Bean
  public TokenStore jwtTokenStore() {
    return new JwtTokenStore(jwtAccessTokenConverter());
  }

  @Bean
  public JwtAccessTokenConverter jwtAccessTokenConverter() {
    JwtAccessTokenConverter jwtAccessTokenConverter = new JwtAccessTokenConverter();
    // 保證JWT安全的唯一方式
    jwtAccessTokenConverter.setSigningKey("ZPW");
    return jwtAccessTokenConverter;
  }
}
/**
 * 自定義用戶登陸邏輯配置
 * Created by ZhuPengWei on 2018/1/13.
 */
@Configuration
public class SsoSecurityConfig extends WebSecurityConfigurerAdapter {

  @Autowired
  private UserDetailsService userDetailsService;

  /**
   * 加密解密邏輯
   */
  @Bean
  public PasswordEncoder passwordEncoder() {
    return new BCryptPasswordEncoder();
  }

  @Override
  protected void configure(HttpSecurity http) throws Exception {
    // 改成表單登陸的方式 所有請(qǐng)求都需要認(rèn)證
    http.formLogin().and().authorizeRequests().anyRequest().authenticated();
  }

  @Override
  protected void configure(AuthenticationManagerBuilder auth) throws Exception {
    // 用自己的登陸邏輯以及加密器
    auth.userDetailsService(userDetailsService).passwordEncoder(passwordEncoder());
  }
}
/**
 * 自定義用戶登陸
 * Created by ZhuPengWei on 2018/1/13.
 */
@Component
public class SsoUserDetailsService implements UserDetailsService {

  @Autowired
  private PasswordEncoder passwordEncoder;

  @Override
  public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {

    return new User(username,
        passwordEncoder.encode("123456"),
        AuthorityUtils.commaSeparatedStringToAuthorityList("ROLE_USER"));
  }
}

其中SsoApprovalEndPoint與SsoSpelView目的是去掉登陸之后授權(quán)的效果

注解 @FrameworkEndpoint

與@RestController注解相類似

如果聲明和@FrameworkEndpoint一模一樣的@RequestMapping

Spring框架處理的時(shí)候會(huì)優(yōu)先處理@RestController里面的

這里寫(xiě)圖片描述

/**
 * 自定義認(rèn)證邏輯
 * Created by ZhuPengWei on 2018/1/13.
 */
@RestController
@SessionAttributes("authorizationRequest")
public class SsoApprovalEndpoint {

  @RequestMapping("/oauth/confirm_access")
  public ModelAndView getAccessConfirmation(Map<String, Object> model, HttpServletRequest request) throws Exception {
    String template = createTemplate(model, request);
    if (request.getAttribute("_csrf") != null) {
      model.put("_csrf", request.getAttribute("_csrf"));
    }
    return new ModelAndView(new SsoSpelView(template), model);
  }

  protected String createTemplate(Map<String, Object> model, HttpServletRequest request) {
    String template = TEMPLATE;
    if (model.containsKey("scopes") || request.getAttribute("scopes") != null) {
      template = template.replace("%scopes%", createScopes(model, request)).replace("%denial%", "");
    } else {
      template = template.replace("%scopes%", "").replace("%denial%", DENIAL);
    }
    if (model.containsKey("_csrf") || request.getAttribute("_csrf") != null) {
      template = template.replace("%csrf%", CSRF);
    } else {
      template = template.replace("%csrf%", "");
    }
    return template;
  }

  private CharSequence createScopes(Map<String, Object> model, HttpServletRequest request) {
    StringBuilder builder = new StringBuilder("<ul>");
    @SuppressWarnings("unchecked")
    Map<String, String> scopes = (Map<String, String>) (model.containsKey("scopes") ? model.get("scopes") : request
        .getAttribute("scopes"));
    for (String scope : scopes.keySet()) {
      String approved = "true".equals(scopes.get(scope)) ? " checked" : "";
      String denied = !"true".equals(scopes.get(scope)) ? " checked" : "";
      String value = SCOPE.replace("%scope%", scope).replace("%key%", scope).replace("%approved%", approved)
          .replace("%denied%", denied);
      builder.append(value);
    }
    builder.append("</ul>");
    return builder.toString();
  }

  private static String CSRF = "<input type='hidden' name='${_csrf.parameterName}' value='${_csrf.token}' />";

  private static String DENIAL = "<form id='denialForm' name='denialForm' action='${path}/oauth/authorize' method='post'><input name='user_oauth_approval' value='false' type='hidden'/>%csrf%<label><input name='deny' value='Deny' type='submit'/></label></form>";

  // 對(duì)源代碼進(jìn)行處理 隱藏授權(quán)頁(yè)面,并且使他自動(dòng)提交
  private static String TEMPLATE = "<html><body><div style='display:none;'> <h1>OAuth Approval</h1>"
      + "<p>Do you authorize '${authorizationRequest.clientId}' to access your protected resources?</p>"
      + "<form id='confirmationForm' name='confirmationForm' action='${path}/oauth/authorize' method='post'><input name='user_oauth_approval' value='true' type='hidden'/>%csrf%%scopes%<label><input name='authorize' value='Authorize' type='submit'/></label></form>"
      + "%denial%</div><script>document.getElementById('confirmationForm').submit();</script></body></html>";

  private static String SCOPE = "<li><div class='form-group'>%scope%: <input type='radio' name='%key%'"
      + " value='true'%approved%>Approve</input> <input type='radio' name='%key%' value='false'%denied%>Deny</input></div></li>";

}

SsoSpelView 與 原來(lái)SpelView 是一樣的 只不過(guò)原來(lái)SpelView 不是public的類

application.properties

server.port=9999
server.context-path=/server

2.sso-client

相對(duì)于認(rèn)證服務(wù)器 資源服務(wù)器demo的配置就十分簡(jiǎn)單了

這里寫(xiě)圖片描述

/**
 * Created by ZhuPengWei on 2018/1/11.
 */
@SpringBootApplication
@RestController
@EnableOAuth2Sso
public class SsoClient1Application {

  @GetMapping("/user")
  public Authentication user(Authentication user) {
    return user;
  }

  public static void main(String[] args) {
    SpringApplication.run(SsoClient1Application.class, args);
  }
}
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>SSO Client1</title>
</head>
<body>
<h1>SSO Demo Client1</h1>
<a  rel="external nofollow" >訪問(wèn)client2</a>

</body>
</html>

application.properties

security.oauth2.client.client-id=client1
security.oauth2.client.client-secret=client1
#需要認(rèn)證時(shí)候跳轉(zhuǎn)的地址
security.oauth2.client.user-authorization-uri=http://127.0.0.1:9999/server/oauth/authorize
#請(qǐng)求令牌地址
security.oauth2.client.access-token-uri=http://127.0.0.1:9999/server/oauth/token
#解析
security.oauth2.resource.jwt.key-uri=http://127.0.0.1:9999/server/oauth/token_key


#sso
server.port=8080
server.context-path=/client1

3.sso-client2

資源服務(wù)器1和資源服務(wù)器2的目錄結(jié)構(gòu)是一樣的,改了相關(guān)的參數(shù)

/**
 * Created by ZhuPengWei on 2018/1/11.
 */
@SpringBootApplication
@RestController
@EnableOAuth2Sso
public class SsoClient2Application {

  @GetMapping("/user")
  public Authentication user(Authentication user) {
    return user;
  }

  public static void main(String[] args) {
    SpringApplication.run(SsoClient2Application.class, args);
  }
}
<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="UTF-8">
  <title>SSO Client2</title>
</head>
<body>
<h1>SSO Demo Client2</h1>
<a  rel="external nofollow" >訪問(wèn)client1</a>

</body>
</html>
security.oauth2.client.client-id=client2
security.oauth2.client.client-secret=client2
#需要認(rèn)證時(shí)候跳轉(zhuǎn)的地址
security.oauth2.client.user-authorization-uri=http://127.0.0.1:9999/server/oauth/authorize
#請(qǐng)求令牌地址
security.oauth2.client.access-token-uri=http://127.0.0.1:9999/server/oauth/token
#解析
security.oauth2.resource.jwt.key-uri=http://127.0.0.1:9999/server/oauth/token_key


#sso
server.port=8060
server.context-path=/client2

好了 基于JWT實(shí)現(xiàn)SSO單點(diǎn)登錄的DEMO以及搭建完成了 下面來(lái)看看頁(yè)面的效果

在初次訪問(wèn)的時(shí)候

圖1

這里寫(xiě)圖片描述

登陸成功之后

圖2

這里寫(xiě)圖片描述

圖3

這里寫(xiě)圖片描述

注意

寫(xiě)SsoApprovalEndPoint與SsoSpelView目的是去掉登陸之后授權(quán)的效果如果不寫(xiě)這2個(gè)類

在初次訪問(wèn)的登陸成功之后是有一步授權(quán)的操作的

比如說(shuō)圖1操作成功之后

這里寫(xiě)圖片描述 

點(diǎn)擊Authorize才會(huì)跳轉(zhuǎn)到圖2

以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

  • 基于Spring的Maven項(xiàng)目實(shí)現(xiàn)發(fā)送郵件功能的示例

    基于Spring的Maven項(xiàng)目實(shí)現(xiàn)發(fā)送郵件功能的示例

    這篇文章主要介紹了基于Spring的Maven項(xiàng)目實(shí)現(xiàn)發(fā)送郵件功能,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2020-03-03
  • Spring Boot 整合 MongoDB的示例

    Spring Boot 整合 MongoDB的示例

    這篇文章主要介紹了Spring Boot 整合 MongoDB的示例,幫助大家更好的理解和學(xué)習(xí)spring boot框架,感興趣的朋友可以了解下
    2020-10-10
  • 簡(jiǎn)單注解實(shí)現(xiàn)集群同步鎖(spring+redis+注解)

    簡(jiǎn)單注解實(shí)現(xiàn)集群同步鎖(spring+redis+注解)

    本文主要介紹了簡(jiǎn)單注解實(shí)現(xiàn)集群同步鎖的步驟與方法。具有一定的參考價(jià)值,下面跟著小編一起來(lái)看下吧
    2017-01-01
  • Java中接口Set的特點(diǎn)及方法說(shuō)明

    Java中接口Set的特點(diǎn)及方法說(shuō)明

    這篇文章主要介紹了Java中接口Set的特點(diǎn)及方法說(shuō)明,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2022-02-02
  • IDEA2023 配置使用Docker的詳細(xì)教程

    IDEA2023 配置使用Docker的詳細(xì)教程

    這篇文章主要介紹了IDEA2023 配置使用Docker的詳細(xì)教程,本文通過(guò)圖文并茂的形式給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2023-07-07
  • Java流處理stream使用詳解

    Java流處理stream使用詳解

    Java8的另一大亮點(diǎn)Stream,它與java.io包里的InputStream和OutputStream是完全不同的概念,下面這篇文章主要給大家介紹了關(guān)于Java8中Stream詳細(xì)使用方法的相關(guān)資料,需要的朋友可以參考下
    2022-10-10
  • 使用spring+maven不同環(huán)境讀取配置方式

    使用spring+maven不同環(huán)境讀取配置方式

    這篇文章主要介紹了使用spring+maven不同環(huán)境讀取配置方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2023-08-08
  • 關(guān)于SpringBoot大文件RestTemplate下載解決方案

    關(guān)于SpringBoot大文件RestTemplate下載解決方案

    這篇文章主要介紹了SpringBoot大文件RestTemplate下載解決方案,最近結(jié)合網(wǎng)上案例及自己總結(jié),寫(xiě)了一個(gè)分片下載tuling/fileServer項(xiàng)目,需要的朋友可以參考下
    2021-10-10
  • SpringSecurity實(shí)現(xiàn)自定義登錄方式

    SpringSecurity實(shí)現(xiàn)自定義登錄方式

    本文介紹自定義登錄流程,包括自定義AuthenticationToken、AuthenticationFilter、AuthenticationProvider以及SecurityConfig配置類,詳細(xì)解析了認(rèn)證流程的實(shí)現(xiàn),為開(kāi)發(fā)人員提供了具體的實(shí)施指導(dǎo)和參考
    2024-09-09
  • idea.vmoptions 最佳配置方案

    idea.vmoptions 最佳配置方案

    本文介紹了針對(duì)IntelliJ IDEA的優(yōu)化配置建議,包括提升內(nèi)存設(shè)置、啟用G1垃圾回收器、優(yōu)化垃圾回收策略以及調(diào)整網(wǎng)絡(luò)設(shè)置等,旨在提高IDE的性能和響應(yīng)速度,同時(shí),指導(dǎo)用戶如何修改vmoptions文件以應(yīng)用這些配置,并提供了監(jiān)控內(nèi)存使用和插件管理的建議
    2024-09-09

最新評(píng)論

陇南市| 来宾市| 新巴尔虎左旗| 台南市| 凤台县| 申扎县| 张家港市| 陇川县| 梁平县| 横峰县| 富顺县| 秦安县| 体育| 台东市| 修水县| 大宁县| 赫章县| 新干县| 故城县| 红桥区| 新津县| 灵丘县| 屏东县| 鹤壁市| 北安市| 阿拉善右旗| 高尔夫| 琼海市| 抚州市| 镇雄县| 林口县| 元朗区| 鄄城县| 怀来县| 兰州市| 中方县| 浮山县| 滨州市| 都安| 罗定市| 南昌市|