Blog articles

What is the difference between state vs. props in React?

June 08, 2016

React is an open-source JavaScript library that provides the V (view)  of traditional MVC JavaScript framework. React promises programmers a model in which subcomponents cannot directly affect enclosing components- meaning data is flown downwards, updating data changes in HTML efficiently, and abstracts away the DOM allowing better performance using Virtual DOM.

You may ask, if data is only flown downwards from components to components, how could we access data we need from previous component? The answer to that is props. React uses props to transfer data we need to different components.

Let’s jump into the code to show you the difference between the two. We’ll first create simple React Component to render to virtual DOM to show examples.

Code Example: https://jsfiddle.net/qtn6xphx/

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

 render: function() {

   return (

     <h1>sample</h1>

   );

 }

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

We can also pass in components state data through props but we’ll go over that later. Say that we have another component and we’d like to pass a data from our SampleOneComponent. React’s prop can handle this for us.

We’ll create another component called SampleTwoComponent. Lets make simple <h2></h2> element and render it below our <h1></h1> heading from SampleOneComponent.

Code Example:https://jsfiddle.net/qtn6xphx/1/

Remember that we always need to wrap our elements within parent’s <div></div> when rendering more than one element within a component.

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

 render: function() {

   return (

    <div>

       <h1 className="sample-one"> this is sample one </h1>

       <SampleTwoComponent />

     </div>

   );

 }

});

var SampleTwoComponent = React.createClass({

render: function() {

  return (

    <h2 className="sample-two"> this is sample two </h2>

   )

 }

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

Now that we have our two components set up, let’s use React’s prop to pass a data from SampleOneComponent to SampleTwoComponent. For our example, we’ll pass along a simple string data.

By placing a reference called “sampleString” in our <SampleTwoComponent /> element in our SampleOneComponent, we’re able to pass the string “this is string from sample one component” down to our SampleTwoComponent.

Code Example:https://jsfiddle.net/qtn6xphx/2/

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

render: function() {

return (

<div>

<h1 className="sample-one"> this is sample one </h1>

<SampleTwoComponent sampleString="this is string from sample one component"/>

</div>

);

}

});

var SampleTwoComponent = React.createClass({

render: function() {

return (

<div>

<h2 className="sample-two"> this is sample two </h2>

<p className="sample-string">{this.props.sampleString}</p>

</div>

)

}

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

As you can see, SampleTwoComponent is able to access our string data that was sent from SampleOneComponent. This is a simple example and as I have mentioned before, we can transfer any type of data through props. Before I get into React’s state, as I pointed out earlier, you can have multiple props in the component. Prop is a JavaScript object, so all you have to have is key value pairs.

Code Example:https://jsfiddle.net/qtn6xphx/5/

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

render: function() {

return (

<div>

<h1 className="sample-one"> this is sample one </h1>

<SampleTwoComponent

sampleString="this is string from sample one component"

sampleObject={ { text: 'object string'} }

sampleArray={ [1,2,3] }

/>

</div>

);

}

});

var SampleTwoComponent = React.createClass({

render: function() {

return (

<div>

<h2 className="sample-two"> this is sample two </h2>

<p className="sample-string">{this.props.sampleString}</p>

<p className="sample-object">{this.props.sampleObject.text}</p>

<p className="sample-array">{this.props.sampleArray[0]} : zero index</p>

<p className="sample-array">{this.props.sampleArray[1]} : first index</p>

<p className="sample-array">{this.props.sampleArray[2]} : second index</p>

</div>

)

}

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

While developing using React, you’ll be using a lot of prop but another important feature is state. React’s state can be defined as key value pair defined in each component and can be accessed with this.state. State can be initialized when code is loaded or state can be set on event changes. Let’s go ahead and use our same example we used for props to understand state.

We can initialize component’s state on load by using getInitialState() function.

Code Example:https://jsfiddle.net/qtn6xphx/6/

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

getInitialState: function() {

return {

firstname: "John",

lastname: "Doe",

age: 32

}

},

 

render: function() {

return (

<div>

<h1 className="sample-one"> this is sample one </h1>

<SampleTwoComponent

sampleString="this is string from sample one component"

sampleObject={ { text: 'object string'} }

sampleArray={ [1,2,3] }

/>

</div>

);

}

});

