/// <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> /// <param name="cancellationToken">The cancellation token.</param> /// <returns> /// The deserialized message, if one is found. Null otherwise. /// </returns> protected override async Task<IDirectedProtocolMessage> ReadFromRequestCoreAsync(HttpRequestMessage request, CancellationToken cancellationToken) { Requires.NotNull(request, "request"); var fields = new Dictionary<string, string>(); string accessToken; if ((accessToken = await SearchForBearerAccessTokenInRequestAsync(request, cancellationToken)) != null) { fields[Protocol.token_type] = Protocol.AccessTokenTypes.Bearer; fields[Protocol.access_token] = accessToken; } if (fields.Count > 0) { MessageReceivingEndpoint recipient; try { recipient = request.GetRecipient(); } catch (ArgumentException ex) { Logger.OAuth.WarnFormat("Unrecognized HTTP request: " + ex.ToString()); return null; } // Deserialize the message using all the data we've collected. var message = (IDirectedProtocolMessage)this.Receive(fields, recipient); return message; } return null; }
/// <summary> /// Searches an incoming HTTP request for data that could be used to assemble /// 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 async Task<IDirectedProtocolMessage> ReadFromRequestCoreAsync(HttpRequestMessage request, CancellationToken cancellationToken) { // First search the Authorization header. 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 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 = HttpUtility.ParseQueryString(request.RequestUri.Query); foreach (string key in qs) { if (key != null) { fields.Add(key, qs[key]); } else { Logger.OAuth.WarnFormat("Ignoring query string parameter '{0}' since it isn't a standard name=value parameter.", qs[key]); } } MessageReceivingEndpoint recipient; try { recipient = request.GetRecipient(); } catch (ArgumentException ex) { Logger.OAuth.WarnFormat("Unrecognized HTTP request: " + ex.ToString()); return null; } // Deserialize the message using all the data we've collected. var message = (IDirectedProtocolMessage)this.Receive(fields, recipient); // Add receiving HTTP transport information required for signature generation. var signedMessage = message as ITamperResistantOAuthMessage; if (signedMessage != null) { signedMessage.Recipient = request.RequestUri; signedMessage.HttpMethod = request.Method; } return message; }
/// <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> /// <param name="cancellationToken">The cancellation token.</param> /// <returns> /// The deserialized message, if one is found. Null otherwise. /// </returns> protected override async Task<IDirectedProtocolMessage> ReadFromRequestCoreAsync(HttpRequestMessage request, CancellationToken cancellationToken) { Requires.NotNull(request, "request"); Logger.Channel.DebugFormat("Incoming HTTP request: {0} {1}", request.Method, request.RequestUri.AbsoluteUri); var fields = HttpUtility.ParseQueryString(request.RequestUri.Query).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.RequestUri.Fragment; if (!string.IsNullOrEmpty(fragment)) { foreach (var pair in HttpUtility.ParseQueryString(fragment.Substring(1)).AsKeyValuePairs()) { 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> /// 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> /// <param name="cancellationToken">The cancellation token.</param> /// <returns> /// The deserialized message, if one is found. Null otherwise. /// </returns> protected override async Task<IDirectedProtocolMessage> ReadFromRequestCoreAsync(HttpRequestMessage request, CancellationToken cancellationToken) { Requires.NotNull(request, "request"); if (!string.IsNullOrEmpty(request.RequestUri.Fragment)) { var fields = HttpUtility.ParseQueryString(request.RequestUri.Fragment.Substring(1)).ToDictionary(); MessageReceivingEndpoint recipient; try { recipient = request.GetRecipient(); } catch (ArgumentException ex) { Logger.Messaging.WarnFormat("Unrecognized HTTP request: " + ex.ToString()); return null; } return (IDirectedProtocolMessage)this.Receive(fields, recipient); } return await base.ReadFromRequestCoreAsync(request, cancellationToken); }