Hacker News new | past | comments | ask | show | jobs | submit login
Rails is not MVC (andrzejonsoftware.blogspot.com)
138 points by andrzejkrzywda on Sept 25, 2011 | hide | past | favorite | 45 comments



practicality beats purity, even though the Python frameworks are moving away from the "MVC" term it always felt like "MVC" to me, in that there are three distinct components - data objects (model), some kind of "load the model in response to a URL and display a template" (controller, what better name is there, I think "view" is a crappy name for that since it doesn't define presentation), then the "template", seems like a view to me - it's the thing you're viewing!

That the model isn't notifying the view through an event system is splitting hairs. The GOF book is much maligned I think because people insist on taking each pattern completely literally down to the last detail. GOF's pattern (GOF didn't create it but they discuss it on page 4, I thought I was crazy until I just checked just now) is specifically "MVC, and because we only know about C++^H^H^H Smalltalk graphical libraries and not very much about stateless HTTP systems yet in 1993, the model notifies the view of changes too, how else would it work ?" IMHO. It's an implementation detail, it's not the essence of the pattern.

So if a JS framework is now doing MVC that includes the concept of "model notifies the view", sure call it "classical MVC" or "model-notify-view-controller" (MNVC). Shrugs.


Exactly. OP offers a great article and commentary, and then arrives at the completely wrong conclusion. Like it or not, MVC is in the vernacular now, and it means any framework organized in model-view-controller structure – regardless of whether the app has stateful views.

A better conclusion perhaps would be to distinguish "stateful MVC" from "stateless MVC"?


It's not splitting hairs at all. It's the definition of the pattern. The pattern was created for stateful UI systems, and it can't be emulated with request-response frameworks without UI state kept on the client side.

But that said, the fact that Rails (and Pylons, etc) called themselves MVC has rendered any definition meaningless, so it just kind of doesn't matter. Truth be told, it was already getting there long before web frameworks entered the picture when Java coopted the term to mean something it didn't in the 90s.

I prefer to use different terminology to avoid confusion, but if you wanna keep using "MVC" for your own stuff, I'm not going to fight city hall.


>I think "view" is a crappy name for that since it doesn't define presentation

http://en.wikipedia.org/wiki/View_(database)


the "controller" in MVC is specifically tasked with responding to user input and persisting those changes into the model. So it's nothing like a database view either, which is traditionally read-only. Like a database view, a template organizes information from disparate sources into a particular presentational configuration - just at different levels of the stack. IMHO they are roughly analogous.


It's different, but it's not "nothing like it". I was explaining where the term comes from, since you didn't seem to know.


I'm familiar with database views, thanks.

Wikipedia credits Trygve Reenskaug with inventing the term "model-view-controller", he was a Smalltalk guy with Xerox at that time - I don't think there's any relation in the origin of that terminology to the notion of a "database view" - otherwise not sure what you're referring to here (here's a link to the original paper: http://st-www.cs.illinois.edu/users/smarch/st-docs/mvc.html)


The downside of muddying the definition of MVC is that it hinders communication about other design patterns that may actually make more sense for web applications, eg. Model-View-Presenter / Passive View

(Edit: if one cares about design patterns at all, that is. Otherwise it makes perfect sense to use MVC as the marketing term it has become and do whatever)


This is exactly why Django used to call itself an "MTV" framework (Models, Templates, Views) rather than an "MVC" framework - we realised that the classic MVC pattern didn't really apply to the Web.

We lost that argument because no one cared - in fact, I think we probably caused a whole load of confusion by not using the same terminology as all of the other frameworks.


> We lost that argument because no one cared

I think the Python community in general adopted that Concept though. The term "view function" is much more common than "controller method". Flask at one point even had the term MTV in the docs I think but we just got rid of it and no longer mention any design patterns there. It's just too much confusion.

Often enough people jump into the IRC channel and ask how to use "MVC" with Flask and what their question really boils down to is how to use a class instead of a function. Design patterns are good and well, but I think documentation should encourage more thinking outside the box.


> encourage more thinking outside the box.

think outside the box ? how about...."controller function" !

There now I've blown your mind.

Who says controllers have to be classes ? Again in GOF days, it was all smalltalk/C++, everything was a class. Not the case with what we use today. A "module of functions" is not terribly different.


You are preaching to the choir. :-)


I have never fully grokked the architecture of web "MVC" frameworks. I now realize it was because of confusing naming.

For people who are familiar with the MVC pattern for desktop UI's, I think it is confusing to use the same name for web frameworks which follow a different architecture. On the other hand, for people without this background, for whom MVC means "like rails", it is probably more confusing to introduce a new name for the same.


I'm a Rails person, but I always respected the Django community. The fact, that you were clear with the MVC vs MTV approach since the beginning was one of the reasons.


Are there any notable Python Frameworks that don't use MTV?


TFA

> In short, we're talking about MVC when a model can notify (through the Observer pattern) the views about the changes. It's not possible in a classical Rails app (it's possible when you use WebSockets, Pusher or a similar technology, but it's not so popular yet.). MVC was popular in desktop apps.

MTV isn't really Web nature. You change the database schema, and the browser client automatically refreshes? I don't think it's really useful. An ad-hoc solution would be better.


pyramid is also following you there however you are right on causing confusion.


I don't see the point in making these subtle pattern distinctions. The model notifying the view is not significant enough of an architectural criteria to merit its own term. I submit that there are dozens of such architectural variances between MVC frameworks and that defining high-level terms to codify those differences isn't helpful. I'll even take it a step further and suggest that a focus on taxonomy diminishes ones ability to think fluidly about the low-level architecture and how to improve it to solve different problems.

This is quite different from (for example) the debates about the definition of REST. In that case there is a seminal paper and all kinds of subtle points leading to material benefits in web apps. What does Model2 have to teach us?


Because it's not subtle. In particular, once you introduce "client/server" into the pattern, you've walked into a completely different domain, with completely different problems, solutions, and patterns, and in particular you suddenly have a great deal of concern over matters of latency and bandwidth, which MVC has no particular consideration for, because the entire paradigm was built on the desktop.

Just like trying to hide network-based RPC behind the same abstraction layer as a simple function call is a profoundly bad idea, inviting a pattern of thought into your head which will encourage you to neglect the client-server component of your solution is also a bad idea. Even if you think it won't fool you that badly, why let it fool you at all? Why not actually think of it in the proper terms?

Some combination of MVC and client-server is possible, but even then further specification is required to be clear about what you're doing, because the client/server can be placed in arbitrary locations in patterns, and particularly for web environments one must be careful to specify which components of the various elements are the canonical ones, where they live, and which are ultimately just cached copies.

Further it appears to be empirically the case that people who get MVC-happy begin to mistake MVC for being the one and sole and singular definition of good design, and start sticking it places it doesn't belong, while neglecting the proper design practices that should be used. MVC is actually a brain bug; seeing someone go on about MVC is an almost 100% accurate marker for someone who doesn't deeply understand design at all, and just has a hammer and is hitting things with it.


Your reply is spot on, but wasn't the time raise this issue 7 years ago when Rails was released? Or maybe earlier if Java frameworks were self-described as MVC? To try to push Model2 now seems like an impossible task with almost no reward. It's like complaining about common usage of the word "hacker". It serves no one to take up arms, just let it be and move forward. Maybe coin a new term.


I've been raising it for a couple of years now.

And my beef isn't the terminology issue, though I would observe that if we decide to just declare that everybody using "MVC" is using it correctly, we immediately dilute the term to the point that it has no meaning whatsoever. It's more the brain bug part.

I wouldn't want to "fix" MVC usage, we'd be much better off simply eliminating it. It's almost never used in a productive manner. As for what to replace it with, that's easy: DRY, Don't Repeat Yourself. The particular structure of the code is always particular to your local problem, rarely fits into any particular paradigm when considered as a whole anyhow, and the real design criterion is DRY. I can't quite say it's impossible to have badly-designed code that is also completely DRY, but I would imagine it must be a challenge.


I don't see how you can call this a subtle pattern distinction.

MVC contains 3 words: 'model', 'view' and 'controller'. These interact completely different in "real" MVC and in most "MVC" web frameworks.

The point isn't the observer pattern; that's just a tool. The point is that in MVC, only the controller talks to the model. The model in turn notifies the view, but doesn't know anything about it. In Rails & co, the controller knows a lot about the view. Also, there typically is only one view per controller. These limitations are not there in real MVC, because the controller does not know anything about the view.

This nearly complete independence of the three components of MVC is what makes it good. Exactly this is what traditional web frameworks don't have.


Agreed. I can't find any insight or advantage in making this kind of a distinction.

The article attempts to address it by saying that people attempt to implement Model2 on a Javascript front-end. That is awkward. However, it isn't awkward because you should be using real MVC. It is awkward because Javascript is asynchronous and you want to make sure the user interaction stays responsive without devolving into spaghetti. The key insight is "asynchronous" rather than "let's do REAL MVC!"

I've seen this obsessive focus on taxonomy of solutions divorced from specific problems in domains outside computing. I suspect it's a cultural thing. Some cultures obsess over gadgets more than others. That works out until people start arguing about who has the shinier toy, instead of actually using said toys as tools.


> It is awkward because Javascript is asynchronous and you want to make sure the user interaction stays responsive without devolving into spaghetti.

This is exactly the feeling I've been getting recently as I foray into writing my first Chrome extension. The asynchronous nature of XHR is ending up making my code a little more spaghetti-like that I would prefer. Would you happen to have any recommended resources for possible approaches to addressing this issue?


So could one call Rails a sort of "synchronous MVC" and javascript MVC "asynchronous MVC"?


Hmm. Maybe? Seems impoverished to me.

Someone on the comments for the original article said, the big idea in Rails wasn't so much MVC as much as separation of concerns. I'm on-board with that. Thinking in that way has brought a lot of advantages for me over the years I've been working with Rails.

By extension, if the big idea is "separation of concerns", then I should be applying it in my non-Rails code too, whether that's "MVC" or not "MVC". In fact, my small taste of functional programming allowed me to play with "separation of concerns" in a different coding style, one that I've imported back into the Ruby code I write. Write functions without side-effects. Treat data as immutable. Interesting times.


He is correct, but I doubt there is much confusion. The term MVC is used mainly to illustrate the separation of concerns, which is, IMO, the number one task for any framework.

Also, as far as I recall, the MVC pattern does not require communication between the models and the views, although it certainly allows it.

Looking at it from another perspective, MVC is a huge buzzword nowadays. It's simply not worth it to be conceptually correct for such a little gain.


Here are the definitions as I know them:

MVC - MVC is separated, Models can notify Views.

Model1 - mixing all code in one place, often seen in first PHP apps

Model2 - separation between Model and View, I think Struts started it. Rails made it prettier.

Yes, the gain from correcting the confusion may be small. However, the topic of JavaScript MVC is going to be huge soon, good to know the differences.


MVC - MVC is separated, Models can notify Views.

I don't think the ability for models to directly notify views can be considered a strict requirement. NextStep/Cocoa followed the MVC pattern closely without having this ability for a long time. (It was added as "key-value observing" in Mac OS X 10.3.)

Without direct notifications from models to views, it's up to the controllers to notify each other of model updates. Personally I find this pattern preferable to having models doing uninhibited notification broadcasting on their own.


Model1 started by everybody (including Servlet, pre-JSP) Model2 started by Servlet + JSP.


In my opinion the term MVC should be avoided. It was badly defined from the very start and has been misused to the point where it is mostly a buzzword. Beginners spend precious time trying to understand the concept using flawed guides and tutorials, whereas experts dismiss the term as being to unspecific. My favourite CS teacher tought us MVC simply by suggesting that we made a command-line client before building a GUI. There must be more practical ways like this which one can use to explain the idea.


I was hoping someone would point this out. I tried many times to understand what MVC meant and came to the conclusion it was ill-defined. The M and V are easy to understand: separation of presentation from content. That is what your teacher was teaching. But the definitions of what C is and how it interacts with M and V are so vague and varied that I eventually threw the whole concept out. (Note that there's no C in your teacher's example. Both command-line and GUI programs have control responsibilities. Actually, both have views too. Yet the distinction is still instructive.)

I believe we should focus on first principles on the one hand (in this case, separation of concerns) and specific problems on the other. Trying to formalize first principles into proto-programs has proven to be a mistake. You end up with ersatz abstractions that don't stand up to interrogation - things that take the form of something precise, but aren't precise. That is confusing, leads to a great deal of useless secondary thinking like "is my program really MVC", and inevitably bogs down in semantic disputes. The more one focuses on such stuff, the less one focuses on real software. It makes you worse at building systems, not better.

First principles are imprecise, but simple and profound. They guide you very well if you let them. Specific designs are precise, but always relative to the specific problem they're trying to solve. Both these levels of abstraction make sense; it's the in-between layer that leads to confusion and should be eschewed. But it's perennially seductive to people who are attracted by the thought of figuring software out at a meta (but still technical) level.

Edit: skimming through the comments in this thread shows how differently, and how incompatibly, people interpret these terms. They exist to provide "a common vocabulary so people can know what they're talking about" (the standard rationale for patternspeak), but the facts on the ground are Babelian.


Hate to say this but I have to agree with you.

It's a nice concept/patterns/principal but it caused a lot more confusions.


agree. Last time when I thought about MVC was interview years ago(hope nobody today ask same questions). As Rails developer with 4 years experience, I'm not care now about these things, I'm care about product.


Here is my personal understanding of the principles of MVC, without regard to any specific platform or implementation:

The model is an API to the domain of the application that is not coupled to anything else. It is suitable for use with a user interface, automation, or as a component of a larger model. If the application domain is about storing data, then the model will provide access to that data and enforce its validity. But the domain could also be something that is not stateful per se, like interfacing with hardware.

A view is an independent component of a user interface for the model, and is tightly coupled to it. It allows humans to interact with some part of the model in some way.

The controller organizes views into a complete end-user application by instantiating them and connecting them to models. It should be minimally coupled to the details of views and models, and is optionally composable.


People have been confused about MVC for a very long time. This article should have come out back in 2003.

Struts, Ruby-on-Rails and most (if not all) of the other server-side web frameworks have always been something very different from the original MVC implementation in Smalltalk, and in fact, most "MVC" implementations in GUI systems deviate in some major way from the original.

From my viewpoint, the "model" is less fundamental in "Server-side MVC" than the other components. The first step towards a framework is having a controller than can serve up different views in different situations: if your form doesn't validate, you can serve the form up again or you can serve a different page if it does... I remember the "bad old days" of cgi-script programming where the form and the form processor were in different scripts and you couldn't do server-side validation the right way.

Ruby has a particular strong role for the model, which has some advantages and some disadvantages.


Interesting point there. I haven't thought about it that way before, because intuitively the model appears to be the most important. And of course it is when you look at the application as a whole, but from a http perspective, the controller is the pivotal point. If you begin to think about the model as an external service for the web application, clearly the controller becomes the most important element.


OP here.

There's one more reason why I want to clarify the situation with terminology.

Apart from being a Rails developer and running a Rails company I also teach Ruby on Rails at a university.

Obviously, I'm not the single source of knowledge for the students, however I want to clearly explain to them what is Rails, what is MVC and what is Model2.

It doesn't help me that when they go to any Rails website there's information that Rails is MVC, which is not.

Here and on my blog you can find comments from people who are confused with the current situation. I'm not expecting that today we're going to agree on any solution. I just want to point out that the definitions and their usage are not precise.


Well technically most backend server MVC frameworks are using the Front Controller pattern. This is perfectly fine MVC though of course different from event driven, which matches a desktop application or JS based MVC.

Really this is just spitting hairs. The Front Controller pattern is perfectly suited to a non-event driven (node) backend system like rails or Zend framework, etc. Essentially the front controller is a router, similar to Backbone.js using hashbangs.

http://en.wikipedia.org/wiki/Front_Controller_pattern


what a strange feeling this post gave me. i've read it, then i thought about other frameworks, even wanted to argue, that purity in terminology is overestimated, and you know what? who cares.

i dont know if thats because client side frameworks are becoming much more important, and talks about differences between django and rails sound more and more pathetic, or maybe its a personal thing and i just need to get some sleep )


