/* global _:true, document:true */
describe('Mixinless component', function () {
  'use strict';

  var el, component, mountedComponent, spy;

  beforeEach(function () {
    el = document.createElement('div');
  });

  afterEach(function () {
    React.unmountComponentAtNode(el);
    spy = void 0;
  });

  describe('with a model', function () {
      var model1 = new Backbone.Model({hello: 'world!'});

      var Component = React.createFactory(React.createClass({
        componentWillMount: function () {
          Backbone.React.Component.mixin.on(this, model1);
        },
        componentDidMount: function () {
          if (spy) spy.call(this);
        },
        componentWillUnmount: function () {
          Backbone.React.Component.mixin.off(this);
        },
        componentDidUpdate: function () {
          if (spy) spy.call(this);
        },
        getInitialState: function () {
          return {};
        },
        render: function () {
          return React.DOM.div({}, this.state.hello);
        }
      }));

      it('renders', function (done) {
        spy = jasmine.createSpy().and.callFake(function () {
          expect(this.state.model.hello).toEqual('world!');
          done();
        });

        component = Component();
        mountedComponent = React.render(component, el);
        _.defer(function () {
          expect(spy).toHaveBeenCalled();
        });
      });

      it('binds to a model', function (done) {
        component = Component();
        mountedComponent = React.render(component, el);
        spy = jasmine.createSpy().and.callFake(function () {
          expect(this.state.model.hello).toEqual('hell!');
        });
        model1.set('hello', 'hell!');
        _.defer(function () {
          expect(spy).toHaveBeenCalled();
          done();
        });
      });
  });

  describe('with a collection', function () {
    var collection1 = new Backbone.Collection([{hello: 1}, {hello: 2}]);

    var Component = React.createFactory(React.createClass({
      componentWillMount: function () {
        Backbone.React.Component.mixin.on(this, collection1);
      },
      componentDidMount: function () {
        if (spy) spy.call(this);
      },
      componentWillUnmount: function () {
        Backbone.React.Component.mixin.off(this);
      },
      componentDidUpdate: function () {
        if (spy) spy.call(this);
      },
      getInitialState: function () {
        return {};
      },
      render: function () {
        return React.DOM.div({}, this.state.collection.map(function (model) {
          return model.hello;
        }));
      }
    }));

    it('renders', function (done) {
      spy = jasmine.createSpy().and.callFake(function () {
        expect(this.state.collection[0].hello).toEqual(1);
        expect(this.state.collection[1].hello).toEqual(2);
        done();
      });

      component = Component();
      mountedComponent = React.render(component, el);
      _.defer(function () {
        expect(spy).toHaveBeenCalled();
      });
    });

    it('binds to a collection', function (done) {
      component = Component();
      mountedComponent = React.render(component, el);
      spy = jasmine.createSpy().and.callFake(function () {
        expect(this.state.collection[0].hello).toEqual(3);
        expect(this.state.collection[1].hello).toEqual(2);
        done();
      });
      collection1.at(0).set('hello', 3);
      _.defer(function () {
        expect(spy).toHaveBeenCalled();
      });
    });
  });
});

@@ -1315,92 +1315,8 @@
 l);%0A
-        _.defer(function () %7B%0A          expect(spy).toHaveBeenCalled();%0A        %7D);%0A
     
@@ -1570,32 +1570,50 @@
 Equal('hell!');%0A
+          done();%0A
         %7D);%0A    
@@ -1650,110 +1650,8 @@
 ');%0A
-        _.defer(function () %7B%0A          expect(spy).toHaveBeenCalled();%0A          done();%0A        %7D);%0A
     
@@ -2779,86 +2779,8 @@
 l);%0A
-      _.defer(function () %7B%0A        expect(spy).toHaveBeenCalled();%0A      %7D);%0A
     
@@ -3167,86 +3167,8 @@
 3);%0A
-      _.defer(function () %7B%0A        expect(spy).toHaveBeenCalled();%0A      %7D);%0A
     

fix unit tests to support deferred setState