Friday, November 21, 2003

ASP.NET Quirklet - Nested VDirs

I ran into something that took me almost all of yesterday to figure out. I was trying
to set up a series of virtual directories in IIS. The basic idea was that I had a
set of ASPX pages and a set of ASP.NET Web Services, and that they should be organized
under a single URL, like http://localhost/MyApplication.

I couldn’t put everything into the same virtual directory, because we already
had a disk structure defined that located the ASMX and ASPX pages in different places.
So I figured I’d map /MyApplication to the ASPX directory, and just create a
child virtual directory like /MyApplication/WebServices that mapped to the ASMX directory.
(You did know that virtual directories can contain other virtual directories, didn’t
you? And that they can point to any physical directory, even one that isn’t
a child of the parent vdir’s physical directory?)

The problem I ran into immediately with this approach was that some of the settings
in my ASPX web.config were incompatible with my web services. This is a problem because
many web.config settings are inherited by child virtual directories. My solution to
this was to create two children of /MyApplication - /MyApplication/UI and /MyApplication/WebServices.
Both children had to be proper virtual directories, and not just regular directories
underneath a virtual directory. This is because

1)      The
two physical directories in question don’t share a common parent physical directory,

2)      Some
of the things in my web.config file only work when the web.config file lives in a
virtual directory root.

It was a bit annoying that I was going to have to type http://localhost/MyApplication/UI
instead of http://localhost/MyApplication to get to the ASPX pages, but it’s
a minor annoyance, and if it really bugs me I can fix it later with a server-side
remapping or a simple client-side redirect. So I mapped the parent virtual directory
off to a random empty directory on my hard drive, mapped the two child vdirs off to
the appropriate place, and went on coding.

Everything was going great until I tried to install the stuff on someone else’s
machine. I’d written a setup script, and although it seemed to run to completion,
the app didn’t work when I was done. It was failing in all sorts of weird ways,
doing things it just shouldn’t. Most troubling was when it would error out because
it couldn’t find the current username…because even though I had ASP.NET
Forms Authentication set up, it was never redirecting to the login page!

Ultimately, I found the answer through trial and error. It turns out that during setup,
the check-out from source control wasn’t creating the empty directory that the
parent directory virtual directory was mapped to. And for whatever reason, if you
have nested virtual directories, if the parent directory does not exist, ASP.NET
completely ignores the web.config files in the child virtual directories
. Leading
to the highly confusing behavior I mentioned. The solution was simple: just make sure
the parent vdir points to a valid physical directory, and everything returns to normal.


  1. Craig, isn't the <location> tag working for you? I would think that you should be able to deploy the UI in http://localhost/MyApp and the asmx in http://localhost/MyApp/WS by isolating the problematic configuration settings in <location>. Please, let me know what is the problem.

  2. Right. I seem to remember going down that route at one point...but I can't remember why I turned aside. I may have to go back and try to figure out what stopped me the last time.

  3. Ah yes, I'd blanked out the wasted hours I spent hunting down this same problem a few months ago. Thanks for the reminder. :o)

  4. I'm always happy to rip open old wounds and pour lemon juice on them. ;)

  5. thats just dumb. stupid stupid error! *Grrr*