I'm experimenting with ReactJS, and much of my application relies on loading data from an API, using jQuery to help me with that.
I have loading text/icon setup, but it feels a bit hacky and not very reusable:
ListWrapper = React.createClass({
getInitialState: function() {
return {
loading: true,
listData: []
};
},
componentDidMount: function() {
Api.get('/v1/listdata', function (data) {
react.setState({
loading: false,
listData: data
});
});
},
render: function() {
return (
<List loading={this.state.loading} data={this.state.listData} />
);
}
});
List = React.createClass({
render: function() {
var mapData;
if (this.props.loading)
mapData = <Loader />;
else {
mapData = this.props.data.map(function(item) {
return (
<ListItem name={item.name} />
);
});
}
return (
<div>
{mapData}
</div>
);
}
});
This works fine, however the whole if/else statement has hints of code smells since I'd have to do that logic all over the place.
Can't really find anything on the web about how to best approach this... Whats a better way?
The major cause for this issue is adding too many components into a single bundle file, so the loading of that bundle file might take more time. To avoid this kind of issue, we need to structure our components in an optimized way.
showLoader(); ajax(config) . then((response) => { let data; this. props. hideLoader(); data = response.
import React, { useState, useEffect } from 'react'; const App = () => { const [loading, setLoading] = useState(false); return ( <! -- ... --> ); }; export default App; Note: The state is set to false by default in the code above, and we can change it to true whenever we want the loader-container to appear.
You can simplify your existing code to be less verbose just by removing the else statement:
render: function() {
if (this.props.loading) {
return <Loader />;
}
var mapData = this.props.data.map(function(item) {
return (
<ListItem name={item.name} />
);
});
return (
<div>
{mapData}
</div>
);
}
But one solution I can think of is have your component accept a isActive
bool and moving the if logic into the loader component instead of the individual components. When isActive = true
it shows the spinner/loading icon. Otherwise it just returns a null component or empty .
List = React.createClass({
render: function() {
var mapData = this.props.data.map(function(item) {
return (
<ListItem name={item.name} />
);
});
return (
<div>
<Loader isActive={this.props.isLoading} />
{mapData}
</div>
);
}
});
This case instead of doing the if logic everywhere, you just do it once in your Loader
component, and it just returns null/empty if its inactive.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With