Преобразование функций из чистой реакции в избыточную реакцию - PullRequest
4 голосов
/ 04 октября 2019

В чистом реагировании я написал функцию, которую я вызываю в componentDidMount ():

  getTasks = (userId, query, statusTask, pageNumber) => {
    let check = {};
    axios({
      url: `/api/v1/beta/${userId}`,
      method: 'GET'
    })
      .then(res => {
        check = res.data;

        if (res.data) {
          this.setState({
            checkRunning: res.data,
            checkRunningId: res.data.id
          });
          this.utilizeTimes(res.data.task_id);
        }
      })
      .catch(error => {
        console.log(error);
      })
      .then(() => {
        const params = {
          sort: 'name'
        };

        if (query) {
          params['filter[qwp]'] = query;
          if (this.state.tasks[0]) {
            this.setState({
              selectedId: this.state.tasks[0].id,
              selectedTabId: this.state.tasks[0].id
            });
          }
        }

        axios({
          url: '/api/v1//tasks',
          method: 'GET',
          params
        })
          .then(res => {
            if (res.status === 200 && res.data) {
              this.setState({
                tasks: res.data,
                lengthArrayTasks: parseInt(res.headers['x-pagination-total-count'])
              });

              if (!check && res.data && res.data[0]) {
                this.setState({
                  selectedTabId: res.data[0].id,
                });

                this.load(res.data[0].id);
              }

              let myArrayTasks = [];
              myArrayTasks = res.data;
              let findObject = myArrayTasks.find(task => task.id === this.state.runningTimerTask.id);

              if (
                !findObject &&
                this.state.runningTimerTask &&
                this.state.runningTimerTask.id &&
                this.state.query === ''
              ) {
                this.setState({
                  tasks: [this.state.runningTimerTask, ...myArrayTasks]
                });
              }
            }
          })
          .catch(error => {
            console.log(error);
          });
      });
  };

Я пытаюсь переписать ее для редукции, но с плохими результатами. Сначала он делает один запрос / api / v1 / beta / $ {userId}, записывает ответ в переменную check. check переходит к следующему then. В следующем then выполняет запрос '/ api / v1 // tasks' Может кто-нибудь мне помочь? Я прошу несколько советов. Это как-то сложно?

Пока мне удалось создать что-то вроде этого:

store

import { createStore, applyMiddleware } from 'redux';
import thunk from 'redux-thunk';
import rootReducer from '../reducers';

const store = createStore(rootReducer, applyMiddleware(thunk));

export default store;

actions

export const RUNNING_TIMER = 'RUNNING_TIMER';
export const GET_TASKS = 'GET_TASKS';
export const FETCH_FAILURE = 'FETCH_FAILURE';

export const runningTimer = (userId, query, statusTask, pageNumber) => dispatch => {
  console.log(userId);
  axios({
    url: `/api/v1/beta/${userId}`,
    method: 'GET'
  })
    .then(({ data }) => {
      dispatch({
        type: RUNNING_TIMER,
        payload: data
      });
    })
    .catch(error => {
      console.log(error);

      dispatch({ type: FETCH_FAILURE });
    })
    .then(() => {
      const params = {
        sort: 'name'
      };

      axios({
        url: '/api/v1//tasks',
        method: 'GET',
        params
      })
        .then(({ data }) => {
            dispatch({
                type: GET_TASKS,
                payload: data
            });
        })
        .catch(error => {
            console.log(error);
        });
    });
};

редуктор

import { RUNNING_TIMER, GET_TASKS } from '../actions';

const isRunningTimer = (state = {}, action) => {
  const { type, payload } = action;
  switch (type) {
    case RUNNING_TIMER:
      return {
        checkRunningTimer: payload,
        checkRunningTimerId: payload && payload.id ? payload.id : null
      };
      break;
      case GET_TASKS:
      return {
        tasks: payload,
        lengthArrayTasks: parseInt(action.headers['x-pagination-total-count'])
      };
    default:
      return state;
  }
};

const rootReducer = combineReducers({ isRunningTimer });

export default rootReducer;

Приложение

