1
//-----------------------------------------------------------------------
2 // <copyright file="HttpRequestInfo.cs" company="Andrew Arnott">
3 // Copyright (c) Andrew Arnott. All rights reserved.
5 //-----------------------------------------------------------------------
7 namespace DotNetOpenAuth
.Messaging
{
9 using System
.Collections
.Specialized
;
10 using System
.Diagnostics
;
13 using System
.ServiceModel
.Channels
;
17 /// A property store of details of an incoming HTTP request.
20 /// This serves a very similar purpose to <see cref="HttpRequest"/>, except that
21 /// ASP.NET does not let us fully initialize that class, so we have to write one
24 public class HttpRequestInfo
{
26 /// The key/value pairs found in the entity of a POST request.
28 private NameValueCollection form
;
31 /// The key/value pairs found in the querystring of the incoming request.
33 private NameValueCollection queryString
;
36 /// Initializes a new instance of the <see cref="HttpRequestInfo"/> class.
38 internal HttpRequestInfo() {
42 /// Initializes a new instance of the <see cref="HttpRequestInfo"/> class.
44 /// <param name="request">The ASP.NET structure to copy from.</param>
45 internal HttpRequestInfo(HttpRequest request
) {
46 if (request
== null) {
47 throw new ArgumentNullException("request");
50 this.HttpMethod
= request
.HttpMethod
;
51 this.Url
= request
.Url
;
52 this.Headers
= GetHeaderCollection(request
.Headers
);
53 this.InputStream
= request
.InputStream
;
55 // These values would normally be calculated, but we'll reuse them from
56 // HttpRequest since they're already calculated, and there's a chance (<g>)
57 // that ASP.NET does a better job of being comprehensive about gathering
59 this.form
= request
.Form
;
60 this.queryString
= request
.QueryString
;
64 /// Initializes a new instance of the <see cref="HttpRequestInfo"/> class.
66 /// <param name="request">The WCF incoming request structure to get the HTTP information from.</param>
67 /// <param name="requestUri">The URI of the service endpoint.</param>
68 internal HttpRequestInfo(HttpRequestMessageProperty request
, Uri requestUri
) {
69 if (request
== null) {
70 throw new ArgumentNullException("request");
73 this.HttpMethod
= request
.Method
;
74 this.Headers
= request
.Headers
;
75 this.Url
= requestUri
;
79 /// Initializes a new instance of the <see cref="HttpRequestInfo"/> class.
81 /// <param name="request">The HttpWebRequest (that was never used) to copy from.</param>
82 internal HttpRequestInfo(WebRequest request
) {
83 this.HttpMethod
= request
.Method
;
84 this.Url
= request
.RequestUri
;
85 this.Headers
= GetHeaderCollection(request
.Headers
);
86 this.InputStream
= null;
90 /// Initializes a new instance of the <see cref="HttpRequestInfo"/> class.
92 /// <param name="message">The message being passed in through a mock transport.</param>
93 internal HttpRequestInfo(IDirectedProtocolMessage message
) {
94 this.Message
= message
;
98 /// Gets or sets the message that is being sent over a mock transport (for testing).
100 internal IDirectedProtocolMessage Message { get; set; }
103 /// Gets or sets the verb in the request (i.e. GET, POST, etc.)
105 internal string HttpMethod { get; set; }
108 /// Gets or sets the entire URL of the request.
110 internal Uri Url { get; set; }
113 /// Gets the query part of the URL (The ? and everything after it).
115 internal string Query
{
116 get { return this.Url != null ? this.Url.Query : null; }
120 /// Gets or sets the collection of headers that came in with the request.
122 internal WebHeaderCollection Headers { get; set; }
125 /// Gets or sets the entity, or body of the request, if any.
127 internal Stream InputStream { get; set; }
130 /// Gets the key/value pairs found in the entity of a POST request.
132 internal NameValueCollection Form
{
134 if (this.form
== null) {
135 if (this.HttpMethod
== "POST" && this.Headers
[HttpRequestHeader
.ContentType
] == "application/x-www-form-urlencoded") {
136 StreamReader reader
= new StreamReader(this.InputStream
);
137 long originalPosition
= this.InputStream
.Position
;
138 this.form
= HttpUtility
.ParseQueryString(reader
.ReadToEnd());
139 if (this.InputStream
.CanSeek
) {
140 this.InputStream
.Seek(originalPosition
, SeekOrigin
.Begin
);
143 this.form
= new NameValueCollection();
152 /// Gets the key/value pairs found in the querystring of the incoming request.
154 internal NameValueCollection QueryString
{
156 if (this.queryString
== null) {
157 this.queryString
= HttpUtility
.ParseQueryString(this.Query
);
160 return this.queryString
;
165 /// Converts a NameValueCollection to a WebHeaderCollection.
167 /// <param name="pairs">The collection a HTTP headers.</param>
168 /// <returns>A new collection of the given headers.</returns>
169 private static WebHeaderCollection
GetHeaderCollection(NameValueCollection pairs
) {
170 Debug
.Assert(pairs
!= null, "pairs == null");
172 WebHeaderCollection headers
= new WebHeaderCollection();
173 foreach (string key
in pairs
) {
174 headers
.Add(key
, pairs
[key
]);