Share via


Adding servervariables

Question

Friday, June 22, 2007 7:28 AM

I am trying to write an HTTP Module that will add server variables to the Request.ServerVariables collection. If I try to modify the collection I receive an exception that states:

Cannot directly modify server variables<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" /><o:p></o:p>

Essentially our code uses the server variables written by the 3<SUP>rd</SUP> party ISAPI filter. The requirements for the 3<SUP>rd</SUP> party set up are too great to setup and maintain on each and every developers box. So I am trying to find a way to write these values without having to have the 3<SUP>rd</SUP> party ISAPI filter available at all times, thus allowing us to sandbox our machines.

 

All replies (10)

Thursday, July 5, 2007 7:55 AM ✅Answered

Reflection did the trick, and was it pretty nasty [:D]

In intrest in sharing the solution with everyone, the following is the code I used. this was placed in my Begin Init of the HTTP Module. However, I'm guessing it could be placed in a few other events, I just chose this one for testing.

    void context_BeginRequest(object sender, EventArgs e)
    {
      HttpApplication application = (HttpApplication)sender;

      BindingFlags temp = BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static;


      MethodInfo addStatic = null;
      MethodInfo makeReadOnly = null;
      MethodInfo makeReadWrite = null;


      Type type = application.Request.ServerVariables.GetType();
      MethodInfo[] methods = type.GetMethods(temp);
      foreach (MethodInfo method in methods)
      {
        switch (method.Name)
        {
          case "MakeReadWrite": makeReadWrite = method;
            break;
          case "MakeReadOnly": makeReadOnly = method;
            break;
          case "AddStatic": addStatic = method;
            break;
        }
      }

      makeReadWrite.Invoke(application.Request.ServerVariables, null);
      string[] values = { "NewVar1", "Test" };
      addStatic.Invoke(application.Request.ServerVariables, values);
      makeReadOnly.Invoke(application.Request.ServerVariables, null);
    }

Thanks again for the help and direction, Hope this helps someone else out there.
Wayne


Monday, June 25, 2007 10:35 PM

HI, ThisBytes5 : 

How about using Context.Items? 

Or you can use a Application variable for sharing within the whole application. 

Application.Lock();
Application["AppName"] = "My Application";
Application.UnLock();

If you can't use cookies then you shouldn't be using header variables
either as header variables are easy to find with a simple http sniffer.
  I'm thinking that you really should go with the suggestion of using a
database or some other shared server side storage location for holding
this value.  Anyone that would go to the trouble of opening your cookie
would probably not have too much problem running something like Fiddler
(or any number of other tools) to see what is inside the headers for the
page.  Also from a security standpoint, you probably don't want to pass
anything to the client that you are worried about getting hacked, it is
better to keep it at the server and use an authentication mechanism to
get to it each time it is needed. 

I hope the above information will be helpful. If you have any issues or concerns, please let me know. It's my pleasure to be of assistance

 

 

 


Tuesday, July 3, 2007 9:40 AM

As stated in the original post we have code that reads the Server Variables and the variables are populated by a 3rd party app. I am trying to simulate the third party app. To use the Context.Items would mean having to change already existing code which at this point is not an option. Also this is ALL server side information, not client. So cookies/Headers don't apply here. Not sure why you were suggesting headers/cookies.

Thanks
Wayne


Tuesday, July 3, 2007 7:39 PM

Wayne,

In order to get your own custom server variables, I think you need to reinvent the wheel and create your own implementation of a HttpWorkerRequest object. All variants ASP.NET uses are created internally by a factory and doesn't allow for extensions in any way, so no hope there.

The HttpRequest.ServerVariables property (a NameValueCollection) is set readonly after populating all the variables. So if you really really need it, your only option that might be left is to create some kind of black magic HttpModule that uses a bit of reflection to make that collection writable again and add your custom server variables.

Disclaimer: I don't know if that approach will work, but I'm almost 100% sure that you can't do anything to that ServerVariables collection after .NET has populated it for you.
So if you take that approach I wish you good luck.

