Мерн, удаление вопроса с комментариями - PullRequest
0 голосов
/ 21 января 2020

Не могу удалить комментарии внутри одного поста. Я не знаю, что вызывает это, но, видимо, я получил 404 Ошибка, я не знаю, почему пост не был найден, если честно. Я хотел бы получить помощь и посмотреть, что вызывает это и почему я получаю эту ошибку, и почему я не могу удалить комментарий из сообщения. Ниже я опубликую некоторые из моих бэк-эндов, а также мой код переднего плана, но я также обязательно свяжусь с моим Github ниже. Я боролся с этим в течение почти 3 дней, я не вижу, что именно вызывает ошибку, и я хотел бы помочь. Еще одна вещь, о которой стоит упомянуть, это то, что я довольно новичок в MERN, поэтому, пожалуйста, взгляните также на мой код на Github и предложите изменения или вещи, которые я мог бы сделать лучше, это бы очень много значило для меня. Ниже приведен код и ссылка на мой репозиторий Github для этого специфика c проекта

https://github.com/tigerabrodi/ELance

Маршрут удаления Комментарий из поста


// @route    DELETE api/posts/comment/:commentId 
// @desc     Delete comment
// @access   Private
router.delete("/comment/:commentId", auth, async (req, res) => {
  try {
    const comment = await Comment.findById(req.params.commentId);

    if (!comment) {
      return res.status(404).json({ msg: "Comment do not exist" });
    }

    if (comment.user.toString() !== req.user.id) {
      return res.status(401).json({ msg: "User not authorized" });
    }

    await comment.remove();

    res.json({msg: "Comment Removed"})
  } catch (err) {
    console.error(err.message);
    res.status(500).send("Server Error");
  }
});

module.exports = router;

Пост. js

import React, { Fragment, useEffect } from 'react';
import { Link } from 'react-router-dom';
import { connect } from 'react-redux';
import Spinner from '../layout/Spinner';
import PostItem from '../posts/PostItem';
import CommentForm from '../post/CommentForm';
import CommentItem from '../post/CommentItem';
import { getPost } from '../../redux/post/post.actions';
import {getSinglePostComments} from "../../redux/comment/comment.actions"

const Post = ({ getPost, getSinglePostComments, post: { post, loading }, comment, match }) => {
  useEffect(() => {
    getPost(match.params.id);
    getSinglePostComments(match.params.id)
  }, [comment.comments]);

  return loading || comment.loading || post === null ? (
    <Spinner />
  ) : (
    <Fragment>
      <Link to='/posts' className='btn btn-info m-3'>
        Back To Posts
      </Link>
      <PostItem post={post} showActions={false} />
      <CommentForm postId={post._id} />
      <div className='comments'>
        {comment.comments.map(comment => (
          <CommentItem key={comment._id} comment={comment} />
        ))}
      </div>
    </Fragment>
  );
};

const mapStateToProps = state => ({
  post: state.post,
  comment: state.comment
});

export default connect(
  mapStateToProps,
  { getPost, getSinglePostComments }
)(Post);

CommentItem. js

import React from 'react';
import { Link } from 'react-router-dom';
import { connect } from 'react-redux';
import Moment from 'react-moment';
import {deleteComment} from '../../redux/comment/comment.actions';
import defaultUserImage from "../../assets/default-user-icon.jpg"

const CommentItem = ({
  comment: { _id, text, user, date },
  auth,
  deleteComment
}) => (

    <div class="card m-5 bg-warning">
  <div class="row no-gutters align-items-center">
    <div class="col-md-2">
    <Link to={`/profile/${user._id}`}>
            <img className='card-img rounded-circle pl-2' src={user.avatar ? user.avatar : defaultUserImage} alt='' />
            </Link>
    </div>
    <div class="col-md-10">
      <div class="card-body">
        <h5 class="card-title text-center">{user.name}</h5>
        <p class="card-text">{text}</p>
        <p class="card-text"><small class="text-muted">Posted on <Moment format='YYYY/MM/DD'>{date}</Moment>
</small></p>
      {!auth.loading && user._id === auth.user._id && (
        <button
          onClick={() => deleteComment(_id)}
          type='button'
          className='btn btn-danger float-right mb-4'
        >
          <i className='fas fa-times' />
        </button>
      )}
      </div>
    </div>
  </div>
</div>
);

const mapStateToProps = state => ({
  auth: state.auth
});

export default connect(
  mapStateToProps,
  { deleteComment }
)(CommentItem);

CommentForm. js

import React, { useState } from 'react';
import { connect } from 'react-redux';
import { addComment } from '../../redux/comment/comment.actions';

const CommentForm = ({ postId, addComment }) => {
  const [text, setText] = useState('');

  return (
    <div className='container'>
        <div className="row">
        <div className="col text-center">
         <div>
        <h4>Leave a Comment</h4>
      </div>
      <form
        className='form my-1 d-flex flex-row align-items-center justify-content-center'
        onSubmit={e => {
          e.preventDefault();
          addComment(postId, { text });
          setText('');
        }}
      >
        <textarea
          name='text'
          className="form-control bg-info text-light"
          placeholder='Comment the post'
          value={text}
          onChange={e => setText(e.target.value)}
          required
        />
        <input type='submit' className='btn btn-outline-info ml-3' value='Submit' />
      </form>
    </div>
        </div>
        </div>

  );
};

export default connect(
  null,
  { addComment }
)(CommentForm);

comment.actions. js

import axios from "axios";
import {setAlert} from "../alert/alert.actions"
import {CommentActionTypes} from "./comment.types"


// Get Comments For a Single Post
export const getSinglePostComments = id => async dispatch => {
  try {
    const res = await axios.get(`/api/posts/comments/${id}`);

    dispatch({
      type: CommentActionTypes.GET_SINGLE_POST_COMMENTS,
      payload: res.data
    });
  } catch (err) {
    dispatch({
      type: CommentActionTypes.COMMENT_ERROR,
      payload: { msg: err.response.statusText, status: err.response.status }
    });
  }
};



  // Add Comment
  export const addComment = (postId, formData) => async dispatch => {
    const config = {
      headers: {
        'Content-Type': 'application/json'
      }
    };

    try {
        const res = await axios.post(`/api/posts/comment/${postId}`, formData, config);

        dispatch({
          type: CommentActionTypes.ADD_COMMENT,
          payload: res.data
        });
      } catch (err) {
        dispatch({
          type: CommentActionTypes.COMMENT_ERROR,
          payload: { msg: err.response.statusText, status: err.response.status }
        });
      }
  }

 // Delete comment
export const deleteComment = (commentId) => async dispatch => {
  try {
    await axios.delete(`api/posts/comment/${commentId}`);

    dispatch({
      type: CommentActionTypes.DELETE_COMMENT,
      payload: commentId
    });

    dispatch(setAlert('Comment Removed', 'success'));
  } catch (err) {
    dispatch({
      type: CommentActionTypes.COMMENT_ERROR,
      payload: { msg: err.response.statusText, status: err.response.status }
    });
  }
};  

comment.reducer. js

import {CommentActionTypes} from "./comment.types";



const initialState = {
    comments: [],
    loading: true,
    error: {}
}

const commentReducer = (state = initialState, action) => {
    const {payload, type} = action;
    switch (type) {
            case CommentActionTypes.GET_SINGLE_POST_COMMENTS:
                return {
                    ...state,
                    comments: payload,
                    loading: false
                }
            case CommentActionTypes.ADD_COMMENT:
                return {
                    ...state,
                    comments: [payload, ...state.comments],
                    loading: false
                }
            case CommentActionTypes.DELETE_COMMENT:
                return {
                    ...state,
                    comments: state.comments.filter(comment => comment._id !== payload),
                    loading: false
                }
            case CommentActionTypes.COMMENT_ERROR:
                return {
                    ...state,
                    error: payload,
                    loading: false
                }
        default:
            return state;
    }
}

export default commentReducer

comment.types. js

export const CommentActionTypes = {
    DELETE_COMMENT: "DELETE_COMMENT",
    ADD_COMMENT: "ADD_COMMENT",
    COMMENT_ERROR: "COMMENT_ERROR",
    GET_SINGLE_POST_COMMENTS: "GET_SINGLE_POST_COMMENTS"
}

1 Ответ

1 голос
/ 22 января 2020

В comment.actions. js метод deleteComment, вам нужно добавить sla sh в начало URL удаления:

    await axios.delete(`/api/posts/comment/${commentId}`);
...