天天看點

使用jwt生成token

使用jwt生成token

JWT是什麼

Json web token (JWT), 是為了在網絡應用環境間傳遞聲明而執行的一種基于JSON的開放标準((RFC 7519).該token被設計為緊湊且安全的,特别适用于分布式站點的單點登入(SSO)場景。JWT的聲明一般被用來在身份提供者和服務提供者間傳遞被認證的使用者身份資訊,以便于從資源伺服器擷取資源,也可以增加一些額外的其它業務邏輯所必須的聲明資訊,該token也可直接被用于認證,也可被加密。

JWT組成部分

  1. Header(預設辨別, 和加密算法)
  2. Claims(載荷)
    Audience  string `json:"aud,omitempty"` //token接收者
    ExpiresAt int64  `json:"exp,omitempty"`	//過期時間
    Id        string `json:"jti,omitempty"`	//自定義id号
    IssuedAt  int64  `json:"iat,omitempty"`	//簽名發行時間
    Issuer    string `json:"iss,omitempty"`	//簽名發行者
    NotBefore int64  `json:"nbf,omitempty"`	//token資訊生效時間
    Subject   string `json:"sub,omitempty"` //簽名面向的使用者
               
  3. Signature(加密簽名)

go中應用

使用到的開源庫

go get github.com/urfave/negroni  //web中間件
go get github.com/dgrijalva/jwt-go
go get github.com/dgrijalva/jwt-go/request
           

生成token代碼(根據Wangjiaxing123/JwtDemo 修改)

//定義載荷
type CustomClaims struct {
	Username string  `json:"username"` //1
	ExpireTime int64 `json:"expire_time"` //2這些可以自己随意設定
	jwt.StandardClaims //過期時間等初始化定義在這個結構體中
}

type JWT struct {
	SigningKey []byte
}

//初始化設定sign
func NewJWT() *JWT {
	return &JWT{
		[]byte(GetSignKey()),
	}
}

//根據載荷建立一個token
func (j *JWT) CreatToken(claims CustomClaims) (string, error) {
	token := jwt.NewWithClaims(jwt.SigningMethodHS256, claims)
	return token.SignedString(j.SigningKey)
}
           

驗證token

//錯誤資訊常量
var (
	TokenExpired     = errors.New("Token is expired")
	TokenNotValidYet = errors.New("Token not active yet")
	TokenMalformed   = errors.New("That's not even a token")
	TokenInvalid     = errors.New("Couldn't handle this token:")
	SignKey          = "lottery"
)

//解析token
func (j *JWT) ParseToken(tokenString string) (*CustomClaims, error) {
    //根據jwt-go庫代碼解析token
	token, err := jwt.ParseWithClaims(tokenString, &CustomClaims{}, func(token *jwt.Token) (i interface{}, e error) {
		return j.SigningKey, nil
	})
	//輸出錯誤資訊
	if err != nil {
		if ve, ok := err.(*jwt.ValidationError); ok {
			if ve.Errors & jwt.ValidationErrorMalformed != 0 {
	return nil, TokenMalformed
			}else if ve.Errors & jwt.ValidationErrorExpired != 0 {
				return nil, TokenExpired
			}else if ve.Errors & jwt.ValidationErrorNotValidYet != 0 {
				return nil, TokenNotValidYet
			}else {
				return nil, TokenInvalid
			}
		}
	}
	//如果驗證成功則傳回載體
	if Claims, ok := token.Claims.(*CustomClaims); ok && token.Valid {
		return Claims, nil
	}
	return nil, TokenInvalid
}