AJAX API三驾马车: Axios vs . jQuery和Fetch

栏目: jQuery · 发布时间: 7年前

内容简介:如果你曾经使用过类似本文通过一个简单的示例,学习通过不同的方式(如

如果你曾经使用过类似 Angular 框架的经验,你会发现这些框架集成了开发一个应用应该具备的所有功能,例如用于进行HTTP调用的服务( Angular 中的 $HTTP )。

React 是一个视图层框架,用于构建用户界面。在 MVC 架构中,它仅仅负责视图部分。在实际的开发过程中,往往需要我们引入一些第三方组件,比如今天要说的 AJAX API

本文通过一个简单的示例,学习通过不同的方式(如 AxiosXMLHttpRequestfetch API )使用来进行 AJAX 请求(GET、POST、PUT和DELETE),以获取、创建、更新和删除数据。

AJAX API三驾马车: Axios vs . jQuery和Fetch

AJAX API

有很多的方案, 你所做的就是选择合适的解决方案:

1、对 JavaScriptPromise 比较熟悉,可以使用 Axios

2、喜欢使用前沿标准,可以使用 fetch API

3、也可以使用 jQuery ,但不建议仅仅为了进行API调用而引入整个库。

可以直接使用 XMLHttpRequest 接口。

Fetch API的示例

我推荐使用 create-react-app 来创建应用,因为它省去了好多的配置。

npm install -g create-react-app

通过执行以下命令创建并启动我们的应用: react-ajax-demo

create-react-app react-ajax-demo
cd react-ajax-demo
npm start

Fetch API

下面引自 Mozilla MDN :

Fetch API 提供了一个获取资源的接口(包括跨域)。任何使用过 XMLHttpRequest 的人都能轻松上手,但新的API提供了更强大和灵活的功能集。

读取Reddit上发布的一些帖子, src/App.js

import React, { Component } from 'react';
import logo from './logo.svg';
import './App.css';

class App extends Component {

  constructor(props) {
    super(props);

    this.state = {
      posts: []
    };
  }  
  fetchFirst(url) {
    var that = this;
    if (url) {
      fetch('https://www.reddit.com/r/' + url + '.json').then(function (response) {
        return response.json();
      }).then(function (result) {
        that.setState({ posts: result.data.children, lastPostName: result.data.children[result.data.children.length - 1].data.name });
        console.log(that.state.posts);
      });
    }
  }  
  componentWillMount() {
      this.fetchFirst("reactjs");
  }    
  render() {

    return (
      <div className="App">
        <header className="App-header">
          <img src={logo} className="App-logo" alt="logo" />
          <h1 className="App-title">React AJAX Example</h1>
        </header>
        <p className="App-intro">
          <ul>
            {this.state.posts.map(post =>
              <li key={post.id}>{post.title}</li>
            )}
          </ul>          
        </p>
      </div>
    );
  }
}

export default App;

fetchFirst() 方法中,我们发起了一个GET请求:

fetch('https://www.reddit.com/r/' + url + '.json').then(function (response) {
        return response.json();
}).then(function (result) {
    console.log(result.data.children);
});

API很简单,需要的唯一参数就是资源的URI。这里它是一个JSON文件,也可以是任何类型的资源,如图像或其他类型。

**fetch(url)**在默认情况下发送GET HTTP请求。

还可以通过第二个参数中指定方法名来调用其他HTTP方法,如POST、PUT或DELETE。

例如,使用 fetch() 发送POST请求:

var form = new FormData(document.getElementById('login-form'));
fetch("/login", {
  method: "POST",
  body: form
});

AJAX API调用时机

一个典型的 React 应用是一系列包含根组件、父组件以及子组件(以及子组件的子组件)的组件,这些组件可以可看作为一个树状结构。

这里会产生许多问题:

1、如何处理数据?

2、数据如何从组件流到其他组件?

3、最重要的是,在哪里放异步请求的代码?

componentWillMount() 是React生命周期的一个重要事件,执行时机在组件第一次渲染之前,在组件即将挂载时调用该事件。

前面的例子中,我们就是在 componentWillMount() 事件内部发起 AJAX 请求。

其实还有几个地方可以这么做:

1、 componentDidMount() : 这是官方推荐的地方

2、 componentWillMount() : 官方不推荐

3、 constructor() :它被认为是反模式! 但是可以像 componentWillMount() 一样使用。

componentDidMount() vs componentWillMount()

componentWillMount() 方法在组件的第一次渲染之前被调用。任何人误以为这是获取数据的最佳场所。但事实并非如此!因为 fetch 调用是异步的,这意味着在组件渲染之前异步请求有可能还没返回。一般采取的做法是:在 constructor() 设置初始状态,为了 React 能正确地渲染组件,在异步请求返回后触发组件的重新渲染。

componentDidMount() 方法是在组件第一次渲染之后调用的,因此可以放心在这里执行任何异步代码,这些操作可以是获取服务器数据,也可以是操作DOM。

在实现服务端渲染时,componentWillMount()会调用两次,因此会有两次请求发送给服务器,这是一种浪费。而componentDidMount()只会在客户端调用一次。

我们对上面的示例做下改动:

componentDidMount() {
    this.fetchFirst("reactjs");
}

componentWillMount() vs constructor

从程序的角度分析,是否可以用 constructor 代替 componentWillMount()

表面上看确实是可以替代的,但这并不是一种正确的方式。

因为我们如果学过纯函数的话,都知道其实异步请求是一种典型的有副作用的非纯函数。如果组件构造函数中存非纯函数, React 会抛出一个警告, 而 componentWillMount() 中是允许非纯函数的。如果代码中需要更新其他组件中的状态,最好不要使用构造函数。

最后一个结论是:对于任何不产生副作用(如状态更新)的初始化代码使用构造函数,否则使用componentDidMount()。

组件之间通信

另一种方法是从父组件向子组件传递数据。当然,父组件也应该避免之前获取数据的方法,那么在哪里呢?父节点可以使用React路由器钩子(如 onEnter() )获取数据,然后通过 props 将数据传递给子节点。

在本文示例中,由于只有一个组件,但这可以很容易地分解为以下内容:

Fetch.js

export default {
    fetchFirst: function(url){
        fetch('https://www.reddit.com/r/' + url + '.json').then(function (response) {
                return response.json();
        }).then(function (result) {
             return result.data.children;   
        }); 
    }  
}

RedditPost.js

import React from "react";

class RedditPost extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      title: props.title,
      id: props.id
    }
  }

  componentWillReceiveProps(nextProps) {
    this.setState(nextProps);
  }

  render() {
            <li key={this.state.id}>{this.state.title}</li>
      );
    }
  }
}

