首页 > 解决方案 > 我正在尝试从同一组件中的 2 个不同的 API 调用中呈现两个不同的字符串

问题描述

import { useState, useEffect } from 'react';
import socketConnection from '../../connection';
import NavBar from '../../../Component/NavBar.';

const ws = socketConnection();

export default function GetEvent() {
  const [matchTime, setMatchTime] = useState('');
  const [teamNames, setTeamNames] = useState('');
  const [market, setMarket] = useState('');
  const [isLoading, setLoading] = useState(true);
  const [socketData, setSocketData] = useState([]); // array of objects.



useEffect(() => {
    ws.onopen = () => ws.send(
      /* eslint-disable */
        JSON.stringify({
          keys: ['xyz'],
          type: 'getEvent',
          id: 111,
          keys: ['skd'],
          type: 'getMarket',
          id: 222,
        }),
      );
function handleMessage(event) {
  console.log('Handling message');
  setLoading(true);
  const parsedData = JSON.parse(event.data);
  console.log(parsedData);
  setMatchTime(parsedData.data.startTime);
  setTeamNames(parsedData.data.name);
  setSocketData((currentSocketData) => [...currentSocketData, parsedData]);
  setMarket((currentSocketData) => [...currentSocketData, parsedData[1]]);
  setLoading(false);
}
    ws.addEventListener('message', handleMessage);

    return () => ws.removeEventListener('message', handleMessage);
  }, []);

@developers 控制台

console.log(matchTime); 未定义对象的数组。 -预期“2020 09 02” console.log(teamNames); 半场/全场 -预期“游侠对狼” console.log(market); 未定义对象数组。-预期“半场/全场”

我也尝试过渲染为不同的组件,但这没有意义,因为它们只是来自 API 的字符串。

return (
    <>
      <NavBar />
      <div className="footyevent" data-testid="footy-event-id">
        <div className="container">
          <h1>Football</h1>
          <div className="title-box">
            {isLoading && <div className="loading">Not Connected... Please 
             Refresh</div>}
          </div>
          <div className="title-box">
            <div className="startTime" data-testid="event-time-id">
              Date & Time: {matchTime}  {/* blanc */}
            </div>
          </div>
          <div className="title-box">
            <div className="teams" data-testid="playing-teams-id">
              {teamNames}  {/* HalfTime/FullTime */}
            </div>
          </div>
          <div className="title-box">
            <div className="socket-data" data-testid="socket-data-id">
              {socketData.map((x, index) => (
                <p>
                  {x.data.name}  {/* HalfTime/FullTime */}
                </p>
              ))}
            </div>
          </div>
        </div>
      </div>
    </>
  );
}

行为良好的单个 API 调用

JSON.stringify({
          keys: ['xyz'],
          type: 'getEvent',
          id: 212,
        }),
      );

更新:我现在发现很难解析或映射从 WebSocket 服务器响应接收到的数据(对象)。

export default function GetEvent() {
  const [isLoading, setLoading] = useState(true);
  const [socketData, setSocketData] = useState([]); // objects.

  useEffect(() => {
    ws.onopen = () => {
      ws.send(
        /* eslint-disable */
        JSON.stringify({
          keys: ['xyz'],
          type: 'getEvent',
          id: 111,
        }),
      );
      ws.send(
        /* eslint-disable */
        JSON.stringify({
          keys: ['skd'],
          type: 'getMarket',
          id: 222
        }),
      );
    };


    function handleMessage(event) {
      console.log('Handling message');
      setLoading(true);
      const parsedData = JSON.parse(event.data);
      console.log(parsedData);
      setSocketData((currentSocketData) => [...currentSocketData, parsedData]);
      setLoading(false);
    }

    ws.addEventListener('message', handleMessage);

    return () => ws.removeEventListener('message', handleMessage);
  }, []);



socketData.forEach(x => x.forEach(y => {
    if (x.type === 'EVENT_DATA') {
      console.log(`event data: ${y.data.name}`);
    } else if (x.type === 'BET_DATA') {
      console.log(y.data.name);
    }
  }));
  

return (
    <>
      <div className="title-box">
    <div key="uniqueId2" className="teams" data-testid="playing-teams-id">
      {socketData.map(data1 => console.log(data1))}
    </div>
</div>
    </>
  );
}

控制台数据和错误

迭代记录的套接字数据:

Uncaught TypeError: x.forEach is not a function

控制台日志(数据1):

{type: 'EVENT_DATA', data: {…}}
data: {
  id: 1;
  name: 'A';
  date: '12020507'
}
{type: 'MARKET_DATA', data: {…}}
data: {
  id: 1;
  name: 'Final Result';
}

控制台.log(data1[0])

undefined

控制台.log(data1.name):

'A'
'Final Result'

标签: javascriptreactjs

解决方案


您的主要问题可能是:

JSON.stringify({
  keys: ['xyz'],
  type: 'getEvent',
  id: 111,
  keys: ['skd'],
  type: 'getMarket',
  id: 222,
})

如果您在对象文字中使用重复键,它们将覆盖先前的值

({ a: 1, b: 2, c: 3, a: 4, b: 5 }) //=> { a: 4, b: 5, c: 3 }

这意味着前 3 个键(keystypeid)的值将丢失。

我不知道你的套接字在期待什么。如果它接受数组,则应改用以下内容。

ws.send(JSON.stringify([{
  keys: ['xyz'],
  type: 'getEvent',
  id: 111,
}, {
  keys: ['skd'],
  type: 'getMarket',
  id: 222,
}]))

或者,您可以发送 2 个单独的请求。

ws.send(JSON.stringify({
  keys: ['xyz'],
  type: 'getEvent',
  id: 111,
}))
ws.send(JSON.stringify({
  keys: ['skd'],
  type: 'getMarket',
  id: 222,
}))

对于最后一个,您可能需要调整handleMessage功能。因为不是两个结果都在一个响应中,而是处理程序将被调用 2 次。


推荐阅读