Search code examples
reactjsflaskflask-socketio

Continuous Data Transfer with Flask Socket Io and Reactjs


I'm trying to stream data every second from my server to the frontend. Currently I could only connect to the socket io and all the tutorials I found was using a chat application as an example.

The project consist of pymodbus so I could communicate to a plc and gather those data. The data is then visualize using reactjs

Python

from flask import Flask, jsonify
from flask_restful import Api, Resource
from flask_socketio import SocketIO, emit
import random

app = Flask(__name__)
app.config["SECRET_KEY"] = "somethingRandom"
app.config["DEBUG"] = True
api = Api(app)

socketio = SocketIO(app, cors_allowed_origins="*")

@app.route("/")
def hello_world():
    return jsonify(mssg="hello world")

def PlcTankData():
  i = 5
  j = 0
  while j != 5: # should be while True
    j+=1
    sample = random.randint(1, 10)
    print(sample)
    emit("newdata", {"td": sample}, namespace="/home")
    socketio.sleep(1)

@socketio.on("connect", namespace="/home")
def frontend_connection():
  print("Client is Connected")
  emit("connect", {"hello": "world"})
  PlcTankData()

class MachineStatus(Resource):
  def put(self):
    data = request.json
    print(data)

api.add_resource(MachineStatus, '/machine-stat')

if __name__ == '__main__':
  socketio.run(app, host="192.168.0.105", port=5000)

Reactjs

import React, { useState, useEffect } from 'react'
import axios from 'axios'
import io from 'socket.io-client'

//To Control the machcine
const handleMachineStatus = async (e) => {
    await axios
      .put('http://192.168.0.105:5000/machine-status', { status: e.target.name })
      .then((res) => {
        console.log(res)
      })
      .catch((err) => console.log(err))
  }

//To get real time data
useEffect(() => {
    const socket = io.connect('http://192.168.0.105:5000/home')
    socket.on('connect', (data) => console.log(data))

    socket.on('newdata', (data) => console.log(data))
  }, [])

I know that the while loop is the one causing the trouble cause the data is being thrown after the while loop is finish.

PS: I'm not sure if the react code also has a problem so I'll tag it.


Solution

  • The connect handler is not a good place to run a lengthy task, because Flask-SocketIO completes the connection process once you return from this handler.

    I suggest you move your PlcTankData function to a separate event instead of calling it from the connect handler.