Vue.js——vue-resource全攻略

来源:http://www.cnblogs.com/keepfool/archive/2016/07/10/5657065.html
-Advertisement-
Play Games

概述 上一篇我們介紹瞭如何將$.ajax和Vue.js結合在一起使用,並實現了一個簡單的跨域CURD示例。Vue.js是數據驅動的,這使得我們並不需要直接操作DOM,如果我們不需要使用jQuery的DOM選擇器,就沒有必要引入jQuery。vue-resource是Vue.js的一款插件,它可以通過... ...


概述

上一篇我們介紹瞭如何將$.ajax和Vue.js結合在一起使用,並實現了一個簡單的跨域CURD示例。Vue.js是數據驅動的,這使得我們並不需要直接操作DOM,如果我們不需要使用jQuery的DOM選擇器,就沒有必要引入jQuery。vue-resource是Vue.js的一款插件,它可以通過XMLHttpRequest或JSONP發起請求並處理響應。也就是說,$.ajax能做的事情,vue-resource插件一樣也能做到,而且vue-resource的API更為簡潔。另外,vue-resource還提供了非常有用的inteceptor功能,使用inteceptor可以在請求前和請求後附加一些行為,比如使用inteceptor在ajax請求時顯示loading界面。

本文的主要內容如下:

  • 介紹vue-resource的特點
  • 介紹vue-resource的基本使用方法
  • 基於this.$http的增刪查改示例
  • 基於this.$resource的增刪查改示例
  • 基於inteceptor實現請求等待時的loading畫面
  • 基於inteceptor實現請求錯誤時的提示畫面

本文11個示例的源碼已放到GitHub,如果您覺得本篇內容不錯,請點個贊,或在GitHub上加個星星!

GitHub Source

本文的所有示例如下:

各位在閱讀這篇文章的內容時,可以先嘗試該列表的最後兩個示例,這兩個示例綜合使用了this.$http和inteceptor。

vue-resource特點

vue-resource插件具有以下特點:

1. 體積小

vue-resource非常小巧,在壓縮以後只有大約12KB,服務端啟用gzip壓縮後只有4.5KB大小,這遠比jQuery的體積要小得多。

2. 支持主流的瀏覽器

和Vue.js一樣,vue-resource除了不支持IE 9以下的瀏覽器,其他主流的瀏覽器都支持。

3. 支持Promise API和URI Templates

Promise是ES6的特性,Promise的中文含義為“先知”,Promise對象用於非同步計算。
URI Templates表示URI模板,有些類似於ASP.NET MVC的路由模板。

4. 支持攔截器

攔截器是全局的,攔截器可以在請求發送前和發送請求後做一些處理。
攔截器在一些場景下會非常有用,比如請求發送前在headers中設置access_token,或者在請求失敗時,提供共通的處理方式。

vue-resource使用

引入vue-resource

<script src="js/vue.js"></script>
<script src="js/vue-resource.js"></script>

基本語法

引入vue-resource後,可以基於全局的Vue對象使用http,也可以基於某個Vue實例使用http。

// 基於全局Vue對象使用http
Vue.http.get('/someUrl', [options]).then(successCallback, errorCallback);
Vue.http.post('/someUrl', [body], [options]).then(successCallback, errorCallback);

// 在一個Vue實例內使用$http
this.$http.get('/someUrl', [options]).then(successCallback, errorCallback);
this.$http.post('/someUrl', [body], [options]).then(successCallback, errorCallback);

在發送請求後,使用then方法來處理響應結果,then方法有兩個參數,第一個參數是響應成功時的回調函數,第二個參數是響應失敗時的回調函數。

then方法的回調函數也有兩種寫法,第一種是傳統的函數寫法,第二種是更為簡潔的ES 6的Lambda寫法:

// 傳統寫法
this.$http.get('/someUrl', [options]).then(function(response){
	// 響應成功回調
}, function(response){
	// 響應錯誤回調
});


// Lambda寫法
this.$http.get('/someUrl', [options]).then((response) => {
	// 響應成功回調
}, (response) => {
	// 響應錯誤回調
});

PS:做過.NET開發的人想必對Lambda寫法有一種熟悉的感覺。

支持的HTTP方法

vue-resource的請求API是按照REST風格設計的,它提供了7種請求API:

  • get(url, [options])
  • head(url, [options])
  • delete(url, [options])
  • jsonp(url, [options])
  • post(url, [body], [options])
  • put(url, [body], [options])
  • patch(url, [body], [options])

除了jsonp以外,另外6種的API名稱是標準的HTTP方法。當服務端使用REST API時,客戶端的編碼風格和服務端的編碼風格近乎一致,這可以減少前端和後端開發人員的溝通成本。

