Проблема с использованием истории в React - PullRequest
0 голосов
/ 02 августа 2020

Я делаю приложение, которое включает чаты, и в каждом чате пользователь, являющийся частью этого чата, может создавать сообщения. Я использую стек MERN и redux, и у меня есть компонент PostForm, в котором пользователи могут публиковать сообщения. У меня также есть действие addPost для redux. После того, как кто-то добавляет сообщение в чат, я хочу перенаправить его в свой профиль, используя историю. Однако по какой-то причине у меня это не работает. Я прикрепил свой файл PostForm, а также свое действие addPost и свое сообщение. js reducer (который является соответствующим редуктором). Если кто-то может найти проблему, почему он не перенаправляется на страницу профиля, я был бы очень признателен. Спасибо!

PostForm. js:

    import React, { useState } from 'react';
    import PropTypes from 'prop-types';
    import { connect } from 'react-redux';
    import { addPost } from '../../actions/chat';
    
    const PostForm = ({ addPost, match, history }) => {
      const [formData, setFormData] = useState({
        title: '',
        text: ''
      });
    
      const {
        title,
        text
      } = formData;
    
      const onChange = e => setFormData({ ...formData, [e.target.name]: e.target.value });
    
      const onSubmit = e => {
        e.preventDefault();
        addPost(match.params.id, { title, text }, history);
        console.log(formData);
        setFormData({
          [title]: '',
          [text]: ''
        })
    
      }
      return (
        <div>
          <div className="post-form">
            <div className="post-form-header bg-primary">
              <h3>Create a Post</h3>
            </div>
            <form className="form my-1" onSubmit={e => onSubmit(e)}
            >
              <textarea
                name='title'
                cols="30"
                rows="2"
                placeholder="Create post title"
                value={title}
                onChange={e => onChange(e)}
              />
              <textarea
                cols="30"
                rows="5" placeholder="Create a post"
                name='text'
                value={text}
                onChange={e => onChange(e)}
              />
              <input type="submit" value="Submit" class="btn btn-dark my-1" />
            </form>
          </div>
        </div>
      )
    }
    
    PostForm.propTypes = {
      addPost: PropTypes.func.isRequired
    }
    
    export default connect(null, { addPost })(PostForm);



chat.js actions file

import axios from 'axios';
import { setAlert } from './alert';
import {
  CREATE_SUCCESS,
  CREATE_FAIL,
  GET_PROFILE,
  PROFILE_ERROR,
  USER_LOADED,
  AUTH_ERROR,
  JOIN_SUCCESS,
  JOIN_FAIL,
  ADD_POST
} from './types';
import setAuthToken from '../utils/setAuthToken';

// Add post
export const addPost = (chatId, formData, history) => async dispatch => {
  const config = {
    headers: {
      'Content-Type': 'application/json'
    }
  }

  //const body = JSON.stringify({ title, text });

  try {
    const res = await axios.post(`/api/chats/${chatId}`, formData, config);
    dispatch({
      type: ADD_POST,
      payload: res.data
    });

    dispatch(setAlert('Post Created', 'success'));

    history.push('/profile');
  } catch (err) {
    const errors = err.response.data.errors;

    if (errors) {
      errors.forEach(error => dispatch(setAlert(error.msg, 'danger')));
    }

    
  }
}

чат. js редуктор

import {
  JOIN_SUCCESS,
  JOIN_FAIL,
  ADD_POST
} from '../actions/types';

const initialState = {

  token: localStorage.getItem('token'),
  //isAuthenticated: null,
  isCompleted: null,
  loading: true,
  user: null,
  error: {}
}

export default function (state = initialState, action) {
  const { type, payload } = action;

  switch (type) {
    case JOIN_SUCCESS:
      return {
        ...state,
        ...payload,
        isCompleted: true,
        loading: false
      };
    case JOIN_FAIL:
      return {
        ...state,
        error: payload,
        loading: false
      };
    default:
      return state;
  }
}

Приложение. js

 import React, { Fragment, useEffect } from 'react';
import { BrowserRouter as Router, Route, Switch } from 'react-router-dom';
import Navbar from './components/layout/Navbar';
import Landing from './components/layout/Landing';
import Login from './components/auth/Login';
import Register from './components/auth/Register';
import Alert from './components/layout/Alert';
// Redux
import { Provider } from 'react-redux';
import store from './store';
import { loadUser } from './actions/auth';
import setAuthToken from './utils/setAuthToken';
import Profile from './components/profile/Profile';
import PrivateRoute from './components/routing/PrivateRoute';
import CreateChat from './components/chat-form/CreateChat';
import JoinChat from './components/chat-form/JoinChat';
import Chat from './components/profile/Chat';
import PostForm from './components/profile/PostForm';

import './App.css';

if (localStorage.token) {
  setAuthToken(localStorage.token);
}

const App = () => {
  useEffect(() => {
    store.dispatch(loadUser());
  }, []);

  return (
    <Provider store={store}>
      <Router>
        <Fragment>
          <Navbar />
          <Route exact path="/" component={Landing} />
          <section className="container">
            <Alert />
            <Switch>
              <Route exact path="/register" component={Register} />
              <Route exact path="/login" component={Login} />
              <PrivateRoute exact path='/profile' component={Profile} />
              <PrivateRoute exact path='/create-chat' component={CreateChat} />
              <PrivateRoute exact path='/join-chat' component={JoinChat} />
              <PrivateRoute exact path='/chat/:id' component={Chat} />
              <PrivateRoute exact path='/post-form/:id' component={PostForm} />
            </Switch>
          </section>
        </Fragment>
      </Router>
    </Provider>
  )
};

export default App;
...