This is in response to a GitHub issue for Nancy. The user is trying to self-host Nancy without locking their DLLs. One easy way to do this is to create a wrapper program which runs the actual program with shadow copying assemblies. No DLLs are locked and the changes are minimal.
I will first show a simple application which self-hosts Nancy and can serve a
request to "/"
. The program will start listening, wait for a key to be
pressed and then exit. This is the code:
We will add a simple NancyModule
so we can test the application at http://localhost:12345/
:
This program will work as is. The problem is that it locks any assemblies it references.
To work around this problem, add another executable to wrap the actual implementation. In order to keep the DLLs unlocked, we will run the implementation from a separate AppDomain with Shadow Copying enabled.
AppDomains are a very powerful feature of the Common Language Runtime for isolating code. They can use different security contexts, modify how assemblies are loaded and can be managed independently. There can be multiple AppDomains within a single process and can achieve some of the same isolation benefits as processes.
Using the separate AppDomain allows us to set the ShadowCopyFiles
option to "true"
. This option will cause the
assembly loading process to copy each assembly into a different directory and then load them from the new location.
The local copies are left unlocked. For more information on Shadow Copying Assemblies refer to MSDN.
The whole solution would look like the diagram below:
This is the wrapper program to call the actual executable Implementation.exe
:
That is all there is to it. Don’t want your DLLs to be locked? The easy solution is to use another AppDomain with Shadow Copying enabled.
All the code for this blog post can be found in this sample project.