Adds JWS encode and decode

It also adds interfaces Signer and HS256 and RS256 implementation.
This commit is contained in:
2015-08-18 16:11:56 +02:00
parent 4eb3bdaa13
commit 00c5853b45
6 changed files with 591 additions and 25 deletions

View File

@@ -3,30 +3,61 @@ package jwt
import (
"encoding/base64"
"fmt"
"strings"
)
// Base64Encode encodes a payload of data as a string, like specified
// in RFC 7515 (no trailing '='
func Base64Encode(b []byte) string {
return strings.TrimRight(base64.URLEncoding.EncodeToString(b), "=")
// Base64EncodedBufferLen return the size needed to encode the
// Base64Encode (padding '=' would be added, can be stripped with
// Base64DecodedStrippedLen
func Base64EncodedBufferLen(n int) int {
return base64.URLEncoding.EncodedLen(n)
}
// Base64Decode decodes a payload of data as a []byte, like specified
// in RFC 7515 (no trailing '=')
func Base64Decode(s string) ([]byte, error) {
switch len(s) % 4 {
// Base64EncodedStrippedLen return the size of the encoded slice with no
// padding.
func Base64EncodedStrippedLen(n int) int {
eN := Base64EncodedBufferLen(n)
mod := n % 3
if mod == 0 {
return eN
}
return eN - (3 - mod)
}
// Base64DecodedStrippedLen returns the size of the data, without 0
// bit padding, from the stripped length n.
func Base64DecodedStrippedLen(n int) int {
return Base64DecodedLenFromStripped(n) + n - ((n+3)/4)*4
}
// Base64DecodedLenFromStripped returns the size of the data, with 0
// bit padding, from the stripped length n.
func Base64DecodedLenFromStripped(n int) int {
return base64.URLEncoding.DecodedLen(4 * ((n + 3) / 4))
}
// Base64Decode decodes a payload of data as a []byte, from a stripped
// '=' encoded string.
func Base64Decode(dst, src []byte) error {
switch len(src) % 4 {
// in this case, we have to copy the src, in order to allow decode part of the input
case 2:
s += "=="
oldSrc := src
src = make([]byte, len(src)+2)
copy(src, oldSrc)
src[len(src)-2] = '='
src[len(src)-1] = '='
case 3:
s += "="
oldSrc := src
src = make([]byte, len(src)+1)
copy(src, oldSrc)
src[len(src)-1] = '='
case 1:
return nil, fmt.Errorf("jwt: Invalid base64 string (length:%d %% 4 == 1): '%s'", len(s), s)
return fmt.Errorf("jwt: Invalid base64 string (length:%d %% 4 == 1): '%s'", len(src), src)
}
d, err := base64.URLEncoding.DecodeString(s)
_, err := base64.URLEncoding.Decode(dst, src)
if err != nil {
return nil, fmt.Errorf("jwt: %s", err)
return fmt.Errorf("jwt: %s", err)
}
return d, nil
return nil
}