React Bootstrap vs Bootstrap - Comparison
?????? Nitsan Cohen
Frontend Engineer | Microfrontends Specialist | React & TypeScript Expert
One of the core concepts in React is the creation of custom components and the reuse of them. There are several React components libraries that give you out-of-the-box components, such as the famous Material UI, Semantic UI React, Gestalt, and many more.
With that said, in some situations, React developers still prefer the usage of the plain JSX combined with CSS upon using those prepared React components libraries.
This article will compare the React-Bootstrap library, which gives you those ready React components (with the CSS design of Bootstrap), and Bootstrap - the most famous CSS library that lets you use plain JSX and CSS in your React projects and enables you to create your own React custom components. Ready? Set? Let's go!
Bootstrap
Bootstrap library was released in 2011 by the Twitter team, and since then it gained lots of popularity and became one of the most famous CSS libraries with about 2.5M (!) weekly downloads.
It is worth noting, that even though officially Bootstrap is a CSS library, it still heavily relies on JavaScript(with jquery). This fact has implications of how Bootstrap migrates with React, we will see all about it later on.
Bootstraps' latest version is 5.00 and the library is maintained by a huge number of contributors - 1200.
React-Bootstrap
React Bootstrap was released in November 2019 and since then gained a lot of popularity in the React community. It has about 900K downloads per week. Actually, if you take into account that in order to use React-Bootstrap you have to install Bootstrap as well (React-Bootstrap still uses the CSS from the original Bootstrap package) then React-Bootstrap is not so far away from the Bootsraps' weekly downloads rate (if you deduct the number of React-Bootstrap downloads from the Bootstrap downloads).
React-Bootstrap implements the 4th version of Bootstrap.
React is all about virtual DOM
The main problem that React-Bootstrap has come to solve is the integration of Bootstraps' JavaScript with React. Bootstrap uses jquery in order to implement animation and other changes to the DOM, and React, let's say, does not like that.
Long story short - React primarily uses the virtual DOM in order to manipulate the actual DOM. That means that every change to the DOM has to be recorded in the virtual DOM first. jquery, on the other hand, manipulates the DOM directly (aka $ object in jquery). The problem that arises with that is that after jquery manipulates the DOM, React would actually not know anything about that change (because as said, React keeps track of changes with the virtual DOM), and that could lead to lots of bugs and unexpected behavior.
Short is better
Another advantage with React-Bootstrap is that you could implement the same component with shorter syntax. Take the following snippet as an example. Please notice that we had changed the class attribute to className as it is expected to be in a React app:
import React from 'react'; const ReactWithBootstrap = () => { return ( <form> <div className="form-row"> <div className="form-group col-md-6"> <label for="inputEmail4">Email</label> <input type="email" className="form-control" id="inputEmail4" placeholder="Email" /> </div> <div className="form-group col-md-6"> <label for="inputPassword4">Password</label> <input type="password" className="form-control" id="inputPassword4" placeholder="Password" /> </div> </div> <div className="form-group"> <label for="inputAddress">Address</label> <input type="text" className="form-control" id="inputAddress" placeholder="1234 Main St" /> </div> <div className="form-group"> <label for="inputAddress2">Address 2</label> <input type="text" className="form-control" id="inputAddress2" placeholder="Apartment, studio, or floor" /> </div> <div className="form-row"> <div className="form-group col-md-6"> <label for="inputCity">City</label> <input type="text" className="form-control" id="inputCity" /> </div> <div className="form-group col-md-4"> <label for="inputState">State</label> <select id="inputState" className="form-control"> <option selected>Choose...</option> <option>...</option> </select> </div> <div className="form-group col-md-2"> <label for="inputZip">Zip</label> <input type="text" className="form-control" id="inputZip" /> </div> </div> <div className="form-group"> <div className="form-check"> <input className="form-check-input" type="checkbox" id="gridCheck" /> <label className="form-check-label" for="gridCheck"> Check me out </label> </div> </div> <button type="submit" className="btn btn-primary"> Sign in </button> </form> ); }; export default ReactWithBootstrap;
You might have also noticed that we had to add a self-closing tag (/) to all the input tags. This is due to the fact that in JSX all tags must have a closing tag or be self-closed. Now let's see how the exact same component would look in React-Bootstrap:
import React from 'react'; import { Form, Col, Button } from 'react-bootstrap'; const ReactWithReactBootstrap = () => { return ( <Form> <Form.Row> <Form.Group as={Col} controlId="formGridEmail"> <Form.Label>Email</Form.Label> <Form.Control type="email" placeholder="Enter email" /> </Form.Group> <Form.Group as={Col} controlId="formGridPassword"> <Form.Label>Password</Form.Label> <Form.Control type="password" placeholder="Password" /> </Form.Group> </Form.Row> <Form.Group controlId="formGridAddress1"> <Form.Label>Address</Form.Label> <Form.Control placeholder="1234 Main St" /> </Form.Group> <Form.Group controlId="formGridAddress2"> <Form.Label>Address 2</Form.Label> <Form.Control placeholder="Apartment, studio, or floor" /> </Form.Group> <Form.Row> <Form.Group as={Col} controlId="formGridCity"> <Form.Label>City</Form.Label> <Form.Control /> </Form.Group> <Form.Group as={Col} controlId="formGridState"> <Form.Label>State</Form.Label> <Form.Control as="select" defaultValue="Choose..."> <option>Choose...</option> <option>...</option> </Form.Control> </Form.Group> <Form.Group as={Col} controlId="formGridZip"> <Form.Label>Zip</Form.Label> <Form.Control /> </Form.Group> </Form.Row> <Form.Group id="formGridCheckbox"> <Form.Check type="checkbox" label="Check me out" /> </Form.Group> <Button variant="primary" type="submit"> Submit </Button> </Form> ); }; export default ReactWithReactBootstrap;
Now that is arguably much better than the "div-hell" we had before isn't it?
Another nice thing to consider is that we don't use the className attribute at all (even though we could use it if we want to pass our own styles). Instead, React-Bootstrap uses another syntax. So for example if we want to create a flex-row with 2 columns in Bootstrap it would look like this:
<div className="form-row"> <div className="form-group col-md-6"> <label for="inputEmail4">Email</label> <input type="email" className="form-control" id="inputEmail4" placeholder="Email" /> </div> <div className="form-group col-md-6"> <label for="inputPassword4">Password</label> <input type="password" className="form-control" id="inputPassword4" placeholder="Password" /> </div> </div>
and in React-Bootsrap it would look like this:
<Form.Row> <Form.Group as={Col} controlId="formGridEmail"> <Form.Label>Email</Form.Label> <Form.Control type="email" placeholder="Enter email" /> </Form.Group> <Form.Group as={Col} controlId="formGridPassword"> <Form.Label>Password</Form.Label> <Form.Control type="password" placeholder="Password" /> </Form.Group> </Form.Row>
Again this is a "cleaner" syntax and it is much more readable. You can definitely see where the row begins and where it ends (thanks to the closing tags). If you are coming from the CSS world into the React realm though, you might consider staying with pure Bootstrap, if the only reason is the syntax, because this also means you will have to learn a whole new API.
So...React-Bootstrap > Bootstrap?
Actually, there are some reasons to stick with Bootstrap and not implement React-Bootstrap all over the place.
First of all, as mentioned at the beginning of this article Bootstrap's latest version is 5 and guess what? good news! jquery dependency was totally removed. Instead Bootstrap now uses vanilla JavaScript and that is awesome for React developers because all the implications with the virtual DOM are now fixed. Now we can use all of the latest features of Bootstrap in a React app without worrying about Reacts' virtual DOM. With React-Bootstrap we would not be able to use the latest features of BootStrap 5 since, as said, React-Bootstrap only implements the 4th version of Bootstrap.
Another reason to stick around with Bootstrap is the flexibility of your project. If you would ever want to replace your whole frontend with let's say - Vue (although I seriously don't see any reason to do it), it would be much more simple if you use plain Bootstrap.
Lastly, there is another issue with React custom components. It is not about React-Bootstrap in specific, but it has to do with all React custom components. The issue is about the 'ref' field of custom components. The ref field in a custom component will refer to the component itself and not to its building blocks.
Consider the following snippet:
import React from 'react'; const MyCustomInput = () => { return <input className="MyCustomInput" />; }; <MyCustomInput />;
We have created a custom input component. Now let's say we want to get a ref to the current value of that input element. If we try to put the ref on the component itself it will fail and we would not be able to get the current value with the .current property. to fix that we have to use React.forwaredRef like this:
import React from 'react'; const MyCustomInput = React.forwardRef((props, ref) => { <input ref={ref} className="MyCustomInput" />; }); const ref = React.createRef(); <MyCustomInput ref={ref} />;
Well, and in React-Bootstrap we will not be able to do it. If it was our own library we could have implemented it, but it is a public library and we can not make any changes to it. There is actually a solution (call ReactDOM.findDOMNode(ref) to get the DOM node) but for big applications, it gets very cumbersome to apply it. Moreover, the findDomeNode is deprecated in StrictMode, so you don't really want to use it.
Summary
You should use Bootstrap if:
-You have a lot of experience with the Bootstrap library and don't want to learn a new API.
-You care about the flexibility of your app and want to reserve the option to change your framework in the feature.
-You want to use the latest version of Bootstrap.
-You have to use lots of refs in your app.
You should use React-Bootstrap if:
-You care about a clean and readable syntax of your components.
-You want to use the 4th version of Bootstrap with all its JavaScript features.
-You are new to the web development world and don't care about learning a new API.
Student at the College of Western Idaho
4 个月Thanks for the informative article Nitsan, I learned a bunch!
Full Stack Engineer | Machine Learning Enthusiast | Mobile App Developer
1 年thanks
Be creative / curious , it starts with an idea
1 年Nice Article, Thanks
Software Developer/QA Automation
2 年Thanks, very useful info
Frontend Developer
2 年thanks nitsan ????