我正在学习 React Native with Redux,无法弄清楚如何从我的组件中访问商店/actionCreators。 我觉得我已经尝试了十种左右的代码变体,观看了Dan Abramov的大部分Egghead视频(多次),但仍然不明白我做错了什么。我认为到目前为止我看到的最好的解释是这里公认的答案:Redux,如果我想访问数据,我是否必须在所有容器中导入存储?
我得到的错误是:undefined不是一个对象(评估'state.clinic.drName')。 以下是相关的代码位:
我正在通过提供商传递商店(所以我认为):
index.ios.js
import clinicReducer from './reducers/clinic';
import { createStore, combineReducers } from 'redux';
import { Provider } from 'react-redux';
const rootReducer = combineReducers({
clinic : clinicReducer
});
let store = createStore(combineReducers({clinicReducer}));
//testing - log every action out
let unsubscribe = store.subscribe( () =>
console.log(store.getState())
);
class ReactShoeApp extends React.Component {
render() {
return (
<Provider store={store}>
<ReactNative.NavigatorIOS
style={styles.container}
initialRoute={{
title: 'React Shoe App',
component: Index
}}/>
</Provider>
);
}
}
这是我的动作创造者:
export const CLINIC_DR_NAME_UPDATE = 'CLINIC_DR_NAME_UPDATE_UPDATE';
export function updateClinicDrName(newValue) {
return {type: CLINIC_DR_NAME_UPDATE, value: newValue};
}
这是我的减速器:
import {
CLINIC_DR_NAME_UPDATE
} from '../actions/';
let cloneObject = function(obj) {
return JSON.parse(JSON.stringify(obj));
};
const initialState = {
drName : null
};
export default function clinicReducer(state = initialState, action) {
switch (action.type) {
case CLINIC_DR_NAME_UPDATE:
return {
...state,
drName: action.value
};
default:
return state || newState;
}
}
这是我的组件:
import { bindActionCreators } from 'redux';
import { connect } from 'react-redux';
import * as Actions from '../actions';
const mapStateToProps = function(state){
return {
drName: state.clinic.drName,
}
};
const mapDispatchToProps = function (dispatch) {
return bindActionCreators({
updateClinicDrName: Actions.updateClinicDrName,
}, dispatch)
};
//class definition
class Clinic extends React.Component {
constructor(props) {
super(props);
}
render() {
return (
<View style={styles.rowContainer}>
<View style={styles.row}>
<TextGroup label={'Dr. Name'} placeholder={'placeholder'} value={this.props.drName} onChangeText={(text) => this.handlers.onNameChange({text})}></TextGroup>
<TextGroup label={'City'} placeholder={'placeholder'}></TextGroup>
</View>
</View>
);
}
}
export default connect(mapStateToProps, mapDispatchToProps)(Clinic);
我要做的就是在用户输入博士姓名文本组时更新存储(clinic.drName)。 感谢任何和所有的帮助。
问题是您调用combineReducers()
的方式与您期望的切片名称不匹配。 这是一个常见的错误。 您正在使用键clinicReducer
定义一个对象,但期望数据位于名为 clinic
的键处。
有关该问题的说明,请参阅定义状态形状。
此外,您的clinicReducer()
函数看起来很奇怪,并且存在以下几个问题:
- 不要像使用
newState
那样访问函数外部的变量。 - 不要像那样进行深度克隆(根据 Redux 常见问题解答:性能)。 相反,如有必要,请使用"浅层克隆"来更新状态(请参阅不可变更新模式中的示例)。
- 看起来化简器也在双重嵌套它试图访问的数据。
我认为你想要更多的东西:
// clinicReducer.js
const initialState = {
drName : null
};
export default function clinicReducer(state = initialState, action) {
switch(action.type) {
case CLINIC_DR_NAME_UPDATE: {
return {
...state,
drName : actino.value
};
}
default: return state
}
}
// index.js
import clinicReducer from "./reducers/clinic";
const rootReducer = combineReducers({
clinic : clinicReducer
});
你得到什么错误?我看到你所拥有的两个问题。
-
newState.clinic.drName = action.value;
应该抛出一个类型错误。因此,要使其正常工作,您需要将 newState 更改为:const newState = { clinic: {} }
-
什么是
this.handlers.onNameChange({text})
?我认为您需要将其更改为this.props.updateClinicDrName(text)
.