English |  Español |  Français |  Italiano |  Português |  Русский |  Shqip

Choosing a JavaScript Framework

Frameworks: EmberJS

Basic Facts
Released: 2011
Stars on GitHub: 9k+
Dependencies: jQuery and Handlebars
License: MIT License

Background

Like Angular, EmberJS is becoming very popular in a very short amount of time. The first EmberConf is happening in 2014 and they released their 1.0 version in August 2013. Ember is billed as a “framework for creating ambitious web applications” – a solid foundation (a framework!) for developers to flesh out a full app on the client-side.

Ember is a fork of SproutCore, a framework Apple greatly contributed to. Ember and SproutCore have gone in different directions, but SproutCore is still around (active mailing list and still active on Github). The two well-known developers on the project are Yehuda Katz and Tom Dale, but there are currently nine members of the Ember core team. Katz is well-known from his work on the jQuery and Rails core teams, and his great contributions to open source projects.

The Ember community held their first community conference in March 2014 and has meetups (meetup.com) around the world; the core team highly prioritizes community involvement, and supporting people who want to contribute back to the community.

Strengths and weaknesses

One of Ember’s big selling points is “developer happiness.” Many decisions made for you in Ember so that you don’t need to worry about them and get on to writing your application logic – that is, by following the Ember way, you abstract away a number of details related to your special 15% that makes your app special.

Ember has a lot of reference and learning resources to help you along the way, such as a downloadable starter kit and the extensive “Getting Started” section in the Ember guides that’s well written and understandable – if at times there’s too much information.

Another example of Ember’s developer-centric attitude is how Ember’s errors are full sentences (rather than the cryptic errors you usually see in your JavaScript console). In the development/debug build there are lots of asserts, in full sentences, which helps a lot with the Ember learning curve. The authors give you documentation in many places to help you out, and prevent you from being resigned to reading stacktraces to nowhere.

Among the features of Ember are templating, two-way data binding, and components, Ember’s version of a web component, and analogous to an Angular directive.

Once you’ve checked out Ember, you’ll also want to explore Ember Data, a persistence layer you can use in Ember. It’s been slow to get to “production-ready,” with the core team assuring their community that 1.0 is coming soon. That said, Ember is not dependent Ember Data. You should also know that there are plenty of libraries that are a part of Ember (dependencies that are rolled into the library) that stand on their own as great libraries.

As for weaknesses, EmberJS requires a bit more domain knowledge than Angular or Backbone just to get started, but some developers would call that a strength. One developer I spoke with said that Ember “removes a lot of potential foot guns” (apparently the term for shooting oneself in ones foot).

Just getting started figuring out where you’re supposed to put the Ember script tag and start an application can be a hassle without guidance. There’s a reason even expert Rails developers tend to use generators to get things set up in the right place and then cut away; making sure your project has the right folder structure can be the key to having a good day in Ember.

There are lots of rules in Ember, and they’re difficult to break. It’s more difficult to make a “bad” architecture in Ember than in Backbone or Angular because there’s a strong preference for the tree structure and where to put data.

A final weakness: Ember has less popular interest when compared to Backbone or Angular, and isn’t backed by a major corporation, but instead by a group of committed open source developers. Ember is constantly gaining traction, but the field is very competitive.

How big is it?

Ember is 69kb minified and gzipped.

Ember in action: Sample app

The Ember sample app, of all the major frameworks, had me the most nervous. Largely because Ember is very analogous to Rails in that it’s extremely fast to develop with … once you know your way around. That said, the overall experience was very fast, largely thanks to asking an Ember developer for advice around the documentation.

Zero to Ember

Adding Ember requires jQuery and handlebars separately, and they are not cooked into the library. So starting out, the index page looks like so:

<!DOCTYPE html>

<html>

<head>

    <title>Realtors &amp; Co.</title>

</head>

