0

我想看看是否可以就如何在此 api 调用中调用数据点获得一些帮助,它是一个数字数组,因此字段值可能是 6。但我无法在屏幕上加载任何内容。我的呼叫正在工作,因为我正在加载...当为空时,但它只是消失并且不显示任何内容。每当我尝试为数据分配一个数字时,它都会显示无法识别。

import React, { Component } from 'react'

let headers = {
  'QB-Realm-Hostname': 'XXXXXXXXXXXXXX.quickbase.com',
  'User-Agent': 'FileService_Integration_V2.1',
  'Authorization': 'QB-USER-TOKEN XXX_XXXX_XXXXXXXXXXXXXXXXXXX',
  'Content-Type': 'application/json'
};

class JobsTableApi extends Component {
  state = {
    data: null,
  }

  componentDidMount() {
    this.fetchData();
  }    

  fetchData = () => {    
    let body = {"from":"bpz99ram7","select":[3,6,80,81,82,83,86,84,88,89,90,91,92,93,94,95,96,97,98,99,101,103,104,105,106,107,109,111,113,115,120,123,224,225,226,227,228,229,230,231,477,479,480,481],"sortBy":[{"fieldId":6,"order":"ASC"}],"groupBy":[{"fieldId":40,"grouping":"equal-values"}],"options":{"skip":0,"top":0,"compareWithAppLocalTime":false}}

    fetch('https://api.quickbase.com/v1/records/query', {
      method: 'POST',
      headers: headers,
      body: JSON.stringify(body)
    }).then(response => {
      if (response.ok) {
        return response.json().then(res => {
          this.setState({
            data: [],
          })
        });
      }

      return response.json().then(resBody => Promise.reject({status: response.status, ...resBody}));
    }).catch(err => console.log(err))
  }

  render() {
    const { data } = this.state;

    if (data === null) return 'Loading...';

    return (
        <div>{data["3"]}</div>
    )
  }
}

export default JobsTableApi;

API 数据 例如:

{
    "data": [
        {
            "3": {
                "value": 43
            },
            "18": {
                "value": "Radiant"
            },
            "20": {
                "value": null
            },
            "144": {
                "value": null
            },
            "145": {
                "value": 33230
            },
            "171": {
                "value": 8
            },
            "172": {
                "value": 228
            },
            "174": {
                "value": 270
            },
            "212": {
                "value": 0
            },
            "215": {
                "value": 8.34487776140499
            },
            "216": {
                "value": 16.34487776140499
            },
            "217": {
                "value": 244.344877761405
            },
            "218": {
                "value": 572.3449342166289
            },
            "219": {
                "value": 842.3449342166289
            },
            "220": {
                "value": 861.8163156599072
            },
            "221": {
                "value": 877.8106647026001
            },
            "222": {
                "value": 0
            },
            "223": {
                "value": 239.256
            },
            "227": {
                "value": 5050.96
            },
            "230": {
                "value": 239.256
            },
            "231": {
                "value": 239.256
            },
            "232": {
                "value": 17339.414
            },
            "233": {
                "value": 26743.504
            },
            "234": {
                "value": 22390.374
            },
            "235": {
                "value": 22948.638
            },
            "236": {
                "value": 23407.212
            },
            "244": {
                "value": 0
            },
            "249": {
                "value": 0
            },
            "322": {
                "value": 870.6260000000001
            },
            "325": {
                "value": 17100.158
            },
            "338": {
                "value": ""
            },
            "349": {
                "value": 8
            },
            "350": {
                "value": 0
            },
            "351": {
                "value": 220
            },
            "366": {
                "value": 0
            },
            "438": {
                "value": null
            },
            "513": {
                "value": 278
            },
            "516": {
                "value": 23261
            },
            "517": {
                "value": 17339.414
            }
        }

更新:能够在我的 App.js 中将 {jobId} 设置为道具,因为这是我的折线图的父项,这就是真相需要的地方,然后我可以将它发送到每个折线图以拉取为基础在哪个 Title(以及 ID)上显示哪个指示 API 调用的结果。

应用程序.js

import React, { useEffect, useState } from "react";
import './App.css'
import Title from './components/header/Title'
import TotalLineChart from './components/charts/TotalLineChart'
import RadiantLineChart from './components/charts/RadiantLineChart'
import PlumbingLineChart from './components/charts/PlumbingLineChart'
import SnowmeltLineChart from './components/charts/SnowmeltLineChart'
import HVACLineChart from './components/charts/HVACLineChart'
import GasPipeLineChart from './components/charts/GasPipeLineChart'
import FixturesLineChart from './components/charts/FixturesLineChart'
// import TitleCycle from './components/TitleCycle'
// import Logo from './components/Logo';

let headers = {
  "QB-Realm-Hostname": "XXXXXX.quickbase.com",
  "User-Agent": "FileService_Integration_V2.1",
  "Authorization": "QB-USER-TOKEN XXXXXXX",
  "Content-Type": "application/json",
  "Retry-After": 120000
};

function App() {
  const [allData, setAllData] = useState([]);
  const [index, setIndex] = useState(0);

  // Fetch all data, all jobs
  useEffect(() => {
      function fetchData() {
          let body = {
              from: "bpz99ram7",
              select: [3, 6, 40],
              where: "{40.CT. 'In Progress'}",
              sortBy: [{ fieldId: 6, order: "ASC" }],
              groupBy: [{ fieldId: 40, grouping: "equal-values" }],
              options: { skip: 0, top: 0, compareWithAppLocalTime: false },
          };
          fetch("https://api.quickbase.com/v1/records/query", {
            method: "POST",
            headers: headers,
            body: JSON.stringify(body),
        })
            .then((response) => response.json())
            .then(({ data }) => setAllData(data));
    }
    fetchData();
}, []);

// Cycle through the jobIds and indexes
useEffect(() => {
    const timerId = setInterval(
        () => setIndex((i) => (i + 1) % allData.length),
        5000 // 5 seconds.
    );
    return () => clearInterval(timerId);
}, [allData]);
// console.log(allData)
// console.log(index)
// Calculate info based on index
const jobId = allData[index]?.['3']?.value || '291'; // Default 291
const title = allData[index]?.['6']?.value || 'Default Title'; 
// console.log(jobId)
  return (
      <div>
        {/* <div className="flexbox-container">
          <div className="Logo">
          {/* <Logo /> */}
         {/* </div> */}
        <div className="App">
          <Title title = {title} />
        </div>
        <div className="TopChart">
          <TotalLineChart jobId = {jobId} />
        </div>
        <div className="FirstRowContainer">
          {/* <RadiantLineChart jobId = {jobId} /> */}
          <PlumbingLineChart jobId = {jobId} />
          <FixturesLineChart jobId = {jobId} />
        </div>
        <div className="SecondRowContainer">
          <SnowmeltLineChart jobId = {jobId} />
          <HVACLineChart jobId = {jobId} />
          <GasPipeLineChart jobId = {jobId} />
        </div> 
      </div>
  );
}

export default App;

LineChart.js

import React, { useState, useEffect } from "react";
import { Scatter } from "react-chartjs-2";
// import jobId from '../TitleCycle';
// import Title from '../header/Title';

function TotalLineChart(props) {
  const { jobId } = props;
  // console.log(`${jobId}`)
  const [chartData, setChartData] = useState({});

  const chart = () => {
    let designHours = [];
    let designAmount = [];
    let subRoughHours = [];
    let subRoughAmount = [];
    let roughHours = [];
    let roughAmount = [];
    let finishHours = [];
    let finishAmount = [];
    let closeHours = [];
    let closeAmount = [];
    let actualHours = [];
    let actualAmount = [];

    let headers = {
      "QB-Realm-Hostname": "XXXXXXXXXX.quickbase.com",
      "User-Agent": "FileService_Integration_V2.1",
      "Authorization": "QB-USER-TOKEN XXXXXXXXXXX",
      "Content-Type": "application/json",
      "x-ratelimit-reset": 10000,
      "Retry-After": 30000
    };
    // useEffect(() => {
    //   function fetchData() {
      const body = {
        from: "bpz99ram7",
        select: [
          3,
          88,
          91,
          92,
          95,
          96,
          98,
          104,
          107,
          224,
          477,
          479,
          480,
        ],
        where: `{3.EX. ${ jobId }}`,
        sortBy: [{ fieldId: 6, order: "ASC" }],
        groupBy: [{ fieldId: 40, grouping: "equal-values" }],
        options: { skip: 0, compareWithAppLocalTime: false }
      };
      fetch("https://api.quickbase.com/v1/records/query", {
        method: "POST",
        headers: headers,
        body: JSON.stringify(body)
      })
    //   }
    //   fetchData();
    // }, [])

      .then((response) => response.json())
      .then((res) => {
        // console.log(res);
        Object.keys(res.data).map(jobId => {
          designHours = parseInt(res.data[jobId]['88'].value, 10);
          designAmount = parseInt(res.data[jobId]['91'].value, 10);
          subRoughHours = parseInt(res.data[jobId]['92'].value, 10);
          subRoughAmount = parseInt(res.data[jobId]['95'].value, 10);
          roughHours = parseInt(res.data[jobId]['96'].value, 10);
          roughAmount = parseInt(res.data[jobId]['98'].value, 10);
          finishHours = parseInt(res.data[jobId]['104'].value, 10);
          finishAmount = parseInt(res.data[jobId]['107'].value, 10);
          closeHours = parseInt(res.data[jobId]['477'].value, 10);
          closeAmount = parseInt(res.data[jobId]['480'].value, 10);
          actualHours = parseInt(res.data[jobId]['479'].value, 10);
          actualAmount = parseInt(res.data[jobId]['224'].value, 10);

          setChartData({
            type: 'scatter',
            redraw: true,
              datasets: [
                {
                label: 'TOTAL',
                data: [
                  { x: designHours, y: designAmount },
                  { x: subRoughHours, y: subRoughAmount },
                  { x: roughHours, y: roughAmount },
                  { x: finishHours, y: finishAmount },
                  { x: closeHours, y: closeAmount }
                ],
                borderWidth: 2,
                borderColor: '#4183c4',
                backgroundColor: '#4183c4',
                tension: 0.8,
                spanGaps: true,
                lineTension: 0.5,
                showLine: true,
                fill: false,
                showTooltip: false,
                pointBorderWidth: 1
              },
              {
                label: 'ACTUALS',
                data: [{ x: actualHours, y: actualAmount }],
                fill: false,
                borderColor: '#e34747',
                backgroundColor: '#e34747',
                borderWidth: 3,
                showTooltip: false
              }
            ],
            options: {
              showAllTooltips: true,
              enabled: true,
              maintainAspectRatio: false,
              legend: {  
                display: true
              }
            }
          })
        })
      })
      .catch((err) => {
        console.log(err);
      });
  };

  useEffect(() => {
    chart();
  }, []);

  return (
    <div className="App">
      <div>
        <Scatter 
        // ref={(reference) => this.chartReference = reference } 
          data={chartData}
          options={{
            title: { text: "Total Project", display: false },
            scales: {
              yAxes: [
                {
                  scaleLabel: {
                    display: true,
                    labelString: '$ AMOUNT'
                  },
                  ticks: {
                    autoSkip: true,
                    maxTicksLimit: 10,
                    beginAtZero: true
                  },
                  gridLines: {
                    display: true
                  }
                }
              ],
              xAxes: [
                {
                  scaleLabel: {
                    display: true,
                    labelString: 'HOURS'
                  },
                  gridLines: {
                    display: true
                  }
                }
              ],
            },
          }}
        />
      </div>
    </div>
  );
};

export default TotalLineChart;

如您所见,API 正在获取来自 App.js 的任何 {jobId} 的 '#' id。你也可以在我的 API 正文中看到。

4

0 回答 0