Ceci n'est pas une pipe.


Is JavaScript MVC really JavaScript MVC (I've never used any so I don't know)?

And is MVC the right pattern for rich UI app (GUI or Web client)?

The last time we tried to use MVC in GWT app, it didn't work out quite well. We decided to use MVP + EventBus instead.

These days the MS camp came up with MVVM (a variation of MVP or more closely related to Presentation Model, which I think MVVM is borderline architecture astronaut, but meh, I might be biased).

MVC seems to suit widgets level better as opposed to the architecture pattern for a Rich UI app.


I have used Backbone to build a rich UI app, which would be way beyond my capability and patience level if it was not for the design decision to strictly adhere to MVC. The app is about presenting scientific data in multiple forms, and allowing user to interact with the data and see the outcome of an action instantly. Think Excel with data-driven charts and lots of them. Adhering to MVC allows me to wire models and views up once properly and then forget about the views to focus on the data. It also makes it easy to add after-thought extra views easily without the need to find places to add the wires. Sorry the app is for internal use so I cannot post a link to it. The take-home message for me was that MVC is about separation of concerns to reduce complexity. It becomes an obvious choice when an application is complicated by tangled lines of dependencies across components.


Mine was business LOB with lots of forms and lists and updates from the back-end. All as a single-page app.

MVC got overwhelmed at some point and forced us to switch to MVP, which apparently the more widely accepted pattern for GWT apps.


A similar discussion about Cocoa MVC: http://stackoverflow.com/questions/353646/design-patterns-fo...

The point is that it gets you to think about design patterns that the framework writers intended.

Anybody know if the rails MVC pattern was based on Cocoa? I know a lot of Rails devs who are also Cocoa/Touch devs.




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: