React:如何从 Redux/Flux 操作访问组件引用?
Posted
技术标签:
【中文标题】React:如何从 Redux/Flux 操作访问组件引用?【英文标题】:React: How to access component refs from Redux/Flux actions? 【发布时间】:2017-08-05 09:54:54 【问题描述】:当实现像 Redux 或 MobX 这样的状态容器时,你的状态和事件通常被移动到一个单独的类或对象中,不再可以读取 refs。
例如,在普通组件中:
import Alert from Alert.js;
class Dummy extends React.Component
constructor(props)
super(props);
this.state = clicked: false
handleClick()
fetch('api').then(function()
this.setState( clicked: true );
this._alert.show('Cool response!');
);
render()
return (
<div>
<Alert ref=a => this._alert = a />
<Button onClick=this.handleClick/>
</div>
)
如果我点击按钮,一旦服务器请求完成,状态就会更新并触发警报。在一些 modal 和 alert 库中使用这样的 refs 是很常见的。
现在,在 Redux(或任何 Flux 实现)中,该 fetch() 将存在于一个动作中,该动作存在于一个单独的文件中,该文件无权访问 this._alert
。
在不重写外部“警报”库的情况下维护功能的最佳方法是什么?
【问题讨论】:
在你的行动中你可以返回一个承诺 I.E. api 调用,您可以执行以下操作:this.props.fetchSomething.then(() => this._alert.show('Cool response!')
您只需要确保您在操作中返回了承诺。
返回一个 Promise 是个好主意,但是您需要使用一些中间件来让您的操作返回诸如 redux-promise-middleware
或类似的承诺
【参考方案1】:
作为说明,我来自您的帖子:https://dannyherran.com/2017/03/react-redux-mobx-takeaways/
这从一开始就是错误的。 Refs 不应该在组件之间共享,因为这会耦合它们。组件的设计应完全相互分离,并根据赋予它们的状态做出反应。
问题是 ref 没有告诉你组件本身的状态,你不知道它是否已安装,你甚至不知道它是否存在,所以你在玩一些 volatile 的东西。
所以让我们解耦一切并适当地利用 react/redux 的力量,所有代码都应该以这种方式组织:
1。减速机:
Reducer 将保持警报的显示状态。 现在,整个应用程序中的任何组件都可以访问它,独立于 refs,因此该组件是否实际存在并不重要。
const DummyPageReducer = function(state, action)
if (state === undefined)
state =
alertShow: false
;
switch(action.type)
case 'ALERT_DISPLAY':
return Object.assign(, state, alertShow: action.display );
return state;
2。动作和异步动作:
调整警报显示设置的操作,以及执行获取并产生正确结果的异步操作。
export const ALERT_DISPLAY = 'ALERT_DISPLAY '
export function alertDisplay(display)
return
type: ALERT_DISPLAY,
display
export function showAlert()
return function (dispatch)
fetch('api').then(function()
dispatch(alertDisplay(true))
);
3。连接组件:
连接的组件。无需共享 refs,将使用 ref,但组件将对其给定的 props 做出反应并相应地设置 Alert。
import Alert from Alert.js;
class Dummy extends React.Component
constructor(props)
super(props);
this.setAlert = this.setAlert.bind(this);
setAlert()
if(this.props.alertShow)
this._alert.show('Cool response!');
else
this._alert.hide();
componenDidMount()
setAlert();
componentDidUpdate(prevProps, prevState)
if(prevProps.alertShow !== this.props.alertShow)
setAlert();
render()
return
(
<div>
<Alert ref=a => this._alert = a />
<Button onClick=this.props.showAlert/>
</div>
)
Dummy = connect(
state =>
(
alertShow: state.Dummy.alertShow
),
dispatch =>
(
showAlert: () => dispatch(showAlert(true))
)
)(Dummy);
【讨论】:
我认为您忘记在连接的 Dummy 组件上导入您的 showAlert 操作。【参考方案2】:首先,你有没有尝试在handleClick中使用箭头功能?
handleClick()
fetch('api').then(() =>
this.setState( clicked: true );
this._alert.show('Cool response!');
);
这可能会影响this
的上下文
另一方面,如果您使用 Redux,则应该创建两个操作。
比如fetchAPI()
和APIfetched()
。
【讨论】:
以上是关于React:如何从 Redux/Flux 操作访问组件引用?的主要内容,如果未能解决你的问题,请参考以下文章
图书推荐React全栈:Redux+Flux+webpack+Babel整合开发