RedditPost.propTypes = {
  id: React.PropTypes.number,
  title: React.PropTypes.string
};

RedditPost.defaultProps = {
  id: null,
  title: ""

};

export default RedditPost;

App.js

import fetchFirst from "./Fetch";

import React, { Component } from 'react';
import logo from './logo.svg';
import './App.css';

class App extends Component {

  constructor(props) {
    super(props);

    this.state = {
      posts: []
    };
  }  

  componentDidMount() {

      fetchFirst("reactjs").then((posts)=>{
          this.state.posts = posts;
      });

  }    
  render() {

    return (
      <div className="App">
        <header className="App-header">
          <img src={logo} className="App-logo" alt="logo" />
          <h1 className="App-title">React AJAX Example</h1>
        </header>
        <p className="App-intro">
          <ul>
            {this.state.posts.map(post =>
              <RedditPost {...post}/>
            )}
          </ul>          
        </p>
      </div>
    );
  }
}

export default App;

使用Redux State Manager

第三种方法是使用 Redux 这样的状态管理器。

从代码中的任何地方获取数据,然后将数据存储在全局存储中,所有其他组件都可以使用这些数据。

关于对 Redux 的学习,你可以自行了解,也可以读一下我之前写的几篇文章:

1、 Redux-如何更优雅的修改全局状态

2、重新思考Redux

结尾

越来越多的企业在构建自己的网站时开始注重体验、性能,出现了大量的单页面应用,将 AJAX 这种无刷技术发挥到了极致。而我们在使用 React 开发应用时可以有多种 AJAX 方案:

1、 使用XMLHttpRequest ,如果觉得复杂,可直接使用 jQuery

2、 Fetch API , 现代浏览器都支持,老版浏览器需要使用 polyfills

3、 Axios :一个基于 promiseHTTP 库, 可以用在浏览器和 node.js 中。


以上所述就是小编给大家介绍的《AJAX API三驾马车: Axios vs . jQuery和Fetch》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

Pro Django

Pro Django

Marty Alchin / Apress / 2008-11-24 / USD 49.99

Django is the leading Python web application development framework. Learn how to leverage the Django web framework to its full potential in this advanced tutorial and reference. Endorsed by Django, Pr......一起来看看 《Pro Django》 这本书的介绍吧!

HTML 压缩/解压工具
HTML 压缩/解压工具

在线压缩/解压 HTML 代码

XML 在线格式化
XML 在线格式化

在线 XML 格式化压缩工具

HEX CMYK 转换工具
HEX CMYK 转换工具

HEX CMYK 互转工具