Refactoring
If It Bleeds, It Leads
Summarized using AI

If It Bleeds, It Leads

by Evan Light

The video titled "If It Bleeds, It Leads" features Evan Light discussing the evolution of the Rails framework and the importance of returning to the simplicity that initially attracted developers to Ruby on Rails. The talk highlights the Rails community's shift towards increased complexity over time and suggests ways to recapture that simplicity. Key points include:

  • Introduction: Evan introduces himself, his background in programming, and his upcoming work with Basho. He explains his organization of RubyD Camp, an unconference that fosters in-depth discussions rather than traditional one-to-many lectures.
  • Loosely Coupled Systems: The talk begins by emphasizing the value of loose coupling in programming, using Rails as a focal point. Evan discusses how dependency inversion and injection can lead to better architecture, yet raises concerns about this approach within Rails.
  • Historical Context: Evan draws parallels between the evolution of Rails and the past trends in Java development—particularly around the advent of Enterprise JavaBeans and the Spring Framework—showing a historical cycle of obsession with complexity and loose coupling.
  • The Paradox of Choice: He explores how the abundance of options available in the Rails ecosystem may overwhelm developers, referencing the book "The Paradox of Choice," which discusses how too many options can lead to decision paralysis and dissatisfaction.
  • Rails Patterns: Evan encourages attendees to study "Patterns of Enterprise Application Architecture" by Martin Fowler, asserting that Rails is built on several design patterns that should guide development practices. He emphasizes the need for choosing the right tools and adhering to established patterns to prevent unnecessary complexity.
  • Active Record vs. Data Mapper: A significant portion of the talk critiques the Active Record pattern, advocating for the Data Mapper pattern instead. Evan explains that while Active Record is sufficient for simple mappings, complex situations require a more robust separation of concerns.
  • Simplicity in Design: He concludes that while the Rails community has made significant progress, there's a pressing need to re-evaluate complex frameworks and strive for simpler, more maintainable architecture.

In summary, Evan Light urges the Rails community to recognize the pitfalls of complexity, embrace simplicity, and learn from historical programming paradigms to improve future development practices.

