1.什么是AJAX
Asynchronous Javascript And Xml
異步的 JS 和 xml(*EX*tensible *M*arkup *L*anguage)
通過(guò) JS 異步的向服務(wù)器發(fā)送請(qǐng) 求并接收響應(yīng)數(shù)據(jù)
同步訪問(wèn):
當(dāng)客戶端向服務(wù)器發(fā)送請(qǐng)求時(shí)填渠,服務(wù)器在處理的過(guò)程中冠胯,瀏覽器只能等待回季,效率較低
異步訪問(wèn):
當(dāng)客戶端向服務(wù)器發(fā)送請(qǐng)求時(shí),服務(wù)器在處理的過(guò)程中现拒,客戶端可以做其他的操作,不需要一直等待
AJAX優(yōu)點(diǎn):
1.異步訪問(wèn)
2.局部刷新
使用場(chǎng)合:
1.搜索建議
2.表單驗(yàn)證
3.前后端分離
2.AJAX核心對(duì)象 - 異步對(duì)象(XMLHttpRequest)
1.什么是XMLHttpRequest [簡(jiǎn)稱為 xhr]
稱為 "異步對(duì)象"肛根,代替瀏覽器向服務(wù)器發(fā)送異步的請(qǐng)求并接收響應(yīng)
[xhr 是由JS來(lái)提供的]
2.創(chuàng)建 異步對(duì)象 (xhr)
1.IE7+,Chrome,Firefox,Safari,Opera) -> 調(diào)用 XMLHttpRequest 生成 xhr對(duì)象
2.IE低版本瀏覽器中(IE6以及以下) -> 調(diào)用 ActiveXObject() 生成xhr
<script>
if(window.XMLHttpRequest){
//支持 XMLHttpRequest
var xhr = new XMLHttpRequest();
}else{
//不支持XMLHttpRequest,使用 ActiveXObject 創(chuàng)建異步對(duì)象
var xhr = new ActiveXObject("Microsoft.XMLHTTP");
}
</script>
3.xhr 的成員
1.方法 - open()
作用:創(chuàng)建請(qǐng)求
語(yǔ)法:open(method,url,asyn)
參數(shù):
method:請(qǐng)求方式,取值'GET' 或 'POST'
url:請(qǐng)求地址粉渠,字符串
asyn:是否采用異步的方式 - true:異步 / false:同步
ex: xhr.open('GET','/server',true);
2.方法 - send()
作用:通知xhr向服務(wù)器端發(fā)送請(qǐng)求
語(yǔ)法:send(body)
參數(shù):
GET請(qǐng)求:body的值為null -> send(null)
POST請(qǐng)求:body的值為請(qǐng)求數(shù)據(jù) -> send("請(qǐng)求數(shù)據(jù)")
3.屬性 - readyState
作用:xhr狀態(tài),通過(guò)不同的xhr狀態(tài)來(lái)表示xhr與服務(wù)器的交互情況
由0-4共5個(gè)值來(lái)表示5個(gè)不同的狀態(tài)
狀態(tài) | 說(shuō)明 |
---|---|
0 | 代理被創(chuàng)建圾另,但尚未調(diào)用 open() 方法霸株。 |
1 |
open() 方法已經(jīng)被調(diào)用。 |
2 |
send() 方法已經(jīng)被調(diào)用集乔,響應(yīng)頭也已經(jīng)被接收 |
3 | 下載中去件; responseText 屬性已經(jīng)包含部分?jǐn)?shù)據(jù)。 |
4 | 下載操作已完成 |
4.屬性 - responseText
作用:響應(yīng)數(shù)據(jù)
5.屬性 - status
作用:服務(wù)器端的響應(yīng)狀態(tài)碼
狀態(tài)嗎 | 說(shuō)明 |
---|---|
200 | 表示服務(wù)器正確處理所有的請(qǐng)求以及給出響應(yīng) |
404 | 請(qǐng)求資源不存在 |
500 | 服務(wù)器內(nèi)部錯(cuò)誤 |
6.事件 - onreadystatechange
作用:每當(dāng)xhr的readyState發(fā)生改變的時(shí)候都要觸發(fā)的操作扰路;
也稱作回調(diào)函數(shù)尤溜;當(dāng)readyState的值為4且status值為200的時(shí)候,才可以獲取響應(yīng)數(shù)據(jù)
3.AJAX的操作步驟
1.GET請(qǐng)求
//1.創(chuàng)建xhr請(qǐng)求
var xhr = createXhr();
//2.創(chuàng)建請(qǐng)求 - open()
xhr.open('GET',url,asyn[true|false])
//3.設(shè)置回調(diào)函數(shù) - onreadystatechange
xhr.onreadystatechange = function(){
if(xhr.readyState == 4 && xhr.status == 200){
//接收響應(yīng)
xhr.responseText;
}
}
//4.發(fā)送請(qǐng)求
xhr.send(null);
//注意:若含有請(qǐng)求參數(shù) - URL后拼接 查詢字符串 QueryString
//ex: xhr.open('get','/url?key=value&key=value',asyn)
2.POST請(qǐng)求
//1.創(chuàng)建xhr請(qǐng)求
var xhr = createXhr();
//2.創(chuàng)建請(qǐng)求 - open()
xhr.open('post',url,asyn[true|false])
//3.設(shè)置回調(diào)函數(shù) - onreadystatechange
xhr.onreadystatechange = function(){
if(xhr.readyState == 4 && xhr.status == 200){
//接收響應(yīng)
xhr.responseText;
}
}
//4設(shè)置Content-Type;
//默認(rèn)ajax post的Content-Type為 "text/plain;charset=utf-8"
xhr.setRequestHeader('Content-Type','application/x-www-form-urlencoded');
//5.發(fā)送請(qǐng)求
xhr.send('請(qǐng)求數(shù)據(jù)');
//請(qǐng)求數(shù)據(jù)同查詢字符串 "uname=guoxiaonao&age=18"
注意:django中post需要傳遞csrf_token,否則觸發(fā)響應(yīng)碼403汗唱,拒絕訪問(wèn)宫莱;
獲取csrf_token方法如下
var csrf=$("[name='csrfmiddlewaretoken']").val();
#獲取后,將token放在post body數(shù)據(jù)中一并提交
2.jquery對(duì) ajax 的支持
$.ajax({})
參數(shù)對(duì)象中的屬性:
1.url : 字符串哩罪,表示異步請(qǐng)求的地址
2.type : 字符串授霸,請(qǐng)求方式,GET 或 POST
3.data : 傳遞到服務(wù)器端的參數(shù)
可以是字符串 :"name=sf.zh&age=18"
也可以是js對(duì)象:
{
name:"sf.zh",
age:18
}
4.dataType : 字符串际插,響應(yīng)回來(lái)的數(shù)據(jù)的格式
1.'html'
2.'xml'
3.'text'
4.'script'
5.'json'
6.'jsonp' : 有關(guān)跨域的響應(yīng)格式
5.success:回調(diào)函數(shù)碘耳,請(qǐng)求和響應(yīng)成功時(shí)回來(lái)執(zhí)行的操作
6.error : 回調(diào)函數(shù),請(qǐng)求或響應(yīng)失敗時(shí)回來(lái)執(zhí)行的操作
7.beforeSend : 回調(diào)函數(shù)框弛,發(fā)送ajax請(qǐng)求之前執(zhí)行的操作藏畅,如果return false,則終止請(qǐng)求
8.contentType : 當(dāng)有請(qǐng)求體有數(shù)據(jù)提交時(shí)功咒,標(biāo)明提交方式愉阎,默認(rèn)值為'application/x-www-form-urlencoded; charset=UTF-8'
3.JSON
1.JSON介紹
JSON:JavaScript Object Notation
定義:是一種輕量級(jí)的數(shù)據(jù)交換格式。JS的一個(gè)語(yǔ)法子集力奋;采用完全獨(dú)立于編程語(yǔ)言的文本格式來(lái)存儲(chǔ)和表示數(shù)據(jù)榜旦。簡(jiǎn)潔和清晰的層次結(jié)構(gòu)使得 JSON 成為理想的數(shù)據(jù)交換語(yǔ)言。 易于人閱讀和編寫景殷,同時(shí)也易于機(jī)器解析和生成溅呢,并有效地提升網(wǎng)絡(luò)傳輸效率。
場(chǎng)景:在ajax中猿挚,允許將 復(fù)雜格式的響應(yīng)數(shù)據(jù) 構(gòu)建成 JSON的格式再進(jìn)行響應(yīng)
2.JSON表現(xiàn)
1.JSON表示單個(gè)對(duì)象
1.使用 {} 表示單個(gè)對(duì)象
2.在 {} 中使用 key:value 的形式來(lái)表示屬性(數(shù)據(jù))
3.Key必須要用 " " 引起來(lái)
4.value如果是字符串的話咐旧,也需要用" "引起來(lái)
var obj = {
"name":"王老師",
"age" : 30,
"gender" : "Unknown"
}
2.JSON表示一個(gè)數(shù)組
1.使用 [] 表示一個(gè)數(shù)組
2.數(shù)組中允許包含若干JSON對(duì)象 或 字符串
1.使用JSON數(shù)組表示若干字符串
var arr = ["王偉超","王夫人","王小超"];
2.使用JSON數(shù)組表示若干對(duì)象
var arr = [
{
"name":"王老師",
"age":30,
"gender":"男"
},
{
"name":"王夫人",
"age":28,
"gender":"男"
}
];
3.使用 jq 的 each() 迭代數(shù)組
回顧 JS中遍歷數(shù)組
var a = [{"name":"guoxiaonao", "age": 18 }, {"name":"guoxiaonao2", "age": 22}];
for (var i = 0 ; i < a.length ; i++ ){
var obj = a[i];
console.log('name is ' + obj.name);
console.log('age is '+ obj.age);
}
1.$(arr).each();
$arr : jQuery中的數(shù)組
//語(yǔ)法:
$(arr).each(function(index,obj){
index:遍歷出來(lái)的元素的下標(biāo)
obj:遍歷出來(lái)的元素
});
2.$.each()
//語(yǔ)法:
$.each(arr,function(index,obj){});
arr : js 中的普通數(shù)組
4.后臺(tái)處理JSON
在后臺(tái)查詢出數(shù)據(jù)再轉(zhuǎn)換為JSON格式的字符串,再響應(yīng)給前端
1.后臺(tái)先獲取數(shù)據(jù)
類型允許為:元組|列表|字典
2.在后臺(tái)將數(shù)據(jù)轉(zhuǎn)換為符合JSON格式的字符串
3.在后臺(tái)將JSON格式的字符串進(jìn)行響應(yīng)
5.Python中的JSON處理
import json
#序列化 - python對(duì)象變?yōu)閖son字符串
jsonStr = json.dumps(元組|列表|字典)
#反序列化 - json字符串變?yōu)閜ython對(duì)象
py_obj = json.loads(jsonStr)
Django中的JSON處理
#方法1 使用Django中提供的序列化類來(lái)完成QuerySet到JSON字符串的轉(zhuǎn)換
from django.core import serializers
json_str = serializers.serialize('json',QuerySet)
return HttpResponse(json_str)
#方法2
d = {'a': 1}
return JsonResponse(d)
6.前端中的JSON處理
#序列化
JSON字符串JSON.stringify(JSON對(duì)象)
#反序列化
JSON對(duì)象=JSON.parse(JSON字符串)
練習(xí):
1绩蜻,頁(yè)面點(diǎn)擊摁鈕 铣墨, 發(fā)送ajax 請(qǐng)求至后端獲取用數(shù)據(jù)
2,將后端返回的用戶數(shù)據(jù)顯示至頁(yè)面
4,跨域
1办绝,什么是跨域
跨域:非同源的網(wǎng)頁(yè)伊约,相互發(fā)送請(qǐng)求的過(guò)程姚淆,就是跨域
瀏覽器的同源策略:
同源:多個(gè)地址中,相同協(xié)議屡律,相同域名腌逢,相同端口被視為是"同源"
在HTTP中,必須是同源地址才能互相發(fā)送請(qǐng)求超埋,非同源拒絕請(qǐng)求(<script>和<img>除外)搏讶。
http://www.tedu.cn/a.html
http://www.tedu.cn/b.html
以上地址是 "同源"
http://www.tedu.cn/a.html
https://www.tedu.cn/b.html
由于 協(xié)議不同 ,所以不是"同源"
http://localhost/a.html
http://127.0.0.1/a.html
由于 域名不同 霍殴,所以不是"同源"
http://www.tedu.cn:80/a.html
http://www.tedu.cn:8080/b.html
由于端口不同 媒惕, 所以不是"同源"
2,解決方案
通過(guò) <script> 向服務(wù)器資源發(fā)送請(qǐng)求
由服務(wù)器資源指定前端頁(yè)面的哪個(gè)js方法來(lái)執(zhí)行響應(yīng)的數(shù)據(jù)
3, jquery 的跨域
jsonp - json with padding
用戶傳遞一個(gè)callback參數(shù)給服務(wù)端繁成,然后服務(wù)端返回?cái)?shù)據(jù)時(shí)會(huì)將這個(gè)callback參數(shù)作為函數(shù)名來(lái)包裹住JSON數(shù)據(jù)
ex:
當(dāng)前地址: http://127.0.0.1:8000/index
欲訪問(wèn)地址: http://localhost:8000/data?callback=xxx
$.ajax({
url:'xxx',
type:'get',
dataType:'jsonp',//指定為跨域訪問(wèn)
jsonp:'callback',//定義了callback的參數(shù)名吓笙,以便獲取callback傳遞過(guò)去的函數(shù)名
jsonpCallback:'xxx' //定義jsonp的回調(diào)函數(shù)名
});
$.ajax({
url:'xxx',
type:'get',
dataType:'jsonp',//指定為跨域訪問(wèn)
success: function(data){}
});