 As you can see, I'm trying to approach looking like the image I always put up before my talks, getting closer and closer every time I do this. Maybe I should roll my sleeves up. It would be a little bit more accurate. So the title of this talk is Those Who Forget the Past. Some of you have seen this at SCNA, but this is a slightly different version of it. I am Gary Bernhardt. I look like that on the internet. And I run a company called Destroy All Software. And this talk structure is going to look like this. First of all, capability and suitability. I'm going to define those terms. I will give you some examples of what I mean by those words. Then we'll look at patterns over the history of the industry with capability and suitability. Then the jump drawer, every talk needs a jump drawer, and this one is about relationships. And then finally, productivity, the word productivity, which I hate, and then some divination about what might happen in the future. So first up, capability and suitability. By capability, I mean the power for a software system to express an idea. This could be a language or a practice or a tool. And the canonical, capable system is Lisp. And I'm thinking here of a fully featured Lisp with macros and everything like Common Lisp, for example. Common Lisp is very good at expressing arbitrarily abstract ideas as long as you don't care about the syntax. And, yeah, so that's capability. Suitability is the power to take the capability you had, the ability to express an idea and actually build working software that is reliable and build that software reliably. So this is a different thing. This is not just saying, I can express an idea, but this is saying I can use the idea to do useful work. And the canonical example of this is Java. Java is, in most ways, an extremely boring language from a programming language perspective. There's nothing really interesting in it. It was designed to take a bunch of ideas that already existed and just make them usable to build software that works reliably. So that's capability and suitability. Those are the core ideas for this talk. I'm going to give you a few examples to make it a little more concrete because that was very abstract. I have six examples spanning 47 years of the industry, the first of which is 1957 Fortran. Fortran is pretty much a pure capability response to assembly language. It is slightly higher level. It has things like if and variables, although also it has go to and go to is extremely widely used back in the early days of Fortran. But it is a slightly higher level vocabulary. It allows you to express slightly higher level ideas. So it's a capability response to assembly language. 11 years after Fortran, you get structured programming. This is, of course, the idea of using ifs and whiles and things like that instead of just throwing go tos everywhere. And this is a pure suitability response to Fortran. So you have this sequence where you have assembly language, which is an extremely dangerous system to program in. Then you have increased capability with Fortran. And then structured programming takes some capability away to make a more suitable system, to make more reliable software. And of course, this is when you get the famous paper go to considered harmful, which has been the source of many terrible jokes in the software industry since. And this is Dijkstra, of course. And I have a quote, a contemporary quote about structured programming, someone reacting to this new idea of using ifs and loops instead of just throwing go to everywhere. And here it is. Structured programming is a nice academic exercise, which works well for small examples. But I doubt that any real world program will ever be written in such a style. So this is if they're talking about, and while, and for, these kinds of things. So that's 68. Two years later, 1970, the relational model happens. 1969 plus or minus one year is where everything happened in software, for those of you who don't know. The relational model was a almost pure suitability response to flat files. Flat files are very difficult to reason about. You have to do a lot of work yourself. So you give up a little bit of that flexibility by saying, I'm going to put my data in tables, and my table is going to relate to each other, and I'm going to have a fixed schema up front. And then you gain a tremendous amount of reliability in your software. I have another contemporary quote. At first sight, I doubt that anything complex enough to be of practical interest can be modeled using relations. And of course, they didn't win immediately, but for about 30 years, they've dominated data storage. That might be ending now. But clearly, this person was extremely confused. OK, so that's 70. 1985, C++ happens. I'm skipping C in Unix because they're kind of a murky area. But C++ is a very clear capability response to C. In fact, it has two design criteria. It must have classes, and it must be backwards compatible with C. Its original name was C with classes, which expresses both of its design constraints. So C++ is just C, except you can say some new things. But nothing was really removed. A couple of things were changed, but nothing was really removed. It's almost completely backwards compatible. So pure capability, almost. 10 years later, Java, which is a response to C++, a suitability response. Java takes C++ and rounds all the sharp edges off. It removes pointer arithmetic, and it removes manual memory management. It does add some things like namespaces, and it removes free-floating functions. But these are all things that are just constraining the way that you can write software. And finally, nine years after that, 2004, Rails. And the question is, should we consider Rails a capability change or a suitability change? Did Rails increase the set of things we can say? Or did it allow us to say things we already could say, but to say them more reliably? Now, if you asked a Java programmer in, say, 2006, he would tell you, Rails is obviously unsuitable for large systems. But herpy derp derp, we've heard this before with the reactions to the relational model to structured programming. This is what always happens when there's new stuff. So I think that Rails is primarily a capability increase. There are a lot of things you can say directly in Rails that you could not directly say before it. And one of the ways that I'm fairly confident in this is that Rails has a culture of brokenness, as does Ruby, largely as a result of Rails' influence. Most things are broken most of the time. Things don't compose. Everything is being abandoned all the time. It's a very chaotic system. Now I'm a Ruby programmer, so I'm not saying it sucks. It just sucks less than everything else, I guess. But so in a capability system, you see things like this. You see this chaotic behavior of the people because everyone's excited because they can say new things. Ruby, if you're coming from Java, lets you say new things. You get excited, you build your gem, and then you abandon it six months later because the new shiny thing comes along. So this is how I know that Rails and Ruby are capability increases. So those are six examples. Fortran, structured programming, relational model, C++, Java, Rails. Now we can actually talk about the industry, not just about these isolated examples. I think what happens in the course of the software industry is that we gain capability and then we lose some of it as we get a more reliable system. So you have this periodic structure to the trajectory of the industry where it's going up and down in capability. This is the pessimistic view, of course. Hopefully it looks more like this where when we retract into a more suitable system, we don't lose everything we gained. We save some of it. And you can see that with C++ expanding from C, adding tons of crap, and then Java contracting from C++, we're moving a little bit, but keeping most of the improvements that C++ made. Now, why does that happen? Well, I think abundant resources are the primary driving factor for expanded capability. You have more CPU laying around, you have more memory laying around, and suddenly you can write a Fortran compiler because you're not constrained to two kilobytes of memory. You have enough memory to actually compile another language in memory. Or you have enough memory in CPU to run your web app in Ruby instead of having to write it in a faster language. The reaction to this from the people who use the older thing is always that it's too slow. C was too slow when it was new. C++ was too slow, Java was too slow, and of course nowadays, all of those are considered extremely fast, even Java. Now, on the other hand, I think that confusion motivates contractions into more suitable systems like C++ to Java. And you can see this in structured programming. Go-to, arbitrary go-tos, are extremely confusing. So you restrict yourself to control constructs like if and while, it's more understandable. Same thing with the relational model. You add some structures, some rigidity, and things are more understandable. The reaction here from the people using the older thing is always that it's too limiting. And you can see that in both of the quotes that I showed you about people saying they don't think you can build software in these constrained systems. So, primary motivating forces in the industry, abundant resources and confusion, which lead to expansion and contraction phases of capability, which lead to people whining that things are too slow or too limiting. Now onto the junk drawer, relationships. So, C was too slow, C++ was too slow, Java was too slow, Ruby was too slow. I don't see any reason to assume that this is the end of this list. So I want to present for your consideration the idea that something is going to be slower than Ruby someday. Now, this is important because when that thing comes, it is your job as Ruby programmers, not to say, oh my God, it's so slow, you can't build software in that. It's not too slow, even if it's slower than Ruby. So that's the first relationship point. Second one, suitability is a stronger claim. So if I say I'm capable of expressing this idea, I'm making sort of the common list argument. I can express anything in common list. Well, yes you can, but can you actually build a working system with a team? That's suitability, suitability is being able to actually use it to build real software. So this is the difference between, just because you can doesn't mean you should, or just because you can doesn't mean you really can, which is the lesson of Lisp, at least before closure, which may change this. Now on to productivity, one of my least favorite words. Pragmatic is worse, but not many others are worse. A story first, to introduce this. I had a client before I was running destroyall software, and he was like the VP of engineering or something, this guy was the VP of engineering or something like that at a small company, and he was ranting at me one day, not about the company, but about sort of the industry at large. And he was complaining that people in manager type roles tend to observe activity and confuse it for progress. So they say, Bob is always here, he's here long hours, he's always typing, he closes lots of bugs, which is a very dangerous one, or closes lots of tickets, very dangerous. So he's very productive. But really, all the manager has observed is that Bob is active, Bob is doing things, but it's a different question to judge whether those things are actually moving anyone forward towards a useful goal. So activity and progress are easily mistaken and are not the same thing. And this is a really important point for me, because I type fast, and I use Unix fast, I use Vim fast, and people see me doing these things, and they say Gary's so productive, and I say, well, what does that mean? It means that I'm typing a lot, maybe I'm committing 23 times in two hours, wow, so many commits, so much typing, but could I have done that in one commit that was one page of Diff, maybe? So I am very visibly active, and this scares me because I might be one of those people who's active, but not making any progress. So what the heck is progress? Well, I don't know. Judging activity is very easy, you type a lot, that's activity, judging progress, it's kind of a historical thing, you need a lot of perspective, and it's sort of a subjective thing. But I'm pretty sure that expansion phases, increased capability, lead to lots of activity, like you see in Ruby for the last seven years or so, like you see in JavaScript for the last two years or so. People get excited, lots of stuff happens, but I think that the contraction phase, the increased suitability phase, is where progress happens in this industry. And this is a very unsexy thing to say because I'm basically saying Java is where progress happens, and I don't like Java, I don't want to program in Java, but for the industry as a whole, I think Java is what actually matters, unfortunately. And speaking of what matters, and speaking of trajectory, now we can finally talk about what might the next thing be. So Rails was a capability increase, I claim. But the truth about Rails is that apps are still very bad on the inside, and I think that we as a community are really realizing this, I think this is probably the year of object-oriented design finally actually happening in the Rails world. Because Rails basically took the big angry ball of mud school of design from PHP where you don't have well-defined boundaries, you just have all these pieces randomly talking to each other, represented graphically here. So that's a PHP app, and... What Rails did is it gave us the slightly smaller, big angry ball of mud school of design where you shave off the edge of the app and you say that's the good part. Now, in 0607, that small part would be the model layer, the controller layer was still a big angry ball of mud, and someone, I don't know what year it was, 08 or so, 09, someone had this brilliant idea that if we invert these, then everything will be perfect. So then you have the very thin controller layer that's well-designed, and you have the giant model layer that's still a big angry ball of mud. So clearly problem solved, right, everything's perfect. Not so much. What is going to happen next? What is the next thing that's going to happen? Rails only gives you two buckets to put code in, controller, model. We've tried both, neither of them worked very well. So what are we going to do? What will the post-rails contraction be that will actually lead to us designing good systems? I'm going to present you two possibilities that I can imagine happening of many, and the first is that Goose wins. This is growing object-oriented software guided by TESP, by Freeman and Price, and it is the canonical book about doing outside-in test-driven development where you design the lower layers of the system by building the higher layers of the system first and the higher layers, stubs and mocks design the lower layers. That probably sounds really weird if you haven't done it. Read the book, it's good, it's good stuff. I've been doing it for five or six years. The problem is, this is obviously impossible. And I'll tell you why it's impossible. It's impossible because outside-in TDD is a nice academic exercise, which works well for small examples, but I doubt that any real-world program will ever be written in such a style. Very easy words to say when something is new. So that's the first possibility. The second one is that one of these guys wins. Haskell, Clojure, Erlang is what those three are. Finally, the functional revolution comes after 60 years of it being coming next year for 60 years. Of course, the problem here is that this is obviously impossible because functional programming is a nice academic exercise which works well for small examples. So those are my two possibilities. Both of these, I look at them and I say, I cannot imagine these winning in the way that the relational model won, that structured programming won, that Java won, and languages like it. I can't imagine these winning, even though I've been doing both of these for a long time. But I also wouldn't have been able to imagine structured programming or the relational model winning in 1968 or in 1970. So I think that my intuition about this could be wrong. Of course, maybe neither of these will win. I'm not claiming they will, but I could almost imagine it. In either case, whatever it is, I'm pretty sure it's contraction time, especially in the Ruby world. With the growing unrest about bad design and active record and the massive coupling that controllers cause, Rails controllers cause, all of this stuff is really coming to a head right now. I think something is going to happen. Some contraction has to happen. So if you want to read more about those quotes I used, I have them at this URL. This will send you to a PDF from, I think an article from the C++ Journal in the 90s that contains these. It is your job to figure out whether they are satire or whether they are real, and it is harder than you might think. So with that, I am Gary Bernhardt. I run Destroy All Software, which has screencasts about outside NTDD and building smaller, happier balls of mud. And I thank you guys very much for listening to me.