...

Source file src/github.com/ory/fosite/oauth2.go

Documentation: github.com/ory/fosite

     1  /*
     2   * Copyright © 2015-2018 Aeneas Rekkas <aeneas+oss@aeneas.io>
     3   *
     4   * Licensed under the Apache License, Version 2.0 (the "License");
     5   * you may not use this file except in compliance with the License.
     6   * You may obtain a copy of the License at
     7   *
     8   *     http://www.apache.org/licenses/LICENSE-2.0
     9   *
    10   * Unless required by applicable law or agreed to in writing, software
    11   * distributed under the License is distributed on an "AS IS" BASIS,
    12   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13   * See the License for the specific language governing permissions and
    14   * limitations under the License.
    15   *
    16   * @author		Aeneas Rekkas <aeneas+oss@aeneas.io>
    17   * @copyright 	2015-2018 Aeneas Rekkas <aeneas+oss@aeneas.io>
    18   * @license 	Apache-2.0
    19   *
    20   */
    21  
    22  package fosite
    23  
    24  import (
    25  	"context"
    26  	"net/http"
    27  	"net/url"
    28  	"time"
    29  
    30  	"golang.org/x/text/language"
    31  )
    32  
    33  type TokenUse = TokenType
    34  
    35  type TokenType string
    36  
    37  const (
    38  	AccessToken   TokenType = "access_token"
    39  	RefreshToken  TokenType = "refresh_token"
    40  	AuthorizeCode TokenType = "authorize_code"
    41  	IDToken       TokenType = "id_token"
    42  
    43  	BearerAccessToken string = "bearer"
    44  )
    45  
    46  // OAuth2Provider is an interface that enables you to write OAuth2 handlers with only a few lines of code.
    47  // Check fosite.Fosite for an implementation of this interface.
    48  type OAuth2Provider interface {
    49  	// NewAuthorizeRequest returns an AuthorizeRequest.
    50  	//
    51  	// The following specs must be considered in any implementation of this method:
    52  	// * https://tools.ietf.org/html/rfc6749#section-3.1
    53  	//	 Extension response types MAY contain a space-delimited (%x20) list of
    54  	//	 values, where the order of values does not matter (e.g., response
    55  	//	 type "a b" is the same as "b a").  The meaning of such composite
    56  	//	 response types is defined by their respective specifications.
    57  	// * https://tools.ietf.org/html/rfc6749#section-3.1.2
    58  	//   The redirection endpoint URI MUST be an absolute URI as defined by
    59  	//   [RFC3986] Section 4.3.  The endpoint URI MAY include an
    60  	//   "application/x-www-form-urlencoded" formatted (per Appendix B) query
    61  	//   component ([RFC3986] Section 3.4), which MUST be retained when adding
    62  	//   additional query parameters.  The endpoint URI MUST NOT include a
    63  	//   fragment component.
    64  	// * https://tools.ietf.org/html/rfc6749#section-3.1.2.2 (everything MUST be implemented)
    65  	NewAuthorizeRequest(ctx context.Context, req *http.Request) (AuthorizeRequester, error)
    66  
    67  	// NewAuthorizeResponse iterates through all response type handlers and returns their result or
    68  	// ErrUnsupportedResponseType if none of the handler's were able to handle it.
    69  	//
    70  	// The following specs must be considered in any implementation of this method:
    71  	// * https://tools.ietf.org/html/rfc6749#section-3.1.1
    72  	//	 Extension response types MAY contain a space-delimited (%x20) list of
    73  	//	 values, where the order of values does not matter (e.g., response
    74  	//	 type "a b" is the same as "b a").  The meaning of such composite
    75  	//	 response types is defined by their respective specifications.
    76  	//	 If an authorization request is missing the "response_type" parameter,
    77  	//	 or if the response type is not understood, the authorization server
    78  	//	 MUST return an error response as described in Section 4.1.2.1.
    79  	NewAuthorizeResponse(ctx context.Context, requester AuthorizeRequester, session Session) (AuthorizeResponder, error)
    80  
    81  	// WriteAuthorizeError returns the error codes to the redirection endpoint or shows the error to the user, if no valid
    82  	// redirect uri was given. Implements rfc6749#section-4.1.2.1
    83  	//
    84  	// The following specs must be considered in any implementation of this method:
    85  	// * https://tools.ietf.org/html/rfc6749#section-3.1.2
    86  	//   The redirection endpoint URI MUST be an absolute URI as defined by
    87  	//   [RFC3986] Section 4.3.  The endpoint URI MAY include an
    88  	//   "application/x-www-form-urlencoded" formatted (per Appendix B) query
    89  	//   component ([RFC3986] Section 3.4), which MUST be retained when adding
    90  	//   additional query parameters.  The endpoint URI MUST NOT include a
    91  	//   fragment component.
    92  	// * https://tools.ietf.org/html/rfc6749#section-4.1.2.1 (everything)
    93  	// * https://tools.ietf.org/html/rfc6749#section-3.1.2.2 (everything MUST be implemented)
    94  	WriteAuthorizeError(rw http.ResponseWriter, requester AuthorizeRequester, err error)
    95  
    96  	// WriteAuthorizeResponse persists the AuthorizeSession in the store and redirects the user agent to the provided
    97  	// redirect url or returns an error if storage failed.
    98  	//
    99  	// The following specs must be considered in any implementation of this method:
   100  	// * https://tools.ietf.org/html/rfc6749#rfc6749#section-4.1.2.1
   101  	//   After completing its interaction with the resource owner, the
   102  	//   authorization server directs the resource owner's user-agent back to
   103  	//   the client.  The authorization server redirects the user-agent to the
   104  	//   client's redirection endpoint previously established with the
   105  	//   authorization server during the client registration process or when
   106  	//   making the authorization request.
   107  	// * https://tools.ietf.org/html/rfc6749#section-3.1.2.2 (everything MUST be implemented)
   108  	WriteAuthorizeResponse(rw http.ResponseWriter, requester AuthorizeRequester, responder AuthorizeResponder)
   109  
   110  	// NewAccessRequest creates a new access request object and validates
   111  	// various parameters.
   112  	//
   113  	// The following specs must be considered in any implementation of this method:
   114  	// * https://tools.ietf.org/html/rfc6749#section-3.2 (everything)
   115  	// * https://tools.ietf.org/html/rfc6749#section-3.2.1 (everything)
   116  	//
   117  	// Furthermore the registered handlers should implement their specs accordingly.
   118  	NewAccessRequest(ctx context.Context, req *http.Request, session Session) (AccessRequester, error)
   119  
   120  	// NewAccessResponse creates a new access response and validates that access_token and token_type are set.
   121  	//
   122  	// The following specs must be considered in any implementation of this method:
   123  	// https://tools.ietf.org/html/rfc6749#section-5.1
   124  	NewAccessResponse(ctx context.Context, requester AccessRequester) (AccessResponder, error)
   125  
   126  	// WriteAccessError writes an access request error response.
   127  	//
   128  	// The following specs must be considered in any implementation of this method:
   129  	// * https://tools.ietf.org/html/rfc6749#section-5.2 (everything)
   130  	WriteAccessError(rw http.ResponseWriter, requester AccessRequester, err error)
   131  
   132  	// WriteAccessResponse writes the access response.
   133  	//
   134  	// The following specs must be considered in any implementation of this method:
   135  	// https://tools.ietf.org/html/rfc6749#section-5.1
   136  	WriteAccessResponse(rw http.ResponseWriter, requester AccessRequester, responder AccessResponder)
   137  
   138  	// NewRevocationRequest handles incoming token revocation requests and validates various parameters.
   139  	//
   140  	// The following specs must be considered in any implementation of this method:
   141  	// https://tools.ietf.org/html/rfc7009#section-2.1
   142  	NewRevocationRequest(ctx context.Context, r *http.Request) error
   143  
   144  	// WriteRevocationResponse writes the revoke response.
   145  	//
   146  	// The following specs must be considered in any implementation of this method:
   147  	// https://tools.ietf.org/html/rfc7009#section-2.2
   148  	WriteRevocationResponse(rw http.ResponseWriter, err error)
   149  
   150  	// IntrospectToken returns token metadata, if the token is valid. Tokens generated by the authorization endpoint,
   151  	// such as the authorization code, can not be introspected.
   152  	IntrospectToken(ctx context.Context, token string, tokenUse TokenUse, session Session, scope ...string) (TokenUse, AccessRequester, error)
   153  
   154  	// NewIntrospectionRequest initiates token introspection as defined in
   155  	// https://tools.ietf.org/search/rfc7662#section-2.1
   156  	NewIntrospectionRequest(ctx context.Context, r *http.Request, session Session) (IntrospectionResponder, error)
   157  
   158  	// WriteIntrospectionError responds with an error if token introspection failed as defined in
   159  	// https://tools.ietf.org/search/rfc7662#section-2.3
   160  	WriteIntrospectionError(rw http.ResponseWriter, err error)
   161  
   162  	// WriteIntrospectionResponse responds with token metadata discovered by token introspection as defined in
   163  	// https://tools.ietf.org/search/rfc7662#section-2.2
   164  	WriteIntrospectionResponse(rw http.ResponseWriter, r IntrospectionResponder)
   165  }
   166  
   167  // IntrospectionResponder is the response object that will be returned when token introspection was successful,
   168  // for example when the client is allowed to perform token introspection. Refer to
   169  // https://tools.ietf.org/search/rfc7662#section-2.2 for more details.
   170  type IntrospectionResponder interface {
   171  	// IsActive returns true if the introspected token is active and false otherwise.
   172  	IsActive() bool
   173  
   174  	// AccessRequester returns nil when IsActive() is false and the original access request object otherwise.
   175  	GetAccessRequester() AccessRequester
   176  
   177  	// GetTokenUse optionally returns the type of the token that was introspected. This could be "access_token", "refresh_token",
   178  	// or if the type can not be determined an empty string.
   179  	GetTokenUse() TokenUse
   180  
   181  	//GetAccessTokenType optionally returns the type of the access token that was introspected. This could be "bearer", "mac",
   182  	// or empty string if the type of the token is refresh token.
   183  	GetAccessTokenType() string
   184  }
   185  
   186  // Requester is an abstract interface for handling requests in Fosite.
   187  type Requester interface {
   188  	// SetID sets the unique identifier.
   189  	SetID(id string)
   190  
   191  	// GetID returns a unique identifier.
   192  	GetID() string
   193  
   194  	// GetRequestedAt returns the time the request was created.
   195  	GetRequestedAt() (requestedAt time.Time)
   196  
   197  	// GetClient returns the request's client.
   198  	GetClient() (client Client)
   199  
   200  	// GetRequestedScopes returns the request's scopes.
   201  	GetRequestedScopes() (scopes Arguments)
   202  
   203  	// GetRequestedAudience returns the requested audiences for this request.
   204  	GetRequestedAudience() (audience Arguments)
   205  
   206  	// SetRequestedScopes sets the request's scopes.
   207  	SetRequestedScopes(scopes Arguments)
   208  
   209  	// SetRequestedAudience sets the requested audience.
   210  	SetRequestedAudience(audience Arguments)
   211  
   212  	// AppendRequestedScope appends a scope to the request.
   213  	AppendRequestedScope(scope string)
   214  
   215  	// GetGrantScopes returns all granted scopes.
   216  	GetGrantedScopes() (grantedScopes Arguments)
   217  
   218  	// GetGrantedAudience returns all granted audiences.
   219  	GetGrantedAudience() (grantedAudience Arguments)
   220  
   221  	// GrantScope marks a request's scope as granted.
   222  	GrantScope(scope string)
   223  
   224  	// GrantAudience marks a request's audience as granted.
   225  	GrantAudience(audience string)
   226  
   227  	// GetSession returns a pointer to the request's session or nil if none is set.
   228  	GetSession() (session Session)
   229  
   230  	// SetSession sets the request's session pointer.
   231  	SetSession(session Session)
   232  
   233  	// GetRequestForm returns the request's form input.
   234  	GetRequestForm() url.Values
   235  
   236  	// Merge merges the argument into the method receiver.
   237  	Merge(requester Requester)
   238  
   239  	// Sanitize returns a sanitized clone of the request which can be used for storage.
   240  	Sanitize(allowedParameters []string) Requester
   241  }
   242  
   243  // AccessRequester is a token endpoint's request context.
   244  type AccessRequester interface {
   245  	// GetGrantType returns the requests grant type.
   246  	GetGrantTypes() (grantTypes Arguments)
   247  
   248  	Requester
   249  }
   250  
   251  // AuthorizeRequester is an authorize endpoint's request context.
   252  type AuthorizeRequester interface {
   253  	// GetResponseTypes returns the requested response types
   254  	GetResponseTypes() (responseTypes Arguments)
   255  
   256  	// SetResponseTypeHandled marks a response_type (e.g. token or code) as handled indicating that the response type
   257  	// is supported.
   258  	SetResponseTypeHandled(responseType string)
   259  
   260  	// DidHandleAllResponseTypes returns if all requested response types have been handled correctly
   261  	DidHandleAllResponseTypes() (didHandle bool)
   262  
   263  	// GetRedirectURI returns the requested redirect URI
   264  	GetRedirectURI() (redirectURL *url.URL)
   265  
   266  	// IsRedirectURIValid returns false if the redirect is not rfc-conform (i.e. missing client, not on white list,
   267  	// or malformed)
   268  	IsRedirectURIValid() (isValid bool)
   269  
   270  	// GetState returns the request's state.
   271  	GetState() (state string)
   272  
   273  	// GetResponseMode returns response_mode of the authorization request
   274  	GetResponseMode() ResponseModeType
   275  
   276  	// SetDefaultResponseMode sets default response mode for a response type in a flow
   277  	SetDefaultResponseMode(responseMode ResponseModeType)
   278  
   279  	// GetDefaultResponseMode gets default response mode for a response type in a flow
   280  	GetDefaultResponseMode() ResponseModeType
   281  
   282  	Requester
   283  }
   284  
   285  // AccessResponder is a token endpoint's response.
   286  type AccessResponder interface {
   287  	// SetExtra sets a key value pair for the access response.
   288  	SetExtra(key string, value interface{})
   289  
   290  	// GetExtra returns a key's value.
   291  	GetExtra(key string) interface{}
   292  
   293  	SetExpiresIn(time.Duration)
   294  
   295  	SetScopes(scopes Arguments)
   296  
   297  	// SetAccessToken sets the responses mandatory access token.
   298  	SetAccessToken(token string)
   299  
   300  	// SetTokenType set's the responses mandatory token type
   301  	SetTokenType(tokenType string)
   302  
   303  	// SetAccessToken returns the responses access token.
   304  	GetAccessToken() (token string)
   305  
   306  	// GetTokenType returns the responses token type.
   307  	GetTokenType() (token string)
   308  
   309  	// ToMap converts the response to a map.
   310  	ToMap() map[string]interface{}
   311  }
   312  
   313  // AuthorizeResponder is an authorization endpoint's response.
   314  type AuthorizeResponder interface {
   315  	// GetCode returns the response's authorize code if set.
   316  	GetCode() string
   317  
   318  	// GetHeader returns the response's header
   319  	GetHeader() (header http.Header)
   320  
   321  	// AddHeader adds an header key value pair to the response
   322  	AddHeader(key, value string)
   323  
   324  	// GetParameters returns the response's parameters
   325  	GetParameters() (query url.Values)
   326  
   327  	// AddParameter adds key value pair to the response
   328  	AddParameter(key, value string)
   329  }
   330  
   331  // G11NContext is the globalization context
   332  type G11NContext interface {
   333  	// GetLang returns the current language in the context
   334  	GetLang() language.Tag
   335  }
   336  

View as plain text