Here's what I think the problem is: we started with a language that is insufficiently reflective (so that it can only be extended in limited ways from inside) and that has too much syntax (making it difficult to adapt to more declarative tasks). So we have containers, code generators, interface generators, EJB compilers, and bytecode enhancers, XML config files running out the ears, and on and on.
It doesn't have to be that way. Try building web apps in Ruby, using Borges. Or Smalltalk, using Seaside2 or Comanche. Or in Common Lisp, using KPAX or WebActions.
Or VisualWorks Smalltalk, using Web Toolkit. Creating SSP pages and servlets in Smalltalk is a model of simplicity. You have to wonder when (or even if) developers will start to realize that there are better ways than the Java and C# paths to heck...