<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>https://sarwiki.informatik.hu-berlin.de/index.php?action=history&amp;feed=atom&amp;title=ReverseProxy.cs</id>
	<title>ReverseProxy.cs - Revision history</title>
	<link rel="self" type="application/atom+xml" href="https://sarwiki.informatik.hu-berlin.de/index.php?action=history&amp;feed=atom&amp;title=ReverseProxy.cs"/>
	<link rel="alternate" type="text/html" href="https://sarwiki.informatik.hu-berlin.de/index.php?title=ReverseProxy.cs&amp;action=history"/>
	<updated>2026-04-28T21:27:13Z</updated>
	<subtitle>Revision history for this page on the wiki</subtitle>
	<generator>MediaWiki 1.43.8</generator>
	<entry>
		<id>https://sarwiki.informatik.hu-berlin.de/index.php?title=ReverseProxy.cs&amp;diff=5584&amp;oldid=prev</id>
		<title>Wolfm at 07:29, 12 May 2006</title>
		<link rel="alternate" type="text/html" href="https://sarwiki.informatik.hu-berlin.de/index.php?title=ReverseProxy.cs&amp;diff=5584&amp;oldid=prev"/>
		<updated>2006-05-12T07:29:48Z</updated>

		<summary type="html">&lt;p&gt;&lt;/p&gt;
