React 中的 AJAX 請求:獲取數據的方法與時機
React 新手一開始可能會問到這樣一個問題,“在 React 中如何發送 AJAX 請求呢?”
本文正要回答該問題。
首先:React 本身對獲取數據的方式并無任何特殊偏好。實際上,在 React 的圖景中,根本就不知道“服務器”這種東西的存在。
React 只是使用 props 和 state 兩處的數據進行組件渲染。
因此,想要使用來自服務端的數據,必須將數據放入組件的 props 或 state 中。
你完全可以按照喜好使用服務、數據模型(額,“建立抽象”)完成這個過程,但歸根結底只不過是通過 props 和 state 渲染組件。
選擇 HTTP 工具庫
要從服務端拿到數據,首先得有一個 HTTP 工具庫。現成的輪子數都數不清。它們最終做的事情都一樣,但在一些特性上有所不同。
喜歡 Promise?那就試試 axios 吧。
不喜歡 Promise,對回調函數情有獨鐘?可以看一眼 superagent 。
要不試試將要成為標準的一些工具? fetch 可能是你的菜。
這些其實根本不重要。沒有“最佳”工具。
有些人可能會說, fetch 是最好的,因為 fetch 差不多已經是標準了。但我敢打賭,就算fetch 真正 成為標準,還是會有人喜歡、使用一些與之匹敵的 HTTP 工具庫。所以隨你怎么選咯。
我個人比較喜歡 axios ,這也是本文示例所使用的。不過,認真的說,如果你偏偏不喜歡它,那就選其他的唄。
獲取數據
下面是一個簡單的示例組件,它從 Reddit 站點獲取文章列表。先看一眼,后面會講述代碼是如何工作的。
import React from 'react';
import ReactDOM from 'react-dom';
import axios from 'axios';
class FetchDemo extends React.Component {
constructor(props) {
super(props);
this.state = {
posts: []
};
}
componentDidMount() {
axios.get(`http://www.reddit.com/r/${this.props.subreddit}.json`)
.then(res => {
const posts = res.data.data.children.map(obj => obj.data);
this.setState({ posts });
});
}
render() {
return (
<div>
<h1>{`/r/${this.props.subreddit}`}</h1>
<ul>
{this.state.posts.map(post =>
<li key={post.id}>{post.title}</li>
)}
</ul>
</div>
);
}
}
ReactDOM.render(
<FetchDemo subreddit="reactjs"/>,
document.getElementById('root')
);
如何工作
首先引入 axios 。
import axios from 'axios';`
constructor 方法非常標準,調用 super ,然后初始化 state,設置一個空的 posts 數組。
真正神奇的事情發生在 componentDidMount 方法中。組件首次“掛載”(mount)時,該方法就會執行。在組件生命周期中,該方法只會執行 一次 。
TL;DR: 在 componentDidMount 方法中獲取服務端數據
componentDidMount 方法中,根據傳入的 subreddit 屬性,調用 axios.get 方法獲取數據。反引號中是 ES6 模板字符串,可能如你所想, ${...} 部分會被其中表達式的值所替換,因此傳給 axios.get 的 URL 實際上是 http://www.reddit.com/r/reactjs.json 。
此處需注意兩點,和 Reddit 有關:
-
可以在 Reddit 網站下面所有的 URL 后面添加 .json 后綴,以獲取 JSON 格式的內容。
-
如果去掉 www ,會產生 CORS 錯誤(至少我碰到了這個錯誤)。
因為 Axios 使用了 Promise,所以可以通過 .then 方法鏈式處理響應。經過一些處理后, posts 被提取出來了,緊接著是重點:
傳入新的 posts 數組,使用 this.setState 方法更新組件狀態。這會導致重新渲染,接下來文章列表就顯示出來了。
這就是所有的一切啦哈哈!
額外獎勵:添加加載指示
知道怎樣修改代碼,在請求尚未返回時添加一個 "Loading..." 消息嗎?
提示:在 state 中設置一個標志,一旦請求完成則將其切換其值。在 render 函數中使用這個標志顯示加載提示。
如果想看示例代碼(包括加載提示以及附加的 error state ),可以點擊 這里 下載可運行的例子,無需注冊喲~
解壓文件,依次執行 npm install 和 npm start 。示例基于棒棒噠 Create React App 創建。
來自:http://www.zcfy.cc/article/ajax-requests-in-react-how-and-where-to-fetch-data-1348.html