The internet was invented so we could publicly complain about things, right? http://robsaunders.io

Mar 30, 2016

Today I accept that Rails is yesterday’s software.

I make my living, and run my entire company, on Rails, and it has been the underpinning of my career. I’ve sold every client I’ve ever had on the virtues of rapid, agile development and the insane community involvement of the Rails platform. I’ve watched DHH with ‘interest’ and admired most of the things he has to say. I’ve watched other platforms spring up to compete and enjoyed the competition between them. I stumbled across Why’s guide, I absorbed books by Pragmatic Press, watched Peepcode tutorials, Railscasts, subscribed to Codeschool, and felt a part of the industry which formed around this new style of development. Design played a bigger part not just in the websites we made, but the development tools we used. Even our API documentation appeared to breathe life.

Development felt cool, and this was a big deal given the culture we were used to.

Perhaps alongside other factors, it attracted a new wave of developers. You started to see jolt-cola drinking wizards unconcerned about their appearance being replaced with skinny-jeans-wearing bearded hipsters, (admittedly I am as guilty of this as any of us). In our company, we would cycle to work in our converted warehouse office space, eschew job titles and hot desk on couches and cafes around the area if we felt like it. Design and code blended as one and the birth of the full-stack developer made them commonplace.

Being a programmer was hip, at least for a while.

Before Rails came along, we were in a monolithic nightmare of JSP and PHP and over-architected home-brewed frameworks left behind at your place of work by some developer who once thought he understood design patterns and decided to roll his own MVC framework. Opinionated software was the way of the future. Object Oriented design was easy to grep, and our lives felt fun again. We could feel like we were not only in control, but that software was working for us. We could focus more on the things we always felt were important, but never practiced — typography, great design, responsiveness, and elegant data design.

REST and MVC were patterns we had heard before, and maybe even used in some form or another, but it felt like work before Rails, or more specifically — before Ruby.

Ruby felt like no-nonsense code. It certainly had what seemed like an elegant syntax, simple even — and simplicity means there are fewer places for bugs to hide, right? Fewer places for braces and semicolons to hide, no debates about BSD and K+R style, and duck typing everywhere! Embrace the simplicity!

I think it is this very misunderstanding of simplicity, contrasted with easy, that underlies and implicitly causes the problems with web architecture today. This is not a new idea, and has been evangelised by greater developers than I (Richard Hickey for example amongst others), but it is still largely ignored in the modern web development community.

The ambiguous, english-like syntax of ruby that makes rails so easy, is exactly why it’s not simple.

The meta-programming and object injection that makes it easy to install 1,000 gems into your project without a single line of configuration, is exactly why it’s hard to debug. It also gives you zero confidence or guarantees about what you’ve just added to your work and whether it all plays nice together. You may have just peed in your own kiddie pool.

The magic of active record, the crazy levels of duck typing and the expressiveness of ruby, are exactly why it runs poorly even on your development box, and costs so much in server fees when you try to scale. It’s why you have to build a caching strategy in as a requirement from first line of code.

It’s why you get confused when something randomly breaks and you don’t know the first place to look, so your solution is hit google for others with a similar problem first instead of trying to reason about your program.

It’s why your testing suites are out of control because errors that should be caught by either your programming environment or your compiler, are written as verbose levels of multi-stage tests.

It’s why every programming task seems to include a small amount of thinking about your implementation, a small amount of time implementing it, and the rest of the day debugging the regressions you introduced. No matter who you are or what your coding skills are like.

Competitors to Rails seemed subject to the same problem — basing themselves on interpreted, slow languages that favoured ‘easy to learn’ over ‘easy to maintain’. Package systems made it easy to install a mess of whatever gaps you had in your development knowledge — and who cares if it completely polluted every piece of code you wrote from that point on. It appeared to work.

As I sit here, looking at a stack trace of my coffee-script code, which runs through a ruby-based javascript interpreter sitting on top of the asset pipeline which runs through rails and spits out an error via a gem which globally hooks into the exceptions bubbled up from the depths of hell, and yet the stack trace can only give me a vague file reference and the type of error it is, but not actually point me at the actual error at all, and this ajax call has no good way of debugging itself besides injecting a debugger into the runtime and breaking and poking around, and the myriad of gems we use all seem to be conflicting into —

You get the point.

Rails was a pioneer for the web — it gave us the desire to be better, and not trust our own isolated skills so much but to learn from the ideas of the wider community. It got us involved in the entire process of building an application on the web. But, to rely on an old trope, what has it done for us lately?

The roadmap for Rails is bleak. Asset pipeline still sucks, it’s still slow (and always will be), and errors are becoming harder and harder to reason about as the stack has more and more libraries are piled onto it. Problems are built into it by design, because of its preference for ‘easy’, which, somewhat ironically, is the very reason we moved away from languages like PHP in the first place.

Platforms like node.js suffer the exact same problems. We need new thinking, not just repackaging of the same old failures. I should be spending time writing code, not debugging a haystack of mutable, dependency-wired mess.

Forward thinking concepts from other areas of language design like aiming for more modular, immutable, compositional, simpler less dependent code makes so much sense for the web — but we are stuck in a voice of OOP and inheritance and meta-programming that encourages lazy thinking and lazy software.

Swift, Rust, Go, and the rest of tomorrow’s languages, can you marry modern thinking, build a community with simple as a core design goal, and save web development from itself?