React Kendo Grid - TSX - unable to toggle detail view when data retrieved by fetch

1 Answer 40 Views
Grid
Michael
Top achievements
Rank 1
Iron
Michael asked on 06 Feb 2024, 05:39 AM | edited on 06 Feb 2024, 05:47 AM

Hi,

I am trying to get this grid to display the TEST message in the detail when I click the expander against the row.  Everything looks to be working as expected (I am using state.fetchErrorMsg to provide debug text to prove that state is changing and triggering re-rendering when necessary, I can also confirm that the expander toggles between + and - as expected).

Any ideas what I am doing wrong here?  I suspect it is something to do with how I am handling the promise that returns the data, since I can get this working when I use locally built static arrays instead of the fetch.

Cheers

Mike

import React, { useEffect, useState } from 'react';
import { UserInfo, TcbObjMilestoneGrp, TcbObjInfo } from '../../models/models';
import { loadingDiv } from '../../functions/componentFunctions';
import { Grid, GridColumn, GridExpandChangeEvent,  GridDetailRowProps } from '@progress/kendo-react-grid';
import './TcbObjMilestones.css';

type TcbObjMilestonesProps = {
    tcbObj: TcbObjInfo;
    userInf: UserInfo;
}

type TcbObjMilestonesState = {
    milestoneList: TcbObjMilestoneGrp[];
    milestonesFetched: boolean;
    fetchError: boolean;
    fetchErrorMsg: string;
    fetchInProg: boolean;
}

function TcbObjMilestones(props: TcbObjMilestonesProps) { 

    const [state, setState] = useState<TcbObjMilestonesState>({
        milestoneList: [],
        milestonesFetched: false,
        fetchError: false,
        fetchErrorMsg: '',
        fetchInProg: false
    });

    useEffect(() => {

        state.fetchErrorMsg = 'FetchInProg';
        state.fetchInProg = true;
        setState({ ...state});

        let url = props.userInf.currProject.apiUrl + '/api/details/GetTcbObjMilestones';

        fetch(url, { method: 'POST', body: JSON.stringify(props.tcbObj), headers: { 'Content-Type': 'application/json', 'Authorization': 'Bearer ' + props.userInf.token } })
            .then(resp => resp.json())
            .then(res => {
                switch (res.callStatus) {
                    case "OK":
                        let ml: Array<TcbObjMilestoneGrp> = res.results;

                        state.fetchErrorMsg = 'Got MilestoneData '
                        state.milestoneList = ml;
                        state.milestonesFetched = true;
                        state.fetchInProg = false;
                        setState({ ...state });

                        break;
                    case "UNAUTH":
                        let uInf: UserInfo = { ...props.userInf, isAuthorised: false };

                        state.fetchInProg = false;
                        setState({ ...state });
                        break;

                    default:
                        state.fetchInProg = false;
                        state.fetchError = true;
                        state.fetchErrorMsg = res.callStatusMessage;

                        setState({ ...state });

                }
            })
            .catch(err => {
                state.fetchInProg = false;
                state.fetchError = true;
                state.fetchErrorMsg = 'Error fetching Item Details - ' + err.toString();
                setState({ ...state });
            });
    }, []);


  
    const expandGrpChange = (e: GridExpandChangeEvent) => {
        let dr: TcbObjMilestoneGrp = e.dataItem;
        let ml = state.milestoneList;
        let mlg = ml.find(x => x.milestoneId === dr.milestoneId)!;
        mlg.isExpanded = !e.dataItem.isExpanded;
   

        state.fetchErrorMsg = 'Expanded ' + mlg.isExpanded;
        setState({ ...state});

    }

    const renderMilestoneDetails = (e: GridDetailRowProps) => {
        return (<section><p>TEST</p></section>);

    };


     if (state.fetchInProg)
        return loadingDiv();

        let formatStr = "{0:dd-MMM-yyyy HH:mm }";

        return (
            <>
            <p>{state.fetchErrorMsg}</p>
            <Grid
                data={state.milestoneList}
                detail={renderMilestoneDetails}
                expandField="isExpanded"
                onExpandChange={expandGrpChange}
                resizable
            >
                <GridColumn field="milestoneDesc" title="Milestone" className="TcbObjMilestoneGridMainCell" />
                <GridColumn field="latestMilestoneDate" title="Latest" format={formatStr} width="120px" className="TcbObjMilestoneGridCell" />
                <GridColumn field="latestSource" title="Source" width="90px" className="TcbObjMilestoneGridCell" />
            </Grid>
            </>
        );
    }
    
export default TcbObjMilestones;


Michael
Top achievements
Rank 1
Iron
commented on 07 Feb 2024, 06:49 AM

I managed to solve this.

My mistake was to try to save the data as part of the other state variables.

Once I created a separate useState to handle the data array it all worked perfectly.

Cheers

 

Mike

1 Answer, 1 is accepted

Sort by
0
Michael
Top achievements
Rank 1
Iron
answered on 07 Feb 2024, 06:52 AM
Solved by separating data from other state variables.
Tags
Grid
Asked by
Michael
Top achievements
Rank 1
Iron
Answers by
Michael
Top achievements
Rank 1
Iron
Share this question
or