<output id="qn6qe"></output>

    1. <output id="qn6qe"><tt id="qn6qe"></tt></output>
    2. <strike id="qn6qe"></strike>

      亚洲 日本 欧洲 欧美 视频,日韩中文字幕有码av,一本一道av中文字幕无码,国产线播放免费人成视频播放,人妻少妇偷人无码视频,日夜啪啪一区二区三区,国产尤物精品自在拍视频首页,久热这里只有精品12

      JWT公司的主流Json Web Token 令牌 如何使用,取代session,還可以運用分布式認證,

      JWT簡介:

      JWT(JSON WEB TOKEN):JSON網絡令牌,JWT是一個輕便的安全跨平臺傳輸格式,定義了一個緊湊的自包含的方式在不同實體之間安全傳輸信息(JSON格式)。它是在Web環境下兩個實體之間傳輸數據的一項標準。實際上傳輸的就是一個字符串。廣義上講JWT是一個標準的名稱;狹義上JWT指的就是用來傳遞的那個token字符串

      jwt特點:

      • JWT無需存儲在服務器(不使用Session/Cookie),不占用服務器資源(也就是Stateless無狀態的),也就不存在多服務器共享Session的問題
      • 使用簡單,用戶在登錄成功拿到 Token后,一般訪問需要權限的請求時,在Header附上Token即可。

      JWT公司官網:   

      https://jwt.io/

       

      jwt的token結構:

      JWT的數據結構以及簽發的過程
      JWT由三部分構成:header(頭部)、payload(載荷)和signature(簽名)。

      Header 頭部信息:指定類型和算法
      Payload 荷載信息:存放Claims聲明信息
      Signature 簽名:把前兩者對應的Json結構進行base64url編碼之后的字符串拼接起來和密鑰放一起加密后的簽名
      組成方式為: header.payload.signature

      eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.
      eyJpc3MiOiLlvKDlvLoiLCJuYW1lIjoiNzg5IiwiZXhwIjoxNTI4MzY0MjU5LCJpYXQiOjE1MjgzNjMwNTl9.574koY-c9SqMNNzfvAWQuKEnimWeZAcoFQ5XudNWF3o

      因為是拼接的所以base64很容易破解,所以建議在傳輸過程中采用ssl加密是最穩妥的,這樣就不會被別人破解了你的荷載信息,

      你該如何去理解JWT幫你做些什么?

        結合業務場景,首先前端登錄 后端通過用戶名與密碼驗證成功后,使用jwt生成 一個具備有效期的token令牌, 這個token里面存儲著 token本身的結構,加上token的過期時間,和一個你自己定義的字符串類似于加密 簽名所用的鹽,這個鹽只有你自己知道,這樣你的加密才是安全的,還可以包含一些自定義的用戶信息放在荷載信息里,

      本文需要你具備javaSE的基礎, 所涉及的jar包如下:

      <!-- JWT javawebToken-->
              <dependency>
                  <groupId>io.jsonwebtoken</groupId>
                  <artifactId>jjwt</artifactId>
                  <version>0.9.1</version>
              </dependency>
              <!-- 阿里巴巴json -->
              <dependency>
                  <groupId>com.alibaba</groupId>
                  <artifactId>fastjson</artifactId>
                  <version>1.2.4</version>
              </dependency>

      jwt 如何生成Token呢?

      注意:這里使用的阿里巴巴提供的json工具包,實現序列化,后續會貼上所用的jar

      /**
       * token 工具類
       * @author 郎俊楠
       *
       */
      public class JwtUtil {
          private static Logger logger = Logger.getLogger(JwtUtil.class);
          public static final String TOKEN_HEADER = "Authorization";//token的key 也是名 不要寫成token這樣,要按照規范來
          public static final String TOKEN_PREFIX = "Bearer ";//token值的前綴,這是一種規范 ok
          private static final String SECRET = "mrLang";//你自己定的字符串 別讓別人知道,加密時候用  是對稱的秘鑰 鹽
          public static final String FUNCTS = "FUNCTS";//獲取用戶的功能使用的key
          public static final String USERINFO = "USER";//獲取用戶使用的key
          private static final long EXPIRATION = 1800L;// token的生命周期30分
          /**
           * 創建token令牌 以下為參數都是自定義信息
           * @param loginName  一般我們放用戶的唯一標識登錄名
           * @param functs 當前用戶的功能集合, 本人的rbac權限比較個性化且很負責,一般你們放role角色就可以了
           * @param user 當前用戶
           * @return
           */
          public static String createToken(String loginName, List<Object> functs, Users user) {
              Map<String, Object> map = new HashMap<>();
              //當前用戶擁有的功能
              map.put(FUNCTS, JsonUtil.set(functs));
              //當前用戶信息
              map.put(USERINFO, JsonUtil.set(user));
              
              String token = Jwts.builder()
                      .setSubject(loginName)//主題  主角是誰?    賦值登錄名
                      .setClaims(map)
                      .setIssuedAt(new Date())//設置發布時間,也是生成時間
                      .setExpiration(new Date(System.currentTimeMillis() + EXPIRATION * 1000))//設置過期時間
                      .signWith(SignatureAlgorithm.HS256, SECRET)//設置HS256加密,并且把你的鹽 放里,這里推薦使用SH256證書加密
                      .compact();//創建完成
              return token;
          }

      jwt 如何驗證Token是否過期呢?

      // token是否過期
          public static boolean isExpiration(String token) {
              try {
                  return getTokenBody(token).getExpiration().before(new Date());
              } catch (Exception e) {
                  return true;
              }
          }

      jwt 如何獲取自定義的信息呢?

      // 獲取主角,登錄名
          public static String getUserName(String token) {
              return getTokenBody(token).getSubject();
          }
      
          // 獲取token中存儲的功能
          public static List<Object> getUserFuncts(String token) {
              String str = getTokenBody(token).get(FUNCTS).toString();
              List<Object> list = JsonUtil.getArray(str);
              return list;
          }
      
          // 獲取token存儲的用戶
          public static Object getUser(String token) {
              String str = getTokenBody(token).get(USERINFO).toString();
              return JsonUtil.getObj(str);
          }
      
          // 公共獲取自定義數據
          public static Claims getTokenBody(String token) {
              return Jwts.parser().setSigningKey(SECRET).parseClaimsJws(token).getBody();
          }

      jwt 如何刷新Token呢?

      // 刷新token
          public static String refreshToken(String token) {
              if (isExpiration(token)) {
                  logger.info("token刷新失敗!! 過期了!!");
                  return null;
              }
              // 獲取用戶 權限信息
              String functs = getTokenBody(token).get(FUNCTS).toString();
              String user = getTokenBody(token).get(USERINFO).toString();
              String username = getTokenBody(token).getSubject();
              Map<String, Object> map = new HashMap<>();
              map.put(FUNCTS, JsonUtil.set(functs));
              map.put(USERINFO, JsonUtil.set(user));
              token = Jwts.builder().signWith(SignatureAlgorithm.HS256, SECRET).setClaims(map).setSubject(username)
                      .setIssuedAt(new Date()).setExpiration(new Date(System.currentTimeMillis() + EXPIRATION * 1000))
                      .compact();
              return token;
          }

      token 如何發送給前端?.

      傳入 當前用戶的 功能與用戶信息,登錄名 生成token,寫入response的返回頭中,前端獲取后保存在前端的本地緩存中,后續前端請求要把token放在 頭header里

      //登錄成功之后
                      List<Object> functs=(List<Object>) authResult.getAuthorities();//當前功能列表
                      String loginName=authResult.getName();//登錄名
                      Users obj=(Users)authResult.getPrincipal();//用戶信息
                      String token=JwtUtil.createToken(loginName,functs,obj);//生成token
                      //TOKEN_HEADER= Authorization TOKEN_PREFIX=Bearer token值
                      response.setHeader(JwtUtil.TOKEN_HEADER,JwtUtil.TOKEN_PREFIX+token);
                      response.setContentType("application/json;charset=utf-8");
                      response.setStatus(HttpServletResponse.SC_OK);
                      //個人編寫的視圖對象
                      DTO dto=new DTO<>();
                      dto.setCode("000000");
                      dto.setMessage("認證通過");
                      
                      PrintWriter pw=response.getWriter();
                      pw.write(JsonUtil.set(dto));//寫入json
                      pw.flush();//強制刷新
                      pw.close();//關閉流

      用戶請求攜帶token如何驗證?

      你可以自定義一個過濾器,或者使用某某框架,自定義攔截器,或者aop

       

      String header = request.getHeader(JwtUtil.TOKEN_HEADER);
              if (null == header || !header.toLowerCase().startsWith(JwtUtil.TOKEN_PREFIX)) {
                  // 如果頭部 Authorization 未設置或者不是 basic 認證頭部,則當前
                  // 請求不是該過濾器關注的對象,直接放行,繼續filter chain 的執行
                  chain.doFilter(request, response);
                  return;
              }
              try {
                  String token = header.replace(JwtUtil.TOKEN_PREFIX, "");
                  // 驗證token是否過期
                  if(JwtUtil.isExpiration(token)){
                      throw new javax.security.sasl.AuthenticationException("token 驗證不通過");
                  }
                  //檢查token是否能解析
                  Users user = (Users) JwtUtil.getUser(token);
                  if (null == user) {
                      throw new javax.security.sasl.AuthenticationException("token 驗證不通過");
                  }
                  
                  //驗證成功

      總結:

      使用jwt生成 一個具備有效期的token令牌, 這個token里面存儲著 token本身的結構,加上token的過期時間,和一個你自己定義的字符串類似于加密 ,也就是簽名所用的鹽,這個鹽只有你自己知道,這樣你的加密才是安全的,還可以包含一些自定義的用戶信息放在荷載信息里,本文所用的HS256+鹽 對token加密是沒有RS256安全的,

      JWT簽名算法中HS256和RS256有什么區別?

      JWT簽名算法中,一般有兩個選擇,一個采用HS256,另外一個就是采用RS256。
      簽名實際上是一個加密的過程,生成一段標識(也是JWT的一部分)作為接收方驗證信息是否被篡改的依據。

      RS256 (采用SHA-256 的 RSA 簽名) 是一種非對稱算法, 它使用公共/私鑰對: 標識提供方采用私鑰生成簽名, JWT 的使用方獲取公鑰以驗證簽名。由于公鑰 (與私鑰相比) 不需要保護, 因此大多數標識提供方使其易于使用方獲取和使用 (通常通過一個元數據URL)。
      另一方面, HS256 (帶有 SHA-256 的 HMAC 是一種對稱算法, 雙方之間僅共享一個 密鑰。由于使用相同的密鑰生成簽名和驗證簽名, 因此必須注意確保密鑰不被泄密。

      在開發應用的時候啟用JWT,使用RS256更加安全,你可以控制誰能使用什么類型的密鑰。另外,如果你無法控制客戶端,無法做到密鑰的完全保密,RS256會是個更佳的選擇,JWT的使用方只需要知道公鑰。

       建議:

      為了雙重保險,建議您使用RS256,最好是生成一個證書 讀取使用證書里面的公鑰加密,私鑰留著以后每次前端請求驗證token的合法性就可以了
      jwt提供了方法可以驗證token的合法性,過期時間,還可以根據token讀取用戶信息,這樣你把token存儲前端的localstorage中,
      后端的緩存都省了

      這樣做安全么?
      你要知道 RS256非對稱加密都是一套體系的,公鑰私鑰是一組, 都存在的后端,別人不進你服務器盜取你就是安全的,要是真能登錄你服務器那就直接刪你庫了,同樣本文用大的對稱加密也是 你自定定義的秘鑰 鹽 本文的mrlang都是存在你自己的服務器中,別人是不知道的,

      分布式中如何驗證Token?

      你可以把token工具類copy到不同的機器上,讓每臺機器自己去做驗證,只要你每臺機器token工具類里存儲的 鹽或者一對秘鑰 都一致 那么驗證就會得到一致通過 ,這樣做的好處就是 你不必遠調用遠程驗證服務器了,所以真的很好用,換個思維想想 你去調用驗證服務器還需要花費很多時間,這對訪問量特別大的項目來說,壓力真的不小,所以本文的JWT Token 不管作為單機,集群,分布式  你都值得擁有

      本文作者為本人原創:如需轉載 請攜帶出處 謝謝!!!!

      posted @ 2020-03-11 19:24  郎小樂  閱讀(2538)  評論(1)    收藏  舉報
      主站蜘蛛池模板: 免费人成视频在线观看不卡| 日韩av一区二区高清不卡| 亚洲情A成黄在线观看动漫尤物| 亚州少妇无套内射激情视频| 99精品国产一区二区三区| 国产精品播放一区二区三区| 男女xx00xx的视频免费观看| 国产精品毛片一区二区| 久热视频这里只有精品6| 少妇爽到爆视频网站免费| 在线播放无码后入内射少妇| 国产精品疯狂输出jk草莓视频| 国产农村老熟女乱子综合| 麻豆人妻| 国产精品99中文字幕| 久久天天躁狠狠躁夜夜躁2o2o| 久久精品国产福利一区二区| 亚洲AV永久中文无码精品综合| 国产精品视频免费一区二区三区| 国产精品白嫩极品在线看| 少妇人妻无码专区在线视频| 成人动漫综合网| 亚洲精品综合久中文字幕| 欧美人与zoxxxx另类| 亚洲欧美牲交| 九九热在线观看精品视频| 无码人妻丰满熟妇奶水区码| 一卡二卡三卡四卡视频区| 国产成人永久免费av在线| 日本一区二区不卡精品| 午夜dv内射一区二区| 亚洲精品日韩在线观看| 国产精品v欧美精品∨日韩| 国产一区二区三区四区激情| 办公室强奷漂亮少妇视频| 国产熟睡乱子伦视频在线播放| 黑人猛精品一区二区三区| 国产制服丝袜无码视频| 内射一区二区三区四区| jizz国产免费观看| 狠狠亚洲丁香综合久久|