【问题标题】:How to call class component from the functional component如何从功能组件中调用类组件
【发布时间】:2018-10-04 08:00:57
【问题描述】:

这里我想在 axios 拦截器响应中请求失败时显示一个模态窗口(这是类组件)。谁能帮助我如何在下面的代码中调用Modals 类而不是警报。

     //axios interceptor 
    import React, { Component}  from 'react';
    import axios from 'axios';
    import Modals  from '../components/modalAlerts/modalalerts';
    import ReactDOM from 'react-dom';
    import ShallowRenderer from 'react-test-renderer/shallow'
    import { Button, Card, CardBody, CardHeader, Col, Modal, ModalBody, ModalFooter, ModalHeader, Row } from 'reactstrap';
    const instance = axios.create({
        baseURL: '//some url here',
        timeout: 15000,
    });
    instance.defaults.headers.common['Authorization'] = //token;
    instance.defaults.headers.post['Content-Type'] = 'application/x-www-form-urlencoded';
    instance.interceptors.request.use(function (config) {
        return config;
      }, function (error) {
        alert(error)
        console.log(error.response)
        return Promise.reject(error);
      });
    instance.interceptors.response.use(function (config) {
        return config;
      }, function (error) {
        console.log(error)
        if(error.response){
            if(error.response.status === 401||error.response.status === 403 ){
                console.log("401")
                localStorage.clear()
                window.location = '/#/login';
                alert(error.response.data.message)
            }else if(error.response.status === 404){
               alert(404);
            }else if(error.response.status === 400){
               alert(error.response.data.message)
            }else{
                alert("something went wrong. Please try after sometime..!")
            }
        }else{
            alert("server not found")
        }

        return Promise.reject(error);
      });
    export default instance;

这里是我的模型类组件,我想从上面的 axios 拦截器而不是警报中调用此模式。

     class Modals extends Component {
        constructor(props) {
            super(props);
            console.log(props)
            this.state = {
                modal: true,
            }    
            this.toggle = this.toggle.bind(this);
        }

        toggle() {
            this.setState({
                modal: !this.state.modal,
            });
        }
        render() {
            return (
                <div className="animated fadeIn">
                    <Row>
                        <Col>
                            <Modal isOpen={this.state.modal} toggle={this.toggle} className={this.props.className}>
                                <ModalHeader toggle={this.toggle}>{this.props.apistatus == 1? "Success" : "Error"}</ModalHeader>
                                <ModalBody>
                                    {this.props.apistatus == 1? "Form updated successfully" : this.props.errormsg}
                                </ModalBody>
                                <ModalFooter>
                                    <Button color="primary" onClick={this.toggle}>OK</Button>{' '}
                                    {/* <Button color="secondary" onClick={this.toggle}>Cancel</Button> */}
                                </ModalFooter>
                            </Modal>       
                        </Col>
                    </Row>
                </div>
            );
        }
    }
    export default Modals;

【问题讨论】:

  • 您已经发布了这个问题。请取消删除您之前的问题,那里有未发布的答案。
  • 我的意思是这个问题,stackoverflow.com/questions/52620484/…
  • @estus,我刚刚取消了我之前的问题。

标签: javascript reactjs axios interceptor


【解决方案1】:

这个问题类似于this one。存在与 React 应用无关的 Axios 实例,因此无法获取 modal 实例与之交互。将其绑定到 React 组件实例将是一个错误,可能会导致其他问题,例如在测试中。正确的做法是将axios实例与具体的应用实例关联起来,为整个应用提供axios实例。

执行此操作的常用方法是深度传递道具、上下文 API 和全局状态管理(Redux、MobX)。

例如axios工厂函数接收模态组件实例来引用它:

function axiosFactory(modalRef) {
      const instance = ...;
      instance.interceptors.request.use(..., function (error) {
        const modalInstance = modalRef.current;
        modalInstance.toggle();
      });
      ...
    }

const AxiosContext = React.createContext();

class App extends Component {
  modalRef = React.createRef();

  render() {
    return <>
      <Modal ref={this.modalRef}/>
      <AxiosContext.Provider value={axiosFactory(this.modalRef)}>
        ...the rest of the app that depends on Axios...
      </AxiosContext.Provider>
    </>;
  }
}

可以在子组件中检索axios实例:

 <AxiosContext.Consumer>{axios => (
   <ComponentThatNeedsToGetAxiosAsProp axios={axios} />
 )</AxiosContext.Consumer>

使用惯用的 React 配方可以提高可重用性,例如withAxios 使用&lt;AxiosContext.Consumer&gt; 的高阶组件,如上所示。

在 Redux 的情况下,这可能更简单,因为 Axios 实例可以在 Redux 存储中可用,并与 React 组件层次结构分离。它不需要直接获取模态组件,因为它可以通过动作与之交互。

【讨论】:

    猜你喜欢
    • 2017-08-23
    • 1970-01-01
    • 1970-01-01
    • 2020-02-25
    • 1970-01-01
    • 2018-04-15
    • 2021-08-16
    • 2018-10-25
    • 1970-01-01
    相关资源
    最近更新 更多