For the initial render, I have object date
, which is an empty array. I then try to get data from an influxDB, but the get result isn't reflected by React with a re-render. The get function is calling in useEffect
(you can see this in screenshots). I use typescript, and to avoid getting an error on the initial load (that data is an empty array of objects and it doesn't have a value property) I use the typescript syntax, but it still doesn't display the correct value. It doesn't display anything at all.
What could be the problem? In the last photo, we can see another way to display data without a question mark from typescript, but it doesn't work correctly either, even if the length of the array is greater than 0, it still doesn't display data[0].value
.
Get the first element in array:
Browser result (before ':' we should see data[0].value
):
Alternate way (when data isn't empty we should see the value of the first object in array):
I also show we code
import React from 'react';
import './App.css';
import { FluxTableMetaData } from '@influxdata/influxdb-client';
const { InfluxDB } = require('@influxdata/influxdb-client');
export const App = () => {
debugger
const authData = {
token: 'Emyw1rqUDthYRLpmmBc6O1_yt9rGTT57O50zoKiXUoScAjL6G-MgUN6G_U9THilr86BfIPHMYt6_KSDNHhc9Jg==',
org: 'testOrg',
bucket: 'test-bucket',
};
const client = new InfluxDB({
url: 'http://localhost:8086',
token: authData.token,
});
const queryApi = client.getQueryApi(authData.org);
const query = `from(bucket: "${authData.bucket}") |> range(start: -1d)`;
const data: any[] = [];
React.useEffect(() => {
queryApi.queryRows(query, {
next(row: string[], tableMeta: FluxTableMetaData) {
debugger;
const o = tableMeta.toObject(row);
const item = {
time: o._time,
measurement: o._measurement,
field: o._field,
value: o._value,
};
return data.push(item);
},
error(error: Error) {
return error;
},
complete() {
console.log(data)
return data;
},
})
},[]);
debugger;
return (
<div>
<div>{data.length !== data[0].value}:</div>
<div>hello</div>
</div>
);
};
another way:
<div>
<div>{data[0]?.value}:</div>
<div>hello</div>
</div>
CodePudding user response:
I suggest you use the React States for that in the following way
var [nameOfVariableWhichWillChange, changeFunction] = React.useState("");
now whenever whichever function wants to change the value of that function just use changeFunction(newValueOfVariable)
the plus point of using React state is wherever you might have used that variable on change of That variable each instance will change on its own...
Do let me know does that solve your problem, or you need something else
CodePudding user response:
React doesn't re-render the webpage even if the data has changed. You need to store your data inside a React.useState
and call setState
to trigger a re-render.
const [data, setData] = useState([])
React.useEffect(() => {
...
next(row: string[], tableMeta: FluxTableMetaData) {
...
setData([...data, item])
},
...
Read about useState
here for more information: https://reactjs.org/docs/hooks-state.html
CodePudding user response:
The main issue in your code is, You have defined data as a const
variable, and not as a state
. Thus, in useEffect
, even if your data
gets changed, it will not reflect on data[0].value
as it is a const variable and react doesn't render updated values of variables. It updates/renders only if it's a state.
In short, Convert your const
data to be a state
and use setState
like below for your code to work!
const [data, setData] = React.useState([]);
...
setData([...data , item]);