客戶端請求方法 服務端處理方法
this.$http.get(...) Getxxx
this.$http.post(...) Postxxx
this.$http.put(...) Putxxx
this.$http.delete(...) Deletexxx

options對象

發送請求時的options選項對象包含以下屬性:

參數 類型 描述
url string 請求的URL
method string 請求的HTTP方法,例如:'GET', 'POST'或其他HTTP方法
body Object, FormData string request body
params Object 請求的URL參數對象
headers Object request header
timeout number 單位為毫秒的請求超時時間 (0 表示無超時時間)
before function(request) 請求發送前的處理函數,類似於jQuery的beforeSend函數
progress function(event) ProgressEvent回調處理函數
credientials boolean 表示跨域請求時是否需要使用憑證
emulateHTTP boolean 發送PUT, PATCH, DELETE請求時以HTTP POST的方式發送,並設置請求頭的X-HTTP-Method-Override
emulateJSON boolean 將request body以application/x-www-form-urlencoded content type發送

emulateHTTP的作用

如果Web伺服器無法處理PUT, PATCH和DELETE這種REST風格的請求,你可以啟用enulateHTTP現象。啟用該選項後,請求會以普通的POST方法發出,並且HTTP頭信息的X-HTTP-Method-Override屬性會設置為實際的HTTP方法。

Vue.http.options.emulateHTTP = true;

emulateJSON的作用

如果Web伺服器無法處理編碼為application/json的請求,你可以啟用emulateJSON選項。啟用該選項後,請求會以application/x-www-form-urlencoded作為MIME type,就像普通的HTML表單一樣。

Vue.http.options.emulateJSON = true;

response對象

response對象包含以下屬性:

方法 類型 描述
text() string 以string形式返回response body
json() Object 以JSON對象形式返回response body
blob() Blob 以二進位形式返回response body
屬性 類型 描述
ok boolean 響應的HTTP狀態碼在200~299之間時,該屬性為true
status number 響應的HTTP狀態碼
statusText string 響應的狀態文本
headers Object 響應頭

註意:本文的vue-resource版本為v0.9.3,如果你使用的是v0.9.0以前的版本,response對象是沒有json(), blob(), text()這些方法的。

CURD示例

提示:以下示例仍然沿用上一篇的組件和WebAPI,組件的代碼和頁面HTML代碼我就不再貼出來了。

GET請求

var demo = new Vue({
	el: '#app',
	data: {
		gridColumns: ['customerId', 'companyName', 'contactName', 'phone'],
		gridData: [],
		apiUrl: 'http://211.149.193.19:8080/api/customers'
	},
	ready: function() {
		this.getCustomers()
	},
	methods: {
		getCustomers: function() {
			this.$http.get(this.apiUrl)
				.then((response) => {
					this.$set('gridData', response.data)
				})
				.catch(function(response) {
					console.log(response)
				})
		}
	}
})

這段程式的then方法只提供了successCallback,而省略了errorCallback。
catch方法用於捕捉程式的異常,catch方法和errorCallback是不同的,errorCallback只在響應失敗時調用,而catch則是在整個請求到響應過程中,只要程式出錯了就會被調用。

在then方法的回調函數內,你也可以直接使用this,this仍然是指向Vue實例的:

getCustomers: function() {
	this.$http.get(this.apiUrl)
		.then((response) => {
			this.$set('gridData', response.data)
		})
		.catch(function(response) {
			console.log(response)
		})
}

為了減少作用域鏈的搜索,建議使用一個局部變數來接收this。

image

View Demo

JSONP請求

getCustomers: function() {
	this.$http.jsonp(this.apiUrl).then(function(response){
		this.$set('gridData', response.data)
	})
}

View Demo

POST請求

var demo = new Vue({
	el: '#app',
	data: {
		show: false,
		gridColumns: [{
			name: 'customerId',
			isKey: true
		}, {
			name: 'companyName'
		}, {
			name: 'contactName'
		}, {
			name: 'phone'
		}],
		gridData: [],
		apiUrl: 'http://211.149.193.19:8080/api/customers',
		item: {}
	},
	ready: function() {
		this.getCustomers()
	},
	methods: {
		closeDialog: function() {
			this.show = false
		},
		getCustomers: function() {
			var vm = this
			vm.$http.get(vm.apiUrl)
				.then((response) => {
					vm.$set('gridData', response.data)
				})
		},
		createCustomer: function() {
			var vm = this
			vm.$http.post(vm.apiUrl, vm.item)
				.then((response) => {
					vm.$set('item', {})
					vm.getCustomers()
				})
			this.show = false
		}
	}
})

