Sending Pandas DataFrame as JSON to CoreUI/React template
In this tutorial, we are going to use a CoreUI React template as and Python backend with Pandas to read a CSV and render in the UI as JSON Table.
Join the DZone community and get the full member experience.
Join For FreeTutorial Objective
By the end of this tutorial, you will be able to do the following:
- Core UI React Template
- Python with Flask RESTful API
- Using Pandas module to read a CSV from the web and collect rows as Pandas DataFrame
- Convert Pandas DataFrame to JSON
- Send JSON result in UI and render as HTML Table
Getting Starting Code
(Bootstrap Code to Start With):
https://github.com/Avkash/300seconds/tree/master/coreui_react_python_flask_starter
If you are interested in Full Stack Development — Getting Started (Part 1) tutorial to learn how we arrived here, please follow this Part1 tutorial.
Coding Exercise
Here are the steps you would need to take on both (frontend and backend) sides to make this full code working:
FrontEnd Coding:
- Add a new page (CsvDataReader.js) to your core UI template
- Add routes, navigation and menu support in the layout to launch your page when clicked
- Add ts-react-json-table to your package.json and run “npm update”. This will let you use JsonTable react component to render a table from JSON data object.
Following the CsvDataReader.js code:
import React, { Component, lazy, Suspense } from 'react';
import {
Card,
CardBody,
CardFooter,
CardHeader,
CardTitle,
Col,
Row,
} from 'reactstrap';
import JsonTable from 'ts-react-json-table';
import GetRestObject from '../../api/ConnectServerGet';
import PostRestObject from '../../api/ConnectServerPost';
class CsvDataReader extends Component {
constructor(props) {
super(props);
this.state = {
csvDataObject:[]
};
}
HelloGetRequestedDetails = () => {
GetRestObject.GetRestRequest(`/v1/datareader`, getResultObj => {
this.setState({
csvDataObject:getResultObj
})
});
}
renderColumnNames = (colmunList) => {
return(
colmunList.map( (item, index) => {
return(
<span key={index} className="mr-1 text-default">{index+1}: {item}</span>
)
})
)
}
renderCsvDataResults = () => {
if (this.state.csvDataObject && this.state.csvDataObject.resultStatus && this.state.csvDataObject.resultData){
var apiStatus = this.state.csvDataObject.resultStatus;
var apiData = this.state.csvDataObject.resultData;
if (apiStatus === 'SUCCESS' && apiData.length == 1){
apiData = apiData[0]
return(
<div>
<span className="text-success">Rows: <span className="text-primary"><b>{apiData.rows}</b></span></span>
<br/>
<span className="text-success">Columns: <span className="text-primary"><b>{apiData.cols}</b></span></span>
<br/>
<span className="text-success">Column Names:
<span className="text-primary"><b>{this.renderColumnNames(apiData.columns)}</b></span>
</span>
<hr/>
<Card>
<CardHeader>All Rows</CardHeader>
<CardBody className="mb-1" style={{height:'400px', overflowY: "auto", overflow: "-moz-scrollbars-horizontal"}}>
<JsonTable rows={apiData.rowData} columns={apiData.columns} />
</CardBody>
</Card>
</div>
)
} else {
return(
<div>
<span className="text-danger">{apiData[0].message}</span>
</div>
)
}
}
}
componentDidMount(){
this.HelloGetRequestedDetails()
}
loading = () => <div className="animated fadeIn pt-1 text-center">Loading</div>
render() {
return (
<div className="animated fadeIn">
<Row>
<Col md={12}>
<h3>Data Reader Starter</h3>
<hr/>
{this.renderCsvDataResults()}
</Col>
</Row>
</div>
);
}
}
export default CsvDataReader;
Backend Coding
- Add support for API (/v1/datareader) by adding a resource
# app.py
api.add_resource(DataHandlerFunction, '/v1/datareader')
2. Implement DataHandlerFunction in CsvDataHandler.py as below:
xxxxxxxxxx
from flask_restful import Api, Resource, reqparse
import pandas as pd
import requests
import io
class DataHandlerFunction(Resource):
'''
'''
def get(self):
result_status, result_data = CSVReaderToJson()
return {'resultStatus': result_status, 'resultData': result_data}
def CSVReaderToJson():
result_status = 'FAILURE'
result_data = []
csv_url = "https://raw.githubusercontent.com/cs109/2014_data/master/countries.csv"
try:
url_content = requests.get(csv_url).content
csv_data = pd.read_csv(io.StringIO(url_content.decode('utf-8')))
row_count = csv_data.shape[0]
column_count = csv_data.shape[1]
column_names = csv_data.columns.tolist()
# Option [1]
# row_json_data = csv_data.to_json(orient='records')
# Option [2]
final_row_data = []
for index, rows in csv_data.iterrows():
final_row_data.append(rows.to_dict())
json_result = {'rows': row_count, 'cols': column_count, 'columns': column_names, 'rowData': final_row_data}
result_data.append(json_result)
result_status = 'SUCCESS'
except:
result_data.append({'message': 'Unable to process the request.'})
return result_status, result_data
Final Source Code (Both CoreUI Frontend and Python Backend)
https://github.com/Avkash/300seconds/tree/master/coreui_react_python_flask_pandas_starter
YouTube Tutorial (00:43.30 Minutes)
Opinions expressed by DZone contributors are their own.
Comments