如何在Go中迭代Jwt令牌的解码声明?

huangapple go评论92阅读模式
英文:

How to iterate over the decoded claims of a Jwt token in Go?

问题

我正在参考这篇帖子(https://stackoverflow.com/questions/45405626/how-to-decode-a-jwt-token-in-go)来获取Jwt令牌的声明字段。以下是我根据这篇帖子使用的代码:

tokenString := "<YOUR TOKEN STRING>"
claims := jwt.MapClaims{}
token, err := jwt.ParseWithClaims(tokenString, claims, func(token *jwt.Token) (interface{}, error) {
    return []byte("<YOUR VERIFICATION KEY>"), nil
})
// ... 错误处理

// 处理解码后的声明
for key, val := range claims {
    fmt.Printf("Key: %v, value: %v\n", key, val)
}

我成功获取了这些声明及其值。然而,在这个Jwt令牌中,有一个称为'scope'的声明字段,它具有字符串数组值,如'['openId','username','email']。

现在我想使用循环遍历这些值。

for _, v := range claims["scope"] {
    fmt.Println(v)
}

然而,当我尝试循环遍历这个claims["scope"]时,我收到了一个错误消息:

"cannot range over claims["scope"] (type interface {})"

如何遍历这些claims["scope"]的值?另外,是否可以将其转换为其他形式,比如字符串数组或JSON,以便进行遍历?

谢谢。

英文:

I am referring to this post (https://stackoverflow.com/questions/45405626/how-to-decode-a-jwt-token-in-go) to get the claim fields of a Jwt token. Here are the code that I used based on this post:

tokenString := &quot;&lt;YOUR TOKEN STRING&gt;&quot;    
claims := jwt.MapClaims{}
token, err := jwt.ParseWithClaims(tokenString, claims, func(token *jwt.Token) (interface{}, error) {
    return []byte(&quot;&lt;YOUR VERIFICATION KEY&gt;&quot;), nil
})
// ... error handling

// do something with decoded claims
for key, val := range claims {
    fmt.Printf(&quot;Key: %v, value: %v\n&quot;, key, val)
}

I managed to get those claims and its values. However, in this Jwt token, there is a claim field called 'scope', and it has a string array values, like '['openId','username','email'].

如何在Go中迭代Jwt令牌的解码声明?

Now I want to iterate over these values using loop.

for _, v := range claims[&quot;scope&quot;]{
      fmt.Println(v)
}

However, when I try to loop over this claims ["scope"], I got an error message saying that:

> "cannot range over claims["scope"] (type interface {})".

How to iterate over these claims["scope"] values? Also, is it possible to convert it to other forms, like string array or json, to iterate over it?

Thanks.

答案1

得分: 2

有几种方法可以处理这个问题;最简单的方法可能是让库为您解码(playground

type MyCustomClaims struct {
	Scope []string `json:"scope"`
	jwt.StandardClaims
}

claims := MyCustomClaims{}
_, err := jwt.ParseWithClaims(tokenString, &claims, func(token *jwt.Token) (interface{}, error) {
	return []byte(sharedKey), nil
})
if err != nil {
	panic(err)
}

for _, s := range claims.Scope {
	fmt.Printf("%s\n", s)
}

如果您想坚持使用您问题中使用的方法,那么您需要使用类型断言(playground - 有关更多信息,请参阅json文档):

var claims jwt.MapClaims
_, err := jwt.ParseWithClaims(tokenString, &claims, func(token *jwt.Token) (interface{}, error) {
	return []byte(sharedKey), nil
})
if err != nil {
	panic(err)
}

scope := claims["scope"]
if scope == nil {
	panic("no scope")
}
scopeSlc, ok := scope.([]interface{})
if !ok {
	panic("scope not a slice")
}

for _, s := range scopeSlc {
	sStr, ok := s.(string)
	if !ok {
		panic("slice member not a string")
	}
	fmt.Println(sStr)
}
英文:

There are a few ways you can handle this; the simplest is probably to let the library decode things for you (playground)

type MyCustomClaims struct {
	Scope []string `json:&quot;scope&quot;`
	jwt.StandardClaims
}

claims := MyCustomClaims{}
_, err := jwt.ParseWithClaims(tokenString, &amp;claims, func(token *jwt.Token) (interface{}, error) {
	return []byte(sharedKey), nil
})
if err != nil {
	panic(err)
}

for _, s := range claims.Scope {
	fmt.Printf(&quot;%s\n&quot;, s)
}

If you want to stick with the approach used in your question then you will need to use type assertions (playground - see the json docs for more info on this):

var claims jwt.MapClaims
_, err := jwt.ParseWithClaims(tokenString, &amp;claims, func(token *jwt.Token) (interface{}, error) {
	return []byte(sharedKey), nil
})
if err != nil {
	panic(err)
}

scope := claims[&quot;scope&quot;]
if scope == nil {
	panic(&quot;no scope&quot;)
}
scopeSlc, ok := scope.([]any)
if !ok {
	panic(&quot;scope not a slice&quot;)
}

for _, s := range scopeSlc {
	sStr, ok := s.(string)
	if !ok {
		panic(&quot;slice member not a string&quot;)
	}
	fmt.Println(sStr)
}

huangapple
  • 本文由 发表于 2022年7月28日 09:46:57
  • 转载请务必保留本文链接:https://go.coder-hub.com/73146348.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定