Jeff and .NET

The .NET musings of Jeff Putz

Sponsors

News

My Sites

Archives

What's wrong with HttpContext in an HttpHandler?

I experimented some more with the problem I posted recently regarding setting Session values from an HttpHandler. Instead of using Session, I tried using the Cache object instead. The same thing happened... worked fine in Visual Studio, but not in IIS on the server. Here's the class... the value of Session["spamimage"] doesn't update after the first try (called from an <img src="AntiSpamimage.ashx"> tag), even though the image clearly is regenerated. Again, this works fine in the context of the built-in VS server.

using System;
using System.Drawing;
using System.Drawing.Imaging;
using System.Text;
using System.Web;
using System.Web.SessionState;

public class AntiSpamImage : IHttpHandler, IRequiresSessionState
{
    public void ProcessRequest(HttpContext context)
    {
        context.Response.ContentType = "image/gif";
        Bitmap b = new Bitmap(200, 60);
        Graphics g = Graphics.FromImage(b);
        g.FillRectangle(new SolidBrush(Color.White), 0, 0, 200, 60);
        Font font = new Font(FontFamily.GenericSerif, 48, FontStyle.Bold,
        GraphicsUnit.Pixel);
        Random r = new Random();
        string letters = "ABCDEFGHIJKLMNPQRSTUVWXYZ";
        string letter;
        StringBuilder s = new StringBuilder();
        for (int x = 0; x < 5; x++)
        {
            letter = letters.Substring(r.Next(0, letters.Length - 1), 1);
            s.Append(letter);
            g.DrawString(letter, font, new SolidBrush(Color.Black), x * 38, r.Next(0, 15));
        }
        context.Session["antispamimage"] = s.ToString();
        Pen linePen = new Pen(new SolidBrush(Color.Black), 2);
        for (int x = 0; x < 6; x++)
            g.DrawLine(linePen, new Point(r.Next(0, 199), r.Next(0, 59)), new Point(r.Next(0, 199), r.Next(0, 59)));
        b.Save(context.Response.OutputStream, ImageFormat.Gif);
    }
 
    public bool IsReusable
    {
        get { return true; }
    }

}


Posted: Jan 06 2006, 01:29 AM by Jeff | with 21 comment(s)
Filed under:

Comments

John Walker said:

Jeff,

I've noticed a few times, especially with the Graphics Object that an exception will be thrown (often after a method has been run) that is not caught in the debugger.

Have you tried stripping down the method to just include the Session changing call, and exclude all of the other stuff? Might be nice to know if it's some other code in the method that is causing a problem. Just a thought.

jw
# January 6, 2006 2:16 AM

jayson knight said:

It would seem to me your code is correct, and that this is an environmental issue with either A) IIS, or B) ASP.NET 2.0. Have you tested it on 1.1 (just to rule out 2.0 issues)?

Also, in your post you mention Session["spamimage"], yet I don't see that in your code anywhere (perhaps a typo).

In addition, what are your web.config settings for this httpHandler (i.e. what file extension are you trapping for), and is this properly configured in IIS?
# January 6, 2006 2:27 AM

scottgu said:

Have you checked the cache settings being sent down to the browser? It could be that under IIS you are sending down a client cache duration -- which means the browser just uses the local copy in the future and doesn't perform an explicit check for changes.

Hope this helps,

Scott
# January 6, 2006 3:39 AM

Jeff said:

No, the browser isn't caching it, because the graphic changes every time. If the graphic is written to the output stream, the code is executing right to the end.

The handler works the same whether it's specified from web.config or run as a stand-alone .ashx handler. The browser doesn't matter either.
# January 6, 2006 10:28 AM

AndrewSeven said:

Does anyone have a good understanding of what IsReusable really does? I use false just because I'm not positive about true. I guess I should go reflectoring.

Does setting it to false change anything with your issue?
Does the VS-WebServer honor the setting and re-use the handler?

Does it work on your local IIS? Showing different behavior on the smae machine would be nice ;)



I once had some similar strange behavior with cookies;
Instead of using the context parameter that is passed to the method, use the full reference : HttpContext.Current.Session["antispamimage"] = s.ToString();
# January 7, 2006 10:40 AM

