In ASP.NET 4, we added the concept of a PreApplicationStart method that an assembly can use to execute code early on in the appdomain without any configuration. Phil Haack covered it a while back in this post. It’s pretty simple to use. You just define a class that looks like:
public class PreApplicationStartCode { public static void Start() { // Your startup code here } }
And then you add an assembly level attribute pointing to it:
[assembly: PreApplicationStartMethod(typeof(PreApplicationStartCode), "Start")]
With the release of MVC3 and ASP.NET Web Pages, we added another little gem: a RegisterModule() API that lets you dynamically register an IHttpModule without touching config. Sadly, the method is hidden so deep that it is hard to find by accident (it’ll get cleaned up in the next framework version).
By combining the two techniques, you have everything you need to register a module dynamically, e.g.
public class PreApplicationStartCode { public static void Start() { // Register our module Microsoft.Web.Infrastructure.DynamicModuleHelper.DynamicModuleUtility.RegisterModule(typeof(MyModule)); } }
I warned you it was well hidden! :)
The module type that you pass in to that is just a standard IHttpModule, e.g. here is a basic module that writes to the response on every request:
class MyModule : IHttpModule { public void Init(HttpApplication context) { context.BeginRequest += (sender, e) => { var response = ((HttpApplication)sender).Response; response.Write("MyModule.BeginRequest"); }; } public void Dispose() { } }
The beauty of this is that it allows you to create fully encapsulated assemblies that you can just drop into a web app’s bin folder and have them light up without having to add any ugly registration to the app.
And yes, all this works fine in partial trust!
You can download a minimal sample from here.
you're right, it's super deep..:D
ReplyDeletewithout your post i'd have no idea that it's exists. thanks for sharing.
Excellent stuff... but what about HttpHandlers??
ReplyDeleteCan they be auto-registered too??
Great minds must think alike - I posted on this not quite a week ago. :) http://www.paraesthesia.com/archive/2011/02/08/dynamic-httpmodule-registration-in-asp-net-4-0.aspx
ReplyDelete@James_2JS: sorry, I don't know of a way to do this for HttpHandlers, though I agree it would be useful
ReplyDelete@Travis: wow, very similar post indeed! :)
ReplyDeleteI think this is not specific to ASP.NET MVC or WebPages. Every one can just add a reference to Microsoft.Web.Infrastructure.dll in his class library and use it in ASP.NET Web Forms, ASP.NET MVC or ASP.NET Web Pages.
ReplyDeleteNikhil had posted something similar also... http://www.nikhilk.net/Config-Free-HttpModule-Registration.aspx
ReplyDeleteDavid
ReplyDeletePlease post a sample project with 2 dll:
One that exists by default in the MVC project
One that does not exists in the MVC project and , when dropped , is instantiated( put something in the Application...)
Thank you
Andrei
@Andrei: are you running into a specific issue with getting this to work?
ReplyDeleteQuestion, using this method - is there anyway to programatically setup the equalivent entries needed in web.config? Or, do you still need those? You mentioned that you'd just need to drop the dll in the bin, but that's the only missing peice (at least in my scenario) to get that to work .. any ideas?
ReplyDeleteThanks, @djbyter
@korifrancis: the main appeal of this technique is in fact that you don't need to modify web.config at all! :)
ReplyDeleteNo specific issue - just, being a lazy programmer, I want a simple test first and then to understand how. Please , please help me( and other lazy programmers)
ReplyDeleteYes I agree with Andrei.
ReplyDeleteOk, by popular demand, I included a minimal app. Link is at the end of the post. It shows the feature being used in the main assembly of an MVC app, but it's *identical* in any other assembly.
ReplyDeleteThis is very helpful, thank you! Btw it's 2 years later and I still see DynamicModuleUtility hidden in the same place! :-P
ReplyDelete@rushonerok: actually, in Framework 4.5 there is a much cleaner place to find this method: HttpApplication.RegisterModule. But the 'hidden' one still exists for backward compat.
ReplyDeleteIt's good but it can handle only managed requests. What if I want to handle *.js requests?
ReplyDelete@Halil I think can do that if you turn on runAllManagedModulesForAllRequests (search web for details on using this).
ReplyDelete@David, it's ok but I don't want to do it since;
ReplyDelete1) I don't want to modify web.config, if I do, I can register module it web.config. Wyh I try to register it dynamically by code.
2) It has a little performance problem.
@Halil: I don't know of any other solution. Without that flag, requests to static files don't even go to ASP.NET at all, so none of what is described in this post applies. Note that it's not specific to this technique, but you'd see the same thing if you manually registered your module in web.config.
ReplyDeleteThis comment has been removed by the author.
ReplyDelete@David,
ReplyDeleteIf I register in web.config, it handles all request. In web.config/system.webServer/modules
<add type="Taskever.Web.App_Start.MyModule" name="sasdasd">
It works since I did not specified preCondition.
@David, I thank you so much for your quick response.
ReplyDeleteMaybe you're right. Unfortunately, I really don't see how the technique described here can work without RAMMFAR since the requests just don't make it there. And I agree it would be useful; I just don't know how to make it work.
ReplyDelete@Thanks again. I'm just trying to develop a framework that is used to be a start point for asp.net mvc applications (https://github.com/hikalkan/aspnetboilerplate). It has a feature to create web api classes dynamically over your application service layer using castle dynamic proxy. And also creates javascript proxies to need to simplify web api calls. So, I need to handle .js calls for a specific route and create file dynamically using reflection.
ReplyDeleteThank you very much for your responses.
NFL Predictions – get free NFL picks for every NFL game, including the Super Bowl. Local laws prohibit us from permitting you to log in or place bets 온라인카지노 on our web site. A proposition wager is a wager not tied to the result of|the outcomes of} a contest. If the final score totals 6 precisely, it’s thought of a “push” and your original wager is returned to you. If you wager the unfold on Seattle -6, they would need to win by 7 points or extra to “cover” and thus you'll win your wager. Additionally, every group in the contest is accompanied by a +/- subsequent to the unfold quantity.
ReplyDelete