diff options
Diffstat (limited to 'vendor/gopkg.in/square/go-jose.v2/jws.go')
-rw-r--r-- | vendor/gopkg.in/square/go-jose.v2/jws.go | 95 |
1 files changed, 70 insertions, 25 deletions
diff --git a/vendor/gopkg.in/square/go-jose.v2/jws.go b/vendor/gopkg.in/square/go-jose.v2/jws.go index 8b59b6ab2..7e261f937 100644 --- a/vendor/gopkg.in/square/go-jose.v2/jws.go +++ b/vendor/gopkg.in/square/go-jose.v2/jws.go @@ -17,6 +17,7 @@ package jose import ( + "bytes" "encoding/base64" "errors" "fmt" @@ -75,13 +76,21 @@ type Signature struct { } // ParseSigned parses a signed message in compact or full serialization format. -func ParseSigned(input string) (*JSONWebSignature, error) { - input = stripWhitespace(input) - if strings.HasPrefix(input, "{") { - return parseSignedFull(input) +func ParseSigned(signature string) (*JSONWebSignature, error) { + signature = stripWhitespace(signature) + if strings.HasPrefix(signature, "{") { + return parseSignedFull(signature) } - return parseSignedCompact(input) + return parseSignedCompact(signature, nil) +} + +// ParseDetached parses a signed message in compact serialization format with detached payload. +func ParseDetached(signature string, payload []byte) (*JSONWebSignature, error) { + if payload == nil { + return nil, errors.New("square/go-jose: nil payload") + } + return parseSignedCompact(stripWhitespace(signature), payload) } // Get a header value @@ -93,20 +102,39 @@ func (sig Signature) mergedHeaders() rawHeader { } // Compute data to be signed -func (obj JSONWebSignature) computeAuthData(payload []byte, signature *Signature) []byte { - var serializedProtected string +func (obj JSONWebSignature) computeAuthData(payload []byte, signature *Signature) ([]byte, error) { + var authData bytes.Buffer + + protectedHeader := new(rawHeader) if signature.original != nil && signature.original.Protected != nil { - serializedProtected = signature.original.Protected.base64() + if err := json.Unmarshal(signature.original.Protected.bytes(), protectedHeader); err != nil { + return nil, err + } + authData.WriteString(signature.original.Protected.base64()) } else if signature.protected != nil { - serializedProtected = base64.RawURLEncoding.EncodeToString(mustSerializeJSON(signature.protected)) + protectedHeader = signature.protected + authData.WriteString(base64.RawURLEncoding.EncodeToString(mustSerializeJSON(protectedHeader))) + } + + needsBase64 := true + + if protectedHeader != nil { + var err error + if needsBase64, err = protectedHeader.getB64(); err != nil { + needsBase64 = true + } + } + + authData.WriteByte('.') + + if needsBase64 { + authData.WriteString(base64.RawURLEncoding.EncodeToString(payload)) } else { - serializedProtected = "" + authData.Write(payload) } - return []byte(fmt.Sprintf("%s.%s", - serializedProtected, - base64.RawURLEncoding.EncodeToString(payload))) + return authData.Bytes(), nil } // parseSignedFull parses a message in full format. @@ -246,20 +274,26 @@ func (parsed *rawJSONWebSignature) sanitized() (*JSONWebSignature, error) { } // parseSignedCompact parses a message in compact format. -func parseSignedCompact(input string) (*JSONWebSignature, error) { +func parseSignedCompact(input string, payload []byte) (*JSONWebSignature, error) { parts := strings.Split(input, ".") if len(parts) != 3 { return nil, fmt.Errorf("square/go-jose: compact JWS format must have three parts") } + if parts[1] != "" && payload != nil { + return nil, fmt.Errorf("square/go-jose: payload is not detached") + } + rawProtected, err := base64.RawURLEncoding.DecodeString(parts[0]) if err != nil { return nil, err } - payload, err := base64.RawURLEncoding.DecodeString(parts[1]) - if err != nil { - return nil, err + if payload == nil { + payload, err = base64.RawURLEncoding.DecodeString(parts[1]) + if err != nil { + return nil, err + } } signature, err := base64.RawURLEncoding.DecodeString(parts[2]) @@ -275,19 +309,30 @@ func parseSignedCompact(input string) (*JSONWebSignature, error) { return raw.sanitized() } -// CompactSerialize serializes an object using the compact serialization format. -func (obj JSONWebSignature) CompactSerialize() (string, error) { +func (obj JSONWebSignature) compactSerialize(detached bool) (string, error) { if len(obj.Signatures) != 1 || obj.Signatures[0].header != nil || obj.Signatures[0].protected == nil { return "", ErrNotSupported } - serializedProtected := mustSerializeJSON(obj.Signatures[0].protected) + serializedProtected := base64.RawURLEncoding.EncodeToString(mustSerializeJSON(obj.Signatures[0].protected)) + payload := "" + signature := base64.RawURLEncoding.EncodeToString(obj.Signatures[0].Signature) + + if !detached { + payload = base64.RawURLEncoding.EncodeToString(obj.payload) + } + + return fmt.Sprintf("%s.%s.%s", serializedProtected, payload, signature), nil +} + +// CompactSerialize serializes an object using the compact serialization format. +func (obj JSONWebSignature) CompactSerialize() (string, error) { + return obj.compactSerialize(false) +} - return fmt.Sprintf( - "%s.%s.%s", - base64.RawURLEncoding.EncodeToString(serializedProtected), - base64.RawURLEncoding.EncodeToString(obj.payload), - base64.RawURLEncoding.EncodeToString(obj.Signatures[0].Signature)), nil +// DetachedCompactSerialize serializes an object using the compact serialization format with detached payload. +func (obj JSONWebSignature) DetachedCompactSerialize() (string, error) { + return obj.compactSerialize(true) } // FullSerialize serializes an object using the full JSON serialization format. |