00:00:15 Well, I guess I'll do my own introduction. I maliciously didn't give them a lead or bio for me, and that’s fine; I hate it when people do intros for me. So, if you hadn't guessed, my name is Evan Light. Alan Squirkins is in the other room, so if you meant to see Alan, you want to be in there.
00:00:30 So, I’m really Evan Light, and I don’t have any titles or anything because technically, I’m unemployed for two more days—yay! I’m starting to work for Basho on Monday, and I'll talk about that later. Here are all the ways you can reach me. Don’t worry about writing any of this stuff down, except maybe the Twitter, because I’ll have a link to the slides on GitHub. These are all HTML, JavaScript, and CSS, which is why they’re no-frills, because I suck at CSS.
00:01:00 RubyD Camp is an unconference that I run. I should probably take this so I can pace and not make the whole stage collapse. RubyD Camp is a conference that I run in the Northern Virginia area. It’s an unconventional event, particularly because it’s for experts, intermediate people, and new folks.
00:01:30 I feel that events like this aren't necessarily the best environment for learning. Conferences are good for getting a brief introduction, but I prefer depth of conversation and significant learning. RubyD Camp focuses on conversation and drilling down on topics—not so much one-to-many dialogues but rather many-to-many dialogues. However, it’s a small event, so we’re full this year, and I can’t tell you about the D Camps since you can’t attend anyway. Sorry.
00:01:56 If you have any questions about it, you can Google and find more. Now, this talk—well, this isn't exactly where it started. But before I really begin, if you get anything from this talk, please read that damn book. 'Patterns of Enterprise Application Architecture' by Martin Fowler—I'm giving you permission to write that down now. Read the damn book, and I’ll tell you why.
00:02:24 First, I’ll tell you where this talk came from. There’s this little guy, long hair, a studded belt named Avdi who keeps running around here. He likes to talk about how we should be doing a lot more with Rails, especially how we should be using plain old Ruby objects for our model instead of Active Record. This drove me crazy, and that's where most of my talk topics come from—things that annoy me that I want to discuss.
00:02:55 So, the slide said 'loosely couple all the things.' How many of you were in here for Scott Bell's pretty awesome talk? I wish there was more carryover. For those of you who aren’t familiar, we’ll talk very briefly about coupling. This is a simple example of tight coupling, and I’m demonstrating it. We can discuss definitions later, but in this case, we have this user controller.
00:03:09 The user controller refers directly to the user model; it is tightly coupled to it. The user controller depends on the user model in this example. Hyperbolized, we inject dependency or inversion of control, depending on what you want to call it—more buzzwords for you. We inject a finder into the user controller; we inject the user, and we depend on this interface. So we have a weaker dependency; I’d say it’s a looser form of coupling.
00:03:31 This is the sort of technique that’s being advocated for across the board in Rails. Generally, I think loose coupling is a good idea, but not necessarily with Rails. More on that as we progress. First, a history lesson, because I’ve been programming for quite a while; you can look at the beard—I’ve got a lot of gray hairs. I’ve been programming for I guess 17 or 18 years now.
00:03:45 A significant portion of that was in Java. In 1995, it was great, and then Enterprise JavaBeans came along in 1999. At the time, we all thought it was great because there was so much manual labor involved on anything server-side. Before EJB, Java gave me this framework where if you just write lots and lots of XML, you don’t have to write very much code.
00:04:05 Fast forward to 2002, and this crazy thing called the Spring Framework came along, which is an inversion of control-based framework. We talked about loose coupling a moment ago, where you inject things into other things without hardwired dependencies, and everything is connected together.
00:04:24 This was an improvement over EJB, but it was still XML-based. Shortly thereafter, I guess Java development, or server-side Java development, became more commoditized. More people got into it, perhaps as it got a little more sane, though many were really jumping on the J2EE EJB bandwagon.
00:04:44 The one thing that Java had going for it, and still does, is the massive marketing machine behind Sun, now Oracle, and all the money it had behind it. In 2003, we saw more developers, particularly overseas doing Java development. There was a lot of demand, but rates started to go down, and developers weren’t as appreciated, though there was more standardization. Standardization is generally a good thing if you want reliable, predictable code.
00:05:20 But I started to notice a lot of smart people, like if any of you have heard of Relevance Inc in North Carolina—almost that entire company now does Rails. Ironically, they started doing Rails back then. A guy named Dave Thomas, the author of 'The Pragmatic Programmer' and the 'Pickaxe' book, got popular, and the Rails book came out, and everybody started doing Rails.
00:05:40 Now, we’re starting to follow that trend with Ruby and Rails, particularly, and I’ve noticed some things that I consider predictors for that switch in the Java ecology. There were, I don’t know, 10, 15, 20 different jars—libraries—to do the same thing, a lot of which were good, some terrible, but how would you know which ones were which?
00:06:00 They developed a loose coupling fixation. Remember I said loose coupling is a good thing, but the Java community grew overly obsessed with it, and it made some of us—at least me—when they saw Spring, feel it was horrible, even though it had some virtues. Yet, it chased a lot of us away.
00:06:19 So, I’m asking you to consider: where is Rails now? Rails is about ten years old. I’m getting ahead of myself—Rails is about ten years old, which is about where Java was when I jumped ship, and I saw a lot of other people jumping ship too. So, if Rails is good for making small apps, it enables rapid development.
00:06:35 Note: small, not large enterprise apps. It makes development fast, as I’m sure many of you know. Before I go much further, how many of you do Rails for a living? Funny—the almost every hand in the room is up. Sorry, keep your hands up for a second. Now, how many of you use just plain Ruby?
00:06:54 Okay, and that’s very few—a minority. By the way, that’s soon gonna be me. So, Rails goes a lot faster than using selective tight coupling and constraining around the first 80 percent of what’s common in web development and the problems we usually solve.
00:07:15 Some examples of that would include how we get mappings for free from the model to the controller or from the controller to the template, and how we get the metadata mapping from Active Record to the database. These things make our development go a lot faster. But what about the remaining 20 percent? What about the harder problems we have to deal with?
00:07:32 We want to split our apps into two, or our models grow too big or complex. We need some kind of guide for how we can help the design of our domain. This is where we get into a heuristic problem; this is not something that can simply be solved by automation. Now it’s got to be a problem driven by expertise, trial and error!
00:07:52 I did a lot of research for this talk. These slides might not look like much to you, but I spent 60 or 80 hours on this presentation—almost all about the content. Again, I suck at CSS! But the way I see it in the Rails community now is that we are living in a time a lot like Java circa 2005: we have an overabundance of options.
00:08:07 For example, if you want to add authentication to your app, if you’re an experienced Rails developer, you can easily think of seven to ten different solutions, and there’re probably even more popular ones than that. So how do you choose?
00:08:29 This quickly brought me to think about a book I’d heard of, called 'The Paradox of Choice.' I actually read a fair amount of that during my research for this talk, finding a few pithy anecdotes in there. One of them is, 'Choosing well is especially difficult when we’re trying to make the best choices.' Schwartz also talks about a term called 'satisficing,' which means we operate from different criteria for what satisfies our needs.
00:08:49 Some people are more perfection-driven, wanting to explore all the options. Then there are those willing to compromise, looking at a small subset and picking quickly, which can be dangerous. If you go for perfection, you’ll probably end up frustrated, spending lots of time and money.
00:09:07 Next, we’d be better off if we embraced certain voluntary constraints on our freedom of choice instead of rebelling against them. This isn't a reference to the NSA—I'm actually talking more about what Rails has introduced us to: a convention-based approach to development.
00:09:21 Now, granted, some of you may have seen a similar thing with Objective-C protocols before, but Rails made it much more popular. So, when we talk about choosing, Schwartz also noted through some studies—which I won’t cite in these slides, but you can read the book—that we're prone to choosing badly.
00:09:37 This issue likely stems from evolutionary factors; we tend to use available information over reliable information. For example, you might really trust Steve Klapnik or Katrina Owen, but maybe they haven’t blogged about a specific topic or another. Despite viewing them as reliable experts, we often tend to trust nearby sources over the reliable ones.
00:09:53 Say you have a colleague sitting at the desk next to you who’s written a blog post about something; there’s a strong likelihood that despite being rational beings, you're probably still going to go with your less expert colleague—sounds crazy, but it’s something to think about next time you’re making a choice and asking a colleague.
00:10:12 We’re also surprisingly vulnerable to effective advertising. You probably have that naive belief that you’re not affected by advertisements, but think about how much more aware you are of certain products after seeing clever advertisements on TV.
00:10:28 I mention this because I think it's us—our community might be obsessed with new things. The community, perhaps less so than before, has matured over almost ten years. Alan K has this wonderful quote that anything that grows faster in education tends to become pop culture. So what's our current pop culture?
00:10:46 I’d contend that it consists of patterns—every one of these is a link. You can click on these later when I put them online, and there isn’t always a gem associated with them. Interestingly, there’s not always a gem for Principles of Object-Oriented Design, but there is now a gem for that.
00:11:02 This leads me to the title of this talk—you guessed that we’re going to talk about patterns, as I already told you to read that damn book—'Patterns of Enterprise Application Architecture.' Read it. Patterns are exemplars, and when we look for patterns, certain steps seem to be involved. First, we identify practices that we perform routinely.
00:11:15 Next, we decide to give them some kind of nomenclature. Scott’s favorite quote is, 'If it can be imitated, it can be automated.' For those of you not here, automation can be a bad thing. We create a tool from the pattern, use the tool, and then we might fall down if we become limited by those tools.
00:11:30 Once we find out what we dislike about the tool because it has limited us, we go back to step one. Rails is made up of patterns. Ironically, every single one of these patterns is in 'Patterns of Enterprise Application Architecture.' That book came out one year before Rails. I’ve never heard DHH say that POEAA informed Rails, but one could argue that it did.
00:11:54 So, where did all these patterns I cited come from? This leads us to step five: what's wrong with Rails? Let’s talk more about Martin Fowler because we can’t get enough of him. Refactoring tends to break big objects into smaller objects, big methods into smaller ones, and indirection can be a double-edged sword—it can make programs harder to read if they consist of many objects that delegate to others.
00:12:18 My friend, Brian Hogan, said that refactoring the patterns can be better than just starting with them. To borrow a bit from Leonard Bones McCoy: 'I know engineers—they love to change things.' Now let’s get specific and talk about Active Record.
00:12:35 Note that it's 'Active Record' with a space— we’re discussing a pattern described in 'Patterns of Enterprise Application Architecture.' Without the space, we’re referring to the library you probably use in your day-to-day job. This is what Avdi and many others say we should be doing.
00:12:58 On the left is a person model (let’s say it’s a domain model object), and this thing on the right—well, that would be Active Record, but that’s not really what Active Record is.
00:13:12 There’s a pattern for that called 'Table Data Gateway' in 'Patterns of Enterprise Application Architecture.' Do you see the trend here? So don’t bother reading the whole paragraph, just focus on a couple key sentences: If the mapping is simple, Active Record is adequate; if the mapping is complex, a Data Mapper is more suitable.
00:13:30 How do you choose? This is the data mapper pattern; we have a domain model object on the right, which has behavior and properties, and a mapper in the middle. We'll talk about what a mapper is with a database on the other side. The mapper's purpose is to separate the database from your domain model.
00:13:47 It’s responsible for all persistence and data lookup, creating domain model objects when fetching data from the database and persisting them when needed. Thus, your domain model object can be completely ignorant of how it's stored. Sounds great, right? This aligns with what Avdi was talking about earlier.
00:14:10 It turns out you can use a Table Data Gateway to implement a Data Mapper. Do you see how we’re mixing and matching patterns now? There’s this concept called the Repository Pattern, also from 'Patterns of Enterprise Application Architecture.' I’ve seen people float this one around recently.
00:14:27 The Repository Pattern can utilize a Data Mapper or Active Record as a weak data mapper. A repository facade accepts queries and can expose all kinds of different queries.
00:14:45 It’s sort of like the Table Data Gateway, but it can use other structures behind it, such as an in-memory strategy—your Data Mapper or your Active Record. From this, it generates your domain model object, which is essentially another layer of abstraction you may or may not need.
00:15:01 There’s also a gem for this; it’s a simple gem that’s not hard to read and I found it a step in the right direction. Let’s say you want to use the EDR gem, which stands for Entity Data Relationship. Your Active Record works based on naming conventions—it’s important to have an order data Active Record class and an order domain model object.
00:15:24 The EDR gem has a problem wherein if you want to have an association, the model needs to be aware of its interaction with the repository, which is where I feel the framework has failed—your domain model should not depend on something outside itself.
00:15:41 This is a saturated repository model, essentially declaring queries that interface with Active Record, which is effectively just a Plain Old Ruby Object (PORO). You have an order data class that governs relationships. This dependency on the repository can complicate things unnecessarily.
00:16:05 Now, let’s move back to our domain model where we have associations involving Active Record.
00:16:18 The method for interaction doesn’t need to be tied to the repository; I’d prefer that it’s simply an array of items rather than a repository call-wrap.
00:16:34 Let me clarify: you don’t necessarily want to use this gem. Imagine, however, if your domain model looked like this. The code should be declarative and not tied to a database. Here’s what the model might look like—expressing only what it needs without the framework's overhead.
00:16:52 The idea of the Ruby Object Mapper comes from the theory of complex domain models and the utilization of data mappers. Every gem you use should help simplify that process without relying on Active Record, creating endless complications.
00:17:21 The goal is to have a clean solution free from library constraints. The Ruby Object Mapper is an evolution of a project underway, designed to simplify how we structure our Ruby code.
00:17:36 Maintainers emphasize that there is an abundance of code. The great thing is that this code is designed to be useable out of the box but might require some learning. Practicing with it will yield better results.
00:17:55 Thank you for your time, and remember that there’s an ongoing shift in the Rails community.
Explore all talks recorded at LoneStarRuby Conf 2013
+21