var SampleTwoComponent = React.createClass({

render: function() {

return (

<div>

<h2 className="sample-two"> this is sample two </h2>

<p className="sample-string">{this.props.sampleString}</p>

<p className="sample-object">{this.props.sampleObject.text}</p>

<p className="sample-array">{this.props.sampleArray[0]} : zero index</p>

<p className="sample-array">{this.props.sampleArray[1]} : first index</p>

<p className="sample-array">{this.props.sampleArray[2]} : second index</p>

</div>

)

}

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

This will allow us to use our state data without having to render as undefined.

Let’s do an example to show data from our state in our render function in SampleOneComponent

Code Example:https://jsfiddle.net/qtn6xphx/7/.

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

getInitialState: function() {

return {

firstname: "John",

lastname: "Doe",

age: 32

}

},

 

render: function() {

return (

<div>

<h1 className="sample-one"> this is sample one </h1>

<SampleTwoComponent

sampleString="this is string from sample one component"

sampleObject={ { text: 'object string'} }

sampleArray={ [1,2,3] }

/>

<div>

<h3 className="state-example">This is where all our component state will go </h3>

<p>firstname : {this.state.firstname}</p>

<p>lastname: {this.state.lastname}</p>

<p>age: {this.state.age} </p>

</div>

</div>

);

}

});

var SampleTwoComponent = React.createClass({

render: function() {

return (

<div>

<h2 className="sample-two"> this is sample two </h2>

<p className="sample-string">{this.props.sampleString}</p>

<p className="sample-object">{this.props.sampleObject.text}</p>

<p className="sample-array">{this.props.sampleArray[0]} : zero index</p>

<p className="sample-array">{this.props.sampleArray[1]} : first index</p>

<p className="sample-array">{this.props.sampleArray[2]} : second index</p>

</div>

)

}

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

Using this.state, we were able to render our initial state values. We can also send our initial state to props, so that other components can access our state value from SampleOneComponent. We will create a new React component called DataFromState and this will receive state values from SampleOneComponent to its props.

Code Example:https://jsfiddle.net/qtn6xphx/8/

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

getInitialState: function() {

return {

firstname: "John",

lastname: "Doe",

age: 32

}

},

 

render: function() {

return (

<div>

<div>

<h1 className="sample-one"> this is sample one </h1>

<SampleTwoComponent

sampleString="this is string from sample one component"

sampleObject={ { text: 'object string'} }

sampleArray={ [1,2,3] }

/>

</div>

<div>

<h3 className="state-example">This is where all our component state will go </h3>

<p>firstname : {this.state.firstname}</p>

<p>lastname: {this.state.lastname}</p>

<p>age: {this.state.age} </p>

</div>

<DataFromState thisState={this.state}/>

</div>

);

}

});

var SampleTwoComponent = React.createClass({

render: function() {

return (

<div>

<h2 className="sample-two"> this is sample two </h2>

<p className="sample-string">{this.props.sampleString}</p>

<p className="sample-object">{this.props.sampleObject.text}</p>

<p className="sample-array">{this.props.sampleArray[0]} : zero index</p>

<p className="sample-array">{this.props.sampleArray[1]} : first index</p>

<p className="sample-array">{this.props.sampleArray[2]} : second index</p>

</div>

)

}

});

var DataFromState = React.createClass({

render: function() {

return (

<div>

<h3>Our props from SampleOneComponent state</h3>

<p>firstname from SampleOneComponent state: {this.props.thisState.firstname}</p>

</div>

);

}

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

By passing this.state from SampleOneComponent as reference to thisState, we were able to receive data in our DataFromState component by this.props.thisState.

Next, let’s look into setting our state when there is a change in event. For our example, we’ll do a simple button, in which when clicked will set our one of state value.

Within our button element, we’ll have one of event listener onClick, which will listen for event when button is clicked. The button click event will invoke a function handleClick, which is just a method I created to change the state value when clicked. We use React’s this.setState() method change the state of SampleOneComponent’s firstname and lastname every time button is clicked.

Code Example:https://jsfiddle.net/qtn6xphx/10/

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

getInitialState: function() {

return {

firstname: "Michael",

lastname: "Jordan",

age: 53

}

},

 

handleClick: function() {

if(this.state.firstname === "Michael" && this.state.lastname === "Jordan") {

this.setState({

firstname: "Kobe",

lastname: "Bryant",

age: 37

});

} else {

this.setState({

firstname: "Michael",

lastname: "Jordan",

age: 53

});

}

},

 

render: function() {

return (

<div>

<div>

<h1 className="sample-one"> this is sample one </h1>

<SampleTwoComponent

sampleString="this is string from sample one component"

sampleObject={ { text: 'object string'} }

sampleArray={ [1,2,3] }

/>

</div>

<div>

<h3 className="state-example">This is where all our component state will go </h3>

<p>firstname : {this.state.firstname}</p>

<p>lastname: {this.state.lastname}</p>

<p>age: {this.state.age} </p>

</div>

<DataFromState thisState={this.state}/>

<div>

<button onClick={this.handleClick}>Click Me!</button>

</div>

</div>

);

}

});

