That doesn’t mean it’s a bad environment to work in, quite the opposite actually. If you look at popular libraries for node.js or ruby, you will often find that the BCL or Microsoft’s .net Libraries already have something built-in, and it’s usually rock solid and fast. You will find Microsoft supplying the big features that everyone uses or will use – LINQ, LINQ 2 Sql, Dynamics, TPL, Async/Await, ASP.net MVC are just a few I can think of. Combine the “No one ever got fired for choosing Microsoft” mentality in big enterprises with the fact that the vast majority of software development is done in enterprises, and you see why this attitude exists and why Microsoft has to deliver.
There is no denying that Microsoft had quite a few blunders, of course. WPF, EF and Workflow were downright garbage in .net 3.x, WCF is overly complex for simple scenarios and Velocity… let’s just say that I’ve never heard anyone say anything good about it, and looking at it’s API I doubt I’ll have good things to say about it. Then, there are signs of the more than 10 year legacy that .net already has, together with the desire for backwards compatibility. System.Configuration is horrible because you cannot just create a Configuration object from a string or any other mechanism, that thing is hard wired to look at a file on your hard drive, which makes it really inflexible for modern, multi-tenant deployments. Have you tried parsing JSON in .net? How many different JSON Libraries/Deserializers do we have as part of the Framework? And how many did Silverlight add? And yet, people mostly prefer the Newtonsoft JSON.net. Have you worked with the ASP.net Provider Model, specifically Membership Providers? Only a mother could love the API of that thing. And speaking of ASP.net, have you ever tried catching an “Attachment too large” error? The error that gets thrown twice, once in IIS before it reaches your app and then in ASP.net itself without a clear way to associate it with the request?
I could go on and on and on about things that are seriously broken in .net, and I haven’t even started about testability yet (there is a very good reason for products like TypeMock to exist). It is still overall a great experience, but it is frustrating that we can’t do much about the shortcomings of it. To work around the stupid file handling and Configuration madness in ASP.net, we would need a whole different web server since we can’t just patch IIS or the ASP.net core components thanks to their closed source nature. Of course, running Mono on nginx is a way to work around this, but enterprises won’t approve of such a setup and if it breaks, your behind may be on the line.
I’ve often experimented with different setups, only to realize that I really like C#. I like its static nature which usually gives good, understandable compiler errors rather than cryptic runtime errors (face it, rails can be a pain to debug). I like that I can mix in dynamics for non-critical things like view models. I like that the Microsoft-provided libraries are mostly good. I like that we can buy support and that there are tons of resources about most topics, since everyone uses pretty much the same stack. I like that they keep backwards compatibility so sacred, even if it means that there is a lot of obsolete stuff in the API (like System.Collections.ArrayList – there is no reason whatsoever to use it. If you need a container for multiple types, fall back to List<object>.
On the other hand, it can be a really frustrating experience when you run against a wall that you can’t climb because of its closed source nature and Microsofts reluctance to fix things (Take WPF in .net 3.5 as an example: Things were reported but not fixed. Then 4.0 comes out with Visual Studio, they run into the same problem (e.g., the scrolling popup menus) and HotFix it. That was the moment I’ve given up on WPF forever) until a major release, if ever. Sometimes it is a really tough sell to use other non-microsoft components like RabbitMQ instead of MSMQ (Search for MSMQ on MSDN and look on the big highlighted article – to me, that’s proof that Microsoft doesn’t care about their own message queue anymore), or NServiceBus, or a sane ORM instead of Entity Framework.
Most applications start out as simple CRUD applications, and it is usually a lot quicker to start them in node or rails. However, simple CRUD applications usually evolve into more sophisticated pieces, requiring more business logic and safeguards in different places, and here I must say that .net shines – in the long run, its strengths play out well.
However, I really think that we can do better in the web world, much better. Chad Myers had an interesting posting, and even though it was ripped to pieces by Rob Connery, it still holds a lot of truth. Web Applications are unnecessarily complex. I will write a follow up posting with some thoughts about this.
My conclusion would be that .net is overall doing perfectly well. It is used by tons of companies for very important apps, but it was never aimed to be a “hip” language. Microsoft is deeply rooted in the Enterprise, they are pretty much the exact opposite of Apple. That doesn’t mean that they do a worse job at it, it just means you won’t see as much about it since enterprises like to keep their “secrets” internal and err on the side of safety/secrecy. I have no doubt that there will be .net jobs for the next decade and beyond, while some other language will come and go.