summaryrefslogtreecommitdiff
path: root/cmd/ponzu/vendor/github.com/nilslice/jwt/jwt.go
diff options
context:
space:
mode:
authorSteve Manuel <nilslice@gmail.com>2016-10-19 13:50:05 -0700
committerSteve Manuel <nilslice@gmail.com>2016-10-19 13:50:05 -0700
commitea078f9b4221332b9f63cc4e178aa814eec06e4f (patch)
treea90da6f77f265ce63c82da73f502f324bfb89ebc /cmd/ponzu/vendor/github.com/nilslice/jwt/jwt.go
parentea8ea4c22662aa082181a6c456ec56acf2bd777c (diff)
vendoring all the dependencies into vendor directory prior to build step, which still vendors ponzu core code
Diffstat (limited to 'cmd/ponzu/vendor/github.com/nilslice/jwt/jwt.go')
-rw-r--r--cmd/ponzu/vendor/github.com/nilslice/jwt/jwt.go204
1 files changed, 204 insertions, 0 deletions
diff --git a/cmd/ponzu/vendor/github.com/nilslice/jwt/jwt.go b/cmd/ponzu/vendor/github.com/nilslice/jwt/jwt.go
new file mode 100644
index 0000000..6d7eaa3
--- /dev/null
+++ b/cmd/ponzu/vendor/github.com/nilslice/jwt/jwt.go
@@ -0,0 +1,204 @@
+package jwt
+
+import (
+ "crypto/hmac"
+ "crypto/sha256"
+ "encoding/base64"
+ "encoding/json"
+ "errors"
+ "fmt"
+ "strings"
+)
+
+var (
+ privateKey = []byte("")
+ defaultHeader = header{Typ: "JWT", Alg: "HS256"}
+ registeredClaims = []string{"iss", "sub", "aud", "exp", "nbf", "iat", "jti"}
+)
+
+type header struct {
+ Typ string `json:"typ"`
+ Alg string `json:"alg"`
+}
+
+type payload map[string]interface{}
+
+type encoded struct {
+ token string
+}
+type decoded struct {
+ header string
+ payload string
+}
+
+type signedDecoded struct {
+ decoded
+ signature string
+}
+
+func newEncoded(claims map[string]interface{}) (encoded, error) {
+ header, err := json.Marshal(defaultHeader)
+ if err != nil {
+ return encoded{}, err
+ }
+
+ for _, claim := range registeredClaims {
+ if _, ok := claims[claim]; !ok {
+ claims[claim] = nil
+ }
+ }
+
+ payload, err := json.Marshal(claims)
+ if err != nil {
+ return encoded{}, err
+ }
+
+ d := decoded{header: string(header), payload: string(payload)}
+
+ d.encodeInternal()
+ signed, err := d.sign()
+ if err != nil {
+ return encoded{}, err
+ }
+
+ token := signed.token()
+ e := encoded{token: token}
+ return e, nil
+}
+
+func newDecoded(token string) (decoded, error) {
+ e := encoded{token: token}
+ d, err := e.parseToken()
+ if err != nil {
+ return d, nil
+ }
+
+ return d, nil
+}
+
+func encodeToString(src []byte) string {
+ return base64.RawURLEncoding.EncodeToString(src)
+}
+
+func (d decoded) getHeader() []byte {
+ return []byte(d.header)
+}
+
+func (d decoded) getPayload() []byte {
+ return []byte(d.payload)
+}
+
+func (sd signedDecoded) getSignature() []byte {
+ return []byte(sd.signature)
+}
+
+func (d *decoded) encodeInternal() {
+ d.header = encodeToString(d.getHeader())
+ d.payload = encodeToString(d.getPayload())
+}
+
+func (d decoded) dot(internals ...string) string {
+ return strings.Join(internals, ".")
+}
+
+func (d *decoded) sign() (signedDecoded, error) {
+ if d.header == "" || d.payload == "" {
+ return signedDecoded{}, errors.New("Missing header or payload on Decoded")
+ }
+
+ unsigned := d.dot(d.header, d.payload)
+
+ hash := hmac.New(sha256.New, privateKey)
+ _, err := hash.Write([]byte(unsigned))
+ if err != nil {
+ return signedDecoded{}, err
+ }
+
+ signed := signedDecoded{decoded: *d}
+ signed.signature = encodeToString(hash.Sum(nil))
+
+ return signed, nil
+}
+
+func (sd signedDecoded) token() string {
+ return fmt.Sprintf("%s.%s.%s", sd.getHeader(), sd.getPayload(), sd.getSignature())
+}
+
+func (sd signedDecoded) verify(enc encoded) bool {
+ if sd.token() == enc.token {
+ return true
+ }
+ return false
+}
+
+func (e encoded) parseToken() (decoded, error) {
+ parts := strings.Split(e.token, ".")
+ if len(parts) != 3 {
+ return decoded{}, errors.New("Error: incorrect # of results from string parsing")
+ }
+
+ d := decoded{
+ header: parts[0],
+ payload: parts[1],
+ }
+
+ return d, nil
+}
+
+// New returns a token (string) and error. The token is a fully qualified JWT to be sent to a client via HTTP Header or other method. Error returned will be from the newEncoded unexported function.
+func New(claims map[string]interface{}) (string, error) {
+ enc, err := newEncoded(claims)
+ if err != nil {
+ return "", err
+ }
+
+ return enc.token, nil
+}
+
+// Passes returns a bool indicating whether a token (string) provided has been signed by our server. If true, the client is authenticated and may proceed.
+func Passes(token string) bool {
+ dec, err := newDecoded(token)
+ if err != nil {
+ // may want to log some error here so we have visibility
+ // intentionally simplifying return type to bool for ease
+ // of use in API. Caller should only do `if auth.Passes(str) {}`
+ return false
+ }
+ signed, err := dec.sign()
+ if err != nil {
+ return false
+ }
+
+ return signed.verify(encoded{token: token})
+}
+
+// GetClaims() returns a token's claims, allowing
+// you to check the values to make sure they match
+func GetClaims(token string) map[string]interface{} {
+ // decode the token
+ dec, err := newDecoded(token)
+ if err != nil {
+ return nil
+ }
+
+ // base64 decode payload
+ payload, err := base64.RawURLEncoding.DecodeString(dec.payload)
+ if err != nil {
+ return nil
+ }
+
+ dst := map[string]interface{}{}
+ err = json.Unmarshal(payload, &dst)
+ if err != nil {
+ return nil
+ }
+
+ return dst
+
+}
+
+// Secret is a helper function to set the unexported privateKey variable used when signing and verifying tokens.
+// Its argument is type []byte since we expect users to read this value from a file which can be excluded from source code.
+func Secret(key []byte) {
+ privateKey = key
+}