9 type Credentials struct {
13 func NewCredentials() *Credentials {
14 return &Credentials{Tokens: []string{}}
17 func NewCredentialsFromHTTPRequest(r *http.Request) *Credentials {
19 c.LoadTokensFromHTTPRequest(r)
23 // LoadTokensFromHttpRequest loads all tokens it can find in the
24 // headers and query string of an http query.
25 func (a *Credentials) LoadTokensFromHTTPRequest(r *http.Request) {
26 // Load plain token from "Authorization: OAuth2 ..." header
27 // (typically used by smart API clients)
28 if toks := strings.SplitN(r.Header.Get("Authorization"), " ", 2); len(toks) == 2 && toks[0] == "OAuth2" {
29 a.Tokens = append(a.Tokens, toks[1])
32 // Load base64-encoded token from "Authorization: Basic ..."
33 // header (typically used by git via credential helper)
34 if _, password, ok := BasicAuth(r); ok {
35 a.Tokens = append(a.Tokens, password)
38 // Load tokens from query string. It's generally not a good
39 // idea to pass tokens around this way, but passing a narrowly
40 // scoped token is a reasonable way to implement "secret link
41 // to an object" in a generic way.
43 // ParseQuery always returns a non-nil map which might have
44 // valid parameters, even when a decoding error causes it to
45 // return a non-nil err. We ignore err; hopefully the caller
46 // will also need to parse the query string for
47 // application-specific purposes and will therefore
48 // find/report decoding errors in a suitable way.
49 qvalues, _ := url.ParseQuery(r.URL.RawQuery)
50 if val, ok := qvalues["api_token"]; ok {
51 a.Tokens = append(a.Tokens, val...)
54 // TODO: Load token from Rails session cookie (if Rails site
58 // TODO: LoadTokensFromHttpRequestBody(). We can't assume in
59 // LoadTokensFromHttpRequest() that [or how] we should read and parse
60 // the request body. This has to be requested explicitly by the