This is a pretty generic question, but I come from a few years with Flex, and I am not so much experienced with pure web development.
My question is: if you need to build an AJAX app, which one of the two approaches you would prefer:
classical server-side MVC, where controllers return views supplied with model data. Views can be full-blown or partial. Basically, there will be only a small number of full-blown views, which work as the containers, and javascript will help fill-in the gaps with partial HTML views asynchronously. This approach is one step further the traditional web development, as javascript is used only for maintaining the overall control and user interactions
A full-blown js app, such as the ones built with Cappuccino, Sproutcore, or Backbone.js, where the client side is thick, and implements a client-side implementation of MVC that handles model as well, as controlling logi, and view interactions. Server-side in this case plays the role of a set of JSON/XML services with which the client exchanges data. The disadvantage in this case is that view templates have to be loaded at the beginning, when the initial application is bootstrapped, so that javascript can layout the markup based on the data. The advantages are the reduced weight of the server response, as well the better control within the client, which allows for stuff like view-model binding to be applied.
A somewhat mixed approach between those two.
I am favoring the second one, which is normal, since I come from a similar environment, but with that one I a mostly concerned about issues such as url routing (or deeplinking as we call it in Flash), state management, modularity, and view layout (when do the view markup templates get loaded? Should there be specific server endpoints that provide those templates upon being called, so that the template data does not get loaded in the beginning?)
Please, comment
I prefer #2 myself, but I dig javascript :)
Unfortunately, I have never even seen what flex code looks like. My experience is with rails, so I will talk in those terms, but hopefully the concepts are universal enough that the answer will make sense
As for client side templates, the best is when your server side platform of choice has a story for it (like rails 3.1 asset pipeline or the jammit plugin for pre 3.1). If you are using rails I can give more info, but if you aren't the first thing I would do is look into finding an asset management system that handles this out of the box.
My fallback is generally to just embed templates into my server side templates inside of a script tag like
<script type='text/html' id='foo-template'></script>
To retrieve the string later, you can do something like this (jquery syntax)
var template = $('#foo-template').html();
In my server side templates, I will pull those script tags into their own files as partials, so I still get the file separation (rails syntax)
<%= render :partial => 'templates/foo.html.erb' %>
I much prefer just using jammit, and having my client side templates in seperate files ending in .jst, but the second approach will work anywhere, and you still get most of the same benefits.
I would recommend the second approach. The second approach (thick client thin server approach ) which you are already familiar with is the preferred approach by an increasing number of modern developers because The rendering and management of widgets is done on the client and this saves computational and bandwidth overhead on the server. Plus if you have a case of complex widget management then using server side code for widgets can become increasingly complicated and unmanageable.
The disadvantage pointed by you :
view templates have to be loaded at the beginning, when the initial
application is bootstrapped, so that javascript can layout the markup
based on the data.
is not correct. You can very well load static templates on the fly as required through ajax and then render them using javascript into full blown widgets.
For example if you have an imagegallery with an image editor component then you may not load the files required for image editor (including images, templates and widget rendering code) until user actually chooses to edit an image.
Using scriptloaders (eg. requirejs, labjs) you can initially load only a small to medium sized bootstrapping script and then load the rest of the scripts dynamically depending on the requirements.
Also, powerful and mature server side widget libraries are only available for java backends (eg vaadin). If you are working on php,python or ruby backend then writing your own server side ui framework can be a serious overkill. It is much more convenient to use client side server-agonistic javascript ui frameworks eg. dojo, qooxdoo etc.
You seem to have an inclination towards towards client side mvc frameworks. This is a nice approach but the dual mvc architecture (on server as well as well as client) often has a tendency to lead to code duplication and confusion. For this reason I wont recommend the mixed approach.
You can have a proper mvc framework in the frontend and only a server side model layer that interacts with the application through a restful api (or rpc if you are so inclined).
Since you are coming from flex background I would recommend you to check out Ajax.org ui platform http://ui.ajax.org . Their user interface framework is tag based like flex and though the project is new they have a powerful set of widgets and very impressive charting and data-binding solutions. Dojo and Ample SDK also adopt tag based widget layout system.
Qooxdoo and extjs advocate doing everything from layouting and rendering through javascript which might be inconvenient for you.
I am an architect of one mobile Web application that has 100,000 users with 20,000 of them online at the same time.
For that kind of application (e.g. limited bandwidth) #2 is the only option I think.
So server side is just a set of data services and client uses pure AJAX RPC.
In our case we use single static index.htm file that contains everything. Plus we use HTML5 manifest to reduce roundtrips to the server for scripts/styles/images on startup. Plus use of localStorage for app state persistence and caching.
As of MVC: there are many template engines out there so you can use anything that is most convenient for you. Templates by themselves are pretty compact as they do not contain any data so it is OK (in our case) to include them all.
Yes, architecture of such an application needs to be well thought upfront. #1 option is not so critical - entry level is lower.
I don't know what platform you are targeting but as I said #2 is probably the only option for mobile.
Related
So I'm afraid I might be missing something pretty fundamental here, but I really can't get my head around this - Why? Why would we want to use those JS MVC frameworks, instead of sticking with Rails, Django, PHP and so on?
What do these JS frameworks give us that can't be achieved by the old web frameworks? I read about SPA, and there's nothing I couldn't do there with ASP.NET MVC, right?
I'm really baffled by hearing all the people at work wanting to leave our current framework for these new ones, and it's much more than just for the sake of learning something new.
I am totally up for that, and I've always tried playing around with other frameworks to see what I'm missing, but perhaps these new technologies have something really big to offer that I simply cannot see?
Single page applications provide a better experience by having all page transitions be seamless. This means you never see the "page flash" between user actions, in addition to a few other user experience improvements.
Front-end frameworks also generally provide a common way to interface with APIs. So instead of writing an AJAX wrapper for every page in your site, you just say 'This page has this route (path), hooks data with this schema from that API endpoint and presents it with these templates and helpers.' There are many proponents of APIs, because there are many good reason to write you applications from a service standpoint. This talk sums up a lot of the points in favor of APIs. To summarize:
Orchestrating your web offerings as services makes them inherently decoupled. This means they are easily changed out. All the reasons behind strong Object Oriented design principles apply equally to the larger parts of an application. Treat each piece as an independent part, like a car, and the whole platform is more robust and healthy. That way, a defect in the headlights doesn't cause the motor to blow up.
This is very similar to how a SOAP WSDL works, except you have the auto creation tools right out of the box.
Having well defined touch points for each part of your application makes it easier for others to interface with. This may not ever factor into your specific business, but a number of very successful web companies (Google/Yahoo, Amazon AWS) have created very lucrative markets on this principle. In this way, you can have multiple products supported by the same touch points, which cuts a lot of the work out of product development.
As other point out, the front end framework is not a replacement for the backend, server technologies. How could it be? While this may seem like a hindrance ("Great, now we have two products to support!"), it is actually a great boon. Now your front and back ends can be changed and version with much less concern over inadvertently breaking one or the other. As long as you stick to the contract, things will "Just WorkTM".
To answer your additional question in the comment, that is exactly correct. You use a front end framework for handling all the customer interaction and a completely separate back-end technology stack to support it.
I'm forgetting a few good ones...
Angular, Ember, and Backbone are client-side JavaScript frameworks. They could be used interchangeably with a Rails, Django, or PHP backend. These JavaScript MVCs are only responsible for organizing JavaScript code in the browser and don't really care how their data is handled or persisted server-side.
Django/Rails etc are server-side MVC frameworks. Angular/Backbone etc are client-side Javascript MVC frameworks. Django/Rails and Angular/Backbone work together - in a single-page app, usually the server-side MVC will serve the initial HTML/JS/static assets once, and then once that is done, the client-side router will take over and handle all subsequent navigations/interactions with your app.
The difference here lies in the concept of what a "single-page application" is. Think about how a "regular" web Django/Rails website works. A user enters your app, the backend fetches data and serves a page. A user clicks on a link, which triggers the server to serve a new page, which causes the entire page to reload. These traditional types of websites are basically stateless, except for things like cookies/sessions etc.
In contrast, a single-page application is a stateful Javascript application that runs in the browser and appears to act like a traditional webapp in that you can click on things and navigate around as usual, but the page never reloads, instead, specific DOM nodes have their contents refreshed according to the logic of your application. To achieve a pure Javascript client-side experience like this in a maintainable fashion really requires that you start organizing your Javascript code for the same reasons you do on the server - you have a router which takes a URL path and interacts with a controller that often contains the logic for showing/hiding views for a particular URL, you have a model which encapsulates your data (think of a model as roughly one "row" of a database result) which your views consume. And because it's Javascript there are events going on, so you can have your view listen for changes in it's associated model and automatically re-render itself when the data is updated.
Also keep in mind that you don't just have one view on the client side, there are usually many separate views that make up a page and these views are often nested, not only for organizational purposes but because we want the ability to only refresh the parts of the UI that need to be refreshed.
The intro to Backbone is probably a good starter on the topic: http://backbonejs.org/#introduction
Check this article, there is well explained how a modern web application should looks like in the client side, server side and the communication between them.
By the way:
Client side -> Ember, Angular, Backbone, Knockout.
Server side -> Django, Node, Rails
Why do we need to use a JS MVC framework(backbone) if we are already using a backend MVC framework(e.g Django or ROR). I can't understand the concept of two MVC frameworks and how they fit together. I thought all front-end related files or logic(html, css, js) come under the views component of the back-end framework. Can someone explain this in simpler terms?
Backbone lies in the client [browser], in order to have fast interaction and experience.
This way you can take advantage of real-time communication via websockets, or LocalStorage for example.
Using a client MVC [MVVM better, in Backbone's case] implies that you just supply a RESTful set of resource from the server [which you can reuse in many other context], and not a full HTML generation stack.
Said that, client side MVC is closer to desktop/mobile UI-oriented MVC implementations [see Cocoa / iOS] than to web-oriented MVC [Symfony, Django, RoR...].
It's mostly because of scalability, every MV* frameworks allows You to make modular code. To give users high experience by using websites, JS code and some fireworks are necessary. JavaScript gives also posibility to relieve backend side from unnecessary computations and because of these simple facts and the scale of currently made websites (huge amount of modules on backend and on frontend side), such MV* JavaScripts frameworks are made and becomes more and more popular.
You may want to look at this post Why use MVVM?
I have been using MVVM and have found it very useful for the front end. Rendering is much quicker and smoother and view-model binding is done on the client-side.
It seems like one of the reasons these JavaScript MVC frameworks started popping was in an effort to to bring some structure to client side JavaScript code. JavaScript has been used more and more in web apps in recent years because it enhances the client side experience so much but when you keep adding more and more, it can quickly become a big cobbled mess of spaghetti code. If you've ever inherited a web app that has tons of JavaScript, you know it can take a loooong time to sort through all the callbacks, functions, DOM manipulation, etc. that is going on just to to grasp how to app works and is tied together. It can be really messy. These JavaScript MVC frameworks help organize and bring structure too all this code so it doesn't get out of control.
This is a design question. I find myself going back and forth between two UI design styles.
The UI on a prototype I developed recently relied heavily on loading the elements of the UI as partial views via AJAX. I did not like that approach because I had to do a lot of requests to the server while my page was loading. However, the plus of this design was that I could easily edit the partial view templates, so the code was easier to manage.
In the next iteration I decided to package all the information at once and then use JavaScript to generate partial views and plug this information into it (and only use Ajax when on-demand up-to-date information was actually needed). My page loads faster, but I find myself generating a lot of HTML snippets in JavaScript, which is getting harder to manage.
As I see it, using Ajax you get:
Easier to maintain (+)
Longer UI response times (-)
And with JavaScript only, you get
Faster UI response (+)
Easier to handle server-side errors (+)
Harder to maintain (-)
So, There are a few things on which I would like to hear your comments:
I do not like using Ajax unless I don't have a need for actual on-demand data. Am I wrong?
Are there frameworks/libraries that would make managing HTML-generating JavaScript code easier?
Are there any other pros/cons of the two approaches that I have missed?
Thanks,
There are templating libraries for JavaScript, if you want to get that involved. In general I would avoid manually sticking together HTML strings from JS unless there's a particular need to (eg in some cases for performance when dealing with very large tables).
HTML-hacking is difficult to read and prone to HTML-injection security holes when you don't get escaping right.
Start instead with the DOM methods, and use DOM-like content manipulation libraries to make it easier. For example, if using jQuery, do this:
$('<a>', {href: somelink, text: sometext})
and not this:
$(''+sometext+'') // insecure mess
There doesn't need to be a big difference between fetching data through XMLHttpRequest vs including it in the HTML document itself. You can direct a bunch of JSON data to the same function that will build page parts whether it was just fetched by XMLHttpRequest in an update operation, or included in function calls at document load time.
When including data in the page you will generally need to include a timestamp they were generated in any case, so that if the browser goes back to the page a while later without reloading it, the browser can detect that the information is now out-of-date, and cue up an XMLHttpRequest to update it.
The usual question when you're creating your page content from data with client-side JavaScript is, are you going to fill in the initial static HTML version from the server too? If so, you're going to be duplicating a lot of your content generation work in both client-side JS and the server-side language(*). If not, then you're making the content invisible to non-JS user agents which includes search engines. Whether or not that matters to you typically depends on what the app is doing (ie does it need to be searchable and accessible?)
(*: unless you can use server-side JavaScript from something like node.js and re-use your content generation code. This is still a somewhat rare approach.)
Why not look at integrating require.js into your workflow? I'm not entirely sure how it would work with templates, but included in their pipeline is the ability to package all required script files into a single .js to be served by a single server request/response.
I have no personal experience about it, but Closure looks promising. The thing about its templates being usable on both server and client side might be of interest to you. Here is what was said about using it in Google+:
The cool thing about Closure templates is they can be compiled into both Java and JavaScript. So we use Java server-side to turn the templates into HTML, but we can also do the same in JavaScript client-side for dynamic rendering. For instance, if you type in a profile page URL directly, we'll render it server-side, but if you go to the stream say and navigate to someone's profile page, we do it with AJAX and render it client-side using the same exact template.
When working with remote data after a page is loaded, for small datasets I prefer returning data only and adding to the UI with templates.
For large datasets, I recommend using your partial views to render the html on the server to reduce overhead in the client as #bobince mentioned.
For client-side state tracking, check out Knockout at http://www.knockoutjs.com. It uses an MVVM approach with data models bound to UI elements and makes it very simple to send the data back to the server via AJAX. It works with the jquery.tmpl template library out of the box or you can integrate another library of preference with a little more effort.
As far as managing templates, it's easy enough to store common templates in an object, either on the server to be retrieved with your remote data, or in a javascript object on the client.
I know Model-View-Controller well, have known about it for years and used it in terms of server-side development with languages like PHP.
However, I am now working with JavaScript and building a big application with it utilizing SVG, Canvas among other great features modern browsers support. The project is big, so, the architecture behind it must not be fragile.
JavaScript and MVC do not get on like a house on fire, because JavaScript is event-driven by nature. So, are there any architectures or anything else I should definitely learn, understand and implement?
The software will have to deal with data. It already utilizes local storage and web SQL database. I need a Models, right? There is an UI, so I have Views? However, do I have Controllers? What about events? How do I structure everything?
Architecture, architecture, architecture -- that's what I'm interested in. I'm fine with the language of my choice.
First, I'm the author of JavaScriptMVC, so I'm extremely biased in a whole variety of ways. First, there are 6ish things you will ever do in a JS application:
Load Scripts
Respond to user events
Update the DOM
Request data from the server
Convert that data into something useful for JavaScript
Organize your front-end business logic
Your choice of architecture might depend on what tools you want / need.
For general architecture, I do think it's important to separate concerns.
I strongly encourage you to find some way of doing dependency management, and client side templates. They will make your life a lot easier.
JavaScriptMVC uses a tiered MVC approach that's based heavily around custom UI events and OpenAjax events.
I build my low-level widgets with $.Controller in a similar way to how you would build jQuery widgets. The big difference is that the widgets produce a non-ui event that top level controllers can listen to. For example, a tabs widget might produce a "tab.activate" event like:
$('.tab').trigger('tab.activated')
Then, my higher order controller might listen to tab.activated events, and a the model to update the tab content like:
".flickr tab.activated" : function(tabEl, ev){
Flickr.findAll({type : "rainbows"}, function(images){
tabEl.html("//path/to/view", images );
}
}
Flickr.findAll essentially does a query for flickr messages, then calls back with a list of images. Wrapping the service/ajax functionality with models makes them a lot more reusable.
You'll notice that in the callback I update the html of the tab element with the rendered content from a view. This probably isn't the 'best' way of doing it, but I wanted a quick example. Better would be passing the tabs controller the rendered output, for it to do what it will with it. That way if your tab wants to fade in content someday, it will be able to and your master controller won't have to know about the tab's implementation.
The most important thing is to break down your app into the smallest pieces you can. Have them individually testable (and flexible), and combine the little parts into bigger parts as you work your way up to your application.
Take a look at Ext JS. It has a clean architecture that is well-suited towards highly complex javascript applications.
Data handling and server communication is done via stores. Data rendering is done via grids (with in-cell editors), and forms (with a rich set of form controls), which can both talk to the stores. There's also a set of layout classes to abstract away CSS positioning (border layout, box layout, table layout, form layout, ...).
It is however not MVC in the typical sense. The library encourages a programming style that avoids dealing much with HTML and CSS, letting you live (mostly) in pure JavaScript land. You end up thinking in terms of components and data, instead of individual dom elements and style rules. If you don't like that approach, be warned, you won't like this library.
MVC is still the way to go, in my opinion. If you're looking for a good framework to help you achieve that a little less painfully, I would look at JavaScript MVC, it has models, views, controllers, unit testing, jQuery support, etc.
You should learn the Event Based nature of client-side JavaScript and how it blends with MVC based server-side applications.
You should also learn how to properly program inside of the Prototype based inheritance structure of Javascript.
Both of those things will allow you to write you JavaScript so that it meshes with your server-side application framework and is extensible and re-usable.
One thing i have learned over the years of javascript programming is writing UnObtrusive Javascripting which basically means seperating as much as possible structure(HTML) and style(CSS) from Behaviour(JAVASCRIPT).
Althogh not a raw javascript solution, take a look at CoreMVC, the jQuery architechure of MVC.
CorMVC is a jQuery-powered
Model-View-Controller (MVC) framework
that can aide in the development of
single-page, web-based applications.
CorMVC stands for client-only-required
model-view-controller and is designed
to be lowest possible entry point to
learning about single-page application
architecture. It does not presuppose
any server-side technologies, or a web
server of any kind, and requires no
more than a web browser to get up and
running.
If you want a ready-made reference architecture that combines soem industry leading JS libraries with some good JS design patterns for large scale development, have a look at:
http://boilerplatejs.org/
I'm the main author of it and thought of sharing knowledge we gained after developing few large scale javascript products. It addresses following main concerns:
Solution structuring
Creating complex module hierarchy
Self contained UI components
Event based inter module communication
Routing, History, Bookmarking
Unit Testing
Localization
Document Generation
I know that MVC is highly acclaimed for PHP applications, but I am not sure at all that it fits in JavaScript. If you think otherwise, then please explain how and where you handle common scenarios like AJAX requests, data saving (offline storage), presentation, how do you handle controller logic (do you have a front controller?), and so forth.
What about Model-View-Presentation?
I am using ExtJS and using the server only for permanent data storage.
If you're planning on coding your UI purely with JavaScript, you could think your PHP end of things as more of a web service or an API.
Basically your View would be the Ext JS stuff you write in JS. To work with your data, the Ext frontend would perform requests to your "service". Basically you would have a sort of model-controller architecture on your server, where the job of the controller would be to process requests and output JSON (for consumption by your Ext frontend)
Essentially, the "view" in your backend would simply be output from json_encode, which is then consumed by your actual Ext based view.
In JS, you can have controllers depending on what sort of stuff you're doing. If you're just displaying data from the server, you may not require much separate logic. If you're doing some more complex processing, it may be useful to separate the code into a separate controller and view.
It's mostly up to how much you want to separate the logic.
When writing almost complete javascript applications you can think of MVC as:
View: The DOM
Controller: Your JavaScript
Model: Combination of JavaScript Ajax Calls and their PHP (or whatever) backend counterparts
PureMVC is an extremely cool MVC framework. You should check it out.
I'm using the same architecture: predominantly ExtJS on top of a PHP back-end.
My solution:
Strict JSON-RPC communication with the server. The server-side API is clean enough that it's also our third-party interfacing API. Forcing the API to be the same one that third-party interfaces use makes you keep the server-side code clean and minimal, which is good for security and performance.
Heavily componentized architecture, split into modules that group components (Ext.Panel derivatives usually). Each component knows how to request its initial configuration and data via JSON-RPC calls, render itself, and save its state if necessary. I try to keep the communication between components clean and documented.
On-demand architecture, loading in additional components via javascript files as needed. The entire code is designed to be initialized via callbacks, so that components can load their dependancies from the server and render only an empty placeholder before they initialize themselves.
Individual components may employ an MVC pattern, where it makes sense. Ext tends to encourage MVC anyway, separating data out into stores and having a separate rendering infrastructure (although it does blend controller logic with the rendered components).
I'm not sure I understand where you are going with your question, but I'll give it a shot.
MVC is an architectural pattern which in its essence means keeping the data model, the controller and the UI loosely coupled as much as possible.
You are trying to boil it down to the technological level, and it's not really making any sense. You can do proper MVC with a good framework. Just to make things clear, plain-vanilla PHP does not give you good MVC support. A good framework, such as CakePHP or CodeIgniter - will.
JS is just a nice way to enrich the client-side experience. Meaning that unless you are doing server-side JS, the only place you will have JS is in the view itself. AJAX requests have nothing to do with MVC, per-se. Neither does data persistence. Unless you are implementing your own controller (and you better have a damn good reason to do so yourself), you shouldn't be worried about its internal logic.
Bottom line, if you want to do proper MVC, use a proper framework, and all will fall into place.