29

View Demo

PUT請求

updateCustomer: function() {
	var vm = this
	vm.$http.put(this.apiUrl + '/' + vm.item.customerId, vm.item)
		.then((response) => {
			vm.getCustomers()
		})
}

30

View Demo

Delete請求

deleteCustomer: function(customer){
	var vm = this
	vm.$http.delete(this.apiUrl + '/' + customer.customerId)
		.then((response) => {
			vm.getCustomers()
		})
}

31

View Demo

使用resource服務

vue-resource提供了另外一種方式訪問HTTP——resource服務,resource服務包含以下幾種預設的action:

get: {method: 'GET'},
save: {method: 'POST'},
query: {method: 'GET'},
update: {method: 'PUT'},
remove: {method: 'DELETE'},
delete: {method: 'DELETE'}

resource對象也有兩種訪問方式:

  • 全局訪問:Vue.resource
  • 實例訪問:this.$resource

resource可以結合URI Template一起使用,以下示例的apiUrl都設置為{/id}了:

apiUrl: 'http://211.149.193.19:8080/api/customers{/id}'

GET請求

使用get方法發送GET請求,下麵這個請求沒有指定{/id}

getCustomers: function() {

	var resource = this.$resource(this.apiUrl)
		vm = this

	resource.get()
		.then((response) => {
			vm.$set('gridData', response.data)
		})
		.catch(function(response) {
			console.log(response)
		})
}

View Demo

POST請求

使用save方法發送POST請求,下麵這個請求沒有指定{/id}

createCustomer: function() {
	var resource = this.$resource(this.apiUrl)
		vm = this
		
	resource.save(vm.apiUrl, vm.item)
		.then((response) => {
			vm.$set('item', {})
			vm.getCustomers()
		})
	this.show = false
}

View Demo

PUT請求

使用update方法發送PUT請求,下麵這個請求指定了{/id}

updateCustomer: function() {
	var resource = this.$resource(this.apiUrl)
		vm = this
		
	resource.update({ id: vm.item.customerId}, vm.item)
		.then((response) => {
			vm.getCustomers()
		})
}

{/id}相當於一個占位符,當傳入實際的參數時該占位符會被替換。
例如,{ id: vm.item.customerId}中的vm.item.customerId為12,那麼發送的請求URL為:

http://211.149.193.19:8080/api/customers/12

View Demo

DELETE請求

使用remove或delete方法發送DELETE請求,下麵這個請求指定了{/id}

deleteCustomer: function(customer){
	var resource = this.$resource(this.apiUrl)
		vm = this
		
	resource.remove({ id: customer.customerId})
		.then((response) => {
			vm.getCustomers()
		})
}

View Demo

使用inteceptor

攔截器可以在請求發送前和發送請求後做一些處理。

image

基本用法

Vue.http.interceptors.push((request, next) => {
		// ...
		// 請求發送前的處理邏輯
		// ...
	next((response) => {
		// ...
		// 請求發送後的處理邏輯
		// ...
		// 根據請求的狀態,response參數會返回給successCallback或errorCallback
		return response
	})
})

在response返回給successCallback或errorCallback之前,你可以修改response中的內容,或做一些處理。
例如,響應的狀態碼如果是404,你可以顯示友好的404界面。

如果不想使用Lambda函數寫法,可以用平民寫法:

Vue.http.interceptors.push(function(request, next) {
	// ...
	// 請求發送前的處理邏輯
	// ...
	next(function(response) {
		// ...
		// 請求發送後的處理邏輯
		// ...
		// 根據請求的狀態,response參數會返回給successCallback或errorCallback
		return response
	})
})

示例1

之前的CURD示例有一處用戶體驗不太好,用戶在使用一些功能的時候如果網路較慢,畫面又沒有給出反饋,用戶是不知道他的操作是成功還是失敗的,他也不知道是否該繼續等待。

通過inteceptor,我們可以為所有的請求處理加一個loading:請求發送前顯示loading,接收響應後隱藏loading。

具體步驟如下:

1.添加一個loading組件

<template id="loading-template">
	<div class="loading-overlay">
		<div class="sk-three-bounce">
			<div class="sk-child sk-bounce1"></div>
			<div class="sk-child sk-bounce2"></div>
			<div class="sk-child sk-bounce3"></div>
		</div>
	</div>
</template>

2.將loading組件作為另外一個Vue實例的子組件

var help = new Vue({
	el: '#help',
	data: {
		showLoading: false
	},
	components: {
		'loading': {
			template: '#loading-template',
		}
	}
})

3.將該Vue實例掛載到某個HTML元素

