diff options
author | Andrew Arnott <andrewarnott@gmail.com> | 2012-03-31 11:45:42 -0700 |
---|---|---|
committer | Andrew Arnott <andrewarnott@gmail.com> | 2012-03-31 11:45:42 -0700 |
commit | af226f837b7bb5050ab511e66ba75714f79d8865 (patch) | |
tree | 3dba68ac08d55fa46e2b5c0b52c96d6612b12a2a /src/DotNetOpenAuth.OAuth2.Client/OAuth2 | |
parent | b4aa4d4cf25f358e8ca199fe3fbd446d1bb9bc42 (diff) | |
parent | 7265452c16667c6ff499970b0d6778d5184cc8cb (diff) | |
download | DotNetOpenAuth-af226f837b7bb5050ab511e66ba75714f79d8865.zip DotNetOpenAuth-af226f837b7bb5050ab511e66ba75714f79d8865.tar.gz DotNetOpenAuth-af226f837b7bb5050ab511e66ba75714f79d8865.tar.bz2 |
Applied some refactoring of OAuth2 classes.
Diffstat (limited to 'src/DotNetOpenAuth.OAuth2.Client/OAuth2')
12 files changed, 527 insertions, 5 deletions
diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/AuthorizationServerDescription.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/AuthorizationServerDescription.cs new file mode 100644 index 0000000..38a9ff9 --- /dev/null +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/AuthorizationServerDescription.cs @@ -0,0 +1,62 @@ +//----------------------------------------------------------------------- +// <copyright file="AuthorizationServerDescription.cs" company="Outercurve Foundation"> +// Copyright (c) Outercurve Foundation. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace DotNetOpenAuth.OAuth2 { + using System; + using System.Collections.Generic; + using System.Linq; + using System.Text; + + /// <summary> + /// A description of an OAuth Authorization Server as seen by an OAuth Client. + /// </summary> + public class AuthorizationServerDescription { + /// <summary> + /// Initializes a new instance of the <see cref="AuthorizationServerDescription"/> class. + /// </summary> + public AuthorizationServerDescription() { + this.ProtocolVersion = Protocol.Default.ProtocolVersion; + } + + /// <summary> + /// Gets or sets the Authorization Server URL from which an Access Token is requested by the Client. + /// </summary> + /// <value>An HTTPS URL.</value> + /// <remarks> + /// <para>After obtaining authorization from the resource owner, clients request an access token from the authorization server's token endpoint.</para> + /// <para>The URI of the token endpoint can be found in the service documentation, or can be obtained by the client by making an unauthorized protected resource request (from the WWW-Authenticate response header token-uri (The 'authorization-uri' Attribute) attribute).</para> + /// <para>The token endpoint advertised by the resource server MAY include a query component as defined by [RFC3986] (Berners-Lee, T., Fielding, R., and L. Masinter, “Uniform Resource Identifier (URI): Generic Syntax,” January 2005.) section 3.</para> + /// <para>Since requests to the token endpoint result in the transmission of plain text credentials in the HTTP request and response, the authorization server MUST require the use of a transport-layer mechanism such as TLS/SSL (or a secure channel with equivalent protections) when sending requests to the token endpoints. </para> + /// </remarks> + public Uri TokenEndpoint { get; set; } + + /// <summary> + /// Gets or sets the Authorization Server URL where the Client (re)directs the User + /// to make an authorization request. + /// </summary> + /// <value>An HTTPS URL.</value> + /// <remarks> + /// <para>Clients direct the resource owner to the authorization endpoint to approve their access request. Before granting access, the resource owner first authenticates with the authorization server. The way in which the authorization server authenticates the end-user (e.g. username and password login, OpenID, session cookies) and in which the authorization server obtains the end-user's authorization, including whether it uses a secure channel such as TLS/SSL, is beyond the scope of this specification. However, the authorization server MUST first verify the identity of the end-user.</para> + /// <para>The URI of the authorization endpoint can be found in the service documentation, or can be obtained by the client by making an unauthorized protected resource request (from the WWW-Authenticate response header auth-uri (The 'authorization-uri' Attribute) attribute).</para> + /// <para>The authorization endpoint advertised by the resource server MAY include a query component as defined by [RFC3986] (Berners-Lee, T., Fielding, R., and L. Masinter, “Uniform Resource Identifier (URI): Generic Syntax,” January 2005.) section 3.</para> + /// <para>Since requests to the authorization endpoint result in user authentication and the transmission of sensitive values, the authorization server SHOULD require the use of a transport-layer mechanism such as TLS/SSL (or a secure channel with equivalent protections) when sending requests to the authorization endpoints.</para> + /// </remarks> + public Uri AuthorizationEndpoint { get; set; } + + /// <summary> + /// Gets or sets the OAuth version supported by the Authorization Server. + /// </summary> + public ProtocolVersion ProtocolVersion { get; set; } + + /// <summary> + /// Gets the version of the OAuth protocol to use with this Authorization Server. + /// </summary> + /// <value>The version.</value> + internal Version Version { + get { return Protocol.Lookup(this.ProtocolVersion).Version; } + } + } +} diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/AuthorizationState.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/AuthorizationState.cs new file mode 100644 index 0000000..4117b3c --- /dev/null +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/AuthorizationState.cs @@ -0,0 +1,93 @@ +//----------------------------------------------------------------------- +// <copyright file="AuthorizationState.cs" company="Outercurve Foundation"> +// Copyright (c) Outercurve Foundation. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace DotNetOpenAuth.OAuth2 { + using System; + using System.Collections.Generic; + + using DotNetOpenAuth.Messaging; + + /// <summary> + /// A simple in-memory copy of an authorization state. + /// </summary> + [Serializable] + public class AuthorizationState : IAuthorizationState { + /// <summary> + /// Initializes a new instance of the <see cref="AuthorizationState"/> class. + /// </summary> + /// <param name="scopes">The scopes of access being requested or that was obtained.</param> + public AuthorizationState(IEnumerable<string> scopes = null) { + this.Scope = new HashSet<string>(OAuthUtilities.ScopeStringComparer); + if (scopes != null) { + this.Scope.AddRange(scopes); + } + } + + /// <summary> + /// Gets or sets the callback URL used to obtain authorization. + /// </summary> + /// <value>The callback URL.</value> + public Uri Callback { get; set; } + + /// <summary> + /// Gets or sets the long-lived token used to renew the short-lived <see cref="AccessToken"/>. + /// </summary> + /// <value>The refresh token.</value> + public string RefreshToken { get; set; } + + /// <summary> + /// Gets or sets the access token. + /// </summary> + /// <value>The access token.</value> + public string AccessToken { get; set; } + + /// <summary> + /// Gets or sets the access token UTC expiration date. + /// </summary> + /// <value></value> + public DateTime? AccessTokenExpirationUtc { get; set; } + + /// <summary> + /// Gets or sets the access token issue date UTC. + /// </summary> + /// <value>The access token issue date UTC.</value> + public DateTime? AccessTokenIssueDateUtc { get; set; } + + /// <summary> + /// Gets the scope the token is (to be) authorized for. + /// </summary> + /// <value>The scope.</value> + public HashSet<string> Scope { get; private set; } + + /// <summary> + /// Gets or sets a value indicating whether this instance is deleted. + /// </summary> + /// <value> + /// <c>true</c> if this instance is deleted; otherwise, <c>false</c>. + /// </value> + public bool IsDeleted { get; set; } + + /// <summary> + /// Deletes this authorization, including access token and refresh token where applicable. + /// </summary> + /// <remarks> + /// This method is invoked when an authorization attempt fails, is rejected, is revoked, or + /// expires and cannot be renewed. + /// </remarks> + public virtual void Delete() { + this.IsDeleted = true; + } + + /// <summary> + /// Saves any changes made to this authorization object's properties. + /// </summary> + /// <remarks> + /// This method is invoked after DotNetOpenAuth changes any property. + /// </remarks> + public virtual void SaveChanges() { + } + } +}
\ No newline at end of file diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/ChannelElements/OAuth2ClientChannel.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/ChannelElements/OAuth2ClientChannel.cs new file mode 100644 index 0000000..95ec983 --- /dev/null +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/ChannelElements/OAuth2ClientChannel.cs @@ -0,0 +1,135 @@ +//----------------------------------------------------------------------- +// <copyright file="OAuth2ClientChannel.cs" company="Outercurve Foundation"> +// Copyright (c) Outercurve Foundation. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace DotNetOpenAuth.OAuth2.ChannelElements { + using System; + using System.Collections.Generic; + using System.Collections.Specialized; + using System.Diagnostics.Contracts; + using System.Net; + using System.Web; + + using DotNetOpenAuth.Messaging; + using DotNetOpenAuth.OAuth2.Messages; + + /// <summary> + /// The messaging channel used by OAuth 2.0 Clients. + /// </summary> + internal class OAuth2ClientChannel : OAuth2ChannelBase { + /// <summary> + /// The messages receivable by this channel. + /// </summary> + private static readonly Type[] MessageTypes = new Type[] { + typeof(AccessTokenSuccessResponse), + typeof(AccessTokenFailedResponse), + typeof(EndUserAuthorizationSuccessAuthCodeResponse), + typeof(EndUserAuthorizationSuccessAccessTokenResponse), + typeof(EndUserAuthorizationFailedResponse), + typeof(UnauthorizedResponse), + }; + + /// <summary> + /// Initializes a new instance of the <see cref="OAuth2ClientChannel"/> class. + /// </summary> + internal OAuth2ClientChannel() : base(MessageTypes) { + } + + /// <summary> + /// Prepares an HTTP request that carries a given message. + /// </summary> + /// <param name="request">The message to send.</param> + /// <returns> + /// The <see cref="HttpWebRequest"/> prepared to send the request. + /// </returns> + /// <remarks> + /// This method must be overridden by a derived class, unless the <see cref="Channel.RequestCore"/> method + /// is overridden and does not require this method. + /// </remarks> + protected override HttpWebRequest CreateHttpRequest(IDirectedProtocolMessage request) { + HttpWebRequest httpRequest; + if ((request.HttpMethods & HttpDeliveryMethods.GetRequest) != 0) { + httpRequest = InitializeRequestAsGet(request); + } else if ((request.HttpMethods & HttpDeliveryMethods.PostRequest) != 0) { + httpRequest = InitializeRequestAsPost(request); + } else { + throw new NotSupportedException(); + } + + return httpRequest; + } + + /// <summary> + /// Gets the protocol message that may be in the given HTTP response. + /// </summary> + /// <param name="response">The response that is anticipated to contain an protocol message.</param> + /// <returns> + /// The deserialized message parts, if found. Null otherwise. + /// </returns> + /// <exception cref="ProtocolException">Thrown when the response is not valid.</exception> + protected override IDictionary<string, string> ReadFromResponseCore(IncomingWebResponse response) { + // The spec says direct responses should be JSON objects, but Facebook uses HttpFormUrlEncoded instead, calling it text/plain + // Others return text/javascript. Again bad. + string body = response.GetResponseReader().ReadToEnd(); + if (response.ContentType.MediaType == JsonEncoded || response.ContentType.MediaType == JsonTextEncoded) { + return this.DeserializeFromJson(body); + } else if (response.ContentType.MediaType == HttpFormUrlEncoded || response.ContentType.MediaType == PlainTextEncoded) { + return HttpUtility.ParseQueryString(body).ToDictionary(); + } else { + throw ErrorUtilities.ThrowProtocol(OAuthStrings.UnexpectedResponseContentType, response.ContentType.MediaType); + } + } + + /// <summary> + /// Gets the protocol message that may be embedded in the given HTTP request. + /// </summary> + /// <param name="request">The request to search for an embedded message.</param> + /// <returns> + /// The deserialized message, if one is found. Null otherwise. + /// </returns> + protected override IDirectedProtocolMessage ReadFromRequestCore(HttpRequestBase request) { + Logger.Channel.DebugFormat("Incoming HTTP request: {0} {1}", request.HttpMethod, request.GetPublicFacingUrl().AbsoluteUri); + + var fields = request.GetQueryStringBeforeRewriting().ToDictionary(); + + // Also read parameters from the fragment, if it's available. + // Typically the fragment is not available because the browser doesn't send it to a web server + // but this request may have been fabricated by an installed desktop app, in which case + // the fragment is available. + string fragment = request.GetPublicFacingUrl().Fragment; + if (!string.IsNullOrEmpty(fragment)) { + foreach (var pair in HttpUtility.ParseQueryString(fragment.Substring(1)).ToDictionary()) { + fields.Add(pair.Key, pair.Value); + } + } + + MessageReceivingEndpoint recipient; + try { + recipient = request.GetRecipient(); + } catch (ArgumentException ex) { + Logger.Messaging.WarnFormat("Unrecognized HTTP request: ", ex); + return null; + } + + return (IDirectedProtocolMessage)this.Receive(fields, recipient); + } + + /// <summary> + /// Queues a message for sending in the response stream where the fields + /// are sent in the response stream in querystring style. + /// </summary> + /// <param name="response">The message to send as a response.</param> + /// <returns> + /// The pending user agent redirect based message to be sent as an HttpResponse. + /// </returns> + /// <remarks> + /// This method implements spec OAuth V1.0 section 5.3. + /// </remarks> + protected override OutgoingWebResponse PrepareDirectResponse(IProtocolMessage response) { + // Clients don't ever send direct responses. + throw new NotImplementedException(); + } + } +} diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/ClientBase.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/ClientBase.cs index 7697244..1bda5e0 100644 --- a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/ClientBase.cs +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/ClientBase.cs @@ -116,7 +116,7 @@ namespace DotNetOpenAuth.OAuth2 { } } - var request = new AccessTokenRefreshRequest(this.AuthorizationServer) { + var request = new AccessTokenRefreshRequestC(this.AuthorizationServer) { ClientIdentifier = this.ClientIdentifier, ClientSecret = this.ClientSecret, RefreshToken = authorization.RefreshToken, @@ -143,7 +143,7 @@ namespace DotNetOpenAuth.OAuth2 { Requires.NotNull(scope, "scope"); Contract.Ensures(Contract.Result<IAuthorizationState>() != null); - var request = new AccessTokenRefreshRequest(this.AuthorizationServer) { + var request = new AccessTokenRefreshRequestC(this.AuthorizationServer) { ClientIdentifier = this.ClientIdentifier, ClientSecret = this.ClientSecret, RefreshToken = refreshToken, @@ -248,7 +248,7 @@ namespace DotNetOpenAuth.OAuth2 { Requires.NotNull(authorizationState, "authorizationState"); Requires.NotNull(authorizationSuccess, "authorizationSuccess"); - var accessTokenRequest = new AccessTokenAuthorizationCodeRequest(this.AuthorizationServer) { + var accessTokenRequest = new AccessTokenAuthorizationCodeRequestC(this.AuthorizationServer) { ClientIdentifier = this.ClientIdentifier, ClientSecret = this.ClientSecret, Callback = authorizationState.Callback, diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/IAuthorizationState.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/IAuthorizationState.cs new file mode 100644 index 0000000..f38df9a --- /dev/null +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/IAuthorizationState.cs @@ -0,0 +1,67 @@ +//----------------------------------------------------------------------- +// <copyright file="IAuthorizationState.cs" company="Outercurve Foundation"> +// Copyright (c) Outercurve Foundation. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace DotNetOpenAuth.OAuth2 { + using System; + using System.Collections.Generic; + + /// <summary> + /// Provides access to a persistent object that tracks the state of an authorization. + /// </summary> + public interface IAuthorizationState { + /// <summary> + /// Gets or sets the callback URL used to obtain authorization. + /// </summary> + /// <value>The callback URL.</value> + Uri Callback { get; set; } + + /// <summary> + /// Gets or sets the long-lived token used to renew the short-lived <see cref="AccessToken"/>. + /// </summary> + /// <value>The refresh token.</value> + string RefreshToken { get; set; } + + /// <summary> + /// Gets or sets the access token. + /// </summary> + /// <value>The access token.</value> + string AccessToken { get; set; } + + /// <summary> + /// Gets or sets the access token issue date UTC. + /// </summary> + /// <value>The access token issue date UTC.</value> + DateTime? AccessTokenIssueDateUtc { get; set; } + + /// <summary> + /// Gets or sets the access token UTC expiration date. + /// </summary> + DateTime? AccessTokenExpirationUtc { get; set; } + + /// <summary> + /// Gets the scope the token is (to be) authorized for. + /// </summary> + /// <value>The scope.</value> + HashSet<string> Scope { get; } + + /// <summary> + /// Deletes this authorization, including access token and refresh token where applicable. + /// </summary> + /// <remarks> + /// This method is invoked when an authorization attempt fails, is rejected, is revoked, or + /// expires and cannot be renewed. + /// </remarks> + void Delete(); + + /// <summary> + /// Saves any changes made to this authorization object's properties. + /// </summary> + /// <remarks> + /// This method is invoked after DotNetOpenAuth changes any property. + /// </remarks> + void SaveChanges(); + } +}
\ No newline at end of file diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/IClientAuthorizationTracker.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/IClientAuthorizationTracker.cs new file mode 100644 index 0000000..73b7a44 --- /dev/null +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/IClientAuthorizationTracker.cs @@ -0,0 +1,53 @@ +//----------------------------------------------------------------------- +// <copyright file="IClientAuthorizationTracker.cs" company="Outercurve Foundation"> +// Copyright (c) Outercurve Foundation. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace DotNetOpenAuth.OAuth2 { + using System; + using System.Diagnostics.Contracts; + + /// <summary> + /// A token manager implemented by some clients to assist in tracking authorization state. + /// </summary> + [ContractClass(typeof(IClientAuthorizationTrackerContract))] + public interface IClientAuthorizationTracker { + /// <summary> + /// Gets the state of the authorization for a given callback URL and client state. + /// </summary> + /// <param name="callbackUrl">The callback URL.</param> + /// <param name="clientState">State of the client stored at the beginning of an authorization request.</param> + /// <returns>The authorization state; may be <c>null</c> if no authorization state matches.</returns> + IAuthorizationState GetAuthorizationState(Uri callbackUrl, string clientState); + } + + /// <summary> + /// Contract class for the <see cref="IClientAuthorizationTracker"/> interface. + /// </summary> + [ContractClassFor(typeof(IClientAuthorizationTracker))] + internal abstract class IClientAuthorizationTrackerContract : IClientAuthorizationTracker { + /// <summary> + /// Prevents a default instance of the <see cref="IClientAuthorizationTrackerContract"/> class from being created. + /// </summary> + private IClientAuthorizationTrackerContract() { + } + + #region IClientTokenManager Members + + /// <summary> + /// Gets the state of the authorization for a given callback URL and client state. + /// </summary> + /// <param name="callbackUrl">The callback URL.</param> + /// <param name="clientState">State of the client stored at the beginning of an authorization request.</param> + /// <returns> + /// The authorization state; may be <c>null</c> if no authorization state matches. + /// </returns> + IAuthorizationState IClientAuthorizationTracker.GetAuthorizationState(Uri callbackUrl, string clientState) { + Requires.NotNull(callbackUrl, "callbackUrl"); + throw new NotImplementedException(); + } + + #endregion + } +} diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/AccessTokenAuthorizationCodeRequestC.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/AccessTokenAuthorizationCodeRequestC.cs new file mode 100644 index 0000000..ebfb2e8 --- /dev/null +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/AccessTokenAuthorizationCodeRequestC.cs @@ -0,0 +1,27 @@ +//----------------------------------------------------------------------- +// <copyright file="AccessTokenAuthorizationCodeRequestC.cs" company="Andrew Arnott"> +// Copyright (c) Andrew Arnott. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace DotNetOpenAuth.OAuth2.Messages { + using System; + using System.Collections.Generic; + using System.Linq; + using System.Text; + + /// <summary> + /// A request from a Client to an Authorization Server to exchange an authorization code for an access token, + /// and (at the authorization server's option) a refresh token. + /// </summary> + internal class AccessTokenAuthorizationCodeRequestC : AccessTokenAuthorizationCodeRequest { + /// <summary> + /// Initializes a new instance of the <see cref="AccessTokenAuthorizationCodeRequestC"/> class. + /// </summary> + /// <param name="authorizationServer">The authorization server.</param> + internal AccessTokenAuthorizationCodeRequestC(AuthorizationServerDescription authorizationServer) + : base(authorizationServer.TokenEndpoint, authorizationServer.Version) { + Requires.NotNull(authorizationServer, "authorizationServer"); + } + } +} diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/AccessTokenRefreshRequestC.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/AccessTokenRefreshRequestC.cs new file mode 100644 index 0000000..25da3dc --- /dev/null +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/AccessTokenRefreshRequestC.cs @@ -0,0 +1,26 @@ +//----------------------------------------------------------------------- +// <copyright file="AccessTokenRefreshRequestC.cs" company="Andrew Arnott"> +// Copyright (c) Andrew Arnott. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace DotNetOpenAuth.OAuth2.Messages { + using System; + using System.Collections.Generic; + using System.Linq; + using System.Text; + + /// <summary> + /// A request from the client to the token endpoint for a new access token + /// in exchange for a refresh token that the client has previously obtained. + /// </summary> + internal class AccessTokenRefreshRequestC : AccessTokenRefreshRequest { + /// <summary> + /// Initializes a new instance of the <see cref="AccessTokenRefreshRequestC"/> class. + /// </summary> + /// <param name="authorizationServer">The authorization server.</param> + internal AccessTokenRefreshRequestC(AuthorizationServerDescription authorizationServer) + : base(authorizationServer.TokenEndpoint, authorizationServer.Version) { + } + } +} diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/EndUserAuthorizationImplicitRequestC.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/EndUserAuthorizationImplicitRequestC.cs new file mode 100644 index 0000000..78bf48e --- /dev/null +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/EndUserAuthorizationImplicitRequestC.cs @@ -0,0 +1,28 @@ +//----------------------------------------------------------------------- +// <copyright file="EndUserAuthorizationImplicitRequestC.cs" company="Andrew Arnott"> +// Copyright (c) Andrew Arnott. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace DotNetOpenAuth.OAuth2.Messages { + using System; + using System.Collections.Generic; + using System.Linq; + using System.Text; + + /// <summary> + /// A message sent by a web application Client to the AuthorizationServer + /// via the user agent to obtain authorization from the user and prepare + /// to issue an access token to the client if permission is granted. + /// </summary> + [Serializable] + internal class EndUserAuthorizationImplicitRequestC : EndUserAuthorizationImplicitRequest { + /// <summary> + /// Initializes a new instance of the <see cref="EndUserAuthorizationImplicitRequestC"/> class. + /// </summary> + /// <param name="authorizationServer">The authorization server.</param> + internal EndUserAuthorizationImplicitRequestC(AuthorizationServerDescription authorizationServer) + : base(authorizationServer.AuthorizationEndpoint, authorizationServer.Version) { + } + } +} diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/EndUserAuthorizationRequestC.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/EndUserAuthorizationRequestC.cs new file mode 100644 index 0000000..7c06897 --- /dev/null +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/Messages/EndUserAuthorizationRequestC.cs @@ -0,0 +1,31 @@ +//----------------------------------------------------------------------- +// <copyright file="EndUserAuthorizationRequestC.cs" company="Andrew Arnott"> +// Copyright (c) Andrew Arnott. All rights reserved. +// </copyright> +//----------------------------------------------------------------------- + +namespace DotNetOpenAuth.OAuth2.Messages { + using System; + using System.Collections.Generic; + using System.Linq; + using System.Text; + + /// <summary> + /// A message sent by a web application Client to the AuthorizationServer + /// via the user agent to obtain authorization from the user and prepare + /// to issue an access token to the client if permission is granted. + /// </summary> + [Serializable] + internal class EndUserAuthorizationRequestC : EndUserAuthorizationRequest { + /// <summary> + /// Initializes a new instance of the <see cref="EndUserAuthorizationRequestC"/> class. + /// </summary> + /// <param name="authorizationServer">The authorization server.</param> + internal EndUserAuthorizationRequestC(AuthorizationServerDescription authorizationServer) + : base(authorizationServer.AuthorizationEndpoint, authorizationServer.Version) { + Requires.NotNull(authorizationServer, "authorizationServer"); + Requires.True(authorizationServer.Version != null, "authorizationServer"); + Requires.True(authorizationServer.AuthorizationEndpoint != null, "authorizationServer"); + } + } +} diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/UserAgentClient.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/UserAgentClient.cs index c29d167..9834985 100644 --- a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/UserAgentClient.cs +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/UserAgentClient.cs @@ -151,7 +151,7 @@ namespace DotNetOpenAuth.OAuth2 { authorization.Callback = new Uri("http://localhost/"); } - var request = implicitResponseType ? new EndUserAuthorizationImplicitRequest(this.AuthorizationServer) : new EndUserAuthorizationRequest(this.AuthorizationServer); + var request = implicitResponseType ? (EndUserAuthorizationRequest)new EndUserAuthorizationImplicitRequestC(this.AuthorizationServer) : new EndUserAuthorizationRequestC(this.AuthorizationServer); request.ClientIdentifier = this.ClientIdentifier; request.Callback = authorization.Callback; request.ClientState = state; diff --git a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/WebServerClient.cs b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/WebServerClient.cs index 671214f..016c491 100644 --- a/src/DotNetOpenAuth.OAuth2.Client/OAuth2/WebServerClient.cs +++ b/src/DotNetOpenAuth.OAuth2.Client/OAuth2/WebServerClient.cs @@ -78,7 +78,7 @@ namespace DotNetOpenAuth.OAuth2 { authorization.SaveChanges(); } - var request = new EndUserAuthorizationRequest(this.AuthorizationServer) { + var request = new EndUserAuthorizationRequestC(this.AuthorizationServer) { ClientIdentifier = this.ClientIdentifier, Callback = authorization.Callback, }; |