I just had a tweet from ASP.NET MVP and all-round guru @Plip, who'd been caught out by a misspelling in a method name. It happens to the best of us. But something struck me. The method in question: Page_PreRen[d]er.
And this is why AutoEventWireup is evil. Along with any convention based software. This is what OO was *designed* to overcome. The aspx webforms model offers protected virtual On[event] methods for (probably) all the events its objects fire, and you can't cock up overriding these - the compiler *won't let you*. Hell, VS even autocompletes half the job for you.
So why does the default template for a new webform *still* have AutoEventWireup set and a skeleton Page_Load method? This is a VB convention from 10 years ago. Haven't we all moved on?
For those reading who aren't scholars of object oriented programming, let me clarify. There are three tenets of OO. Encapsulation, Inheritance and Polymorphism.
Encapsulation means that you write pieces of code in a self contained unit. The internal implementation details should not be relevant, and hence not visible. This means nobody can break your encapsulated code by changing its internal state - or at least not without jumping through enough hoops to question the validity of the approach. Take the Page class in asp.net, this does a bunch of things that you don't have to care about, and frankly you can't easily change, it just works the way it does. If you want to change the behaviour of an aspx Page, which by default is quite boring to look at, you have to derive from it and add your own logic. The mechanism for this is...
Inheritance, which is the ability to derive more specific code from code that exists already. By inheriting, or if you prefer, deriving from it, you gain that functionality in your own code, and can specialise and enhance that behaviour for a more specific purpose. For example, by deriving from Page and overriding Render, you get to change what the html output of that Page looks like.
Polymorphism is the ability for other code to treat both the more general code, and the derived code equally, and swap out one piece of code from another. In the Page example above, it is polymorphism that allows the rest of ASP.NET to use your derived Page as if it was any other Page without needing any other changes, except at the encapsulated site (i.e. Your custom aspx page)
.NET also supports events as a first class construct. This is close enough to the GoF Observer pattern as to not really matter. It's effectively a means of transferring control from one piece of code to another interested party in response to some "event" such as "I am about to render html". Subscribing to events allows code in another place to act in response, perhaps to switch the target browser to mobile, or to drop a timestamp literal into the page, who knows. But this is what they're for, external objects are notified when things are about to happen or have happened, and they can then act accordingly.
But AutoEventWireup changes all of that. The first mistake is subscribing to your own events. Firstly, there is an overhead in doing this. Not a huge one, but enough to matter on a heavily visited site. Secondly, it's detached from the source of the event - your event handler isn't guaranteed to be called, a base class in your inheritance chain is quite within its rights to *not fire* the event at all.
The second mistake is in requiring the handler method's name to match a naming convention as it's vulnerable to typos
Thirdly, you can switch it off without requiring recompilation, either in the aspx markup or in web.config. This will break your site like crazy if you take advantage of autoeventwireup (or the default new webform template), and you're going to struggle to work out why. Worse, it's *on* by default. You could find yourself with a new web.config file in deployment that doesn't switch it off, and some old random code could get called on *some* of your pages (probably the ones you outsourced to the lowest bidder) and you'll never work out why.
So please please MS, and MS devs, always override the OnEvent methods instead, it can't be broken by client code like events can, it's more OO (encapsulated, and polymorphic) and your code will be cleaner and more robust for it.
That's all.