<body>

    <h1>Realtor's Co Properties</h1>

    <script src="vendor/jquery-1.11.0.min.js"></script>

    <script src="vendor/handlebars-1.1.2.js"></script>

    <script src="vendor/ember-1.4.0.js"></script>

    <script src="vendor/ember-data.js"></script>

   <script src="js/app.js"></script>

</body>

</html>

The sample app is using the uncompressed version of Ember, meaning it’ll include debug statements not seen in production. In app.js, I added:

var App = Ember.Application.create();

And with just that, when I load the page I get information in the console about the versions that I’m running: 

Routing

Now to router.js; names do matter in Ember, because it helps with the “magic” of sorts (very Rails-esque, router.js is like your routes.rb in Rails). In Ember’s routing, you associate the router with a data set, a ‘resource’, and associate it with a path:

App.Router.map(function() {

    this.resource('properties', { path: '/' });

});

I’ll add a template to my view associated with this resource:

    <script type="text/x-handlebars" data-template-name="properties">

        <table>

        {{#each}}

            <tr>

                <td{{address}}</td>

                <td>{{ zip }}</td>

                <td>{{ price }}</td>

            </tr>

        {{/each}}

        </table>

    </script>

The data-template-name attribute associates this template with my resource, and inside the template you’ll see handlebars used as the templating language. Before this will actually work, there needs to be some data to use.

Data

In my index.html I included the Ember data library, which is the highly anticipated data persistence layer for Ember. You can definitely use Ember without Ember Data, but since I’m using mock data to populate the sample apps instead of an API, I’m going to leverage Ember Data’s neat fixture capabilities.

I first setup the data store with a fixture adapter in app.js:

 

App.Store = DS.Store.extend({

  revision: 13,

  adapter: DS.FixtureAdapter

});

And now to define the property model for the project. Models go in /js/models/foo.js; maintaining a consistent tree structure helps Ember know where to look for your data. I added my property model at /js/models/property.js.

Declaring a model is different with vs without Ember Data; without Ember Data, you use Ember’s Object.extend() method, with Ember Data, you extend the data store’s model object. Here’s what property looks like with Ember Data:

App.Property = DS.Model.extend({
   address: DS.attr('string'),
   zip: DS.attr('number'),
   price: DS.attr('number')
});

I declare the properties of the object here, which will correspond to how the data is stored, analogous to defining a type in a database.

There are four options for the types: string, number, boolean, and date, but you can add custom types as you like, with appropriate serialization/deserialization. You can also define default values in an optional params object of the attr() method.

Now that there’s an object, I created an array of fixtures:

App.Property.FIXTURES = [

  …

];

Because of the naming association and that I have the fixtures adapter installed, this will “just work” to add my fixtures … once I finish out the router.

I already have a mapping of the resource, but I need to define the data to be returned for the properties route. In router.js I added:

App.PropertiesRoute = Ember.Route.extend({

    model: function() {

        return this.store.find('property');

    }

});

The great thing about using the fixtures adapter is that I’m using the same code that I would if I had a real data on the backend; the find() method takes a model, and without an id parameter, it will find all objects, creating the index view.

That finishes the index view; adding the show view becomes trivial. Add a route mapping in router.js:

    this.resource('property', { path: '/property/:property_id' });

Add a route:

App.PropertyRoute = Ember.Route.extend({

    model: function(params) {

        return this.store.find('property', params.property_id);

    }

});

And add the view template to index.html:

<script type="text/x-handlebars" data-template-name="property">

  <h2>{{ address }}</h2>

  <p>This great property in the {{ zip }} area is currently

    listed at {{ price }}</p>

</script>

For navigation purposes, I also went back to link the list items to their show views using the link-to helper:

<td>{{#link-to 'property' this }}{{address}}{{/link-to}}</td>

And now there’s the basic realtor’s app in Ember.

Learn more

Ember Guides

EmberJS Edge

There has been error in communication with Booktype server. Not sure right now where is the problem.

You should refresh this page.