summaryrefslogtreecommitdiffstats
path: root/src/DotNetOpenAuth
diff options
context:
space:
mode:
Diffstat (limited to 'src/DotNetOpenAuth')
-rw-r--r--src/DotNetOpenAuth/Configuration/UntrustedWebRequestElement.cs2
-rw-r--r--src/DotNetOpenAuth/Messaging/HttpRequestInfo.cs5
-rw-r--r--src/DotNetOpenAuth/Messaging/MessagingUtilities.cs25
-rw-r--r--src/DotNetOpenAuth/Messaging/OutgoingWebResponse.cs47
-rw-r--r--src/DotNetOpenAuth/Yadis/DiscoveryResult.cs2
-rw-r--r--src/DotNetOpenAuth/Yadis/Yadis.cs6
6 files changed, 76 insertions, 11 deletions
diff --git a/src/DotNetOpenAuth/Configuration/UntrustedWebRequestElement.cs b/src/DotNetOpenAuth/Configuration/UntrustedWebRequestElement.cs
index 461b8a8..89cd435 100644
--- a/src/DotNetOpenAuth/Configuration/UntrustedWebRequestElement.cs
+++ b/src/DotNetOpenAuth/Configuration/UntrustedWebRequestElement.cs
@@ -60,7 +60,7 @@ namespace DotNetOpenAuth.Configuration {
/// <summary>
/// Gets or sets the read/write timeout after which an HTTP request will fail.
/// </summary>
- [ConfigurationProperty(ReadWriteTimeoutConfigName, DefaultValue = "00:00:00.800")]
+ [ConfigurationProperty(ReadWriteTimeoutConfigName, DefaultValue = "00:00:01.500")]
[PositiveTimeSpanValidator]
public TimeSpan ReadWriteTimeout {
get { return (TimeSpan)this[ReadWriteTimeoutConfigName]; }
diff --git a/src/DotNetOpenAuth/Messaging/HttpRequestInfo.cs b/src/DotNetOpenAuth/Messaging/HttpRequestInfo.cs
index cfc122d..418f6b2 100644
--- a/src/DotNetOpenAuth/Messaging/HttpRequestInfo.cs
+++ b/src/DotNetOpenAuth/Messaging/HttpRequestInfo.cs
@@ -234,7 +234,10 @@ namespace DotNetOpenAuth.Messaging {
if (this.form == null) {
if (this.HttpMethod == "POST" && this.Headers[HttpRequestHeader.ContentType] == "application/x-www-form-urlencoded") {
StreamReader reader = new StreamReader(this.InputStream);
- long originalPosition = this.InputStream.Position;
+ long originalPosition = 0;
+ if (this.InputStream.CanSeek) {
+ originalPosition = this.InputStream.Position;
+ }
this.form = HttpUtility.ParseQueryString(reader.ReadToEnd());
if (this.InputStream.CanSeek) {
this.InputStream.Seek(originalPosition, SeekOrigin.Begin);
diff --git a/src/DotNetOpenAuth/Messaging/MessagingUtilities.cs b/src/DotNetOpenAuth/Messaging/MessagingUtilities.cs
index 852d79d..c024cdc 100644
--- a/src/DotNetOpenAuth/Messaging/MessagingUtilities.cs
+++ b/src/DotNetOpenAuth/Messaging/MessagingUtilities.cs
@@ -184,6 +184,31 @@ namespace DotNetOpenAuth.Messaging {
}
/// <summary>
+ /// Adds a set of HTTP headers to an <see cref="HttpResponse"/> instance,
+ /// taking care to set some headers to the appropriate properties of
+ /// <see cref="HttpResponse" />
+ /// </summary>
+ /// <param name="headers">The headers to add.</param>
+ /// <param name="response">The <see cref="HttpListenerResponse"/> instance to set the appropriate values to.</param>
+ internal static void ApplyHeadersToResponse(WebHeaderCollection headers, HttpListenerResponse response) {
+ ErrorUtilities.VerifyArgumentNotNull(headers, "headers");
+ ErrorUtilities.VerifyArgumentNotNull(response, "response");
+
+ foreach (string headerName in headers) {
+ switch (headerName) {
+ case "Content-Type":
+ response.ContentType = headers[HttpResponseHeader.ContentType];
+ break;
+
+ // Add more special cases here as necessary.
+ default:
+ response.AddHeader(headerName, headers[headerName]);
+ break;
+ }
+ }
+ }
+
+ /// <summary>
/// Copies the contents of one stream to another.
/// </summary>
/// <param name="copyFrom">The stream to copy from, at the position where copying should begin.</param>
diff --git a/src/DotNetOpenAuth/Messaging/OutgoingWebResponse.cs b/src/DotNetOpenAuth/Messaging/OutgoingWebResponse.cs
index 55cb4b6..bad582c 100644
--- a/src/DotNetOpenAuth/Messaging/OutgoingWebResponse.cs
+++ b/src/DotNetOpenAuth/Messaging/OutgoingWebResponse.cs
@@ -123,23 +123,56 @@ namespace DotNetOpenAuth.Messaging {
Contract.Requires(HttpContext.Current != null);
ErrorUtilities.VerifyHttpContext();
- HttpContext.Current.Response.Clear();
- HttpContext.Current.Response.StatusCode = (int)this.Status;
- MessagingUtilities.ApplyHeadersToResponse(this.Headers, HttpContext.Current.Response);
+ this.Send(HttpContext.Current);
+ }
+
+ /// <summary>
+ /// Automatically sends the appropriate response to the user agent
+ /// and ends execution on the current page or handler.
+ /// </summary>
+ /// <param name="context">The context of the HTTP request whose response should be set.
+ /// Typically this is <see cref="HttpContext.Current"/>.</param>
+ /// <exception cref="ThreadAbortException">Thrown by ASP.NET in order to prevent additional data from the page being sent to the client and corrupting the response.</exception>
+ public virtual void Send(HttpContext context) {
+ Contract.Requires(context != null);
+ ErrorUtilities.VerifyArgumentNotNull(context, "context");
+
+ context.Response.Clear();
+ context.Response.StatusCode = (int)this.Status;
+ MessagingUtilities.ApplyHeadersToResponse(this.Headers, context.Response);
if (this.ResponseStream != null) {
try {
- this.ResponseStream.CopyTo(HttpContext.Current.Response.OutputStream);
+ this.ResponseStream.CopyTo(context.Response.OutputStream);
} catch (HttpException ex) {
- if (ex.ErrorCode == -2147467259 && HttpContext.Current.Response.Output != null) {
+ if (ex.ErrorCode == -2147467259 && context.Response.Output != null) {
// Test scenarios can generate this, since the stream is being spoofed:
// System.Web.HttpException: OutputStream is not available when a custom TextWriter is used.
- HttpContext.Current.Response.Output.Write(this.Body);
+ context.Response.Output.Write(this.Body);
} else {
throw;
}
}
}
- HttpContext.Current.Response.End();
+
+ context.Response.End();
+ }
+
+ /// <summary>
+ /// Automatically sends the appropriate response to the user agent.
+ /// </summary>
+ /// <param name="response">The response to set to this message.</param>
+ public virtual void Send(HttpListenerResponse response) {
+ Contract.Requires(response != null);
+ ErrorUtilities.VerifyArgumentNotNull(response, "response");
+
+ response.StatusCode = (int)this.Status;
+ MessagingUtilities.ApplyHeadersToResponse(this.Headers, response);
+ if (this.ResponseStream != null) {
+ response.ContentLength64 = this.ResponseStream.Length;
+ this.ResponseStream.CopyTo(response.OutputStream);
+ }
+
+ response.OutputStream.Close();
}
/// <summary>
diff --git a/src/DotNetOpenAuth/Yadis/DiscoveryResult.cs b/src/DotNetOpenAuth/Yadis/DiscoveryResult.cs
index 90495e2..01dae40 100644
--- a/src/DotNetOpenAuth/Yadis/DiscoveryResult.cs
+++ b/src/DotNetOpenAuth/Yadis/DiscoveryResult.cs
@@ -28,7 +28,7 @@ namespace DotNetOpenAuth.Yadis {
if (finalResponse == null) {
this.ContentType = initialResponse.ContentType;
this.ResponseText = initialResponse.GetResponseString();
- this.IsXrds = ContentType.MediaType == ContentTypes.Xrds;
+ this.IsXrds = this.ContentType != null && this.ContentType.MediaType == ContentTypes.Xrds;
} else {
this.ContentType = finalResponse.ContentType;
this.ResponseText = finalResponse.GetResponseString();
diff --git a/src/DotNetOpenAuth/Yadis/Yadis.cs b/src/DotNetOpenAuth/Yadis/Yadis.cs
index c3ae307..98bffc9 100644
--- a/src/DotNetOpenAuth/Yadis/Yadis.cs
+++ b/src/DotNetOpenAuth/Yadis/Yadis.cs
@@ -76,7 +76,7 @@ namespace DotNetOpenAuth.Yadis {
Logger.Yadis.DebugFormat("{0} found in HTTP header. Preparing to pull XRDS from {1}", HeaderName, url);
}
}
- if (url == null && response.ContentType.MediaType == ContentTypes.Html) {
+ if (url == null && response.ContentType != null && response.ContentType.MediaType == ContentTypes.Html) {
url = FindYadisDocumentLocationInHtmlMetaTags(response.GetResponseString());
if (url != null) {
Logger.Yadis.DebugFormat("{0} found in HTML Http-Equiv tag. Preparing to pull XRDS from {1}", HeaderName, url);
@@ -152,6 +152,10 @@ namespace DotNetOpenAuth.Yadis {
/// <c>true</c> if the response constains an XRDS document; otherwise, <c>false</c>.
/// </returns>
private static bool IsXrdsDocument(CachedDirectWebResponse response) {
+ if (response.ContentType == null) {
+ return false;
+ }
+
if (response.ContentType.MediaType == ContentTypes.Xrds) {
return true;
}