package auth
import (
+ "context"
"encoding/base64"
"net/http"
"net/url"
Tokens []string
}
-func NewCredentials() *Credentials {
- return &Credentials{Tokens: []string{}}
+func NewCredentials(tokens ...string) *Credentials {
+ return &Credentials{Tokens: tokens}
}
-func NewCredentialsFromHTTPRequest(r *http.Request) *Credentials {
+func NewContext(ctx context.Context, c *Credentials) context.Context {
+ return context.WithValue(ctx, contextKeyCredentials{}, c)
+}
+
+func FromContext(ctx context.Context) (*Credentials, bool) {
+ c, ok := ctx.Value(contextKeyCredentials{}).(*Credentials)
+ return c, ok
+}
+
+func CredentialsFromRequest(r *http.Request) *Credentials {
+ if c, ok := FromContext(r.Context()); ok {
+ // preloaded by middleware
+ return c
+ }
c := NewCredentials()
c.LoadTokensFromHTTPRequest(r)
return c
// token.
var DecodeTokenCookie func(string) ([]byte, error) = base64.URLEncoding.DecodeString
-// LoadTokensFromHttpRequest loads all tokens it can find in the
+// LoadTokensFromHTTPRequest loads all tokens it can find in the
// headers and query string of an http query.
func (a *Credentials) LoadTokensFromHTTPRequest(r *http.Request) {
// Load plain token from "Authorization: OAuth2 ..." header
a.Tokens = append(a.Tokens, string(token))
}
-// TODO: LoadTokensFromHttpRequestBody(). We can't assume in
-// LoadTokensFromHttpRequest() that [or how] we should read and parse
-// the request body. This has to be requested explicitly by the
-// application.
+// LoadTokensFromHTTPRequestBody() loads credentials from the request
+// body.
+//
+// This is separate from LoadTokensFromHTTPRequest() because it's not
+// always desirable to read the request body. This has to be requested
+// explicitly by the application.
+func (a *Credentials) LoadTokensFromHTTPRequestBody(r *http.Request) error {
+ if r.Header.Get("Content-Type") != "application/x-www-form-urlencoded" {
+ return nil
+ }
+ if err := r.ParseForm(); err != nil {
+ return err
+ }
+ if t := r.PostFormValue("api_token"); t != "" {
+ a.Tokens = append(a.Tokens, t)
+ }
+ return nil
+}