---
title: marty.js v0.9
layout: post
author: James Hollingworth
author_url: http://github.com/jhollingworth
---

It's been 2 months since we first publicly announced Marty. Since then we've been working hard building new features and refining our API. Today I'm happy to announce Marty v0.9!

So what's new in this release?

<h2 id="isomorphisim">Isomorphisim</h2>

Being able to run your JS application on the server and in the browser has been one of the major reasons people have started using React. We've found it's still challenging to build isomorphic applications and so we've built a set of APIs that make it easier.

[``Marty.renderToString``]({% url /api/top-level-api/index.html#renderToString %}) is a smarter version of [``React.renderToString``](http://facebook.github.io/react/docs/top-level-api.html#react.rendertostring) which knows what state each component needs, fetches it for you and then renders the component. It also gives you lots of diagnostic information to understand what Marty is doing on the server:

<a href="{% url /img/renderToString-diagnostics.png %}"><img src="{% url /img/renderToString-diagnostics.png %}" width="100%" alt="Marty Developer Tools"/></a>

For synchronizing state between the server and browser we have [``Marty.dehydrate()``]({% url /api/top-level-api/#dehydrate %}) and [``Marty.rehydrate()``]({% url /api/top-level-api/#rehydrate %}). [``Marty.dehydrate()``]({% url /api/top-level-api/#dehydrate %}) serializes the contents of your stores to a string which is sent down with the rendered HTML. When your application first loads in the browser you just need to call [``Marty.rehydrate()``]({% url /api/top-level-api/#rehydrate %}) to have your stores return back to their state when on the server.

We've also created [marty-express]({% url /guides/isomorphism/marty-express.html %}), a middleware for [express.js](expressjs.com) which consumes [react-router](https://github.com/rackt/react-router) routes so you don't have to have to duplicate your routing on the client and the server. It also modifies the [HTTP state source]({% url /api/state-sources/http.html %}) so HTTP requests made on the server will behave the same as they would in the browser.

If you'd like to learn more, we've written a [guide on how to get started]({% url /guides/isomorphism/index.html %}). Our [example chat app](https://github.com/martyjs/marty-chat-example) has also been updated to be isomorphic.

<h2 id="es6-classes">ES6 Classes</h2>

To complement React ability to define components using ES6 classes we now support defining all types using classes as well. You can read our guide on [ES6]({% url /guides/es6/index.html %}) to find out how to make the switch. We have also created a new version of the [example chat app which uses ES6 classes](https://github.com/martyjs/marty-chat-example-es6).

{% sample %}
classic
=======
var UsersStore = Marty.createStore({
  id: 'UsersStore',
  handlers: {
    addUser: Constants.RECEIVE_USER
  },
  getInitialState: function () {
    return [];
  },
  addUser: function (user) {
    this.state.push(user);
    this.hasChanged();
  }
});

es6
===
class UsersStore extends Marty.Store {
  constructor(options) {
    super(options);
    this.state = [];
    this.handlers = {
      addUser: Constants.RECEIVE_USER
    };
  }
  addUser(user) {
    this.state.push(user);
    this.hasChanged();
  }
}

{% endsample %}

<h2 id="containers">Containers</h2>

When defining components using ES6 classes you can no longer use mixins which means you won't be able to use the [state mixin]({% url /guides/state-mixin/index.html %}). A new pattern emerging to solve this problem is [to wrap your components in "container" components](https://medium.com/@dan_abramov/mixins-are-dead-long-live-higher-order-components-94a0d2f9e750). We're a big fan of this pattern and so we've introduced [``Marty.createContainer``]({% url /api/top-level-api/index.html#createContainer %}) which creates a container component that does the same job as the [state mixin]({% url /guides/state-mixin/index.html %}). You can checkout our [containers guide]({% url /guides/containers/index.html %}) to learn more about them.

{% highlight js %}
class User extends React.Component {
  render() {
    return <div className="User">{this.props.user}</div>;
  }
}

module.exports = Marty.createContainer(User, {
  listenTo: UserStore,
  fetch: {
    user() {
      return UserStore.for(this).getUser(this.props.id);
    }
  },
  failed(errors) {
    return <div className="User User-failedToLoad">{errors}</div>;
  },
  pending() {
    return this.done({
      user: {}
    });
  }
});
{% endhighlight %}

<h2 id="queries">Queries</h2>

<p>
<a href="{% url /guides/queries/index.html %}">Queries</a> are a new type we're introducing that is responsible for coordinating getting new state from outside of the application. They should help reduce some confusion about how to dispatch actions when fetching state. You can read <a href="{% url /guides/queries/index.html %}">our guide</a> to learn why they've been introduced.
</p>

{% sample %}
classic
=======
var UserQueries = Marty.createQueries({
  id: 'UserQueries',
  getUser: function (id) {
    this.dispatch(UserActions.RECEIVE_USER_STARTING, id);
    UserAPI.getUser(id).then(function (res) {
      if (res.status === 200) {
        this.dispatch(UserActions.RECEIVE_USER, res.body, id);
      } else {
        this.dispatch(UserActions.RECEIVE_USER_FAILED, id);
      }
    }.bind(this)).catch(function (err) {
      this.dispatch(UserActions.RECEIVE_USER_FAILED, id, err);
    }.bind(this))
  }
});

es6
===
class UserQueries extends Marty.Queries {
  getUser(id) {
    this.dispatch(UserActions.RECEIVE_USER_STARTING, id);
    UserAPI.getUser(id).then((res) => {
      if (res.status === 200) {
        this.dispatch(UserActions.RECEIVE_USER, res.body, id);
      } else {
        this.dispatch(UserActions.RECEIVE_USER_FAILED, id);
      }
    }).catch((err) => this.dispatch(UserActions.RECEIVE_USER_FAILED, id, err));
  }
}
{% endsample %}

<h2 id="action-creators">Action creators</h2>

Our approach to defining [action creators](http://martyjs.org/v/0.8.15/guides/action-creators/index.html) was the source of lots of confusion and many bugs. We've got a new, simplified approach which should resolve these issues.

{% sample %}
classic
=======
var UserConstants = Marty.createConstants(["UPDATE_EMAIL"]);

var UserActionCreators = Marty.createActionCreators({
  id: 'UserActionCreators',
  updateEmail: function (userId, email) {
    this.dispatch(UserConstants.UPDATE_EMAIL, userId, email)
  }
});
es6
===
var UserConstants = Marty.createConstants(["UPDATE_EMAIL"]);

class UserActionCreators extends Marty.ActionCreators {
  updateEmail(userId, email) {
    this.dispatch(UserConstants.UPDATE_EMAIL, userId, email)
  }
}
{% endsample %}

<h2 id="one-render-per-store">Components only re-rendered once per action</h2>

There was an [interesting discussion in the Flux panel at React Conf about batching store updates to improve performance](https://www.youtube.com/watch?v=LTj4O7WJJ98&list=PLb0IAmt7-GS1cbw4qonlQztYV1TAW0sCr#t=473). Marty now does this automatically for you so no matter how many times your store changes your components will only be re-rendered once per action.

<h2 id="developer-tools">Developer Tools</h2>

[Marty Developer Tools]({% url /guides/developer-tools/index.html %}) has been given an overhaul. It can now tell you things like what components re-rendered as a result of the action and which stores caused a component to re-render. It also gives you the ability to reset the applications state to a specific action (think ``get reset --hard actionId``).

<a href="{% url /img/devtools-data-flow.png %}"><img src="{% url /img/devtools-data-flow.png %}" width="100%" alt="Marty Developer Tools"/></a>

<h2 id="lodash">lodash</h2>

Thanks to [@jdalton](https://github.com/jdalton) we've moved from underscore.js to lodash (This is an internal change so wont effect you if you're using underscore in your application). This has resulted in a **6KB drop** in our gzipped file size. Unfortunately Marty has also grown by 6KB so Marty v0.9 is the same size as Marty v0.8 :(

<h2 id="changelog">Changelog</h2>

For those currently using Marty v0.8, we've written a [guide for upgrading to v0.9]({% url /guides/upgrading/08_09.html %}). [@dariocravero](https://github.com/dariocravero) also has an [excellent guide on making the move to ES6](https://gist.github.com/dariocravero/2ea4308946c15f2da1af).

###Breaking changes

``Store#setState`` has been renamed to [``Store#replaceState``]({% url /api/stores/index.html#replaceState %}). [``Store#setState``]({% url /api/stores/index.html#setState %}) will now merge the existing state with the new state. This is to more closely follow the React API.

###New features

- Isomorphism ([#13](http://github.com/martyjs/marty/issues/13))
- CookieStateSource & LocationStateSource ([#205](http://github.com/martyjs/marty/issues/205))
- ES6 Classes ([#89](http://github.com/martyjs/marty/issues/89))
- Add dataType option to http state source ([#176](http://github.com/martyjs/marty/issues/176))
- Lodash v3 instead of underscore ([#170](http://github.com/martyjs/marty/issues/170))
- HttpStateSource hooks ([#118](http://github.com/martyjs/marty/issues/118))
- FetchResult#toPromise ([#180](http://github.com/martyjs/marty/issues/180))
- Clear fetch history in Store#clear ([#149](http://github.com/martyjs/marty/issues/149))
- Batch store change events ([#183](http://github.com/martyjs/marty/issues/183))
- Allow you to specify when function context ([#184](http://github.com/martyjs/marty/issues/184))
- Marty.createContainer ([#206](http://github.com/martyjs/marty/issues/206))
- Set request credentials to 'same-origin' ([#209](http://github.com/martyjs/marty/issues/209))

**Bugs**

- dependsOn doesn't update when dependent store updates ([#113](http://github.com/martyjs/marty/issues/113))
- Don't auto set content-type if using FormData ([#140](http://github.com/martyjs/marty/issues/140))
- Fetch API compatibility ([#133](http://github.com/martyjs/marty/issues/133))

###Deprecations

- [Invokable action creators]({% url /guides/action-creators/migrating-from-v8.html %})
- [State Mixin]({% url /guides/state-mixin/index.html %}), use [containers]({% url /guides/containers/index.html %}) instead.