Home > Software design >  How to retrieve data from JSON using reactJS and placing them in the right place?
How to retrieve data from JSON using reactJS and placing them in the right place?

Time:01-12

I would like to retrieve the data from a JSON that is sent by a python program and place it in the corresponding boxes via the dictionary keys. I have tried to retrieve the data like this but it does not display the corresponding values to the dictionary keys. So I would like to know how to solve this problem?

I also don't know how I could make sure that I take the corresponding data according to the h2 texts and ids of each section?

Here are the code:

App.js :

import React, { useState, useEffect } from 'react';
import Modal from './Modal/Modal'
//JSON.parse(event.data)

export default function App() {
  const [data, setData] = useState(null);
  const [show,setShow] = useState(false);

  useEffect(() => {
    const socket = new WebSocket('ws://localhost:8000');

    socket.addEventListener('message', (event) => {
      setData(event.data);
    });
  }, []);

  return (
        <div>
            <div className="home">
                <div className="template-1" id="temp1">
                <div className="panel-1">
                    <div className="panel-header">
                    <h1>Foresail</h1>
                    <i className='bx bx-cog modal-trigger-panel'></i>
                    </div>
                    <div className="panel-body">
                    <div className="sec-5 modal-trigger-data" id="hs-sec-5" onClick={()=>setShow(true)}>
                        {data ? <span  id="h1-fs-s5">{data.fs.s5.entry}</span> : <span  id="h1-fs-s5">--</span>}
                        <h2>TWIST</h2>
                        <h3>s5</h3>
                    </div>
                    <div className="sec-4 modal-trigger-data" id="hs-sec-4" onClick={()=>setShow(true)}>
                        {data ? <span  id="h1-fs-s4">{data[1]}</span> : <span  id="h1-fs-s4">--</span>}
                        <h2>TWIST</h2>
                        <h3>s4</h3>
                    </div>
                    <div className="sec-3 modal-trigger-data" id="hs-sec-3" onClick={()=>setShow(true)}>
                        {data ? <span  id="h1-fs-s3">{data[2]}</span> : <span  id="h1-fs-s3">--</span>}
                        <h2>TWIST</h2>
                        <h3>s3</h3>
                    </div>
                    <div className="sec-2 modal-trigger-data" id="hs-sec-2" onClick={()=>setShow(true)}>
                        {data ? <span  id="h1-fs-s2">{data[3]}</span> : <span  id="h1-fs-s2">--</span>}
                        <h2>TWIST</h2>
                        <h3>s2</h3>
                    </div>
                    <div className="sec-1 modal-trigger-data" id="hs-sec-1" onClick={()=>setShow(true)}>
                        {data ? <span  id="h1-fs-s1">{data[4]}</span> : <span  id="h1-fs-s1">--</span>}
                        <h2>TWIST</h2>
                        <h3>s1</h3>
                    </div>
                    </div>
                </div>
                </div>
                <Modal onClose={() => setShow(false)} show={show} />
            </div>
        </div> 
  );
}

Python :

import asyncio
import random
import datetime
import websockets
import json

sv={"fs":{
    "s5":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},
    "s4":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},
    "s3":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},
    "s2":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},
    "s1":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},
    },
    "ms":{
    "s5":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},
    "s4":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},
    "s3":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},
    "s2":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},
    "s1":{"entry":2,"cfwd":3,"camber":2,"draft":3,"caft":5,"exit":5,"twist":15,"sag_lat":10,"sag_long":10},    
    }}
async def handler(websocket, path):
    while True:
        #log_decoder()
        
        #data = [random.randint(0, 20) for _ in range(10)]
        await websocket.send(json.dumps(sv))
        await asyncio.sleep(1)

start_server = websockets.serve(handler, "localhost", 8000)

asyncio.get_event_loop().run_until_complete(start_server)
asyncio.get_event_loop().run_forever()

Regards,

CodePudding user response:

I'm not very well versed in Python libraries, so I'll just address the front-end JavaScript, which is where the problem seems to be.

Based on what I read in the Python Docs for websockets and json, it seems that the WebSockets server is sending a JSON format string of sv. So the problem is likely the front-end indexing a string with data[1] being: ", and trying to access an undefined property of the string with data.fs.s5.entry to get an error like: ReferenceError: reference to undefined property "x" (More on property accessors).

So parsing the JSON string to a JavaScript object should solve the problem for getting data, and then just get the properties of data in the JSX:

import React, { useState, useEffect } from "react"
import Modal from "./Modal/Modal"

export default function App() {
  const [data, setData] = useState(null)
  const [show, setShow] = useState(false)

  useEffect(() => {
    const socket = new WebSocket("ws://localhost:8000")

    socket.addEventListener("message", event => {
      setData(JSON.parse(event.data))
    })
  }, [])

  return (
    <div>
      <div className="home">
        <div className="template-1" id="temp1">
          <div className="panel-1">
            <div className="panel-header">
              <h1>Foresail</h1>
              <i className="bx bx-cog modal-trigger-panel"></i>
            </div>
            <div className="panel-body">
              {data
                ? /* array of JSX elements */
                  Object.entries(data.fs).map(([s1Tos5, properties]) => (
                    <div
                      className={`sec-${s1Tos5.replace("s", "")} modal-trigger-data`}
                      id={`hs-sec-${s1Tos5.replace("s", "")}`}
                      onClick={() => setShow(true)}
                    >
                      <span  id={`h1-fs-${s1Tos5}`}>
                        {properties.entry}
                      </span>
                      <h2>{properties.twist}</h2>
                      <h3>{s1Tos5}</h3>
                    </div>
                  ))
                : /* add a placeholder element for when data is loading */
                  Array(5).map((_value, index) => (
                    <div
                      className={`sec-${index   1} modal-trigger-data`}
                      id={`hs-sec-s${index   1}`}
                      onClick={() => setShow(true)}
                    >
                      <span  id={`h1-fs-s${index   1}`}>
                        ---
                      </span>
                      <h2>TWIST</h2>
                      <h3>s{index   1}</h3>
                    </div>
                  ))}
            </div>
          </div>
        </div>
        <Modal onClose={() => setShow(false)} show={show} />
      </div>
    </div>
  )
}

Hope this helps!

  • Related