一、JSON
1、什么是JSON
JSON(JavaScript Object Notation) 是一种轻量级的数据交换格式。易于人阅读和编写。同时也易于机器解析和生成。它基于JavaScript Programming Language, Standard ECMA-262 3rd Edition - December 1999的一个子集。
JSON是Douglas Crockford在2001年开始推广使用的数据格式,在2005年-2006年正式成为主流的数据格式,雅虎和谷歌就在那时候开始广泛地使用JSON格式。
2、JSON语法
在 JS 语言中,一切都是对象。因此,任何支持的类型都可以通过 JSON来表示,例如字符串、数字、对象、数组等。但是对象和数组是比较特殊且常用的两种类型:
- 对象表示为键值对
- 数据由逗号分隔
- 花括号保存对象
- 方括号保存数组
3、JSON键/值
JSON 键/值对 JSON 键值对是用来保存 JS 对象的一种方式,和 JS 对象的写法也大同小异,键/值对组合中的键名写在前面并用双引号 “” 包裹,使用冒号 : 分隔,然后紧接着值:
{"firstName": "Json"}
这很容易理解,等价于这条 JavaScript 语句:
{firstName : "Json"}
4、JSON与js对象关系
很多人搞不清楚 JSON 和 Js 对象的关系,甚至连谁是谁都不清楚。其实,可以这么理解:JSON 是 JS对象的字符串表示法,它使用文本表示一个 JS 对象的信息,本质是一个字符串。
var obj = {a: 'Hello', b: 'World'}; //这是一个对象,注意键名也是可以使用引号包裹的
var json = '{"a": "Hello", "b": "World"}'; //这是一个 JSON 字符串,本质是一个字符串
5、JSON与js对象互转
要实现从JSON字符串转换为JS对象,使用 JSON.parse() 方法:
var obj = JSON.parse('{"a": "Hello", "b": "World"}'); //结果是 {a: 'Hello', b: 'World'}
要实现从JS对象转换为JSON字符串,使用 JSON.stringify() 方法:
var json = JSON.stringify({a: 'Hello', b: 'World'}); //结果是 '{"a": "Hello", "b": "World"}'
6、JSON与XML比较
- 可读性: XML胜出;
- 解码难度:JSON本身就是JS对象(主场作战),所以简单很多;
- 流行度: XML已经流行好多年,但在AJAX领域,JSON更受欢迎。
7、JSON与python数据类型对应关系
python | JSON |
---|---|
dict | object |
list,tuple | array |
str,unicode | string |
int,long,float | number |
True | true |
False | false |
None | null |
8、.parse()和.stringify()
parse() 用于从一个json字符串中解析出json对象,如
var str = '{"name":"test"}'
JSON.parse(str)
//Object {name: "test"}
var c= {a:1,b:2}
JSON.stringify(c)
// '{"a":1,"b":2}'
9、python的JSON字符串处理
将字典转位JSON,
obj={'name':"test"}//(json里的字符串一定是双引号)
json.dumps(obj)
二、AJAX
1、什么是AJAX
AJAX = Asynchronous JavaScript and XML(异步的 JavaScript 和 XML)。
AJAX不是新的编程语言,而是一种使用现有标准的新方法。
AJAX最大的优点是在不重新加载整个页面的情况下,可以与服务器交换数据并更新部分网页内容。
AJAX不需要任何浏览器插件,但需要用户允许JavaScript在浏览器上执行。
同步交互:客户端发出一个请求后,需要等待服务器响应结束后,才能发出第二个请求;
异步交互:客户端发出一个请求后,无需等待服务器响应结束,就可以发出第二个请求。
2、AJAX请求流程
四步操作:
- 创建核心对象;xmlhttp
- 使用核心对象打开与服务器的连接;oepn
- 发送请求; send
- 注册监听,监听服务器响应; onreadystatechange
XMLHTTPRequest
- open(请求方式, URL, 是否异步)
- send(请求体)
- onreadystatechange,指定监听函数,它会在xmlHttp对象的状态发生变化时被调用
- readyState,当前xmlHttp对象的状态,其中4状态表示服务器响应结束
- status:服务器响应的状态码,只有服务器响应结束时才有这个东东,200表示响应成功;
- responseText:获取服务器的响应体
3、原生ajax(js实现)
views:
def ajax(request):
if request.method == "POST":
print(request.POST)
return HttpResponse("xmlhttp ok!!!")
return render(request, "ajax.html")
ajax.html:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<button onclick="aclick()">click me</button>
</body>
<script>
function aclick() {
var xmlHttp = createXMLHttpRequest();
xmlHttp.onreadystatechange = function() {
if(xmlHttp.readyState == 4 && xmlHttp.status == 200) {
alert(xmlHttp.responseText)
//var div = document.getElementById("div1");
//div.innerText = xmlHttp.responseText;
//div.textContent = xmlHttp.responseText;
}
};
xmlHttp.open("POST", "/polls/ajax", true);
xmlHttp.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');//post 需要设置请求头
xmlHttp.send("name=test"); //需要发送的数据,get写null
}
function createXMLHttpRequest() {
var xmlHttp;
// 适用于大多数浏览器,以及IE7和IE更高版本
try{
xmlHttp = new XMLHttpRequest();
} catch (e) {
// 适用于IE6
try {
xmlHttp = new ActiveXObject("Msxml2.XMLHTTP");
} catch (e) {
// 适用于IE5.5,以及IE更早版本
try{
xmlHttp = new ActiveXObject("Microsoft.XMLHTTP");
} catch (e){}
}
}
return xmlHttp;
}
</script>
</html>
服务端运行代码结果
“GET /polls/ajax HTTP/1.1” 200 1462
<QueryDict: {‘name’: [‘test’]}>
4、$.get() & $.post()
<1>$.get(url, [data], [callback], [type])
<2>$.post(url, [data],[callback], [type]) //type: text|html|json|script
function aclick() {
//$.get...
$.post('/polls/ajax', {type: 1}, function (data, callbacktype, jqXHR) {
console.log(data);//将json字符串解析成json对象
console.log(callbacktype); //返回的结果
console.log(jqXHR); //返回的对象
});
}
服务端运行结果:
"GET /polls/ajax HTTP/1.1" 200 1866
<QueryDict: {'type': ['1']}>
5、$getJSON()
. g e t J S O N ( ) 与 .getJSON() 与 .getJSON()与.get()是一样的,只不过就是做后一个参数type必须是json数据了。一般同域操作用 . g e t ( ) 就 可 以 , .get()就可以, .get()就可以,.getJson最主要是用来进行jsonp跨域操作的。
6、$getSscript()
运行时再加载javascript,不用页面载入时浪费没必要的资源
function testGetScript() {
// alert(testFun(3, 4));
$.getScript('test.js', function () {
alert(add(1, 6));
});
}
// test.js
function add(a,b){
return a+b
}
7、$.ajax()
1. 方式一:
function aclick() {
$.ajax(
{
url: "/polls/ajax",
type: "POST",
data: {a: 1, b: "test"},
//troditional:true, 如果data里有[1,2]类似的数组需要迭代加这个
//processData: false, 让data不做处理,发送字节
}
)
}
服务端运行结果:
"GET /polls/ajax HTTP/1.1" 200 2133
<QueryDict: {'a': ['1'], 'b': ['test']}>
2. 方式二:
$.ajax('/callbackajax', {
success: function (data) {
console.log(arguments);
},
error: function (jqXHR, textStatus, err) {
// jqXHR: jQuery增强的xhr
// textStatus: 请求完成状态
// err: 底层通过throw抛出的异常对象,值与错误类型有关
console.log(arguments);
},
complete: function (jqXHR, textStatus) {
// jqXHR: jQuery增强的xhr
// textStatus: 请求完成状态 success | error
console.log('statusCode: %d, statusText: %s', jqXHR.status, jqXHR.statusText);
console.log('textStatus: %s', textStatus);
},
statusCode: {
'403': function (jqXHR, textStatus, err) {
console.log(arguments); //注意:后端模拟errror方式:HttpResponse.status_code=500
},
'400': function () {
}
}
});
三、跨域请求
1、同源策略机制&什么是跨域
同源策略限制了从一个源加载的文档或脚本如何与来自另一个源的资源进行交互。这是一个用于隔离潜在恶意文件的关键的安全机制。同源指的是同协议、同域名且同端口。
2、JSONP的原理
JSONP的主要原理是,
3、CORS的原理
基本思想是使用自定义的HTTP头部让浏览器与服务器进行沟通,从而决定请求或响应是应该成功还是失败。CORS 需要客户端和服务器同时支持。目前,所有浏览器都支持该机制,会自动添加对应首部进行协商。
CORS分为两种情况,分为简单请求和非简单请求,
- 若请求满足所有下述条件,则该请求可视为“简单请求”:
使用下列方法之一:
GET
HEAD
POST
Fetch 规范定义的对 CORS 安全的首部字段集合,不得人为设置该集合之外的其他首部字段。该集合为:
Accept
Accept-Language
Content-Language
Content-Type (需要注意额外的限制)
DPR
Downlink
Save-Data
Viewport-Width
Width
Content-Type 的值属于下列之一:
application/x-www-form-urlencoded
multipart/form-data
text/plain
2.非简单请求
浏览器会自动使用OPTIONS方法发起一个预检请求到服务器,以获知服务器是否允许该实际请求。该预检请求中包含有origin、Access-Control-Request-Method、Access-Control-Request-Headers分别说明源站URI、实际请求的方法、实际请求所携带的首部字段。
服务器收到预检请求后检查origin、Access-Control-Request-Method、Access-Control-Request-Headers字段后,回复一个带有Access-Control-Allow-Origin、Access-Control-Allow-Methods、Access-Control-Allow-Headers说明服务器对应允许跨域访问的URI、请求方法以及请求头部字段。
服务器通过了"预检"请求之后,基本和简单请求一样。浏览器每次请求带上origin字段,服务器回应带上Access-Control-Allow-Origin。
4、jsonp的js实现(1)
JSONP就像是JSON+Padding一样(Padding这里我们理解为填充)
IP1服务器上的views:
def test(request):
print('hello jsonp')
return render(request,'index.html')
IP1服务器上的index.html:
<h1>JSONP</h1>
<script>
function fun1(arg){
alert("hello"+arg)
}
</script>
<script src="http://192.168.1.101:8002/jsonp/"></script>//返回的是一个js函数方法fun1('server2 data')
IP2服务器上的views:
def jsonp(req):
print('server 192.168.1.102')
return HttpResponse('fun1("server2 data")')
这其实就是JSONP的简单实现模式,或者说是JSONP的原型:创建一个回调函数,然后在远程服务上调用这个函数并且 将JSON 数据形式作为参数传递,完成回调。
将JSON数据填充进回调函数,这应该就是JSONP的JSON+Padding的含义。
5、jsonp的js实现(2)
<button onclick="f()">submit</button>
<script>
function addScriptTag(src){
var script = document.createElement('script');
script.setAttribute("type","text/javascript");
script.src = src;
document.body.appendChild(script);
document.body.removeChild(script);
}
function fun1(arg){
alert("hello"+arg)
}
function f(){
addScriptTag("http://192.168.1.102/jsonp")
}
</script>
6、jsonp的js实现(3)
index.html:
<button onclick="f()">submit</button>
<script>
function addScriptTag(src){
var script = document.createElement('script');
script.setAttribute("type","text/javascript");
script.src = src;
document.body.appendChild(script);
document.body.removeChild(script);
}
function SayHi(arg){
alert("Hello "+arg)
}
function f(){
addScriptTag("http://192.168.1.102/jsonp/?callbacks=test")
}
</script>
views:
def jsonp(req):
func=req.GET.get("callbacks")
return HttpResponse("%s('test')"%func)
7、jQuery的实现
index.html:
<script type="text/javascript">
$.ajax({
url:"http://92.168.1.102/jsonp",
dataType:"jsonp", //由之前json类型改成jsonp
jsonp: 'callbacks', //随机生成字典{“callbacks":"test"}传向服务器
success:function(data){
alert(data)
}
});
</script>
views:
def jsonp(req):
callbacks=req.GET.get('callbacks')
print(callbacks)
return HttpResponse("%s('test')"%callbacks)