Event handlers in Orchard work just like in any other programming environment with a very interesting addition: they enable you to create extensions points to your features without worrying about coupling and references. So let's see how they work!
Every Orchard-y event handler has an interface that derives from
IEventHandler. In your module you can inject a single
IYourEventHandler and now you just created the extension point for your module: if you call the methods on the injected event handler you enable other module authors to interact with your module if they implement this interface. That's okay so far, but in order to make it work, other module authors (or even you, if you want to extend the funtionalities of a feature not written by you) must have a reference on the module's project that hosts this event handler interface.
And here comes the twist: instead all you need to do to implement an event handler that is in another module not referenced by your module is to have an interface in your module with the same name also deriving from
IEventHandler and implement that interface! Aside from that, of course, the methods you implement must also have the same name and signature (if there are types that also come from an other module or project you are not referencing, you can replace them with
dynamics). Orchard will find these even more loosely coupled implementations solely based on their names and try to match the methods with the original interface. How cool is that?
This page and many others here are part of the open-source, portable package of Orchard 1.x goodies: the Orchard Dojo Library. The Library is freely accessible by anyone; just go to its repository to download its full content (you can even download the textual content of the Library as a big concatenated document in HTML), file issues or fork it! You can even edit it online on Bitbucket, just click on the Edit link in the upper right corner!
Note that the Library also has an Orchard Core version, check it out here!