DmitryR said:

Jeff, how do you verify that the session is not set? Given that you tried Cache and it doesn't work either, I suspect that the code is not executing at all. Did you try to put a breakpoint (when running under IIS) to see that the code in fact executes. Are you using in-process session state?

BTW, IsReusable wouldn't make any difference here.

Thanks,

Dmitry
# January 8, 2006 3:04 AM

Jeff said:

But the rest of it IS executing. If it didn't, it wouldn't generate a new graphic every time. If you look at the trace output of any page, you can see the Session values, and they are set the first time and not on subsequent times. If the default (I assume in machine.config) is in-proc state, then that's what it's running. I haven't changed it.
# January 8, 2006 10:58 AM

DmitryR said:

Can you set the breakpoint and see that it is in fact hit? Alternatively, could you comment out everything but setting the session state variable to a new value and see if that works?
# January 8, 2006 11:21 PM

Jeff said:

Yep... it does happen. It executes.
# January 9, 2006 12:08 AM

DmitryR said:

I tried this scenario and it works for me. Here is what i did:

1) Created img.ashx containing your code from this post

2) Created page.aspx containing:
Image: <img src="img.ashx">

3) Created session.aspx containing:
<%= Session("antispamimage") %>

4) Request http://localhost/test/page.aspx
see the generated image

5) Request http://localhost/test/session.aspx
see the contents of the session

When I repeat steps (4) and (5) several times I do see the right data in the step (5). Does is the scenario work for you?
# January 11, 2006 1:29 AM

Jeff said:

Yep... works great in the Visual Studio server. Not in IIS.
# January 11, 2006 2:23 AM

DmitryR said:

This is really strange.

One possible explanation is web browser caching, as was suggested earlier in this thread. Please try it (steps 4 and 5) with a simple command-line client instead of a real browser (for example, tinyget from IIS6 resource kit -- http://support.microsoft.com/default.aspx?scid=kb;en-us;840671).

Other than that I don't know what to suggest... Please try to call PSS and they will help with debugging this problem.
# January 12, 2006 12:00 AM

Jeff said:

No, it can't be caching. I've said it over and over... the returned image changes every time. If it was being cached that wouldn't happen.
# January 12, 2006 12:55 AM

John Walker said:

Jeff,

I was interested to see if you ever found a solution and see you haven't. I had a little time, so I copied your code into a new web project hosted under my local IIS service. I compiled and ran the code and I am getting a different image each time I refresh my browser. It is definitely running here under IIS and not Cassini. Just thought I'd let you know I couldn't repro the problem.

jw
# January 15, 2006 1:07 AM

John Walker said:

PS: Sorry, forgot to mention, that I also have a separate page where I am spitting out Session["antispamimage"] and it is changing after each refresh of the image page.
# January 15, 2006 1:23 AM

Jeff said:

Nope. No solution. I'm stumped.
# January 15, 2006 8:46 AM

Ryan Anderson said:

Late to the game, I am having an odd issue with an HttpModule that pulls a company logo from the db and outputs the file to an html email.

Strange that the image doesn't always coincide with what the database dishes out.

The image file name returned from the database isn't always the file that is displayed in the email.

Similar, and was wondering if everyone is still out there flapping on this...

# August 15, 2006 2:06 AM

Ryan Anderson said:

Oh, yeah. I am not using a session object, but pulling the requested url;

Dim url As String = application.Request.Path 'get the url path

from the app object, it jive beautifully in VS, but not on IIS...

Stumped...

# August 15, 2006 2:08 AM

Anon said:

Morning

Has there ever been a resolution to this problem? We are experiencing the same issue. We have searched and tried all possible scenario, yet when we submit on the server it loses the session variable but not on the Dev boxes.

# May 10, 2007 1:48 AM

Martin Brown said:

You may well find that it's because the page and the httphandler are running under separate app domains.

They will be on localhost - may not be on IIS live.

# August 16, 2007 10:02 AM
Leave a Comment

(required) 

(required) 

(optional)

(required)