var SampleTwoComponent = React.createClass({

render: function() {

return (

<div>

<h2 className="sample-two"> this is sample two </h2>

<p className="sample-string">{this.props.sampleString}</p>

<p className="sample-object">{this.props.sampleObject.text}</p>

<p className="sample-array">{this.props.sampleArray[0]} : zero index</p>

<p className="sample-array">{this.props.sampleArray[1]} : first index</p>

<p className="sample-array">{this.props.sampleArray[2]} : second index</p>

</div>

)

}

});

var DataFromState = React.createClass({

render: function() {

return (

<div>

<h3>Our props from SampleOneComponent state</h3>

<p>firstname from SampleOneComponent state: {this.props.thisState.firstname}</p>

</div>

);

}

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

Another important thing you can notice is that because the state from SampleOneComponent was passed as reference to DataFromState props, everytime state value changes, it will also update the change for the props that was passed.

As mentioned before, React’s state is rendered every change in event. For example, if we have a simple input box, React’s state will update every change in the input box. For example, if the user type’s “foo”, React’s state is updated three times because there is three letters inputted. Every letter input will update and render Reacts state and render function.

Let’s go ahead and create a input text field and a <p></p> tag to show display what’s typed in input text to show this example.

Code Example:https://jsfiddle.net/qtn6xphx/13/

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

getInitialState: function() {

return {

firstname: "Michael",

lastname: "Jordan",

age: 53

}

},

 

handleClick: function() {

if(this.state.firstname === "Michael" && this.state.lastname === "Jordan") {

this.setState({

firstname: "Kobe",

lastname: "Bryant",

age: 37

});

} else {

this.setState({

firstname: "Michael",

lastname: "Jordan",

age: 53

});

}

},

 

render: function() {

return (

<div>

<div>

<h1 className="sample-one"> this is sample one </h1>

<SampleTwoComponent

sampleString="this is string from sample one component"

sampleObject={ { text: 'object string'} }

sampleArray={ [1,2,3] }

/>

</div>

<div>

<h3 className="state-example">This is where all our component state will go </h3>

<p>firstname : {this.state.firstname}</p>

<p>lastname: {this.state.lastname}</p>

<p>age: {this.state.age} </p>

</div>

<DataFromState thisState={this.state}/>

<div>

<button onClick={this.handleClick}>Click Me!</button>

</div>

<div className="input-box">

<h3>Display state change of rendering</h3>

<form>

<input type="text" placeholder="type something here"/>

</form>

<p></p>

</div>

</div>

);

}

});

var SampleTwoComponent = React.createClass({

render: function() {

return (

<div>

<h2 className="sample-two"> this is sample two </h2>

<p className="sample-string">{this.props.sampleString}</p>

<p className="sample-object">{this.props.sampleObject.text}</p>

<p className="sample-array">{this.props.sampleArray[0]} : zero index</p>

<p className="sample-array">{this.props.sampleArray[1]} : first index</p>

<p className="sample-array">{this.props.sampleArray[2]} : second index</p>

</div>

)

}

});

var DataFromState = React.createClass({

render: function() {

return (

<div>

<h3>Our props from SampleOneComponent state</h3>

<p>firstname from SampleOneComponent state: {this.props.thisState.firstname}</p>

</div>

);

}

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

Now every time we type something in the input text box, React’s state will update upon every key press and change the state of our text and rendering it to our virtual DOM. We’ll need to first implement a custom method to handle the change in input text box. We’ll call this method onHandleChange() and we can create this just like a regular javascript function that will take an event as our parameter to grab the target’s value in input box. React also has onChange event listener, so we can use that on our input text box to invoke our onHandleChange() method.

Code Example:https://jsfiddle.net/qtn6xphx/14/

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

getInitialState: function() {

return {

firstname: "Michael",

lastname: "Jordan",

age: 53

}

},

 

handleClick: function() {

if(this.state.firstname === "Michael" && this.state.lastname === "Jordan") {

this.setState({

firstname: "Kobe",

lastname: "Bryant",

age: 37

});

} else {

this.setState({

firstname: "Michael",

lastname: "Jordan",

age: 53

});

}

},

 

onHandleChange: function(e) {

console.log('event', e.target.value);

},

 

render: function() {

return (

<div>

<div>

<h1 className="sample-one"> this is sample one </h1>

<SampleTwoComponent

sampleString="this is string from sample one component"

sampleObject={ { text: 'object string'} }

sampleArray={ [1,2,3] }

/>

</div>

<div>

<h3 className="state-example">This is where all our component state will go </h3>

<p>firstname : {this.state.firstname}</p>

<p>lastname: {this.state.lastname}</p>

<p>age: {this.state.age} </p>

</div>

<DataFromState thisState={this.state}/>

<div>

<button onClick={this.handleClick}>Click Me!</button>

</div>

<div className="input-box">

<h3>Display state change of rendering</h3>

<form>

<input

type="text"

onChange={ this.onHandleChange }

placeholder="type something here"

/>

</form>

<p></p>

</div>

</div>

);

}

});

