ManagedThreadPool - Managing the Thread Pool

Where's the response?
I couldn't figure out why I was not getting an immediate response. I ran through my code several times before I realized I was missing a key test at a crucial decision making point. I was failing to check whether or not the ManagedThreadPool in my application could get to my request now or whether the request would be pooled.

ManagedThreadPool.ActiveThreads < ManagedThreadPool.MaxThreads - 2

Simple as that. A simple test in a more complex if statement. Why the - 2? Well, I needed a margin to allow for the fact that other threads would be jamming their own jobs in. So I figured a margin of 2 unused threads would give me that. We'll see how it does in the real world.

Lesson Learned
If you plan to use a thread pool, be sure to pay attention to how many babies are in the water at the moment you decide to jump in. Otherwise, you may not get what you expect when you expect, especially in a system like I have been working on where hundreds or even thousands of items might be queued up.

(Note: This is being reposted because I inadvertently allowed trackbacks and the previous post got hammered with spam trackbacks and dasBlog would log me out when I tried to go to the post to delete them. Go figure...)

The .NET Developer Search Engine - Google CoOp

Thanks to Google CoOp, www.netbrick.net is now my personal .NET developer search engine. With the help of a few friends, the list of domains searched remains relevant to .NET development. This helps eliminate all the clutter I get when hitting Google directly.

Thanks to Paul Allen for alerting me to this very cool feature. And if you use it, don't be afraid to click on the ads. :)

Refactoring Utah County Dot Net Users Group

Today I attended my first UCNUG meeting. It was great. Easy location. Perfect size crowd. Great presentation by Aaron Zupancic on refactoring.

Previous meetings have been held at UVSC, but fortunately they got kicked out of there. I'm lazy by nature and didn't want to bother with finding the room on a campus I don't know. This one was hosted gratiously by NuSkin at the East Bay location and that was easy to find.

Aaron gave a well thought out, cogent presentation on the ins and outs of refactoring. I actually learned some things. And for me, that makes any presentation valuable. But it was a good presentation as much for what Aaron did not do as what he did do. He did not just read from the book. Martin Fowler is great but the presentation was really valuable because Aaron pulled examples and ideas into slides with even better code examples.

I've attended the Utah .NET Users Group, where Aaron is the president, a few times. The presentations are generally good, including Aaron's, but this one was much better. I'm trying to convice a buddy of mine to present on CruiseControl.Net, NUnit and automated build and testing in general. I'll post it here if I can get him to commit.

IE7 So Far So Good

Installed IE7 (7.0.5730.11) over the top of the beta. Everything working well so far. Ah, but now, because of the increasing clutter on my drive, I'm running out of space and will soon be rebuilding my machine. Just another chance to install, install, install.

Point, click, wait. Repeat.

Google and Warez - Why?

It's been less than a week and my www.photohistorydoc.com site has caught up by many RegNow affiliates, hacked by some warez hackers in the UK, Israel, and Australia, and indexed by Google. The question I have is why does Google continue to index warez sites whose primary purpose is to sabotage the shareware and commercial software industry.

So, Google, why? Why do you help promote these low lifes whose only goal seems to be to troll for software thieves susceptible to the enticements of porn in order to make money from the click flips to the real porn sites. Why? These sites don't use AdSense, so there does not seem to be a monetary motive. What else can it be?

Does anyone have a clue?

Photo History Doc Released

After two months of working nights and weekends, I've finally finished Photo History Doc, my little contribution to the shareware world. I'd love to hear what you think about it. Visit http://www.photohistorydoc.com and download it and let me know what you think.

I'll post more about it and how it gets received out in the world later.

Trackback Spammers Deserve a Horrible Death

I'm disabling trackback on my blog because one particular post gets spammed with about 30 porn trackback spams a week. All of them in one batch. They point to seemingly empty places. So if you want to trackback here, sorry, too bad. It's too much of a pain to delete all the spam trackbacks and there is no easy way to track the offender or block him/her/it.

Image MIME Type from the Byte[]

A little puzzle came up today. Fetch an image out of a database and stream it down to the browser. The trick: we don't know what type of image is stored in the database. So I borrowed a little from our Python friends and this is what I ended up with.

internal static class ImageTypeFinder
{
    internal static string GetMimeType(byte[] image)
    {
        string retval = "image/jpeg";
        string imgtype = GetImageType(image);
        switch (imgtype)
        {
            case "bmp":
                retval = "image/bmp";
                break;
            case "gif":
                retval = "image/gif";
                break;
            case "tif":
                retval = "image/tiff";
                break;
            case "png":
                retval = "image/png";
                break;
        }
        return retval;
    }

    internal static string GetImageType(byte[] image)
    {
        int len = image.Length;
        if (len > 32) len = 32;
        string first32 = ASCIIEncoding.ASCII.GetString(image, 0, len);
        return GetImageType(first32);
    }

    internal static string GetImageType(string first32)
    {
        string retval = string.Empty;
        if (first32.StartsWith("GIF87a") || first32.StartsWith("GIF89a"))
            retval = "gif";
        else if (first32.StartsWith("MM") || first32.StartsWith("II"))
            retval = "tif";
        else if (first32.Substring(6, 4) == "JFIF" || first32.Substring(6, 4) == "Exif")
            retval = "jpg";
        else if (first32.StartsWith("BM"))
            retval = "bmp";
        else if (first32.Substring(1, 3) == "PNG")
            retval = "png";
        return retval;
    }

}

It's a bit of an esoteric puzzle, but if you're trying to solve this one, the above code should help.