Home > Software engineering >  how to pass a list from flask backend to a reactjs frontend?
how to pass a list from flask backend to a reactjs frontend?

Time:02-20

i am working whit a resful api, written by an ex-coworker, when i use a GET to send a json from the flask api to the frontend and then call the value in the json, i get a string instead an array, the list looks like this

['ETH/BTC','LTC/BTC','BNB/BTC']

here is what i think is relevant from the code

the route:

@bp.route('/fetch_bots_names', methods=['GET'])
def fetch_bots_names():
    user_id = current_user.get_id()
    bots = db.session.query(Bot).all()
    viewable_bots = db.session.query(BotUserCanView).all()
    user_bots = []
    names = []
    for x in bots:
        ub = get_bot_data_as_dict(x)
        if ub != None:
            names.append(ub['name'])
    return  {'ok': True, 
            'msg':'Success',
            'data': json.dumps(names)}, 200

the js to fetch the data

const [botnames, setBotsNames] = useState([]);


if(savedStrats.length==0){
      fetch('/auth/fetch_bots_names', {method: 'GET'})
      .then(res => {return res.text()}).then(response => {
        try {
          let r = JSON.parse(response);
          setBotsNames(r['data']);
        } catch {
          console.log(response);
        }
      });
    }

and as i pointed, the botnames value is a string like the example, but i need it as an array(i think an js array?) in order to make a drop menu whit the elements of the list, thanks in advance

CodePudding user response:

You can use jsonify to convert your data into JSON format and send it in a response.
You can either use keyword arguments or pass a dict.
The documentation clearly explains the usage.

from flask import jsonify 

@bp.route('/fetch_bots_names', methods=['GET'])
def fetch_bots_names():
    bot_names = [bot.name for bot in Bot.query.all()]
    return jsonify({
        'ok': True, 
        'msg':'Success',
        'data': bot_names
    })

In React you use the Fetch Api like this.

fetch('/auth/fetch_bots_names')
  .then(resp => resp.json())
  .then(data => {
    setBotsNames(data.data);
  });

I haven't tested the code, but it should work.

You might want to take a look at Flask-Marshmallow if you want to send larger datasets.
Here is a quick example using Flask-Marshmallow in combination with marshmallow-sqlalchemy.

from flask import Flask
from flask import jsonify
from flask_sqlalchemy import SQLAlchemy
from flask_marshmallow import Marshmallow

app = Flask(__name__)
db = SQLAlchemy(app)
ma = Marshmallow(app)

class Bot(db.Model):
    id = db.Column(db.Integer, primary_key=True)
    name = db.Column(db.String)

class BotSchema(ma.SQLAlchemyAutoSchema):
    class Meta:
        model = Bot

with app.app_context():
    db.drop_all()
    db.create_all()

    bots = [Bot(name=f'bot-{i 1}') for i in range(5)]
    db.session.add_all(bots)
    db.session.commit()

@app.route('/bots')
def bots():
    bots = Bot.query.all()
    bot_schema = BotSchema(many=True)
    bot_data = bot_schema.dump(bots)
    return jsonify(data=bot_data)

The result of the query looks like this.

{
  "data": [
    {
      "id": 1, 
      "name": "name-1"
    }, 
    {
      "id": 2, 
      "name": "name-2"
    }, 
    {
      "id": 3, 
      "name": "name-3"
    }, 
    {
      "id": 4, 
      "name": "name-4"
    }
  ]
}
  • Related