title: In ReactJS, why does `setState` behave differently when called synchronously?
body: <p>I am trying to understand the underlying cause for some somewhat "magical" behavior I am seeing that I cannot fully explain, and which is not apparent from reading the ReactJS source code.</p>
  
  <p>When calling the <code>setState</code> method synchronously in response to an <code>onChange</code> event on an input, everything works as expected. The "new" value of the input is already present, and so the DOM is not actually updated. This is highly desirable because it means the cursor will not jump to the end of the input box.</p>
  
  <p>However, when running a component with exactly the same structure but that calls <code>setState</code> <em>asynchronously</em>, the "new" value of the input does not appear to be present, causing ReactJS to actually touch the DOM, which causes the cursor to jump to the end of the input.</p>
  
  <p>Apparently, something is intervening to "reset" the input back to its prior <code>value</code> in the asynchronous case, which it is not doing in the synchronous case. What is this mechanic?</p>
  
  <p><strong>Synchronous Example</strong></p>
  
  <pre class="lang-js prettyprint-override"><code>var synchronouslyUpdatingComponent =
      React.createFactory(React.createClass({
        getInitialState: function () {
          return {value: "Hello"};
        },
  
        changeHandler: function (e) {
          this.setState({value: e.target.value});
        },
  
        render: function () {
          var valueToSet = this.state.value;
  
          console.log("Rendering...");
          console.log("Setting value:" + valueToSet);
          if(this.isMounted()) {
              console.log("Current value:" + this.getDOMNode().value);
          }
  
          return React.DOM.input({value: valueToSet,
                                  onChange: this.changeHandler});
      }
  }));
  </code></pre>
  
  <p>Note that the code will log in the <code>render</code> method, printing out the current <code>value</code> of the actual DOM node.</p>
  
  <p>When typing an "X" between the two Ls of "Hello", we see the following console output, and the cursor stays where expected:</p>
  
  <pre class="lang-none prettyprint-override"><code>Rendering...
  Setting value:HelXlo
  Current value:HelXlo
  </code></pre>
  
  <p><strong>Asynchronous Example</strong></p>
  
  <pre class="lang-js prettyprint-override"><code>var asynchronouslyUpdatingComponent =
    React.createFactory(React.createClass({
      getInitialState: function () {
        return {value: "Hello"};
      },
  
      changeHandler: function (e) {
        var component = this;
        var value = e.target.value;
        window.setTimeout(function() {
          component.setState({value: value});
        });
      },
  
      render: function () {
        var valueToSet = this.state.value;
  
        console.log("Rendering...");
        console.log("Setting value:" + valueToSet);
        if(this.isMounted()) {
            console.log("Current value:" + this.getDOMNode().value);
        }
  
        return React.DOM.input({value: valueToSet,
                                onChange: this.changeHandler});
      }
  }));
  </code></pre>
  
  <p>This is precisely the same as the above, except that the call to <code>setState</code> is in a <code>setTimeout</code> callback.</p>
  
  <p>In this case, typing an X between the two Ls yields the following console output, and the cursor jumps to the end of the input:</p>
  
  <pre class="lang-none prettyprint-override"><code>Rendering...
  Setting value:HelXlo
  Current value:Hello
  </code></pre>
  
  <hr>
  
  <p><strong>Why is this?</strong></p>
  
  <p>I understand React's concept of a <a href="http://facebook.github.io/react/docs/forms.html#controlled-components">Controlled Component</a>, and so it makes sense that user changes to the <code>value</code> are ignored. But it looks like the <code>value</code> is in fact changed, and then explicitly reset. </p>
  
  <p>Apparently, calling <code>setState</code> synchronously ensures that it takes effect <em>before</em> the reset, while calling <code>setState</code> at any other time happens <em>after</em> the reset, forcing a re-render.</p>
  
  <p>Is this in fact what's happening?</p>
  
  <p><strong>JS Bin Example</strong></p>
  
  <p><a href="http://jsbin.com/sogunutoyi/1/">http://jsbin.com/sogunutoyi/1/</a></p>