Reducer 返回未定义(Redux-Thunk 和 Promise)
Reducer returned undefined (Redux-Thunk and Promise)
我已经在网上搜索了几个小时来寻找这个问题的解决方案。我找到了一些相关问题的提示和解决方案,但不是这个问题。也许我的商店配置有误,或者我定义的 reducer 动作不正确。
我的问题是,我的 reducer returns 在向 API 发送 post 请求时未定义。
这是文件。如果有文件丢失,请反馈给我,我会第一时间更新post。
我可以毫无问题地使用 fetchEntry 获取条目,我可以使用 deleteEntry 删除条目,更新条目的 post 请求将成功发送到 API 并且条目得到更新,但是 reducer 不知何故不会被告知这个成功的操作并且 returns undefined...
// redux/actions/entry.js
import axios from 'axios';
export const FETCH_ENTRY = 'fetch_entry';
export const CREATE_ENTRY = 'create_entry';
export const UPDATE_ENTRY = 'update_entry';
export const DELETE_ENTRY = 'delete_entry';
export const ERROR_ENTRY = 'error_entry';
const ROOT_URL = 'http://localhost:8080/api';
// **This is the important part here**
export function updateEntry(type, data, callback) {
return async (dispatch) => {
try {
const request = axios.post(
`${ROOT_URL}/${type}/edit/${data.id}`,
data.formData
).then(() => callback());
dispatch({ type: UPDATE_ENTRY, payload: request });
} catch(error) {
console.log(error);
}
}
}
// Not defined, tbd
export function createEntry(type, data, history) {
}
// **Everything else is working fine**
export function fetchEntry(type, id, history) {
return async (dispatch) => {
try {
const request = await
axios.get(`${ROOT_URL}/${type}/get/${id}`);
dispatch({ type: FETCH_ENTRY, payload: request });
} catch(error) {
history.push('/');
}
};
}
export function deleteEntry(type, id, callback) {
return async (dispatch) => {
try {
const request =
axios.delete(`${ROOT_URL}/${type}/delete/${id}`)
.then(() => callback());
dispatch({ type: DELETE_ENTRY, payload: request });
} catch(error) {
console.log(error);
}
}
}
我的reducer定义如下:
// redux/recuders/reducer_entry.js
import { CREATE_ENTRY, FETCH_ENTRY, DELETE_ENTRY, UPDATE_ENTRY } from
'../actions/entry';
export default function(state = {}, action) {
switch (action.type) {
case CREATE_ENTRY:
return action.payload.data;
case DELETE_ENTRY:
return action.type;
case FETCH_ENTRY:
return action.payload.data;
case UPDATE_ENTRY:
console.log(action);
return action.payload.data;
default:
return state;
}
}
发送触发发送post请求的"calling"点:
// EditEntry.js
this.props.updateEntry('type', data, () => {
console.log("Successfully saved!");
console.log(this.props);
});
我的店铺是这样定义的...
// store.js
import { compose, createStore, applyMiddleware } from 'redux';
import { createBrowserHistory } from 'history';
import { syncHistoryWithStore } from 'react-router-redux';
import { createLogger } from 'redux-logger';
import thunk from 'redux-thunk';
import rootReducer from './redux/reducers';
const middleware = [
createLogger(),
thunk
];
const enhancers = compose(
applyMiddleware(...middleware),
window.devToolsExtension ? window.devToolsExtension() : f => f
)
// Create store
const store = createStore(
rootReducer,
{},
enhancers
);
export const history = syncHistoryWithStore(createBrowserHistory(),
store);
const createStoreWithMiddleware = applyMiddleware(thunk)(createStore);
export { createStoreWithMiddleware };
然后像这样给App..
// index.js
import React from 'react';
import ReactDOM from 'react-dom';
import { Provider } from 'react-redux';
import Routes from './Routes';
import registerServiceWorker from './registerServiceWorker';
import reducers from './redux/reducers';
import { createStoreWithMiddleware } from './store';
const store = createStoreWithMiddleware(reducers);
ReactDOM.render(
<Provider store={store}>
<Routes />
</Provider>,
document.getElementById('root')
);
registerServiceWorker();
最后,reducers/index.js(调用 combineReducers 的地方):
// redux/reducers/index.js
import { combineReducers } from 'redux';
import { routerReducer } from 'react-router-redux';
import EntryReducer from './reducer_entry';
import { reducer as FormReducer } from 'redux-form';
const rootReducer = combineReducers({
routing: routerReducer,
entry: EntryReducer,
form: FormReducer
});
export default rootReducer;
也许你们中有人可以帮忙解决这个问题?
你没有从then
块
返回这里的任何东西
// **This is the important part here**
export function updateEntry(type, data, callback) {
return async (dispatch) => {
try {
const request = axios.post(
`${ROOT_URL}/${type}/edit/${data.id}`,
data.formData
).then(() => callback());
dispatch({ type: UPDATE_ENTRY, payload: request });
} catch(error) {
console.log(error);
}
}
}
好的。非常感谢@SALEH:现在知道了!
这是解决方案:)
export function updateEntry(type, data, callback) {
return async (dispatch) => {
try {
await axios.post(`${ROOT_URL}/${type}/edit/${data.anlageID}`, data.formData)
.then((response) => {
dispatch({ type: UPDATE_ENTRY, payload: response });
callback()
});
} catch(error) {
console.log(error);
}
}
}
我已经在网上搜索了几个小时来寻找这个问题的解决方案。我找到了一些相关问题的提示和解决方案,但不是这个问题。也许我的商店配置有误,或者我定义的 reducer 动作不正确。
我的问题是,我的 reducer returns 在向 API 发送 post 请求时未定义。
这是文件。如果有文件丢失,请反馈给我,我会第一时间更新post。
我可以毫无问题地使用 fetchEntry 获取条目,我可以使用 deleteEntry 删除条目,更新条目的 post 请求将成功发送到 API 并且条目得到更新,但是 reducer 不知何故不会被告知这个成功的操作并且 returns undefined...
// redux/actions/entry.js
import axios from 'axios';
export const FETCH_ENTRY = 'fetch_entry';
export const CREATE_ENTRY = 'create_entry';
export const UPDATE_ENTRY = 'update_entry';
export const DELETE_ENTRY = 'delete_entry';
export const ERROR_ENTRY = 'error_entry';
const ROOT_URL = 'http://localhost:8080/api';
// **This is the important part here**
export function updateEntry(type, data, callback) {
return async (dispatch) => {
try {
const request = axios.post(
`${ROOT_URL}/${type}/edit/${data.id}`,
data.formData
).then(() => callback());
dispatch({ type: UPDATE_ENTRY, payload: request });
} catch(error) {
console.log(error);
}
}
}
// Not defined, tbd
export function createEntry(type, data, history) {
}
// **Everything else is working fine**
export function fetchEntry(type, id, history) {
return async (dispatch) => {
try {
const request = await
axios.get(`${ROOT_URL}/${type}/get/${id}`);
dispatch({ type: FETCH_ENTRY, payload: request });
} catch(error) {
history.push('/');
}
};
}
export function deleteEntry(type, id, callback) {
return async (dispatch) => {
try {
const request =
axios.delete(`${ROOT_URL}/${type}/delete/${id}`)
.then(() => callback());
dispatch({ type: DELETE_ENTRY, payload: request });
} catch(error) {
console.log(error);
}
}
}
我的reducer定义如下:
// redux/recuders/reducer_entry.js
import { CREATE_ENTRY, FETCH_ENTRY, DELETE_ENTRY, UPDATE_ENTRY } from
'../actions/entry';
export default function(state = {}, action) {
switch (action.type) {
case CREATE_ENTRY:
return action.payload.data;
case DELETE_ENTRY:
return action.type;
case FETCH_ENTRY:
return action.payload.data;
case UPDATE_ENTRY:
console.log(action);
return action.payload.data;
default:
return state;
}
}
发送触发发送post请求的"calling"点:
// EditEntry.js
this.props.updateEntry('type', data, () => {
console.log("Successfully saved!");
console.log(this.props);
});
我的店铺是这样定义的...
// store.js
import { compose, createStore, applyMiddleware } from 'redux';
import { createBrowserHistory } from 'history';
import { syncHistoryWithStore } from 'react-router-redux';
import { createLogger } from 'redux-logger';
import thunk from 'redux-thunk';
import rootReducer from './redux/reducers';
const middleware = [
createLogger(),
thunk
];
const enhancers = compose(
applyMiddleware(...middleware),
window.devToolsExtension ? window.devToolsExtension() : f => f
)
// Create store
const store = createStore(
rootReducer,
{},
enhancers
);
export const history = syncHistoryWithStore(createBrowserHistory(),
store);
const createStoreWithMiddleware = applyMiddleware(thunk)(createStore);
export { createStoreWithMiddleware };
然后像这样给App..
// index.js
import React from 'react';
import ReactDOM from 'react-dom';
import { Provider } from 'react-redux';
import Routes from './Routes';
import registerServiceWorker from './registerServiceWorker';
import reducers from './redux/reducers';
import { createStoreWithMiddleware } from './store';
const store = createStoreWithMiddleware(reducers);
ReactDOM.render(
<Provider store={store}>
<Routes />
</Provider>,
document.getElementById('root')
);
registerServiceWorker();
最后,reducers/index.js(调用 combineReducers 的地方):
// redux/reducers/index.js
import { combineReducers } from 'redux';
import { routerReducer } from 'react-router-redux';
import EntryReducer from './reducer_entry';
import { reducer as FormReducer } from 'redux-form';
const rootReducer = combineReducers({
routing: routerReducer,
entry: EntryReducer,
form: FormReducer
});
export default rootReducer;
也许你们中有人可以帮忙解决这个问题?
你没有从then
块
// **This is the important part here**
export function updateEntry(type, data, callback) {
return async (dispatch) => {
try {
const request = axios.post(
`${ROOT_URL}/${type}/edit/${data.id}`,
data.formData
).then(() => callback());
dispatch({ type: UPDATE_ENTRY, payload: request });
} catch(error) {
console.log(error);
}
}
}
好的。非常感谢@SALEH:现在知道了!
这是解决方案:)
export function updateEntry(type, data, callback) {
return async (dispatch) => {
try {
await axios.post(`${ROOT_URL}/${type}/edit/${data.anlageID}`, data.formData)
.then((response) => {
dispatch({ type: UPDATE_ENTRY, payload: response });
callback()
});
} catch(error) {
console.log(error);
}
}
}