summaryrefslogtreecommitdiffstats
path: root/src/DotNetOpenAuth.OAuth
diff options
context:
space:
mode:
Diffstat (limited to 'src/DotNetOpenAuth.OAuth')
-rw-r--r--src/DotNetOpenAuth.OAuth/DotNetOpenAuth.OAuth.csproj15
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/ITamperResistantOAuthMessage.cs4
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthChannel.cs96
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthHttpMethodBindingElement.cs16
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementBase.cs22
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementChain.cs12
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/Messages/AccessProtectedResourceRequest.cs8
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/Messages/MessageBaseSimple.cs10
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/Messages/SignedMessageBase.cs5
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/Messages/UserAuthorizationRequest.cs4
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/Protocol.cs25
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuth/ServiceProviderDescription.cs101
-rw-r--r--src/DotNetOpenAuth.OAuth/OAuthReporting.cs56
-rw-r--r--src/DotNetOpenAuth.OAuth/packages.config3
14 files changed, 137 insertions, 240 deletions
diff --git a/src/DotNetOpenAuth.OAuth/DotNetOpenAuth.OAuth.csproj b/src/DotNetOpenAuth.OAuth/DotNetOpenAuth.OAuth.csproj
index 651b414..af9aea9 100644
--- a/src/DotNetOpenAuth.OAuth/DotNetOpenAuth.OAuth.csproj
+++ b/src/DotNetOpenAuth.OAuth/DotNetOpenAuth.OAuth.csproj
@@ -25,7 +25,6 @@
<Compile Include="Configuration\OAuthServiceProviderElement.cs" />
<Compile Include="Configuration\OAuthServiceProviderSecuritySettingsElement.cs" />
<Compile Include="Messaging\ITamperProtectionChannelBindingElement.cs" />
- <Compile Include="OAuthReporting.cs" />
<Compile Include="OAuth\ChannelElements\ITokenManager.cs" />
<Compile Include="OAuth\ChannelElements\OAuthHttpMethodBindingElement.cs" />
<Compile Include="OAuth\ChannelElements\PlaintextSigningBindingElement.cs" />
@@ -35,13 +34,13 @@
<Compile Include="OAuth\ChannelElements\UriOrOobEncoding.cs" />
<Compile Include="OAuth\ConsumerSecuritySettings.cs" />
<Compile Include="OAuth\Messages\ITokenSecretContainingMessage.cs" />
+ <Compile Include="OAuth\Messages\MessageBaseSimple.cs" />
<Compile Include="OAuth\OAuthStrings.Designer.cs">
<AutoGen>True</AutoGen>
<DesignTime>True</DesignTime>
<DependentUpon>OAuthStrings.resx</DependentUpon>
</Compile>
<Compile Include="OAuth\SecuritySettings.cs" />
- <Compile Include="OAuth\ServiceProviderDescription.cs" />
<Compile Include="OAuth\Messages\ITokenContainingMessage.cs" />
<Compile Include="OAuth\Messages\SignedMessageBase.cs" />
<Compile Include="OAuth\ChannelElements\SigningBindingElementBase.cs" />
@@ -82,11 +81,17 @@
<Project>{60426312-6AE5-4835-8667-37EDEA670222}</Project>
<Name>DotNetOpenAuth.Core</Name>
</ProjectReference>
+ <ProjectReference Include="..\DotNetOpenAuth.OAuth.Common\DotNetOpenAuth.OAuth.Common.csproj">
+ <Project>{115217c5-22cd-415c-a292-0dd0238cdd89}</Project>
+ <Name>DotNetOpenAuth.OAuth.Common</Name>
+ </ProjectReference>
</ItemGroup>
<ItemGroup>
- <Reference Include="Validation">
- <HintPath>..\packages\Validation.2.0.1.12362\lib\portable-windows8+net40+sl5+windowsphone8\Validation.dll</HintPath>
- <Private>True</Private>
+ <Reference Include="System.Net.Http" />
+ <Reference Include="System.Net.Http.WebRequest" />
+ <Reference Include="Validation, Version=2.0.0.0, Culture=neutral, PublicKeyToken=2fc06f0d701809a7, processorArchitecture=MSIL">
+ <SpecificVersion>False</SpecificVersion>
+ <HintPath>..\packages\Validation.2.0.2.13022\lib\portable-windows8+net40+sl5+windowsphone8\Validation.dll</HintPath>
</Reference>
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/ITamperResistantOAuthMessage.cs b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/ITamperResistantOAuthMessage.cs
index 9cb0a44..679b1dc 100644
--- a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/ITamperResistantOAuthMessage.cs
+++ b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/ITamperResistantOAuthMessage.cs
@@ -7,6 +7,8 @@
namespace DotNetOpenAuth.OAuth.ChannelElements {
using System;
using System.Collections.Generic;
+ using System.Net.Http;
+
using DotNetOpenAuth.Messaging;
using DotNetOpenAuth.Messaging.Bindings;
@@ -37,7 +39,7 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// <summary>
/// Gets or sets the HTTP method that will be used to transmit the message.
/// </summary>
- string HttpMethod { get; set; }
+ HttpMethod HttpMethod { get; set; }
/// <summary>
/// Gets or sets the URL of the intended receiver of this message.
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthChannel.cs b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthChannel.cs
index 1362ca9..f483ade 100644
--- a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthChannel.cs
+++ b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthChannel.cs
@@ -13,8 +13,12 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
using System.IO;
using System.Linq;
using System.Net;
+ using System.Net.Http;
+ using System.Net.Http.Headers;
using System.Net.Mime;
using System.Text;
+ using System.Threading;
+ using System.Threading.Tasks;
using System.Web;
using DotNetOpenAuth.Messaging;
using DotNetOpenAuth.Messaging.Bindings;
@@ -22,12 +26,14 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
using DotNetOpenAuth.OAuth.Messages;
using Validation;
+ using HttpRequestHeaders = DotNetOpenAuth.Messaging.HttpRequestHeaders;
+
/// <summary>
/// An OAuth-specific implementation of the <see cref="Channel"/> class.
/// </summary>
internal abstract class OAuthChannel : Channel {
/// <summary>
- /// Initializes a new instance of the <see cref="OAuthChannel"/> class.
+ /// Initializes a new instance of the <see cref="OAuthChannel" /> class.
/// </summary>
/// <param name="signingBindingElement">The binding element to use for signing.</param>
/// <param name="tokenManager">The ITokenManager instance to use.</param>
@@ -36,9 +42,10 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// Except for mock testing, this should always be one of
/// OAuthConsumerMessageFactory or OAuthServiceProviderMessageFactory.</param>
/// <param name="bindingElements">The binding elements.</param>
+ /// <param name="hostFactories">The host factories.</param>
[SuppressMessage("Microsoft.Globalization", "CA1303:Do not pass literals as localized parameters", MessageId = "System.Diagnostics.Contracts.__ContractsRuntime.Requires<System.ArgumentNullException>(System.Boolean,System.String,System.String)", Justification = "Code contracts"), SuppressMessage("Microsoft.Naming", "CA2204:Literals should be spelled correctly", MessageId = "securitySettings", Justification = "Code contracts")]
- protected OAuthChannel(ITamperProtectionChannelBindingElement signingBindingElement, ITokenManager tokenManager, SecuritySettings securitySettings, IMessageFactory messageTypeProvider, IChannelBindingElement[] bindingElements)
- : base(messageTypeProvider, bindingElements) {
+ protected OAuthChannel(ITamperProtectionChannelBindingElement signingBindingElement, ITokenManager tokenManager, SecuritySettings securitySettings, IMessageFactory messageTypeProvider, IChannelBindingElement[] bindingElements, IHostFactories hostFactories = null)
+ : base(messageTypeProvider, bindingElements, hostFactories ?? new DefaultOAuthHostFactories()) {
Requires.NotNull(tokenManager, "tokenManager");
Requires.NotNull(securitySettings, "securitySettings");
Requires.NotNull(signingBindingElement, "signingBindingElement");
@@ -76,11 +83,12 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// expect an OAuth message response to.
/// </summary>
/// <param name="request">The message to attach.</param>
+ /// <param name="cancellationToken">The cancellation token.</param>
/// <returns>The initialized web request.</returns>
- internal HttpWebRequest InitializeRequest(IDirectedProtocolMessage request) {
+ internal async Task<HttpRequestMessage> InitializeRequestAsync(IDirectedProtocolMessage request, CancellationToken cancellationToken) {
Requires.NotNull(request, "request");
- ProcessOutgoingMessage(request);
+ await this.ProcessOutgoingMessageAsync(request, cancellationToken);
return this.CreateHttpRequest(request);
}
@@ -108,29 +116,25 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// a protocol request message.
/// </summary>
/// <param name="request">The HTTP request to search.</param>
+ /// <param name="cancellationToken">The cancellation token.</param>
/// <returns>The deserialized message, if one is found. Null otherwise.</returns>
- protected override IDirectedProtocolMessage ReadFromRequestCore(HttpRequestBase request) {
+ protected override async Task<IDirectedProtocolMessage> ReadFromRequestCoreAsync(HttpRequestMessage request, CancellationToken cancellationToken) {
// First search the Authorization header.
- string authorization = request.Headers[HttpRequestHeaders.Authorization];
+ var authorization = request.Headers.Authorization;
var fields = MessagingUtilities.ParseAuthorizationHeader(Protocol.AuthorizationHeaderScheme, authorization).ToDictionary();
fields.Remove("realm"); // ignore the realm parameter, since we don't use it, and it must be omitted from signature base string.
// Scrape the entity
- if (!string.IsNullOrEmpty(request.Headers[HttpRequestHeaders.ContentType])) {
- var contentType = new ContentType(request.Headers[HttpRequestHeaders.ContentType]);
- if (string.Equals(contentType.MediaType, HttpFormUrlEncoded, StringComparison.Ordinal)) {
- foreach (string key in request.Form) {
- if (key != null) {
- fields.Add(key, request.Form[key]);
- } else {
- Logger.OAuth.WarnFormat("Ignoring query string parameter '{0}' since it isn't a standard name=value parameter.", request.Form[key]);
- }
- }
+ foreach (var pair in await ParseUrlEncodedFormContentAsync(request, cancellationToken)) {
+ if (pair.Key != null) {
+ fields.Add(pair.Key, pair.Value);
+ } else {
+ Logger.OAuth.WarnFormat("Ignoring query string parameter '{0}' since it isn't a standard name=value parameter.", pair.Value);
}
}
// Scrape the query string
- var qs = request.GetQueryStringBeforeRewriting();
+ var qs = HttpUtility.ParseQueryString(request.RequestUri.Query);
foreach (string key in qs) {
if (key != null) {
fields.Add(key, qs[key]);
@@ -153,8 +157,8 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
// Add receiving HTTP transport information required for signature generation.
var signedMessage = message as ITamperResistantOAuthMessage;
if (signedMessage != null) {
- signedMessage.Recipient = request.GetPublicFacingUrl();
- signedMessage.HttpMethod = request.HttpMethod;
+ signedMessage.Recipient = request.RequestUri;
+ signedMessage.HttpMethod = request.Method;
}
return message;
@@ -167,8 +171,8 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// <returns>
/// The deserialized message parts, if found. Null otherwise.
/// </returns>
- protected override IDictionary<string, string> ReadFromResponseCore(IncomingWebResponse response) {
- string body = response.GetResponseReader().ReadToEnd();
+ protected override async Task<IDictionary<string, string>> ReadFromResponseCoreAsync(HttpResponseMessage response, CancellationToken cancellationToken) {
+ string body = await response.Content.ReadAsStringAsync();
return HttpUtility.ParseQueryString(body).ToDictionary();
}
@@ -179,8 +183,8 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// <returns>
/// The <see cref="HttpRequest"/> prepared to send the request.
/// </returns>
- protected override HttpWebRequest CreateHttpRequest(IDirectedProtocolMessage request) {
- HttpWebRequest httpRequest;
+ protected override HttpRequestMessage CreateHttpRequest(IDirectedProtocolMessage request) {
+ HttpRequestMessage httpRequest;
HttpDeliveryMethods transmissionMethod = request.HttpMethods;
if ((transmissionMethod & HttpDeliveryMethods.AuthorizationHeaderRequest) != 0) {
@@ -200,6 +204,7 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
} else {
throw new NotSupportedException();
}
+
return httpRequest;
}
@@ -212,16 +217,12 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// <remarks>
/// This method implements spec V1.0 section 5.3.
/// </remarks>
- protected override OutgoingWebResponse PrepareDirectResponse(IProtocolMessage response) {
+ protected override HttpResponseMessage PrepareDirectResponse(IProtocolMessage response) {
var messageAccessor = this.MessageDescriptions.GetAccessor(response);
var fields = messageAccessor.Serialize();
- string responseBody = MessagingUtilities.CreateQueryString(fields);
- OutgoingWebResponse encodedResponse = new OutgoingWebResponse {
- Body = responseBody,
- OriginalMessage = response,
- Status = HttpStatusCode.OK,
- Headers = new System.Net.WebHeaderCollection(),
+ var encodedResponse = new HttpResponseMessage {
+ Content = new FormUrlEncodedContent(fields),
};
ApplyMessageTemplate(response, encodedResponse);
@@ -256,7 +257,7 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// </summary>
/// <param name="message">The message.</param>
/// <returns>"POST", "GET" or some other similar http verb.</returns>
- private static string GetHttpMethod(IDirectedProtocolMessage message) {
+ private static HttpMethod GetHttpMethod(IDirectedProtocolMessage message) {
Requires.NotNull(message, "message");
var signedMessage = message as ITamperResistantOAuthMessage;
@@ -273,11 +274,9 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// <param name="requestMessage">The message to be transmitted to the ServiceProvider.</param>
/// <returns>The web request ready to send.</returns>
/// <remarks>
- /// <para>If the message has non-empty ExtraData in it, the request stream is sent to
- /// the server automatically. If it is empty, the request stream must be sent by the caller.</para>
- /// <para>This method implements OAuth 1.0 section 5.2, item #1 (described in section 5.4).</para>
+ /// This method implements OAuth 1.0 section 5.2, item #1 (described in section 5.4).
/// </remarks>
- private HttpWebRequest InitializeRequestAsAuthHeader(IDirectedProtocolMessage requestMessage) {
+ private HttpRequestMessage InitializeRequestAsAuthHeader(IDirectedProtocolMessage requestMessage) {
var dictionary = this.MessageDescriptions.GetAccessor(requestMessage);
// copy so as to not modify original
@@ -285,41 +284,38 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
foreach (string key in dictionary.DeclaredKeys) {
fields.Add(key, dictionary[key]);
}
+
if (this.Realm != null) {
fields.Add("realm", this.Realm.AbsoluteUri);
}
- HttpWebRequest httpRequest;
UriBuilder recipientBuilder = new UriBuilder(requestMessage.Recipient);
bool hasEntity = HttpMethodHasEntity(GetHttpMethod(requestMessage));
if (!hasEntity) {
MessagingUtilities.AppendQueryArgs(recipientBuilder, requestMessage.ExtraData);
}
- httpRequest = (HttpWebRequest)WebRequest.Create(recipientBuilder.Uri);
+
+ var httpRequest = new HttpRequestMessage(GetHttpMethod(requestMessage), recipientBuilder.Uri);
this.PrepareHttpWebRequest(httpRequest);
- httpRequest.Method = GetHttpMethod(requestMessage);
- httpRequest.Headers.Add(HttpRequestHeader.Authorization, MessagingUtilities.AssembleAuthorizationHeader(Protocol.AuthorizationHeaderScheme, fields));
+ httpRequest.Headers.Authorization = new AuthenticationHeaderValue(Protocol.AuthorizationHeaderScheme, MessagingUtilities.AssembleAuthorizationHeader(fields));
if (hasEntity) {
- // WARNING: We only set up the request stream for the caller if there is
- // extra data. If there isn't any extra data, the caller must do this themselves.
var requestMessageWithBinaryData = requestMessage as IMessageWithBinaryData;
if (requestMessageWithBinaryData != null && requestMessageWithBinaryData.SendAsMultipart) {
// Include the binary data in the multipart entity, and any standard text extra message data.
// The standard declared message parts are included in the authorization header.
- var multiPartFields = new List<MultipartPostPart>(requestMessageWithBinaryData.BinaryData);
- multiPartFields.AddRange(requestMessage.ExtraData.Select(field => MultipartPostPart.CreateFormPart(field.Key, field.Value)));
- this.SendParametersInEntityAsMultipart(httpRequest, multiPartFields);
+ var content = InitializeMultipartFormDataContent(requestMessageWithBinaryData);
+ httpRequest.Content = content;
+
+ foreach (var extraData in requestMessage.ExtraData) {
+ content.Add(new StringContent(extraData.Value), extraData.Key);
+ }
} else {
ErrorUtilities.VerifyProtocol(requestMessageWithBinaryData == null || requestMessageWithBinaryData.BinaryData.Count == 0, MessagingStrings.BinaryDataRequiresMultipart);
if (requestMessage.ExtraData.Count > 0) {
- this.SendParametersInEntity(httpRequest, requestMessage.ExtraData);
- } else {
- // We'll assume the content length is zero since the caller may not have
- // anything. They're responsible to change it when the add the payload if they have one.
- httpRequest.ContentLength = 0;
+ httpRequest.Content = new FormUrlEncodedContent(requestMessage.ExtraData);
}
}
}
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthHttpMethodBindingElement.cs b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthHttpMethodBindingElement.cs
index 98eb9b3..29ef8d5 100644
--- a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthHttpMethodBindingElement.cs
+++ b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/OAuthHttpMethodBindingElement.cs
@@ -9,6 +9,8 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
using System.Collections.Generic;
using System.Linq;
using System.Text;
+ using System.Threading;
+ using System.Threading.Tasks;
using DotNetOpenAuth.Messaging;
/// <summary>
@@ -33,24 +35,25 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// Prepares a message for sending based on the rules of this channel binding element.
/// </summary>
/// <param name="message">The message to prepare for sending.</param>
+ /// <param name="cancellationToken">The cancellation token.</param>
/// <returns>
/// True if the <paramref name="message"/> applied to this binding element
/// and the operation was successful. False otherwise.
/// </returns>
- public MessageProtections? ProcessOutgoingMessage(IProtocolMessage message) {
+ public Task<MessageProtections?> ProcessOutgoingMessageAsync(IProtocolMessage message, CancellationToken cancellationToken) {
var oauthMessage = message as ITamperResistantOAuthMessage;
if (oauthMessage != null) {
HttpDeliveryMethods transmissionMethod = oauthMessage.HttpMethods;
try {
oauthMessage.HttpMethod = MessagingUtilities.GetHttpVerb(transmissionMethod);
- return MessageProtections.None;
+ return MessageProtectionTasks.None;
} catch (ArgumentException ex) {
Logger.OAuth.Error("Unrecognized HttpDeliveryMethods value.", ex);
- return null;
+ return MessageProtectionTasks.Null;
}
} else {
- return null;
+ return MessageProtectionTasks.Null;
}
}
@@ -59,6 +62,7 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// validates an incoming message based on the rules of this channel binding element.
/// </summary>
/// <param name="message">The incoming message to process.</param>
+ /// <param name="cancellationToken">The cancellation token.</param>
/// <returns>
/// True if the <paramref name="message"/> applied to this binding element
/// and the operation was successful. False if the operation did not apply to this message.
@@ -67,8 +71,8 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// Thrown when the binding element rules indicate that this message is invalid and should
/// NOT be processed.
/// </exception>
- public MessageProtections? ProcessIncomingMessage(IProtocolMessage message) {
- return null;
+ public Task<MessageProtections?> ProcessIncomingMessageAsync(IProtocolMessage message, CancellationToken cancellationToken) {
+ return MessageProtectionTasks.Null;
}
#endregion
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementBase.cs b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementBase.cs
index 780afdc..357ca45 100644
--- a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementBase.cs
+++ b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementBase.cs
@@ -12,6 +12,8 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
using System.Globalization;
using System.Linq;
using System.Text;
+ using System.Threading;
+ using System.Threading.Tasks;
using System.Web;
using DotNetOpenAuth.Messaging;
using DotNetOpenAuth.Messaging.Bindings;
@@ -79,11 +81,12 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// Signs the outgoing message.
/// </summary>
/// <param name="message">The message to sign.</param>
+ /// <param name="cancellationToken">The cancellation token.</param>
/// <returns>
/// The protections (if any) that this binding element applied to the message.
/// Null if this binding element did not even apply to this binding element.
/// </returns>
- public MessageProtections? ProcessOutgoingMessage(IProtocolMessage message) {
+ public Task<MessageProtections?> ProcessOutgoingMessageAsync(IProtocolMessage message, CancellationToken cancellationToken) {
var signedMessage = message as ITamperResistantOAuthMessage;
if (signedMessage != null && this.IsMessageApplicable(signedMessage)) {
if (this.SignatureCallback != null) {
@@ -95,29 +98,30 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
signedMessage.SignatureMethod = this.signatureMethod;
Logger.Bindings.DebugFormat("Signing {0} message using {1}.", message.GetType().Name, this.signatureMethod);
signedMessage.Signature = this.GetSignature(signedMessage);
- return MessageProtections.TamperProtection;
+ return MessageProtectionTasks.TamperProtection;
}
- return null;
+ return MessageProtectionTasks.Null;
}
/// <summary>
/// Verifies the signature on an incoming message.
/// </summary>
/// <param name="message">The message whose signature should be verified.</param>
+ /// <param name="cancellationToken">The cancellation token.</param>
/// <returns>
/// The protections (if any) that this binding element applied to the message.
/// Null if this binding element did not even apply to this binding element.
/// </returns>
/// <exception cref="InvalidSignatureException">Thrown if the signature is invalid.</exception>
- public MessageProtections? ProcessIncomingMessage(IProtocolMessage message) {
+ public Task<MessageProtections?> ProcessIncomingMessageAsync(IProtocolMessage message, CancellationToken cancellationToken) {
var signedMessage = message as ITamperResistantOAuthMessage;
if (signedMessage != null && this.IsMessageApplicable(signedMessage)) {
Logger.Bindings.DebugFormat("Verifying incoming {0} message signature of: {1}", message.GetType().Name, signedMessage.Signature);
if (!string.Equals(signedMessage.SignatureMethod, this.signatureMethod, StringComparison.Ordinal)) {
Logger.Bindings.WarnFormat("Expected signature method '{0}' but received message with a signature method of '{1}'.", this.signatureMethod, signedMessage.SignatureMethod);
- return MessageProtections.None;
+ return MessageProtectionTasks.None;
}
if (this.SignatureCallback != null) {
@@ -131,10 +135,10 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
throw new InvalidSignatureException(message);
}
- return MessageProtections.TamperProtection;
+ return MessageProtectionTasks.TamperProtection;
}
- return null;
+ return MessageProtectionTasks.Null;
}
#endregion
@@ -151,13 +155,13 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
[SuppressMessage("Microsoft.Maintainability", "CA1506:AvoidExcessiveClassCoupling", Justification = "Unavoidable")]
internal static string ConstructSignatureBaseString(ITamperResistantOAuthMessage message, MessageDictionary messageDictionary) {
Requires.NotNull(message, "message");
- Requires.NotNullOrEmpty(message.HttpMethod, "message.HttpMethod");
+ Requires.NotNull(message.HttpMethod, "message.HttpMethod");
Requires.NotNull(messageDictionary, "messageDictionary");
ErrorUtilities.VerifyInternal(messageDictionary.Message == message, "Message references are not equal.");
List<string> signatureBaseStringElements = new List<string>(3);
- signatureBaseStringElements.Add(message.HttpMethod.ToUpperInvariant());
+ signatureBaseStringElements.Add(message.HttpMethod.ToString().ToUpperInvariant());
// For multipart POST messages, only include the message parts that are NOT
// in the POST entity (those parts that may appear in an OAuth authorization header).
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementChain.cs b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementChain.cs
index 2b25566..c37d239 100644
--- a/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementChain.cs
+++ b/src/DotNetOpenAuth.OAuth/OAuth/ChannelElements/SigningBindingElementChain.cs
@@ -9,6 +9,8 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
using System.Collections.Generic;
using System.Linq;
using System.Text;
+ using System.Threading;
+ using System.Threading.Tasks;
using DotNetOpenAuth.Messaging;
using Validation;
@@ -86,14 +88,15 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// Prepares a message for sending based on the rules of this channel binding element.
/// </summary>
/// <param name="message">The message to prepare for sending.</param>
+ /// <param name="cancellationToken">The cancellation token.</param>
/// <returns>
/// The protections (if any) that this binding element applied to the message.
/// Null if this binding element did not even apply to this binding element.
/// </returns>
- public MessageProtections? ProcessOutgoingMessage(IProtocolMessage message) {
+ public async Task<MessageProtections?> ProcessOutgoingMessageAsync(IProtocolMessage message, CancellationToken cancellationToken) {
foreach (IChannelBindingElement signer in this.signers) {
ErrorUtilities.VerifyInternal(signer.Channel != null, "A binding element's Channel property is unexpectedly null.");
- MessageProtections? result = signer.ProcessOutgoingMessage(message);
+ MessageProtections? result = await signer.ProcessOutgoingMessageAsync(message, cancellationToken);
if (result.HasValue) {
return result;
}
@@ -107,14 +110,15 @@ namespace DotNetOpenAuth.OAuth.ChannelElements {
/// validates an incoming message based on the rules of this channel binding element.
/// </summary>
/// <param name="message">The incoming message to process.</param>
+ /// <param name="cancellationToken">The cancellation token.</param>
/// <returns>
/// The protections (if any) that this binding element applied to the message.
/// Null if this binding element did not even apply to this binding element.
/// </returns>
- public MessageProtections? ProcessIncomingMessage(IProtocolMessage message) {
+ public async Task<MessageProtections?> ProcessIncomingMessageAsync(IProtocolMessage message, CancellationToken cancellationToken) {
foreach (IChannelBindingElement signer in this.signers) {
ErrorUtilities.VerifyInternal(signer.Channel != null, "A binding element's Channel property is unexpectedly null.");
- MessageProtections? result = signer.ProcessIncomingMessage(message);
+ MessageProtections? result = await signer.ProcessIncomingMessageAsync(message, cancellationToken);
if (result.HasValue) {
return result;
}
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/Messages/AccessProtectedResourceRequest.cs b/src/DotNetOpenAuth.OAuth/OAuth/Messages/AccessProtectedResourceRequest.cs
index aeee649..9b698b9 100644
--- a/src/DotNetOpenAuth.OAuth/OAuth/Messages/AccessProtectedResourceRequest.cs
+++ b/src/DotNetOpenAuth.OAuth/OAuth/Messages/AccessProtectedResourceRequest.cs
@@ -8,6 +8,8 @@ namespace DotNetOpenAuth.OAuth.Messages {
using System;
using System.Collections.Generic;
using System.Diagnostics.CodeAnalysis;
+ using System.Net.Http;
+
using DotNetOpenAuth.Messaging;
/// <summary>
@@ -18,7 +20,7 @@ namespace DotNetOpenAuth.OAuth.Messages {
/// <summary>
/// A store for the binary data that is carried in the message.
/// </summary>
- private List<MultipartPostPart> binaryData = new List<MultipartPostPart>();
+ private List<MultipartContentMember> binaryData = new List<MultipartContentMember>();
/// <summary>
/// Initializes a new instance of the <see cref="AccessProtectedResourceRequest"/> class.
@@ -56,7 +58,7 @@ namespace DotNetOpenAuth.OAuth.Messages {
/// Gets the parts of the message that carry binary data.
/// </summary>
/// <value>A list of parts. Never null.</value>
- public IList<MultipartPostPart> BinaryData {
+ public IList<MultipartContentMember> BinaryData {
get { return this.binaryData; }
}
@@ -64,7 +66,7 @@ namespace DotNetOpenAuth.OAuth.Messages {
/// Gets a value indicating whether this message should be sent as multi-part POST.
/// </summary>
public bool SendAsMultipart {
- get { return this.HttpMethod == "POST" && this.BinaryData.Count > 0; }
+ get { return this.HttpMethod == HttpMethod.Post && this.BinaryData.Count > 0; }
}
#endregion
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/Messages/MessageBaseSimple.cs b/src/DotNetOpenAuth.OAuth/OAuth/Messages/MessageBaseSimple.cs
new file mode 100644
index 0000000..23822d3
--- /dev/null
+++ b/src/DotNetOpenAuth.OAuth/OAuth/Messages/MessageBaseSimple.cs
@@ -0,0 +1,10 @@
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+using System.Threading.Tasks;
+
+namespace DotNetOpenAuth.OAuth.Messages {
+ class MessageBaseSimple {
+ }
+}
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/Messages/SignedMessageBase.cs b/src/DotNetOpenAuth.OAuth/OAuth/Messages/SignedMessageBase.cs
index 6af75ec..7bc5b7d 100644
--- a/src/DotNetOpenAuth.OAuth/OAuth/Messages/SignedMessageBase.cs
+++ b/src/DotNetOpenAuth.OAuth/OAuth/Messages/SignedMessageBase.cs
@@ -8,6 +8,7 @@ namespace DotNetOpenAuth.OAuth.Messages {
using System;
using System.Collections.Generic;
using System.Diagnostics.CodeAnalysis;
+ using System.Net.Http;
using DotNetOpenAuth.Messaging;
using DotNetOpenAuth.Messaging.Bindings;
using DotNetOpenAuth.OAuth.ChannelElements;
@@ -75,7 +76,7 @@ namespace DotNetOpenAuth.OAuth.Messages {
/// <summary>
/// Gets or sets the HTTP method that will be used to transmit the message.
/// </summary>
- string ITamperResistantOAuthMessage.HttpMethod {
+ HttpMethod ITamperResistantOAuthMessage.HttpMethod {
get { return this.HttpMethod; }
set { this.HttpMethod = value; }
}
@@ -169,7 +170,7 @@ namespace DotNetOpenAuth.OAuth.Messages {
/// <summary>
/// Gets or sets the HTTP method that will be used to transmit the message.
/// </summary>
- protected string HttpMethod { get; set; }
+ protected HttpMethod HttpMethod { get; set; }
/// <summary>
/// Gets or sets the message signature.
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/Messages/UserAuthorizationRequest.cs b/src/DotNetOpenAuth.OAuth/OAuth/Messages/UserAuthorizationRequest.cs
index 4f98622..fd634da 100644
--- a/src/DotNetOpenAuth.OAuth/OAuth/Messages/UserAuthorizationRequest.cs
+++ b/src/DotNetOpenAuth.OAuth/OAuth/Messages/UserAuthorizationRequest.cs
@@ -62,7 +62,7 @@ namespace DotNetOpenAuth.OAuth.Messages {
}
/// <summary>
- /// Gets or sets the Request Token obtained in the previous step.
+ /// Gets the Request Token obtained in the previous step.
/// </summary>
/// <remarks>
/// The Service Provider MAY declare this parameter as REQUIRED, or
@@ -70,7 +70,7 @@ namespace DotNetOpenAuth.OAuth.Messages {
/// case it will prompt the User to enter it manually.
/// </remarks>
[MessagePart("oauth_token", IsRequired = false)]
- internal string RequestToken { get; set; }
+ public string RequestToken { get; internal set; }
/// <summary>
/// Gets or sets a URL the Service Provider will use to redirect the User back
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/Protocol.cs b/src/DotNetOpenAuth.OAuth/OAuth/Protocol.cs
index 72f0ff4..049fd58 100644
--- a/src/DotNetOpenAuth.OAuth/OAuth/Protocol.cs
+++ b/src/DotNetOpenAuth.OAuth/OAuth/Protocol.cs
@@ -60,6 +60,31 @@ namespace DotNetOpenAuth.OAuth {
internal const string AuthorizationHeaderScheme = "OAuth";
/// <summary>
+ /// The name of the 'oauth_callback' parameter.
+ /// </summary>
+ internal const string CallbackParameter = "oauth_callback";
+
+ /// <summary>
+ /// The name of the 'oauth_callback_confirmed' parameter.
+ /// </summary>
+ internal const string CallbackConfirmedParameter = "oauth_callback_confirmed";
+
+ /// <summary>
+ /// The name of the 'oauth_token' parameter.
+ /// </summary>
+ internal const string TokenParameter = "oauth_token";
+
+ /// <summary>
+ /// The name of the 'oauth_token_secret' parameter.
+ /// </summary>
+ internal const string TokenSecretParameter = "oauth_token_secret";
+
+ /// <summary>
+ /// The name of the 'oauth_verifier' parameter.
+ /// </summary>
+ internal const string VerifierParameter = "oauth_verifier";
+
+ /// <summary>
/// Gets the <see cref="Protocol"/> instance with values initialized for V1.0 of the protocol.
/// </summary>
internal static readonly Protocol V10 = new Protocol {
diff --git a/src/DotNetOpenAuth.OAuth/OAuth/ServiceProviderDescription.cs b/src/DotNetOpenAuth.OAuth/OAuth/ServiceProviderDescription.cs
deleted file mode 100644
index 6dbe6ea..0000000
--- a/src/DotNetOpenAuth.OAuth/OAuth/ServiceProviderDescription.cs
+++ /dev/null
@@ -1,101 +0,0 @@
-//-----------------------------------------------------------------------
-// <copyright file="ServiceProviderDescription.cs" company="Outercurve Foundation">
-// Copyright (c) Outercurve Foundation. All rights reserved.
-// </copyright>
-//-----------------------------------------------------------------------
-
-namespace DotNetOpenAuth.OAuth {
- using System;
- using System.Diagnostics;
- using System.Diagnostics.CodeAnalysis;
- using System.Linq;
- using DotNetOpenAuth.Messaging;
- using DotNetOpenAuth.OAuth.ChannelElements;
-
- /// <summary>
- /// A description of the endpoints on a Service Provider.
- /// </summary>
- public class ServiceProviderDescription {
- /// <summary>
- /// The field used to store the value of the <see cref="RequestTokenEndpoint"/> property.
- /// </summary>
- [DebuggerBrowsable(DebuggerBrowsableState.Never)]
- private MessageReceivingEndpoint requestTokenEndpoint;
-
- /// <summary>
- /// Initializes a new instance of the <see cref="ServiceProviderDescription"/> class.
- /// </summary>
- public ServiceProviderDescription() {
- this.ProtocolVersion = Protocol.Default.ProtocolVersion;
- }
-
- /// <summary>
- /// Gets or sets the OAuth version supported by the Service Provider.
- /// </summary>
- public ProtocolVersion ProtocolVersion { get; set; }
-
- /// <summary>
- /// Gets or sets the URL used to obtain an unauthorized Request Token,
- /// described in Section 6.1 (Obtaining an Unauthorized Request Token).
- /// </summary>
- /// <remarks>
- /// The request URL query MUST NOT contain any OAuth Protocol Parameters.
- /// This is the URL that <see cref="OAuth.Messages.UnauthorizedTokenRequest"/> messages are directed to.
- /// </remarks>
- /// <exception cref="ArgumentException">Thrown if this property is set to a URI with OAuth protocol parameters.</exception>
- public MessageReceivingEndpoint RequestTokenEndpoint {
- get {
- return this.requestTokenEndpoint;
- }
-
- set {
- if (value != null && UriUtil.QueryStringContainPrefixedParameters(value.Location, OAuth.Protocol.ParameterPrefix)) {
- throw new ArgumentException(OAuthStrings.RequestUrlMustNotHaveOAuthParameters);
- }
-
- this.requestTokenEndpoint = value;
- }
- }
-
- /// <summary>
- /// Gets or sets the URL used to obtain User authorization for Consumer access,
- /// described in Section 6.2 (Obtaining User Authorization).
- /// </summary>
- /// <remarks>
- /// This is the URL that <see cref="OAuth.Messages.UserAuthorizationRequest"/> messages are
- /// indirectly (via the user agent) sent to.
- /// </remarks>
- public MessageReceivingEndpoint UserAuthorizationEndpoint { get; set; }
-
- /// <summary>
- /// Gets or sets the URL used to exchange the User-authorized Request Token
- /// for an Access Token, described in Section 6.3 (Obtaining an Access Token).
- /// </summary>
- /// <remarks>
- /// This is the URL that <see cref="OAuth.Messages.AuthorizedTokenRequest"/> messages are directed to.
- /// </remarks>
- public MessageReceivingEndpoint AccessTokenEndpoint { get; set; }
-
- /// <summary>
- /// Gets or sets the signing policies that apply to this Service Provider.
- /// </summary>
- [SuppressMessage("Microsoft.Performance", "CA1819:PropertiesShouldNotReturnArrays", Justification = "Type initializers require this format.")]
- public ITamperProtectionChannelBindingElement[] TamperProtectionElements { get; set; }
-
- /// <summary>
- /// Gets the OAuth version supported by the Service Provider.
- /// </summary>
- internal Version Version {
- get { return Protocol.Lookup(this.ProtocolVersion).Version; }
- }
-
- /// <summary>
- /// Creates a signing element that includes all the signing elements this service provider supports.
- /// </summary>
- /// <returns>The created signing element.</returns>
- internal ITamperProtectionChannelBindingElement CreateTamperProtectionElement() {
- RequiresEx.ValidState(this.TamperProtectionElements != null);
- return new SigningBindingElementChain(this.TamperProtectionElements.Select(el => (ITamperProtectionChannelBindingElement)el.Clone()).ToArray());
- }
- }
-}
diff --git a/src/DotNetOpenAuth.OAuth/OAuthReporting.cs b/src/DotNetOpenAuth.OAuth/OAuthReporting.cs
deleted file mode 100644
index e2c0aab..0000000
--- a/src/DotNetOpenAuth.OAuth/OAuthReporting.cs
+++ /dev/null
@@ -1,56 +0,0 @@
-//-----------------------------------------------------------------------
-// <copyright file="OAuthReporting.cs" company="Outercurve Foundation">
-// Copyright (c) Outercurve Foundation. All rights reserved.
-// </copyright>
-//-----------------------------------------------------------------------
-
-namespace DotNetOpenAuth {
- using System;
- using System.Collections.Generic;
- using System.Linq;
- using System.Text;
- using DotNetOpenAuth.Messaging.Bindings;
- using DotNetOpenAuth.OAuth;
- using DotNetOpenAuth.OAuth.ChannelElements;
- using Validation;
-
- /// <summary>
- /// Utility methods specific to OAuth feature reporting.
- /// </summary>
- internal class OAuthReporting : Reporting {
- /// <summary>
- /// Records the feature and dependency use.
- /// </summary>
- /// <param name="value">The consumer or service provider.</param>
- /// <param name="service">The service.</param>
- /// <param name="tokenManager">The token manager.</param>
- /// <param name="nonceStore">The nonce store.</param>
- internal static void RecordFeatureAndDependencyUse(object value, ServiceProviderDescription service, ITokenManager tokenManager, INonceStore nonceStore) {
- Requires.NotNull(value, "value");
- Requires.NotNull(service, "service");
- Requires.NotNull(tokenManager, "tokenManager");
-
- // In release builds, just quietly return.
- if (value == null || service == null || tokenManager == null) {
- return;
- }
-
- if (Reporting.Enabled && Reporting.Configuration.IncludeFeatureUsage) {
- StringBuilder builder = new StringBuilder();
- builder.Append(value.GetType().Name);
- builder.Append(" ");
- builder.Append(tokenManager.GetType().Name);
- if (nonceStore != null) {
- builder.Append(" ");
- builder.Append(nonceStore.GetType().Name);
- }
- builder.Append(" ");
- builder.Append(service.Version);
- builder.Append(" ");
- builder.Append(service.UserAuthorizationEndpoint);
- Reporting.ObservedFeatures.Add(builder.ToString());
- Reporting.Touch();
- }
- }
- }
-}
diff --git a/src/DotNetOpenAuth.OAuth/packages.config b/src/DotNetOpenAuth.OAuth/packages.config
index 58890d8..d32d62f 100644
--- a/src/DotNetOpenAuth.OAuth/packages.config
+++ b/src/DotNetOpenAuth.OAuth/packages.config
@@ -1,4 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
<packages>
- <package id="Validation" version="2.0.1.12362" targetFramework="net45" />
+ <package id="Microsoft.Net.Http" version="2.0.20710.0" targetFramework="net45" />
+ <package id="Validation" version="2.0.2.13022" targetFramework="net45" />
</packages> \ No newline at end of file