7

我正在使用 go-swagger 和BearerAuthJWT 令牌。除了实际的令牌,我还收到了包含用户名等数据的声明。

如何访问api.ItemsCreateItemHandler以下功能中的声明?

package restapi

func configureAPI(api *operations.MyAPI) http.Handler {
    api.BearerAuth = func(token string) (interface{}, error) {
        jwtToken := strings.Replace(token, "Bearer ", "", -1)
        // skipped token verification

        claims, _ := parsedToken.Claims.(jwt.MapClaims)
  }

  api.ItemsCreateItemHandler = items.CreateItemHandlerFunc(func(params items.CreateItemParams, principal interface{}) middleware.Responder {
    // FIXME: Here I need to be able to access JWT claims
    if err := createItem(params.Body, claims); err != nil {
            return nil // handle error
        }
        return items.NewCreateItemCreated()
    })
}
4

3 回答 3

1

首先,您的BearerAuth实现旨在返回安全主体(在这种情况下可以是您的声明),该值随后将在principal参数中传递给您的处理程序。

所以这样做的方法是:

package restapi

import (
    jwt "github.com/dgrijalva/jwt-go"
    // ...
)

func configureAPI(api *operations.MyAPI) http.Handler {
    api.BearerAuth = func(token string) (interface{}, error) {
        jwtToken := strings.Replace(token, "Bearer ", "", -1)
        // skipped token verification
        claims, _ := parsedToken.Claims.(jwt.MapClaims)
        return claims, nil
    }

    api.ItemsCreateItemHandler = items.CreateItemHandlerFunc(func(params items.CreateItemParams, principal interface{}) middleware.Responder {
        claims, ok := principal.(jwt.MapClaims)
        if !ok {
            // handle error
        }
        if err := createItem(params.Body, claims); err != nil {
            return nil // handle error
        }
        return items.NewCreateItemCreated()
    })
}

您可以通过使用--principal jwt.MapClaims选项来减少麻烦,swagger generate以便它使用此类型而不是interface{}.

于 2021-01-08T16:53:25.690 回答
-1

JWT 由 3 个部分组成,按标点符号分隔 - 令牌本身是 base64 编码的。

例如,这是来自https://jwt.io/的令牌

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36Pok6yJV_adQssw5

您将想要拆分和解码,您在第二部分之后,其中包含纯 JSON 的有效负载。

所以在伪代码中它看起来像;

json = Base64Decode(split(".", yourData)[1])

您将在https://jwt.io/看到更具体的示例

于 2018-09-10T09:17:32.227 回答
-1

我有一个存储令牌并包含解析方法的类:

import io.jsonwebtoken.*;

 @AllArgsConstructor
public class RawAccessJwtToken implements JwtToken {

    private String token;

    @Override
    public String getToken() {
        return token;
    }

    public Jws<Claims> parseClaims(String signingKey) {
        try {
            return Jwts.parser().setSigningKey(signingKey).parseClaimsJws(this.token);
        } catch (UnsupportedJwtException | MalformedJwtException | IllegalArgumentException e) {
            throw  new BadCredentialsException("Invalid JWT token: " + e);
        } catch (ExpiredJwtException expiredException){
            throw new JwtExpiredTokenException(this, "JWT Token expired", expiredException);
        }
    }
}

使用该类,我可以提取我的用户角色:

 Jws<Claims> claimsJws = token.parseClaims(signingKey);

        List<String> scopes = claimsJws.getBody().get("scopes",
                 List.class);
于 2018-09-10T14:16:45.613 回答