gpt4 book ai didi

javascript - 使用 通过上下文传递存储在基于 connect() 的场景中不起作用

转载 作者:搜寻专家 更新时间:2023-11-01 04:45:53 25 4
gpt4 key购买 nike

编辑:总结 - 我的问题的最初原因实际上是一个拼写错误:由于大写的“G”,它没有工作。

然而,善良的回答者不仅解决了拼写错误,而且解决了我所采用方法中的错误前提 - 如果您也使用 Provider 使用 connect 传递商店,他们的答案与您相关.我更新了问题的标题以反射(reflect)这一点。


我正在尝试按照 awesome redux videos 中的说明进行操作, 但因使用 <Provider> 传递商店而感到悲伤来自 react-redux。

我有一个根组件:

export default class Root extends Component {
render() {

const { store } = this.props

return (
<Provider store={store}>
<div>
<ReduxRouter />
<DevTools />
</div>
</Provider>
)
}
}

还有一个试图使用商店的展示组件:

const ProjectsSummary = (props, {store}) => {
const state = store.GetState();
const { projects } = state;

return (
<div className="home-projects col-md-10">
<h3>Projects</h3>
<ul>
{ projects.map(p => <li key={p.id}>{p.contract.client}</li>) }
</ul>
</div>
)
}

ProjectsSummary.contextTypes = {
store: React.PropTypes.object
};

class Home extends BasePage {

render() {
return (
<div className="home-page container-fluid">
{super.render()}
<HomeLeftBar/>
<HomePageHeader/>
<ProjectsSummary/>
</div>
)
}
}

export default connect()(Home)

我收到“未捕获的类型错误:store.GetState 不是函数”

商店来自这里:

import configureStore from './store/configureStore'

const store = configureStore({
security:{
jwt: 'mock' // Mock data supplied below: only loaded when this is set.
},
projects: [
{
// elided for brevity
}
]
})

/**
* Main application render method that attaches it
* to the HTML page.
*/
render(
<Root store={store}/>,
document.getElementById('app')
)

并在这里创建:

export default (initialState) => {
const store = createDevStore(initialState)

if (module.hot) {
// Enable Webpack hot module replacement for reducers
module.hot.accept(['../../common/reducers', '../reducers'], () => {
const nextRootReducer = require('../../common/reducers')
const nextBrowserReducers = require('../reducers')
store.replaceReducer(nextRootReducer(nextBrowserReducers))
})
}

return store
}

function createDevStore(initialState){
if(initialState && initialState.security && initialState.security.jwt === 'mock')
return mockCreateStore(rootReducer(browserReducers), initialState)
else
return finalCreateStore(rootReducer(browserReducers))
}

const mockCreateStore = compose(
reduxReactRouter({routes, createHistory}),
applyMiddleware(createLogger()),
DevTools.instrument()
)(createStore)

(不是我的代码,一个支持 native 和浏览器客户端的框架,我正在开始工作)

我错过了什么?


我是从视频中复制的——请注意 AddTodo 组件没有使用 connect() 进行“包装”:

const AddTodo = (props, { store }) => {
let input;

return (
<div>
<input ref={node => {
input = node;
}} />
<button onClick={() => {
store.dispatch({
type: 'ADD_TODO',
id: nextTodoId++,
text: input.value
})
input.value = '';
}}>
Add Todo
</button>
</div>
);
};
AddTodo.contextTypes = {
store: React.PropTypes.object
};

最佳答案

This answer是正确的,但我想澄清一些事情。

您似乎对展示组件和容器组件以及 connect() 的作用有很多困惑。建议大家再看一遍相关视频,一定要看完。

  1. 确实,store.GetState() 不是一个有效的方法; store.getState() 是。
  2. 如果您手动使用store.getState()您必须也在某处使用store.subscribe(),这样您总能获得最大 yield 最近的状态。您从视频中粘贴的示例 AddTodo 组件本身将无法工作——它仅在视频中有效,因为我们在非常顶级
  3. 类(class)后面的视频讨论了从顶部重新渲染如何变得麻烦,此时我们将介绍容器组件。稍后我们将展示使用 connect() 生成容器组件比手动编写它们更容易 — 在本例中,connect() 负责订阅商店。
  4. 仅仅将 Home 包裹在 connect() 中是没有效果的。 connect() 生成一个订阅商店的容器组件,但如果您不指定 mapStateToProps 参数,它甚至不会订阅商店。 使用 connect() 是使用 store.getState()store.subscribe()contextTypes 的有效替代 手动。 both 在某物上使用 connect() 并调用 store.getState() 是没有意义的或指定 contextTypes

所以,再总结一下:

  • store.getState()store.subscribe() 是低级 API。如果您决定使用它们,则必须同时使用它们;缺一不可。

  • connect() 负责调用 getState()subscribe() 并将必要的信息传递给子进程通过 Prop 为您提供组件。如果使用 connect(),则永远不需要 store.getState()store.subscribe()contextTypesconnect() 的全部意义在于将它们抽象出来。

这些类(class)会教给您所有这些工具,以向您展示没有魔法。但是,通常您不应在实际应用中使用 store.getState()store.subscribe()。您应该几乎完全使用 connect() 除非您有非常具体的原因访问低级 API。

我会大致像这样重写您的代码:

// ProjectSummary is a presentational component
// that takes projects as a prop and doesn't care
// where it comes from.
const ProjectsSummary = ({ projects }) => {
return (
<div className="home-projects col-md-10">
<h3>Projects</h3>
<ul>
{projects.map(p => <li key={p.id}>{p.contract.client}</li>)}
</ul>
</div>
)
}

// Home by itself is also a presentational component
// that takes projects as a prop. However we will
// wrap it in a container component below using connect().
// Note that I got rid of inheritance: it's an anti-pattern
// in React. Never inherit components; instead, use regular
// composition and pass data as props when necessary.
const Home = ({ projects }) => (
<div className="home-page container-fluid">
<BasePage />
<HomeLeftBar />
<HomePageHeader />
<ProjectsSummary projects={projects} />
</div>
)

// How to calculate props for <Home />
// based on the current state of the store?
const mapStateToProps = (state) => ({
projects: state.projects
})

// Generate a container component
// that renders <Home /> with props from store.
export default connect(
mapStateToProps
)(Home)

关于javascript - 使用 <Provider> 通过上下文传递存储在基于 connect() 的场景中不起作用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35940405/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com