var SampleTwoComponent = React.createClass({

render: function() {

return (

<div>

<h2 className="sample-two"> this is sample two </h2>

<p className="sample-string">{this.props.sampleString}</p>

<p className="sample-object">{this.props.sampleObject.text}</p>

<p className="sample-array">{this.props.sampleArray[0]} : zero index</p>

<p className="sample-array">{this.props.sampleArray[1]} : first index</p>

<p className="sample-array">{this.props.sampleArray[2]} : second index</p>

</div>

)

}

});

var DataFromState = React.createClass({

render: function() {

return (

<div>

<h3>Our props from SampleOneComponent state</h3>

<p>firstname from SampleOneComponent state: {this.props.thisState.firstname}</p>

</div>

);

}

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

Now that we know onHandleChange() method is being invoked and console logging every time we type something in our input text, let’s go ahead and change the state every time letter is typed. Just like before, we’ll use this.setState() method to update our state value input_text. Lastly, we’ll render our this.state.input_text below our input box so that we can see it render to DOM whatever we type.

Code Example:https://jsfiddle.net/cd5fsxut/2/

HTML

<div id=”sample”></div>

JavaScript

var SampleOneComponent = React.createClass({

getInitialState: function() {

return {

firstname: "Michael",

lastname: "Jordan",

age: 53

}

},

 

handleClick: function() {

if(this.state.firstname === "Michael" && this.state.lastname === "Jordan") {

this.setState({

firstname: "Kobe",

lastname: "Bryant",

age: 37

});

} else {

this.setState({

firstname: "Michael",

lastname: "Jordan",

age: 53

});

}

},

 

onHandleChange: function(e) {

e.preventDefault();

this.setState({

input_text: e.target.value

});

},

 

render: function() {

return (

<div>

<div>

<h1 className="sample-one"> this is sample one </h1>

<SampleTwoComponent

sampleString="this is string from sample one component"

sampleObject={ { text: 'object string'} }

sampleArray={ [1,2,3] }

/>

</div>

<div>

<h3 className="state-example">This is where all our component state will go </h3>

<p>firstname : {this.state.firstname}</p>

<p>lastname: {this.state.lastname}</p>

<p>age: {this.state.age} </p>

</div>

<DataFromState thisState={this.state}/>

<div>

<button onClick={this.handleClick}>Click Me!</button>

</div>

<div className="input-box">

<h3>Display state change of rendering</h3>

<form>

<input

type="text"

onChange={ this.onHandleChange }

placeholder="type something here"

/>

</form>

<p> {this.state.input_text} </p>

</div>

</div>

);

}

});

var SampleTwoComponent = React.createClass({

render: function() {

return (

<div>

<h2 className="sample-two"> this is sample two </h2>

<p className="sample-string">{this.props.sampleString}</p>

<p className="sample-object">{this.props.sampleObject.text}</p>

<p className="sample-array">{this.props.sampleArray[0]} : zero index</p>

<p className="sample-array">{this.props.sampleArray[1]} : first index</p>

<p className="sample-array">{this.props.sampleArray[2]} : second index</p>

</div>

)

}

});

var DataFromState = React.createClass({

render: function() {

return (

<div>

<h3>Our props from SampleOneComponent state</h3>

<p>firstname from SampleOneComponent state: {this.props.thisState.firstname}</p>

</div>

);

}

});

React.render( <SampleOneComponent />, document.getElementById("sample"));

React’s state and prop is the core of React. Having a good understanding of the concept will help you develop an awesome React application. It takes practice and understanding to get used to it, but once you grasp the basic idea, sky’s the limit. I hope that my explanation of state and prop can help you learn, understand, and develop something with React.