使用React AJAX调用避免重复代码

时间:2016-10-11 08:32:37

标签: ajax function reactjs react-router dry

我在一个非常简单的应用程序上使用React和React Router。

路线模式:

   <Route path='/' component={Layout}>
      <IndexRoute component={Home} />
      <Route path='/users' component={Users} />
      <Route path='/posts' component={Posts} />
   </Route>

我想要做的是编写一个有助于避免在每个组件中重复AJAX调用的函数,因为它几乎完全相同的代码。

我的状态/ AJAX配置,在&#39;用户&#39;成分:

   constructor(props) {
      super(props);
      this.state = {
         users: []
      };
   }
   componentDidMount() {
      axios.get('https://jsonplaceholder.typicode.com/users')
         .then( response => {
            const users = response.data
            this.setState({ users });
         });
   }

我想创建一个函数,它接受端点作为它的参数,然后可以在每个组件中重复使用,只需交换端点......就像这样:

function(endpoint) {
   axios.get({`https://jsonplaceholder.typicode.com/${endpoint}`})
   // rest of the AJAX call...
}

但我不知道在哪里定义这个功能。根据我的路由结构,它是否在父组件中,&#39; Layout&#39 ;?如果是这样,我如何将该函数作为prop组件传递给子组件?我知道如何使用嵌套组件,但不是嵌套路由...

我的布局组件:

export default class Layout extends Component {

render() {
   return (
   <div>
      <header><h1>Testing with react-router</h1></header>
      <Nav />
      <div className='pc-content container'>
         {this.props.children}
      </div>
      )
   }
}

我确信使用Redux / Flux有更有效的方法,但我没有先尝试它。

此外(这是一个稍微不同的问题),是否有一种简单的方法来缓存响应有效负载,以便每次呈现组件时它都不会再次请求数据?

任何帮助/指示赞赏。

更新(@Lukas Liesis)

已将ajax调用解压缩到call_helper.js

import axios from 'axios'

const call = (endpoint) => {
   axios.get(`https://jsonplaceholder.typicode.com/${endpoint}`)
      .then( response => {
         endpoint = response.data
         this.setState({ endpoint });
      });
}

export {call};

将其拉入Users组件:

import call from '../js/call_helper'

现在已将componentDidMount更新为:

componentDidMount() {
      call('users')
      // axios.get('https://jsonplaceholder.typicode.com/users')
      //    .then( response => {
      //       const users = response.data
      //       this.setState({ users });
      //    });
   }

控制台日志:Users.js:66 Uncaught TypeError: (0 , _call_helper2.default) is not a function

2 个答案:

答案 0 :(得分:1)

只需将其添加到一个单独的文件中,并随时将其包含在内。

您可以根据需要命名文件,但让我们说call_helper.js

const call = (endpoint) => {
   return new Promise((resolve, reject) => {
      axios.get({`https://jsonplaceholder.typicode.com/${endpoint}`})
      // rest of the AJAX call...
      // when ajax call is done, just call:
      resolve(result);
      // if some error, then:
      reject(error);
   })
};

export {call};

现在您可以将其包含在

的任何组件中
include {call} from './path/to/file/call_helper';

并通过简单的调用在组件中的任何位置使用它:

call('some_endpoint')
  .then(result => {
     // do something with result
  })
  .catch(e => {
    // do something with error
  });

答案 1 :(得分:0)

您将在此处找到您要查找的内容的实现: https://github.com/mzabriskie/axios/issues/320(查看mikechabot评论)