Victor


Friday, August 24, 2007 12:10 PM

Just used this today when I was trying to simulate what IBM's Tivoli Access Manager does to my .NET application in production.  Thank you!


Tuesday, April 1, 2008 5:31 PM

I just used this today to simulate Siteminder's Header variables on local development machine.  Thank you!


Tuesday, May 13, 2008 2:39 AM

This looks like what i need, thoung i need to alter the UserAgent in the request.

Background:

I need to write a HTTP module that alters the UserAgent of the Request. This might seem like at stupid (or dangerous) thing to do, but it's what i need to do. Unfortunately i can't tell you why because of company secrets and bla bla bla. :-)

I assume i can use the method above to make the request writable. Then i just need a method to write to the UserAgent property.

Can anybodu help me out here?

 Thanks in advance.

Esben Rasmussen


Wednesday, May 14, 2008 5:43 AM

I found the following article http://blogs.tedneward.com/2005/11/21/The+Immutable+String.aspx.<?xml:namespace prefix = o ns = "urn:schemas-microsoft-com:office:office" /><o:p></o:p>From that i wrote a HttpModule in C# that alters the Request.UserAgent the same way. (The UserAgent is normally ReadOnly)<o:p></o:p>Now this method works fine while running my site on IIS 5.1 on XP machine. But when running the site on IIS 7.0 (Vista), nothing happens.<o:p></o:p>Literally nothing happens. The code runs smoothly with no errors (I’ve single stepped it) but the UserAgent has not changed?<o:p></o:p><o:p> </o:p>Code that I used was:

1    private void addServerVariable(HttpApplication application)
2            {
3                //Add key/value-pairs to the ServerVaiables collection
4                //http://forums.asp.net/t/1125149.aspx - start
5                BindingFlags temp = BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.Static;
6    
7                MethodInfo insertInPlace = null;
8                MethodInfo appendInPlace = null;
9                MethodInfo  fillStringChecked = null;
10               Type type = application.Request.UserAgent.GetType();
11               MethodInfo[] methods = type.GetMethods(temp);
12               foreach (MethodInfo method in methods)
13               {
14                   switch (method.Name)
15                   {
16                       case "InsertInPlace": insertInPlace = method;
17                           break;
18                       case "AppendInPlace": appendInPlace = method;
19                           break;
20                       case "FillStringChecked": fillStringChecked = method;
21                           break;
22                   }
23               }
24   
25               string strUserAgent = "FiSh HeAd";
26               //InsertInPlace arguments: index where to insert(int), chararray to insert(char[]), starting index in chararray(int), number of chars to insert(int), total length(int)
27               object[] values = { (int)0, strUserAgent.ToCharArray(), (int)0, (int)strUserAgent.Length, (int)strUserAgent.Length, (int)strUserAgent.Length };
28               insertInPlace.Invoke(application.Request.UserAgent, values);
29               //http://forums.asp.net/t/1125149.aspx - end
30           }

 

Any ideas why this would work on IIS 5.1 and not on IIS 7.0?


Sunday, June 20, 2010 5:29 AM

I'm using HttpModule to capture requests to the web server. Before
processing the page I'd like to check the values contained in some keys
of the Request.Form collection and according to some logic change if
necessary. I'd like to do this when BeginRequest event is fired. The
problem is that the Request.Form collection is readonly.

Is there any way to accomplish this task ?

Thanks is advance


Friday, November 19, 2010 1:17 AM

Hi

I am using 

Request.ServerVariables.Get("HTTP_X_NETWORK_INFO");

for getting MSISDN but on opera mini browser it will not return MSISDN.

if i am changing server variable: Requst.ServerVariables.Add("HTTP_USER_AGENT",useragent); OR Rquest.ServerVariables["HTTP_USER_AGENT"] = useragent;

But this is giving me Exception

Plz doo needfull for MSISDN on Opera Mini