使用中间件实现jwt功能,没什么难的地方,只是试一下中间件怎么使用,注意,在编写api文件时,中间件的首字母需要大写
api
api
syntax = "v1"
type loginReq {
Email string `form:"email"`
Password string `form:"password"`
}
type loginResp {
Data string `json:"data"`
}
type getInformResp {
Inform string `json:"inform"`
}
service middleware {
@handler loginHandler
post /user/login (loginReq) returns (loginResp)
}
@server(
middleware: LoginMiddleWare
)
service middleware {
@handler getInform
post /user/getInform returns (getInformResp)
}logic
middleWareLogic
go
package middleware
import (
"context"
"github.com/golang-jwt/jwt/v5"
"net/http"
)
var secret = []byte("123123123")
type Claims struct {
jwt.RegisteredClaims
Email string `json:"email"`
Uid string `json:"uid"`
}
type LoginMiddleWareMiddleware struct {
}
func NewLoginMiddleWareMiddleware() *LoginMiddleWareMiddleware {
return &LoginMiddleWareMiddleware{}
}
func parseJwt(jwtString string) (*jwt.Token, *Claims, error) {
claims := &Claims{}
token, err := jwt.ParseWithClaims(jwtString, claims, func(token *jwt.Token) (interface{}, error) {
return secret, nil
})
return token, claims, err
}
func (m *LoginMiddleWareMiddleware) Handle(next http.HandlerFunc) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
get := r.Header.Get("Authorization")
if get == "" {
http.Error(w, "未认证", http.StatusUnauthorized)
}
token, claims, err := parseJwt(get)
if err != nil && !token.Valid {
http.Error(w, "认证信息错误", http.StatusUnauthorized)
}
context1 := context.WithValue(context.Background(), "uid", claims.Uid)
value := context.WithValue(context1, "email", claims.Email)
r2 := r.WithContext(value)
next(w, r2)
}
}loginLogic
go
package logic
import (
"context"
"github.com/golang-jwt/jwt/v5"
"time"
"example.com/strconv/go-zero-middleware/internal/svc"
"example.com/strconv/go-zero-middleware/internal/types"
"github.com/zeromicro/go-zero/core/logx"
)
var secret = []byte("123123123")
type LoginLogic struct {
logx.Logger
ctx context.Context
svcCtx *svc.ServiceContext
}
type Claims struct {
jwt.RegisteredClaims
Email string `json:"email"`
Uid string `json:"uid"`
}
func NewLoginLogic(ctx context.Context, svcCtx *svc.ServiceContext) *LoginLogic {
return &LoginLogic{
Logger: logx.WithContext(ctx),
ctx: ctx,
svcCtx: svcCtx,
}
}
func getJwt(uid, email string) (string, error) {
duration := time.Minute * 50
now := time.Now()
claims := &Claims{
Email: email,
Uid: uid,
RegisteredClaims: jwt.RegisteredClaims{
NotBefore: jwt.NewNumericDate(now),
IssuedAt: jwt.NewNumericDate(now),
ExpiresAt: jwt.NewNumericDate(now.Add(duration)),
},
}
token := jwt.NewWithClaims(jwt.SigningMethodHS256, claims)
signedString, err := token.SignedString(secret)
if err != nil {
return "", err
}
return signedString, nil
}
func (l *LoginLogic) Login(req *types.LoginReq) (resp *types.LoginResp, err error) {
s, err := getJwt("1", req.Email)
if err != nil {
return
}
resp = new(types.LoginResp)
resp.Data = s
return
}getInformLogic
go
package logic
import (
"context"
"example.com/strconv/go-zero-middleware/internal/svc"
"example.com/strconv/go-zero-middleware/internal/types"
"github.com/zeromicro/go-zero/core/logx"
)
type GetInformLogic struct {
logx.Logger
ctx context.Context
svcCtx *svc.ServiceContext
}
func NewGetInformLogic(ctx context.Context, svcCtx *svc.ServiceContext) *GetInformLogic {
return &GetInformLogic{
Logger: logx.WithContext(ctx),
ctx: ctx,
svcCtx: svcCtx,
}
}
func (l *GetInformLogic) GetInform() (resp *types.GetInformResp, err error) {
s := l.ctx.Value("uid").(string)
email := l.ctx.Value("email").(string)
resp = new(types.GetInformResp)
resp.Inform = s + email
return
}