class App extends Component {
  constructor() {
    super();
    this.state = {
      name: 'React'
    };
  }

  componentDidMount() {
    this.props.runningTimer();
  }

  render() {
    return (
      <div>

      </div>
    );
  }
}

const mapStateToProps = state => {
  const { isRunningTimer } = state;

  return {
    isRunningTimer
  };
};

const mapDispatchToProps = dispatch => ({
  runningTimer: (userId, query, statusTask, pageNumber) => dispatch(runningTimer()),
});

export default connect(
  mapStateToProps,
  mapDispatchToProps
)(App);

Ответы [ 3 ]

6 голосов
/ 06 октября 2019

Number 1 Рассмотрим дизайн вашего состояния.

Я считаю полезным рассмотреть, как будет выглядеть объект состояния в данный момент времени.

Вот пример initialState, используемого в моем приложении.

const initialState = {
        grocers: null,
        coords: {
            latitude: 37.785,
            longitude: -122.406
        }

    };

Это внедряется в createStore.

Разбиение объекта / свойств состояния приложения,также поможет вам упростить ваши действия.

Номер 2

Подумайте о том, чтобы разбить ваши действия.

Мои мысли, отделите код действия, на.then во втором .then. (Рассмотрите возможность сохранения результатов где-нибудь в user: object)

        .then(response => {
          const data = response.data.user;
          setUsers(data);})
        .catch(error => {
            console.log('There has been a problem with your fetch operation: ' + error.message);
        })

    function setUsers(data){
        dispatch({
            type: FETCH_USERS,
            payload: data
        });
    }

Это относится к S в принципах проектирования SOLID. Принцип одиночной ответственности.

https://devopedia.org/solid-design-principles

Number 3

Учтите это, если получение информации getUser не удастся.

Разделение процесса и ответа позволит более четко отлаживать приложение. Например, произошел сбой пользовательского API или API-интерфейса getTask и т. Д.


Больше ресурсов на приставке. https://redux.js.org/introduction/learning-resources#thinking-in-redux

3 голосов
/ 09 октября 2019

Расширяя предыдущий ответ от @Cullen, это то, что я сделал:

  1. Поскольку у вас уже есть действие для GET_TODOS, просто сделайте создателя действий для runningTimer, чтобы выполнить одно и только одно- сделать вызов API на /api/v1/beta/<userId> и отправить соответствующие действия.
export const runningTimer = (
  userId,
  query,
  statusTask,
  pageNumber
) => dispatch => {
  return axios({
    url: `/api/v1/beta/${userId}`,
    method: "GET"
  })
    .then(({ data }) => {
      dispatch({
        type: RUNNING_TIMER,
        payload: data
      });
    })
    .catch(error => {
      console.log(error);

      dispatch({ type: FETCH_FAILURE });
    });
};

Обновление реквизитов компонента приложения для чтения данных магазина.
...
const mapStateToProps = state => {
  const { isRunningTimer, todos, todo } = state;

  return {
    todos,
    todo,
    isRunningTimer,
  };
};

const mapDispatchToProps = dispatch => ({
  getTodos: () => dispatch(getTodos()),
  getTodo: id => dispatch(getTodo(id)),
  runningTimer: (userId, query, statusTask, pageNumber) => dispatch(runningTimer(userId)),
});
...
Обновление реализации componentDidMount для отправки isRunningTimer -
componentDidMount() {
...
    // call with userId 1
    this.props.runningTimer(1).then(() => {
      console.log(this.props);

          // additional params for getTasks
      const params = {
        sort: 'name'
      };

      // another call for getTodos with names sorted
      this.props.getTodos(params);
    });
...

Примечание. Вам необходимо обновить действие getTodos, чтобы выполнить необязательное paramsАргументы (которые инициализируются пустым объектом, если не переданы).

Надеюсь, это вам поможет.

Живая песочница для этого присутствует здесь - https://stackblitz.com/edit/react-redux-more-actions

0 голосов
/ 07 октября 2019

Оформить Реактор-образец . Отличный шаблон для реакции и редукции. Они также используют redux-saga и redux-hooks.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...