5

I need to change the order of headers, I'm using this:

HttpWebRequest request = (HttpWebRequest)WebRequest.Create(URL);
request.Method = context.Request.HttpMethod;
request.UserAgent = context.Request.UserAgent;

The output for that is:

GET /* HTTP/1.1
User-Agent: My Server
Host: 127.0.0.1:1080

But it should be

GET /* HTTP/1.1
Host: 127.0.0.1:1080
User-Agent: My Server

Any ideas?

Thanks for your time.

EDIT: Maybe there's a way using other object ... it's also an option

bignose
  • 30,281
  • 14
  • 77
  • 110
Tute
  • 6,943
  • 12
  • 51
  • 61

2 Answers2

3

There was an outstanding complaint that .NET doesn't let you modify the Host header a while back. It might not have been resolved. If it is really that important, you could always write socket-level code to send a prepared request (since it's just text).

Hank Gay
  • 70,339
  • 36
  • 160
  • 222
  • mmmm... yes, I saw a thread about the Host problem. I think I will use sockets then. Thanks. – Tute Feb 06 '09 at 21:51
1

I had this problem today but I created this hack:

        /// <summary>
        /// We aren't kids microsoft, we shouldn't need this
        /// </summary>
        public static void UnlockHeaders()
        {
            var tHashtable = typeof(WebHeaderCollection).Assembly.GetType("System.Net.HeaderInfoTable")
                            .GetFields(BindingFlags.NonPublic | BindingFlags.Static)
                            .Where(x => x.FieldType.Name == "Hashtable").Single();

            var Table = (Hashtable)tHashtable.GetValue(null);
            foreach (var Key in Table.Keys.Cast<string>().ToArray())
            {
                var HeaderInfo = Table[Key];
                HeaderInfo.GetType().GetField("IsRequestRestricted", BindingFlags.NonPublic | BindingFlags.Instance).SetValue(HeaderInfo, false);
                HeaderInfo.GetType().GetField("IsResponseRestricted", BindingFlags.NonPublic | BindingFlags.Instance).SetValue(HeaderInfo, false);
                Table[Key] = HeaderInfo;
            }

            tHashtable.SetValue(null, Table);
        }

Then You need call this UnlockHeaders function only one time in the program startup, after call the Header Collection in the HttpWebRequest class will accept any header to be manually added.

Then before add any header to the request, do this:
myHttpWebRequest.Headers["Host"] = "www.example.com";

After that first header will be the Host, since looks like in some .net versions the Headers field have more priority.

Note: This code don't works after .Net Core 3 because the reflection can't modify read-only values anymore, as a alternative, in my program I loaded a patched System.Net.WebHeaderCollection assembly early in my app initialization instead.