How to pass data from React Form -> Flask Backend -> React Component (does it have something to do with CORS)?
Sending data to your flask back end is a POST request but you are using a GET request. So your fetch in React js should be
fetch("/result", {
method:"POST",
cache: "no-cache",
headers:{
"content_type":"application/json",
},
body:JSON.stringify(this.state.value)
}
).then(response => {
return response.json()
})
.then(json => {
this.setState({playerName: json[0]})
})
Your flask method should also be a POST method
@app.route('/result', methods = ['POST'])
def result():
player_id = request.json
if player_id:
data = get_player(player_id)
name = str(data['name'][0])
return jsonify(name)
return "No player information is given"
You would need CORS in your flask so
pip install flask-cors then in your code
from flask_cors import CORS
app = Flask(__name__, static_folder='../frontend/build')
CORS(app)
Also you dint post your react js package so make sure you have your proxy added in your package.json like this
"name": "client",
"version": "0.1.0",
"private": true,
"proxy": "http://0.0.0.0:5000",
I assume the rest of your code works so this is just to answer your question in relation to setting up a connection between Flask and React JS.
You would be able to recieve data in flask from React but you would have a problem sending json data from the database in flask to reactjs . For the database handling I usually use Flask-SQLAlchemy and data I get from the database isnt a json object so I have to serialize the model into JSON and this achieved through a package called flask-marshmellow. So look into use those two packages
Related videos on Youtube
Tom Jackson
Updated on October 10, 2022Comments
-
Tom Jackson over 1 year
Hi I am a complete React beginner and have a fairly basic question. I am looking to perform the following steps:
(1) Provide user a form to input some text (2) Ingest the input into the Flask backend and return a new value after performing some operations (3) Provide the result from (2) to the user in front end view
I'd like this process to be a single page app where the user does not get redirected to another page on step (3).
Here is my App.js code:
import React from 'react'; import './App.css'; class App extends React.Component { constructor(props) { super(props); this.state = {value: '', playerName: ''}; this.handleChange = this.handleChange.bind(this); this.handleSubmit = this.handleSubmit.bind(this); } handleChange(event) { this.setState({value: event.target.value}); } handleSubmit(event) { console.log("making request") fetch('/result') .then(response => { console.log(response) return response.json() }) .then(json => { console.log=(json) this.setState({playerName: json[0]}) }) } render() { return ( <div> <form onSubmit={this.handleSubmit} action="http://localhost:5000/result" method="get"> <label> Player ID: <input type="text" name="player_id"/> <input type="submit" onChange={this.handleChange} value={this.state.value} /> </label> </form> <h1> Player Name: {this.state.playerName} </h1> </div> ); } } export default App
Here is my main.py code:
from flask import Flask, request, jsonify, send_from_directory from sqlalchemy import create_engine import pandas as pd app = Flask(__name__, static_folder='../frontend/build') @app.route('/result', methods = ['GET']) def result(): if request.method == 'GET': player_id = request.args.get('player_id', None) if player_id: data = get_player(player_id) name = str(data['name'][0]) return jsonify(name) return "No player information is given" def get_player(player_id): engine = create_engine( 'postgres://fzmokkqt:********************-***-******-@********.com:*****/******') sql = """SELECT * from players WHERE id={player_id}""" data = pd.read_sql_query(sql.format(player_id=player_id), con=engine) return data @app.route('/', defaults={'path': ''}) @app.route('/<path:path>') def serve(path): if path != "" and os.path.exists("frontend/build/" + path): return send_from_directory('../frontend/build', path) else: return send_from_directory('../frontend/build', 'index.html') if __name__ == '__main__': app.run(debug=True, host='0.0.0.0')
When I run this code, I receive the intended result however it is not placed in the HTML as described in the App.js code. Instead, the result is rendered into a new page (on localhost:5000 instead of localhhost:3000 which is where the React code is rendered).