PHPFixing
  • Privacy Policy
  • TOS
  • Ask Question
  • Contact Us
  • Home
  • PHP
  • Programming
  • SQL Injection
  • Web3.0

Friday, October 14, 2022

[FIXED] How to refresh the list after delete in Next.js to-do app

 October 14, 2022     axios, next.js, typescript     No comments   

Issue

I'm making a simple to-do app using Next.js + TypeScript + Axios and trying to get the delete button to work.
My delete button deletes the selected task as expected, but I want it to also refresh my tasks list so that I can see the updated list.

Any suggestions would be appreciated. Thanks in advance!

// pages/index.tsx

import DeleteIcon from "@mui/icons-material/Delete";
import EditIcon from "@mui/icons-material/Edit";
import FactCheckIcon from "@mui/icons-material/FactCheck";
import {
  List,
  ListItem,
  ListItemAvatar,
  Avatar,
  ListItemText,
  Container,
  Typography,
  IconButton,
  Stack,
} from "@mui/material";

import { deleteTask } from "../modules/apiClient/tasks/deleteTask";
import { useFetchTasks } from "../modules/hooks/useFetchTasks";

interface OperationButtonProps {
  taskId: number;
}

const OperationButtons: React.VFC<OperationButtonProps> = (props) => {
  const handleDelete = async () => {
    try {
      await deleteTask(props.taskId); // calls the API and deletes the task fine
      // I have to do something here or somewhere to refresh the tasks list but can't figure out how.
    } catch (e) {
      console.log(e);
    }
  };

  return (
    <Stack direction="row">
      <IconButton aria-label="edit">
        <EditIcon />
      </IconButton>
      <IconButton edge="end" aria-label="delete" onClick={handleDelete}>
        <DeleteIcon />
      </IconButton>
    </Stack>
  );
};

const IndexPage = () => {
  const { tasks } = useFetchTasks();

  return (
    <>
      <Typography variant="h3" align="center" marginTop={3}>
        TODO LIST
      </Typography>
      {tasks && (
        <Container maxWidth="sm">
          <List sx={{ width: "100%" }}>
            {tasks.tasks.map((task) => (
              <ListItem
                key={task.id}
                secondaryAction={<OperationButtons taskId={task.id} />}
              >
                <ListItemAvatar>
                  <Avatar>
                    <FactCheckIcon />
                  </Avatar>
                </ListItemAvatar>
                <ListItemText
                  primary={task.description}
                  secondary={task.created_at}
                />
              </ListItem>
            ))}
          </List>
        </Container>
      )}
    </>
  );
};

export default IndexPage;
// modules/hooks/useFetchTasks.ts

import { useState, useEffect, useCallback } from "react";

import { getTasks, TasksResponse } from "../apiClient/tasks/getTasks";

export const useFetchTasks = () => {
  const [tasks, setTasks] = useState<TasksResponse | null>(null);

  const fetchTasks = useCallback(async () => {
    try {
      const { data } = await getTasks();
      setTasks(data);
    } catch (e) {
      console.log(e);
    }
  }, []);

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

  return {
    tasks,
    fetchTasks,
  };
};

Solution

You can return setTasks your useFetchTasks and pass it to your button, so you can update your list after called API

const OperationButtons: React.VFC<OperationButtonProps> = (props) => {
    const handleDelete = async () => {
        try {
            await deleteTask(props.taskId);
            props.setTasks(prevTasks => prevTasks.tasks.filter(task => task.id !== props.taskId))
        } catch (e) {
            console.log(e);
        }
    };

    return (
        <Stack direction="row">
            <IconButton aria-label="edit">
                <EditIcon />
            </IconButton>
            <IconButton edge="end" aria-label="delete" onClick={handleDelete}>
                <DeleteIcon />
            </IconButton>
        </Stack>
    );
};

const IndexPage = () => {
    const { tasks, setTasks } = useFetchTasks();

    return (
        <>
            <Typography variant="h3" align="center" marginTop={3}>
                TODO LIST
            </Typography>
            {tasks && (
                <Container maxWidth="sm">
                    <List sx={{ width: '100%' }}>
                        {tasks.tasks.map((task) => (
                            <ListItem
                                key={task.id}
                                secondaryAction={<OperationButtons taskId={task.id} setTasks={setTasks} />}
                            >
                                <ListItemAvatar>
                                    <Avatar>
                                        <FactCheckIcon />
                                    </Avatar>
                                </ListItemAvatar>
                                <ListItemText
                                    primary={task.description}
                                    secondary={task.created_at}
                                />
                            </ListItem>
                        ))}
                    </List>
                </Container>
            )}
        </>
    );
};

export const useFetchTasks = () => {
    const [tasks, setTasks] = (useState < TasksResponse) | (null > null);

    const fetchTasks = useCallback(async () => {
        try {
            const { data } = await getTasks();
            setTasks(data);
        } catch (e) {
            console.log(e);
        }
    }, []);

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

    return {
        tasks,
        fetchTasks,
        setTasks
    };
};

export default IndexPage;


Answered By - iamhuynq
Answer Checked By - Robin (PHPFixing Admin)
  • Share This:  
  •  Facebook
  •  Twitter
  •  Stumble
  •  Digg
Newer Post Older Post Home

0 Comments:

Post a Comment

Note: Only a member of this blog may post a comment.

Total Pageviews

Featured Post

Why Learn PHP Programming

Why Learn PHP Programming A widely-used open source scripting language PHP is one of the most popular programming languages in the world. It...

Subscribe To

Posts
Atom
Posts
Comments
Atom
Comments

Copyright © PHPFixing