&lt;p&gt;&lt;b&gt;New page&lt;/b&gt;&lt;/p&gt;&lt;div&gt;&amp;lt;pre&amp;gt;&amp;lt;nowiki&amp;gt;using System;&lt;br /&gt;
using System.Collections;&lt;br /&gt;
using System.Configuration;&lt;br /&gt;
using System.Diagnostics;&lt;br /&gt;
using System.Web;&lt;br /&gt;
using System.Web.SessionState;&lt;br /&gt;
using System.Net;&lt;br /&gt;
using System.Text;&lt;br /&gt;
using System.Text.RegularExpressions;&lt;br /&gt;
using System.IO;&lt;br /&gt;
using ICSharpCode.SharpZipLib.GZip;&lt;br /&gt;
using ICSharpCode.SharpZipLib.Zip.Compression.Streams;&lt;br /&gt;
&lt;br /&gt;
namespace ReverseProxy {&lt;br /&gt;
	class HandlerFactory : IHttpHandlerFactory {&lt;br /&gt;
		ReverseProxy reverseProxy;&lt;br /&gt;
&lt;br /&gt;
		public IHttpHandler GetHandler(HttpContext context, string requestType, String url, String pathTranslated) {&lt;br /&gt;
			if (url.EndsWith(&amp;quot;logon.aspx&amp;quot;))&lt;br /&gt;
				return System.Web.UI.PageParser.GetCompiledPageInstance(url, pathTranslated, context);&lt;br /&gt;
			else&lt;br /&gt;
				return ReverseProxy;&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		public void ReleaseHandler(IHttpHandler handler) { }&lt;br /&gt;
&lt;br /&gt;
		public ReverseProxy ReverseProxy {&lt;br /&gt;
			get {&lt;br /&gt;
				if (reverseProxy == null)&lt;br /&gt;
					reverseProxy = new ReverseProxy();&lt;br /&gt;
&lt;br /&gt;
				return reverseProxy;&lt;br /&gt;
			}&lt;br /&gt;
		}&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
	public class ReverseProxy: IHttpHandler, IRequiresSessionState {&lt;br /&gt;
		const int MaximumRedirections = 0;&lt;br /&gt;
&lt;br /&gt;
		string backEndSite {&lt;br /&gt;
			get {&lt;br /&gt;
				return ConfigurationSettings.AppSettings[&amp;quot;BackEndSite&amp;quot;];&lt;br /&gt;
			}&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		string convertBackEndToFrontEndHtml(string html, string frontEndServerName, string frontEndVirtualPath, string backEndSite) {&lt;br /&gt;
			/*&lt;br /&gt;
		  prepend frontEndVirtualPath to fix up relative urls as follows: (avoiding &amp;quot;value=&amp;quot; tokens which&lt;br /&gt;
		  are most likely html input text boxes)&lt;br /&gt;
&lt;br /&gt;
		  href=&amp;quot;/targetPath&amp;quot;	-&amp;gt;	href=&amp;quot;/frontEndVirtualPath/targetPath&amp;quot;&lt;br /&gt;
		  href=&amp;#039;/targetPath&amp;#039;	-&amp;gt;	href=&amp;quot;/frontEndVirtualPath/targetPath&amp;quot;		(handle single quoted urls too)&lt;br /&gt;
			*/&lt;br /&gt;
&lt;br /&gt;
			html = Regex.Replace(html, &amp;quot;(?&amp;lt;!value=)(?:\&amp;quot;|&amp;#039;)/(\\S*?)(?:\&amp;quot;|&amp;#039;)&amp;quot;, &amp;quot;\&amp;quot;&amp;quot; + frontEndVirtualPath + &amp;quot;/&amp;quot; + &amp;quot;$1&amp;quot; + &amp;quot;\&amp;quot;&amp;quot;, RegexOptions.Multiline | RegexOptions.IgnoreCase);&lt;br /&gt;
&lt;br /&gt;
			/*&lt;br /&gt;
		  also fixup url references in css as follows:&lt;br /&gt;
&lt;br /&gt;
		  style=&amp;quot;background-image: url(/targetPath/myimage.gif)&amp;quot; -&amp;gt; style=&amp;quot;background-image: url(/frontEndVirtualPath/targetPath/myimage.gif)&amp;quot;&lt;br /&gt;
			*/&lt;br /&gt;
&lt;br /&gt;
			html = Regex.Replace(html, @&amp;quot;(?:url\()/(\S*?)(?:\))&amp;quot;, &amp;quot;url(&amp;quot; + frontEndVirtualPath + &amp;quot;/&amp;quot; + &amp;quot;$1)&amp;quot;, RegexOptions.Multiline | RegexOptions.IgnoreCase);&lt;br /&gt;
&lt;br /&gt;
			/*&lt;br /&gt;
		  also fixup absolute urls and absolute encoded urls as follows:&lt;br /&gt;
&lt;br /&gt;
		  http://backEndSite/targetPath/images/myimage.gif --&amp;gt; http://frontEndServerName/frontEndVirtualPath/targetPath/images/myimage.gif&lt;br /&gt;
			*/&lt;br /&gt;
&lt;br /&gt;
			html = Regex.Replace(html, backEndSite, frontEndServerName + frontEndVirtualPath, RegexOptions.Multiline | RegexOptions.IgnoreCase);&lt;br /&gt;
			html = Regex.Replace(html, HttpContext.Current.Server.UrlEncode(backEndSite), HttpContext.Current.Server.UrlEncode(frontEndServerName + frontEndVirtualPath), RegexOptions.Multiline | RegexOptions.IgnoreCase);&lt;br /&gt;
&lt;br /&gt;
			/*&lt;br /&gt;
		  also fixes up strings with &amp;quot;src&amp;quot; and any other token to the left of the equal sign as follows:&lt;br /&gt;
&lt;br /&gt;
		  src=/  -&amp;gt;  src=frontEndVirtualPath/&lt;br /&gt;
			*/&lt;br /&gt;
&lt;br /&gt;
			html = html.Replace(&amp;quot;=/&amp;quot;,&amp;quot;=&amp;quot; + frontEndVirtualPath + &amp;quot;/&amp;quot;);&lt;br /&gt;
			return html;&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		void convertBackEndToFrontEndResponse(HttpWebResponse backEndResponse, HttpRequest frontEndRequest, HttpResponse frontEndResponse) {&lt;br /&gt;
			try {&lt;br /&gt;
				Stream backEndResponseStream = getStream(backEndResponse);&lt;br /&gt;
&lt;br /&gt;
				write(&amp;quot;Content Type of response is [&amp;quot; + backEndResponse.ContentType + &amp;quot;]&amp;quot;);&lt;br /&gt;
				frontEndResponse.ContentType = backEndResponse.ContentType;&lt;br /&gt;
				foreach(Cookie each in backEndResponse.Cookies) {&lt;br /&gt;
					if (frontEndResponse.Cookies[each.Name] != null)&lt;br /&gt;
						frontEndResponse.Cookies.Remove(each.Name);&lt;br /&gt;
&lt;br /&gt;
					HttpCookie cookie = new HttpCookie(each.Name, each.Value);&lt;br /&gt;
&lt;br /&gt;
					if (each.Domain.IndexOf(&amp;#039;.&amp;#039;) != -1) // Add domain only if it is dotted - IE doesn&amp;#039;t send back the cookie if we set the domain otherwise&lt;br /&gt;
						cookie.Domain = frontEndRequest.Url.Host;&lt;br /&gt;
&lt;br /&gt;
					cookie.Expires = each.Expires;&lt;br /&gt;
					cookie.Path = each.Path;&lt;br /&gt;
					cookie.Secure = each.Secure;&lt;br /&gt;
					frontEndResponse.Cookies.Add(cookie);&lt;br /&gt;
				}&lt;br /&gt;
&lt;br /&gt;
				if ((backEndResponse.ContentType.ToLower().IndexOf(&amp;quot;html&amp;quot;) &amp;gt;= 0) || (backEndResponse.ContentType.ToLower().IndexOf(&amp;quot;javascript&amp;quot;)&amp;gt;=0)) {&lt;br /&gt;
					StreamReader backEndResponseStreamReader = new StreamReader(backEndResponseStream, Encoding.Default);&lt;br /&gt;
					string backEndResponseHtml = backEndResponseStreamReader.ReadToEnd();&lt;br /&gt;
&lt;br /&gt;
					write(&amp;quot;********* Start of Raw Backend Response *********&amp;quot;);&lt;br /&gt;
					write(backEndResponseHtml);&lt;br /&gt;
					write(&amp;quot;********* End of Raw Backend Response / Start of Converted Frontend Response *********&amp;quot;);&lt;br /&gt;
					try {&lt;br /&gt;
						string frontEndHtml = convertBackEndToFrontEndHtml(backEndResponseHtml, frontEndRequest.Url.GetLeftPart(UriPartial.Authority), frontEndRequest.ApplicationPath, backEndSite);&lt;br /&gt;
						write(frontEndHtml);&lt;br /&gt;
						write(&amp;quot;********* End of Converted Frontend Response *********&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
						frontEndResponse.ContentEncoding = encodingFor(backEndResponse.ContentEncoding);&lt;br /&gt;
						write(&amp;quot;Content Encoding for response is [&amp;quot; + frontEndResponse.ContentEncoding.ToString() + &amp;quot;]&amp;quot;);&lt;br /&gt;
						frontEndResponse.Write(frontEndHtml);&lt;br /&gt;
					}&lt;br /&gt;
					finally {&lt;br /&gt;
						backEndResponseStreamReader.Close();&lt;br /&gt;
					}&lt;br /&gt;
				}&lt;br /&gt;
				else {&lt;br /&gt;
					write(&amp;quot;Sending opaque content back without modification&amp;quot;);&lt;br /&gt;
					if (backEndResponse.ContentEncoding.Length &amp;gt; 0) {&lt;br /&gt;
						write(&amp;quot;Content Encoding for response is [&amp;quot; + backEndResponse.ContentEncoding + &amp;quot;]&amp;quot;);&lt;br /&gt;
						frontEndResponse.AppendHeader(&amp;quot;Content-Encoding&amp;quot;, backEndResponse.ContentEncoding);&lt;br /&gt;
					}&lt;br /&gt;
&lt;br /&gt;
					copyStream(backEndResponseStream, frontEndResponse.OutputStream);&lt;br /&gt;
				}&lt;br /&gt;
			}&lt;br /&gt;
			finally {&lt;br /&gt;
				write(&amp;quot;End processing of request&amp;quot;);&lt;br /&gt;
				backEndResponse.Close();&lt;br /&gt;
				frontEndResponse.End();&lt;br /&gt;
			}&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		Uri convertFrontEndToBackEndUrl(Uri frontEndUrl, string frontEndVirtualPath, string backEndSite) {&lt;br /&gt;
			return new Uri(Regex.Replace(frontEndUrl.AbsoluteUri, frontEndUrl.GetLeftPart(UriPartial.Authority) + frontEndVirtualPath, backEndSite, RegexOptions.IgnoreCase));&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		void copyStream(Stream input, Stream output) {&lt;br /&gt;
			Byte[] buffer = new byte[1024];&lt;br /&gt;
			int bytes = 0;&lt;br /&gt;
&lt;br /&gt;
			while( (bytes = input.Read(buffer, 0, 1024) ) &amp;gt; 0 )&lt;br /&gt;
				output.Write(buffer, 0, bytes);&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		HttpWebRequest createProxyRequest(HttpRequest originalRequest, Uri uri, string method) {&lt;br /&gt;
			HttpWebRequest proxyRequest = (HttpWebRequest)WebRequest.Create(uri);&lt;br /&gt;
			proxyRequest.Timeout = 3600000; // 1 hour max wait time for request to complete&lt;br /&gt;
			proxyRequest.ContentType = originalRequest.ContentType;&lt;br /&gt;
			proxyRequest.UserAgent = originalRequest.UserAgent;&lt;br /&gt;
			proxyRequest.CookieContainer = new CookieContainer();&lt;br /&gt;
&lt;br /&gt;
			foreach(String each in originalRequest.Headers) {&lt;br /&gt;
				if (!WebHeaderCollection.IsRestricted(each))&lt;br /&gt;
					proxyRequest.Headers.Add(each, originalRequest.Headers.Get(each));&lt;br /&gt;
			}&lt;br /&gt;
&lt;br /&gt;
			proxyRequest.Method = method;&lt;br /&gt;
			if (method == &amp;quot;POST&amp;quot; &amp;amp;&amp;amp; originalRequest.ContentLength &amp;gt; 0) {&lt;br /&gt;
				write(&amp;quot;Sending POST data&amp;quot;);&lt;br /&gt;
				Stream outputStream = proxyRequest.GetRequestStream();&lt;br /&gt;
				copyStream(originalRequest.InputStream, outputStream);&lt;br /&gt;
				outputStream.Close();&lt;br /&gt;
			}&lt;br /&gt;
&lt;br /&gt;
			proxyRequest.AllowAutoRedirect = false;&lt;br /&gt;
&lt;br /&gt;
			if (HttpContext.Current.Session != null &amp;amp;&amp;amp; HttpContext.Current.Session.Count == 2) {&lt;br /&gt;
				write(&amp;quot;Sending basic logon credentials stored in session&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
				// if we performed basic auth via this reverse proxy and the userid / passwd are stored in the current session then use these auth credentials&lt;br /&gt;
				proxyRequest.PreAuthenticate = true;&lt;br /&gt;
				proxyRequest.Credentials = new NetworkCredential(HttpContext.Current.Session[&amp;quot;userid&amp;quot;].ToString(), HttpContext.Current.Session[&amp;quot;passwd&amp;quot;].ToString());&lt;br /&gt;
			}&lt;br /&gt;
			else if(HttpContext.Current.User.Identity.IsAuthenticated) {&lt;br /&gt;
				// user is already authenticated, therefore use the current ticket when accessing backend server -- should work with both Basic &amp;amp; NTLM auth&lt;br /&gt;
				write(&amp;quot;Sending current authentication ticket that is already in place with backend&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
				proxyRequest.PreAuthenticate = true;&lt;br /&gt;
				proxyRequest.Credentials = CredentialCache.DefaultCredentials;&lt;br /&gt;
			}&lt;br /&gt;
			return proxyRequest;&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		Encoding encodingFor(string codeName) {&lt;br /&gt;
			try {&lt;br /&gt;
				return Encoding.GetEncoding(codeName);&lt;br /&gt;
			}&lt;br /&gt;
			catch(Exception) {&lt;br /&gt;
				return Encoding.Default;&lt;br /&gt;
			}&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		Stream getStream(HttpWebResponse response) {&lt;br /&gt;
			Stream compressedStream = null;&lt;br /&gt;
			if (response.ContentEncoding == &amp;quot;gzip&amp;quot;) {&lt;br /&gt;
				write(&amp;quot;Decompressing gzipped response&amp;quot;);&lt;br /&gt;
				compressedStream =  new GZipInputStream(response.GetResponseStream());&lt;br /&gt;
			}&lt;br /&gt;
			else if (response.ContentEncoding == &amp;quot;deflate&amp;quot;) {&lt;br /&gt;
				write(&amp;quot;Decompressing deflated response&amp;quot;);&lt;br /&gt;
				compressedStream = new InflaterInputStream(response.GetResponseStream());&lt;br /&gt;
			}&lt;br /&gt;
			if (compressedStream != null) {&lt;br /&gt;
				MemoryStream decompressedStream = new MemoryStream();&lt;br /&gt;
				int size = 2048;&lt;br /&gt;
				byte[] writeData = new byte[2048];&lt;br /&gt;
				while (true) {&lt;br /&gt;
					size = compressedStream.Read(writeData, 0, size);&lt;br /&gt;
					if (size &amp;gt; 0)&lt;br /&gt;
						decompressedStream.Write(writeData,0,size);&lt;br /&gt;
					else&lt;br /&gt;
						break;&lt;br /&gt;
				}&lt;br /&gt;
				decompressedStream.Seek(0, SeekOrigin.Begin);&lt;br /&gt;
				return decompressedStream;&lt;br /&gt;
			}&lt;br /&gt;
			else&lt;br /&gt;
				return response.GetResponseStream();&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		bool isRedirection(HttpStatusCode code) {&lt;br /&gt;
			string statusCode = Enum.Format(typeof(HttpStatusCode), code, &amp;quot;d&amp;quot;);&lt;br /&gt;
			return statusCode.StartsWith(&amp;quot;3&amp;quot;);&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		public bool IsReusable {&lt;br /&gt;
			get {&lt;br /&gt;
				return true;&lt;br /&gt;
			}&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		string methodToUse(HttpRequest originalRequest, HttpWebResponse response) {&lt;br /&gt;
			if (response == null) {&lt;br /&gt;
				write(&amp;quot;Request is a &amp;quot; + originalRequest.HttpMethod);&lt;br /&gt;
				return originalRequest.HttpMethod;&lt;br /&gt;
			}&lt;br /&gt;
&lt;br /&gt;
			if (originalRequest.HttpMethod == &amp;quot;POST&amp;quot; &amp;amp;&amp;amp; (response.StatusCode == HttpStatusCode.RedirectKeepVerb || response.StatusCode == HttpStatusCode.TemporaryRedirect)) {&lt;br /&gt;
				write(&amp;quot;Request is a POST&amp;quot;);&lt;br /&gt;
				return &amp;quot;POST&amp;quot;;&lt;br /&gt;
			}&lt;br /&gt;
			else {&lt;br /&gt;
				write(&amp;quot;Request is a GET&amp;quot;);&lt;br /&gt;
				return &amp;quot;GET&amp;quot;;&lt;br /&gt;
			}&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		string parseRealm(string authHeader) {&lt;br /&gt;
			Regex regex = new Regex(&amp;quot;.*=\\\&amp;quot;(.*)\&amp;quot;&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
			Match match = regex.Match(authHeader);&lt;br /&gt;
			if (match.Success)&lt;br /&gt;
				return match.Groups[1].Value;&lt;br /&gt;
			else&lt;br /&gt;
				return &amp;quot;&amp;quot;;&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		public void ProcessRequest(HttpContext context) {&lt;br /&gt;
			HttpRequest frontEndRequest = context.Request;&lt;br /&gt;
			HttpResponse frontEndResponse = context.Response;&lt;br /&gt;
&lt;br /&gt;
			Uri frontEndUrl = frontEndRequest.Url;&lt;br /&gt;
			write(&amp;quot;Receiving request for [&amp;quot; + frontEndUrl.AbsoluteUri + &amp;quot;]&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
			Uri backEndUrl = convertFrontEndToBackEndUrl(frontEndUrl, frontEndRequest.ApplicationPath, backEndSite);&lt;br /&gt;
			write(&amp;quot;Converting request to [&amp;quot; + backEndUrl.AbsoluteUri + &amp;quot;]&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
			HttpWebRequest proxyRequest = null;&lt;br /&gt;
			HttpWebResponse backEndResponse = null;&lt;br /&gt;
			try {&lt;br /&gt;
&lt;br /&gt;
				int timesRedirected = 0;&lt;br /&gt;
				do {&lt;br /&gt;
					proxyRequest = createProxyRequest(frontEndRequest, backEndUrl, methodToUse(frontEndRequest, backEndResponse));&lt;br /&gt;
		&lt;br /&gt;
					if (frontEndRequest.UrlReferrer != null) {&lt;br /&gt;
						Uri backEndReferUrl = convertFrontEndToBackEndUrl(frontEndRequest.UrlReferrer, frontEndRequest.ApplicationPath, backEndSite);&lt;br /&gt;
						proxyRequest.Referer = backEndReferUrl.AbsoluteUri;&lt;br /&gt;
					}&lt;br /&gt;
&lt;br /&gt;
					foreach(string each in frontEndRequest.Cookies) {&lt;br /&gt;
						HttpCookie requestCookie = frontEndRequest.Cookies[each];&lt;br /&gt;
						Cookie cookie = new Cookie(requestCookie.Name, requestCookie.Value);&lt;br /&gt;
&lt;br /&gt;
						if (requestCookie.Domain == null)&lt;br /&gt;
							cookie.Domain = backEndUrl.Host;&lt;br /&gt;
&lt;br /&gt;
						cookie.Expires = requestCookie.Expires;&lt;br /&gt;
						cookie.Path = requestCookie.Path;&lt;br /&gt;
						cookie.Secure = requestCookie.Secure;&lt;br /&gt;
&lt;br /&gt;
						proxyRequest.CookieContainer.Add(cookie);&lt;br /&gt;
					}&lt;br /&gt;
&lt;br /&gt;
					write(&amp;quot;Sending request to backend and getting response&amp;quot;);&lt;br /&gt;
					backEndResponse = proxyRequest.GetResponse() as HttpWebResponse;&lt;br /&gt;
					write(&amp;quot;Status code of response is [&amp;quot; + backEndResponse.StatusCode.ToString() + &amp;quot;]&amp;quot;);&lt;br /&gt;
&lt;br /&gt;
					if (isRedirection(backEndResponse.StatusCode)) {&lt;br /&gt;
						timesRedirected++;&lt;br /&gt;
						String newLocation = backEndResponse.Headers[&amp;quot;Location&amp;quot;];&lt;br /&gt;
						if(newLocation.IndexOf(&amp;quot;://&amp;quot;) == -1)&lt;br /&gt;
							newLocation = backEndUrl.GetLeftPart(UriPartial.Authority) + newLocation;&lt;br /&gt;
&lt;br /&gt;
						backEndUrl = new Uri(newLocation);&lt;br /&gt;
						write(&amp;quot;Being redirected to [&amp;quot; + backEndUrl.AbsoluteUri + &amp;quot;]&amp;quot;);&lt;br /&gt;
					}&lt;br /&gt;
&lt;br /&gt;
					if (!isRedirection(backEndResponse.StatusCode) || timesRedirected &amp;gt;= MaximumRedirections) {&lt;br /&gt;
&lt;br /&gt;
						if (timesRedirected &amp;gt;= MaximumRedirections) warn(&amp;quot;Exceeded maximum redirections&amp;quot;);&lt;br /&gt;
						break;&lt;br /&gt;
					}&lt;br /&gt;
&lt;br /&gt;
				} while (true);&lt;br /&gt;
			}&lt;br /&gt;
			catch(System.Net.WebException webException) {&lt;br /&gt;
				HttpWebResponse webResponse = webException.Response as HttpWebResponse;&lt;br /&gt;
				if (webResponse != null) {&lt;br /&gt;
					if (webResponse.StatusCode == HttpStatusCode.Unauthorized) {&lt;br /&gt;
						string realm = parseRealm(webResponse.GetResponseHeader(&amp;quot;WWW-AUTHENTICATE&amp;quot;));&lt;br /&gt;
						warn(&amp;quot;Unauthorized...redirecting to logon page&amp;quot;);&lt;br /&gt;
						frontEndResponse.Redirect(frontEndRequest.ApplicationPath + &amp;quot;/logon.aspx?Realm=&amp;quot; + context.Server.UrlEncode(realm) + &amp;quot;&amp;amp;ReturnUrl=&amp;quot; + context.Server.UrlEncode(frontEndUrl.PathAndQuery));&lt;br /&gt;
						return;&lt;br /&gt;
					}&lt;br /&gt;
&lt;br /&gt;
					frontEndResponse.StatusCode = (int)webResponse.StatusCode;&lt;br /&gt;
					frontEndResponse.StatusDescription = webResponse.StatusDescription;&lt;br /&gt;
				}&lt;br /&gt;
&lt;br /&gt;
				if (webException.Response == null) {&lt;br /&gt;
					frontEndResponse.Write(&amp;quot;&amp;lt;p&amp;gt;&amp;quot; + webException.Status + &amp;quot;&amp;lt;/p&amp;gt;&amp;quot;);&lt;br /&gt;
					frontEndResponse.Write(&amp;quot;&amp;lt;p&amp;gt;&amp;quot; + webException.Message + &amp;quot;&amp;lt;/p&amp;gt;&amp;quot;);&lt;br /&gt;
				}&lt;br /&gt;
				else {&lt;br /&gt;
					frontEndResponse.ContentType = webException.Response.ContentType;&lt;br /&gt;
					Stream responseStream = webException.Response.GetResponseStream();&lt;br /&gt;
					copyStream(responseStream, frontEndResponse.OutputStream);&lt;br /&gt;
					responseStream.Close();&lt;br /&gt;
				}&lt;br /&gt;
&lt;br /&gt;
				warn(webException.Message, webException);&lt;br /&gt;
				warn(&amp;quot;Abnormal end to processing of request&amp;quot;);&lt;br /&gt;
				frontEndResponse.End();&lt;br /&gt;
&lt;br /&gt;
				return;&lt;br /&gt;
			}&lt;br /&gt;
&lt;br /&gt;
			switch((int) backEndResponse.StatusCode) {&lt;br /&gt;
				case 301:&lt;br /&gt;
				case 302:&lt;br /&gt;
				case 303:&lt;br /&gt;
				case 307:&lt;br /&gt;
					frontEndResponse.StatusCode = (int) backEndResponse.StatusCode;&lt;br /&gt;
					string newLocation = backEndResponse.Headers[&amp;quot;Location&amp;quot;];&lt;br /&gt;
					newLocation = Regex.Replace(newLocation, backEndSite, &lt;br /&gt;
						frontEndRequest.Url.GetLeftPart(UriPartial.Authority) + frontEndRequest.ApplicationPath, &lt;br /&gt;
						RegexOptions.IgnoreCase);&lt;br /&gt;
					frontEndResponse.RedirectLocation = newLocation;&lt;br /&gt;
					break;&lt;br /&gt;
			}&lt;br /&gt;
			convertBackEndToFrontEndResponse(backEndResponse, frontEndRequest, frontEndResponse);&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		[Conditional(&amp;quot;TRACE&amp;quot;)]&lt;br /&gt;
		void warn(string message) {&lt;br /&gt;
			StackTrace stack = new StackTrace(1, true);&lt;br /&gt;
			StackFrame frame = stack.GetFrame(0);&lt;br /&gt;
			HttpContext.Current.Trace.Warn(frame.GetMethod().Name, message);&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		[Conditional(&amp;quot;TRACE&amp;quot;)]&lt;br /&gt;
		void warn(string message, Exception exception) {&lt;br /&gt;
			StackTrace stack = new StackTrace(1, true);&lt;br /&gt;
			StackFrame frame = stack.GetFrame(0);&lt;br /&gt;
			HttpContext.Current.Trace.Warn(frame.GetMethod().Name, message, exception);&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		[Conditional(&amp;quot;TRACE&amp;quot;)]&lt;br /&gt;
		void write(string message) {&lt;br /&gt;
			StackTrace stack = new StackTrace(1, true);&lt;br /&gt;
			StackFrame frame = stack.GetFrame(0);&lt;br /&gt;
			HttpContext.Current.Trace.Write(frame.GetMethod().Name, message);&lt;br /&gt;
		}&lt;br /&gt;
	}&lt;br /&gt;
}&lt;br /&gt;
&amp;lt;/nowiki&amp;gt;&amp;lt;/pre&amp;gt;&lt;/div&gt;</summary>
		<author><name>Wolfm</name></author>
	</entry>
</feed>