osg VerifyJWT 추가
This commit is contained in:
@ -9,6 +9,7 @@ import (
|
|||||||
"encoding/json"
|
"encoding/json"
|
||||||
"fmt"
|
"fmt"
|
||||||
"net/http"
|
"net/http"
|
||||||
|
"slices"
|
||||||
"strings"
|
"strings"
|
||||||
"sync/atomic"
|
"sync/atomic"
|
||||||
"time"
|
"time"
|
||||||
@ -155,6 +156,49 @@ func (c *Client) MakeJWT(subject string, role string, ttl time.Duration) string
|
|||||||
return encoded + "." + string(sigenc)
|
return encoded + "." + string(sigenc)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (c *Client) VerifyJWT(token string) (subject string, role string) {
|
||||||
|
dot := strings.LastIndex(token, ".")
|
||||||
|
if dot < 0 {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
encoded := token[:dot]
|
||||||
|
sigenc := token[dot+1:]
|
||||||
|
signature := make([]byte, encoding.DecodedLen(len(sigenc)))
|
||||||
|
encoding.Decode(signature, []byte(sigenc))
|
||||||
|
|
||||||
|
mac := hmac.New(sha256.New, c.signingKey)
|
||||||
|
mac.Write([]byte(encoded))
|
||||||
|
calsig := mac.Sum(nil)
|
||||||
|
if slices.Compare(calsig, signature) != 0 {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
_, payload, ok := strings.Cut(encoded, ".")
|
||||||
|
if !ok {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
srcjson, err := encoding.DecodeString(payload)
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
var src struct {
|
||||||
|
Exp int64 `json:"exp"`
|
||||||
|
Sub string `json:"sub"`
|
||||||
|
Roles string `json:"roles"`
|
||||||
|
}
|
||||||
|
if json.Unmarshal([]byte(srcjson), &src) != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
if src.Exp < time.Now().Unix() {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
return src.Sub, src.Roles
|
||||||
|
}
|
||||||
|
|
||||||
func NewClient(cfg Config) (Client, error) {
|
func NewClient(cfg Config) (Client, error) {
|
||||||
if len(cfg.Addresses) == 0 {
|
if len(cfg.Addresses) == 0 {
|
||||||
return Client{}, nil
|
return Client{}, nil
|
||||||
|
|||||||
@ -1,7 +1,11 @@
|
|||||||
package opensearch
|
package opensearch
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"encoding/base64"
|
||||||
"testing"
|
"testing"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"go.mongodb.org/mongo-driver/bson/primitive"
|
||||||
)
|
)
|
||||||
|
|
||||||
func TestNewClient(t *testing.T) {
|
func TestNewClient(t *testing.T) {
|
||||||
@ -31,3 +35,44 @@ func TestNewClient(t *testing.T) {
|
|||||||
// time.Sleep(time.Second)
|
// time.Sleep(time.Second)
|
||||||
// }
|
// }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func TestClient_MakeJWT(t *testing.T) {
|
||||||
|
sk := "UGdiOTdLVjFBTWtndTRNRiZmVjdwMDdCRW1lSSUxTnA="
|
||||||
|
dst := make([]byte, len(sk)*2)
|
||||||
|
dstlen, _ := base64.StdEncoding.Decode(dst, []byte(sk))
|
||||||
|
signingKey := dst[:dstlen]
|
||||||
|
uid := primitive.NewObjectID().Hex()
|
||||||
|
|
||||||
|
type args struct {
|
||||||
|
subject string
|
||||||
|
role string
|
||||||
|
ttl time.Duration
|
||||||
|
}
|
||||||
|
tests := []struct {
|
||||||
|
name string
|
||||||
|
c *Client
|
||||||
|
args args
|
||||||
|
want string
|
||||||
|
}{
|
||||||
|
// TODO: Add test cases.
|
||||||
|
{
|
||||||
|
c: &Client{
|
||||||
|
signingKey: signingKey,
|
||||||
|
},
|
||||||
|
args: args{
|
||||||
|
subject: uid,
|
||||||
|
role: "ds_client",
|
||||||
|
ttl: time.Minute,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
for _, tt := range tests {
|
||||||
|
t.Run(tt.name, func(t *testing.T) {
|
||||||
|
got := tt.c.MakeJWT(tt.args.subject, tt.args.role, tt.args.ttl)
|
||||||
|
subj, role := tt.c.VerifyJWT(got)
|
||||||
|
if subj != tt.args.subject || role != tt.args.role {
|
||||||
|
t.Errorf("Client.MakeJWT() = %v, %v, want %v, %v", subj, role, tt.args.subject, tt.args.role)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user