<div id="help">
	<loading v-show="showLoading"></loading>
</div>

4.添加inteceptor

Vue.http.interceptors.push((request, next) => {
	loading.show = true
	next((response) => {
		loading.show = false
		return response
	});
});

27

View Demo

示例2

當用戶在畫面上停留時間太久時,畫面數據可能已經不是最新的了,這時如果用戶刪除或修改某一條數據,如果這條數據已經被其他用戶刪除了,伺服器會反饋一個404的錯誤,但由於我們的put和delete請求沒有處理errorCallback,所以用戶是不知道他的操作是成功還是失敗了。

你問我為什麼不在每個請求裡面處理errorCallback,這是因為我比較懶。這個問題,同樣也可以通過inteceptor解決。

1. 繼續沿用上面的loading組件,在#help元素下加一個對話框

<div id="help">
	<loading v-show="showLoading" ></loading>
	<modal-dialog :show="showDialog">
		<header class="dialog-header" slot="header">
			<h1 class="dialog-title">Server Error</h1>
		</header>
		<div class="dialog-body" slot="body">
			<p class="error">Oops,server has got some errors, error code: {{errorCode}}.</p>
		</div>
	</modal-dialog>
</div>

2.給help實例的data選項添加兩個屬性

var help = new Vue({
		el: '#help',
		data: {
			showLoading: false,
			showDialog: false,
			errorCode: ''
		},
		components: {
			'loading': {
				template: '#loading-template',
			}
		}
	})

3.修改inteceptor

Vue.http.interceptors.push((request, next) => {
	help.showLoading = true
	next((response) => {
		if(!response.ok){
			help.errorCode = response.status
			help.showDialog = true
		}
		help.showLoading = false
		return response
	});
});

28

View Demo

總結

vue-resource是一個非常輕量的用於處理HTTP請求的插件,它提供了兩種方式來處理HTTP請求:

  • 使用Vue.http或this.$http
  • 使用Vue.resource或this.$resource

這兩種方式本質上沒有什麼區別,閱讀vue-resource的源碼,你可以發現第2種方式是基於第1種方式實現的。

inteceptor可以在請求前和請求後附加一些行為,這意味著除了請求處理的過程,請求的其他環節都可以由我們來控制。

參考鏈接:https://github.com/vuejs/vue-resource/tree/master/docs


您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 在android的應用層中,涉及到很多應用框架,例如:Service框架,Activity管理機制,Broadcast機制,對話框框架,標題欄框架,狀態欄框架,通知機制,ActionBar框架等等。 經常會使用到通知機制中的通知欄框架(Notificaiton),它適用於交互事件的通知。它是位於頂層 ...
  • 結合自身的實踐開發經驗總結出了22個iOS開發的小技巧,以非常歡樂的語調輕鬆解決開發過程中所遇到的各種苦逼難題,光讀著便已忍俊不禁。 1. TableView不顯示沒內容的Cell怎麼辦? 類似於圖1,我不想讓下麵的那些空顯示。很簡單,添加“self.tableView.tableFooterVie ...
  • 0.簽名 java -Xmx2048m -jar out/host/linux-x86/framework/signapk.jar -w build/target/product/security/testkey.x509.pem build/target/product/security/test ...
  • 效果:(換膚出來一個div,選擇你想要的圖片,作為網頁背景,保存) 要點:cookie保存狀態 html代碼: css代碼: js代碼: 效果圖: ...
  • 前面的話 前端工程師最基本的工作是切圖。photoshop用的6不6,對於工作效率有很大的影響。小火柴將前端工程師需要掌握的photoshop的知識和技能進行了梳理和歸納,總結成以下目錄 目錄 前端工程師技能之photoshop巧用系列第一篇——準備篇 前端工程師技能之photoshop巧用系列第二 ...
  • × 目錄 [1]初始設置 [2]自動切圖 前面的話 隨著photoshop版本的不斷升級,軟體本身增加了很多新的功能,也為切圖工作增加了很多的便利。photoshop最新的版本新增了自動切圖功能,本文將詳細介紹photoshop的這個新功能 初始設置 當然首先還是要進行一些首選項設置 【1】在編輯 ...
  • 源碼: <input type="checkbox" id="cleckAll" />全選 <div class="list"> <input type="checkbox" />覆選一 <input type="checkbox" />覆選二 <input type="checkbox" />覆選 ...
  • Javascript小學生都知道了javascript中的函數調用時會 隱性的接收兩個附加的參數:this和arguments。參數this在javascript編程中占據中非常重要的地位,它的值取決於調用的模式。總的來說Javascript中函數一共有4中調用模式:方法調用模式、普通函數調用模式、 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...