前端websocket框架。
常見的URL舉例:
http://www.baidu.com
http://www.taobao.com
http://www.cnblogs.com/liulongbinblogs/p/11649393.html
URL地址一般由三部組成:
① 客戶端與服務器之間的通信協議
② 存有該資源的服務器名稱
③ 資源在服務器上具體的存放位置
跨域是設置前端還是設置后端。
注意:
post跨域,客戶端與服務器之間的通信過程,分為 請求 – 處理 – 響應 三個步驟。
網頁中的每一個資源,都是通過 請求 – 處理 – 響應 的方式從服務器獲取回來的。
面試題:從輸入URL到頁面展示,這中間發生了什么
[外鏈圖片轉存失敗,源站可能有防盜鏈機制,建議將圖片保存下來直接上傳(img-UiNaRme9-1631186210983)(.\images\dns.png)]
socketjs?渲染流程: 特別耗性能 。框架 使用 虛擬dom
構建 DOM 樹
輸入:HTML 文檔;
處理:HTML 解析器解析;
輸出:DOM 數據解構。
樣式計算
輸入:CSS 文本;
處理:屬性值標準化,每個節點具體樣式(繼承、層疊);
輸出:styleSheets(CSSOM)。
布局(DOM 樹中元素的計劃位置)
DOM & CSSOM 合并成渲染樹;
布局樹(DOM 樹中的可見元素);
布局計算。
分層
特定節點生成專用圖層,生成一棵圖層樹(層疊上下文、Clip,類似 PhotoShop 里的圖層);
擁有層疊上下文屬性(明確定位屬性、透明屬性、CSS 濾鏡、z-index 等)的元素會創建單獨圖層;
沒有圖層的 DOM 節點屬于父節點圖層;
需要剪裁的地方也會創建圖層。
繪制指令
輸入:圖層樹;
渲染引擎對圖層樹中每個圖層進行繪制;
拆分成繪制指令,生成繪制列表,提交到合成線程;
輸出:繪制列表。
分塊
合成線程會將較大、較長的圖層(一屏顯示不完,大部分不在視口內)劃分為圖塊(tile, 256256, 512512)。
光柵化(柵格化)
在光柵化線程池中,將視口附近的圖塊優先生成位圖(柵格化執行該操作);
快速柵格化:GPU 加速,生成位圖(GPU 進程)。
合成繪制
繪制圖塊命令——DrawQuad,提交給瀏覽器進程;
瀏覽器進程的 viz 組件,根據DrawQuad命令,繪制在屏幕上。
傳輸完畢,渲染進程會發出“確認提交”消息給瀏覽器進程。
js跨域請求的三種方法、瀏覽器在接收到“確認提交”消息后,更新瀏覽器界面狀態(包括地址欄信息,仟前進后退歷史,web頁面和網站安全狀態)。
頁面此時可能還沒有渲染完畢,而一旦渲染完畢,渲染進程會發送一個消息給瀏覽器進程,瀏覽器接收到這個消息后會停止標簽圖標的加載動畫。
自此,一個完整的頁面形成了。
websocket跨域推送數據。如果要在網頁中請求服務器上的數據資源,則需要用到 XMLHttpRequest 對象。
XMLHttpRequest(簡稱 xhr)是瀏覽器提供的 js 成員,通過它,可以請求服務器上的數據資源。
最簡單的用法 var xhrObj = new XMLHttpRequest()
Ajax 的全稱是 Asynchronous Javascript And XML(異步 JavaScript 和 XML)。
通俗的理解:Ajax使用XMLHttpRequest對象與服務器端腳本進行通信,支持“異步”通信
面試題: 背下來 ***
js跨域請求。1.打開瀏覽器,發送請求
2.向地址欄輸入地址
3.回車提交
4.等待服務器返回數據,并且接收
5.渲染到頁面上
需要使用的知識點:
Open方法 打開某個鏈接 需定義三個參數
xhr.open("GET","test1.txt",true);
三個參數的含義
1、提交方式 Form-method
2、提交地址 Form-action
3、異步(同步)默認為true 表示是異步請求
Send方法
發送數據請求,相當于Form的submit
請求狀態監控
onreadystatechange事件
readyState屬性:請求狀態
0 (未初始化)還沒有調用open()方法
1 (載入)已調用send()方法,正在發送請求
2 (載入完成)send()方法完成,已收到全部響應內容
3 (解析)正在解析響應內容
4 (完成)響應內容解析完成,可以在客戶端調用了
status屬性:服務器(請求資源)的狀態
返回的內容
responseText:返回以文本形式存放的內容
responseXML:返回XML形式的內容
完整流程
<button id="btn">點擊獲取數據</button><div id="con"></div><script>window.onload = function () {//獲取dom節點var oBtn = document.getElementById("btn");var oCon = document.getElementById("con");//綁定事件oBtn.onclick = function () {// 1.使用 XMLHttpRequest 創建 ajax對象//創建 ajax對象var xhr = new XMLHttpRequest();// 2.向地址欄輸入地址 使用 open函數設置請求方式,請求地址,是否異步//打開瀏覽器,設置 請求方式,請求地址,是否異步xhr.open("get", "./user.json", true);// 3.回車提交 使用 send發送請求xhr.send();// 4.綁定 onreadystatechange 事件 ,等待服務器返回數據, 并且接收//綁定 onreadystatechange 事件 ,當 url請求的狀態值發生變化時會觸發這個事件xhr.onreadystatechange = function () {if (xhr.readyState == 4) {//數據已經從 服務器端返回了//接收數據var data = xhr.responseText;//console.log( data);// 5.需要將 字符串轉json對象,渲染到頁面上//需要將 字符串轉json對象var datajson = JSON.parse(data);console.log(datajson);oCon.innerHTML = `<span>名字:${datajson.name}</span><span>年齡:${datajson.age}</span>`;}}}}</script>
拋出異常處理:
var aa = 12;
//代碼不想報錯,然后又想知道有沒有錯誤,錯誤是什么,就可以使用 捕獲異常
try {alert(a);
} catch (e) {//捕獲異常console.log(e);
}
ajax ie瀏覽器兼容性處理,使用拋出異常
try {var xhr = new XMLHttpRequest();
} catch (e) {var xhr = ActiveXObject("Microsoft.XMLHTTP");//ie低版本
}
a.安裝 phpstudy
b.打開面板后,左側選擇網站,打開面板后左上角有個創建網站按鈕,點擊后創建新站點,
c.將準備好的php文件拷貝進去
d.啟動 Apache服務器
<button id="btn">點擊獲取數據</button>
<div id="con"></div>
<script>window.onload = function () {var oBtn = document.getElementById("btn");var oCon = document.getElementById("con");oBtn.onclick = function () {var xhr = new XMLHttpRequest();//get傳參xhr.open("get", "./get.php?user=lili&pwd=123456", true);xhr.send();xhr.onreadystatechange = function () {if (xhr.readyState == 4) {//數據已經從 服務器端返回了var data = xhr.responseText;console.log(data);oCon.innerHTML = `<span>${data}</span>`;}}}}//注意:本實例,需要使用 php 的服務器才能解析 get.php的文件//打開小皮,啟動 Apache//在瀏覽器輸入:http://127.0.0.1/04-ajax-get.html
get方式的數據提交服務器一般跟在url的后面,get方式提交的數據有大小限制
- **Firefox** 3.0.3: 當$len 賦值為4053時出錯,可見最長字長4098
- IE7.0: 2083, 結果與官方說法一致
- Opera 9.60: 4098 , **Firefox**3.0.3 相同
- google chrome 0.2.149.30: 4098, 與**Firefox**3.0.3,Opera 9.60相同
xhr.open('get','get.php?user=qqq&pwd=123456',true);
優點:1.使用 頭部將post數據提交到 服務端,不會顯示在 地址欄,更安全;2.post方式傳輸的數據量不限制
? post 數據加密了么? 沒加密
? 加密:1.使用 MD5、sha1 、對稱加密、非對稱加密 (手動寫)
? 2.https協議
xhr.open('post','post.php',true);
xhr.setRequestHeader('content-type','application/x-www-form-urlencoded');
//3.回車提交
xhr.send('user=lili&pwd=123456');
各位同學,發現了沒有,ajax的好多代碼都是固定格式的,所以,我們需要把他封裝一下,以方便我們后期調用。
//參數:
method 請求方式
url 請求地址
success 回調函數
data 帶給 服務端的數據
type 同步還是異步
ajax.js
//參數:
// method 請求方式 string
// url 請求地址 string
// success 回調函數 function
// data 帶給 服務端的數據 string
// type 同步還是異步 boolean
function ajax(method, url, data, success, type) {//1.創建 xml 對象try {var xhr = new XMLHttpRequest();} catch (e) {var xhr = ActiveXObject("Microsoft.XMLHTTP");}xhr.open(method, url, type);//判斷請求方式if (method == "get") {xhr.send();} else {xhr.setRequestHeader("content-type", "application/x-www-form-urlencoded");xhr.send(data);}//綁定事件xhr.onreadystatechange = function () {//判斷 數據是不是正常傳回來了if (xhr.readyState == 4) {//保險 status == 200 服務器端正常返回if (xhr.status == 200) {success && success(xhr.responseText);} else {alert("訪問出錯");}}}
}
調用:
<button id="btn">點擊獲取數據</button><div id="con"></div><script src="./ajax.js"></script><script>window.onload = function () {var oBtn = document.getElementById("btn");var oCon = document.getElementById("con");oBtn.onclick = function () {//function ajax(method, url, data, success, type) ajax("get", "./getNews.php", "", function (data) {console.log(data);var datajson = JSON.parse(data);str = "";datajson.forEach((item, index) => {str += `<p >${item.title} - ${item.date}</p>`;})oCon.innerHTML = str;}, true);}}</script>
表單 即form,可以向服務器提交數據,比如:提交用戶信息
實例:
get:
<form action="get.php" method="get"><!-- 表單提交時,表單項一定要寫name get方式 數據是在url后面傳輸到服務端的,大小有限制,不安全--><input type="text" name="user" id="" /><input type="password" name="pwd" id="" /><button type="submit">提交表單</button></form>
post:
<form action="post.php" method="post"><!-- 表單提交時,表單項一定要寫name post方式 數據是在傳輸包的頭部傳輸到服務端的 ,大小無限制,和get相比更安全--><input type="text" name="user" id="" /><input type="password" name="pwd" id="" /><button type="submit">提交表單</button></form>
瀏覽器中提供的 XMLHttpRequest 用法比較復雜,所以 jQuery 對 XMLHttpRequest 進行了封裝,提供了一系列 Ajax 相關的函數,極大地降低了 Ajax 的使用難度。
jQuery 中發起 Ajax 請求最常用的三個方法如下:
jQuery 中 $.get() 函數的功能單一,專門用來發起 get 請求,從而將服務器上的資源請求到客戶端來進行使用。
$.get() 函數的語法如下:
$.get(url,[data],[callback])
參數:
//get方式獲取
$.get('film.json',function(data){console.log(data);
})
$(function () {$.ajax({type: "post",url: "http://www.51houniao.com/requirement/request/getMatchedProducts",data: JSON.stringify({desc: false,orderBy: "outtime",product_type: 2,pageSize: 100}),//候鳥的后臺不支持 對象形式的參數contentType: "application/json;charset=UTF-8",//設置頭部success: function (data) {console.log(data);}})})
//getJSON 專門獲取json數據的
$.getJSON('film.json',function(data){console.log(data);
});
5.4 $.ajax() 函數
相比于 $.get() 和 $.post() 函數,jQuery 中提供的 $.ajax() 函數
$.ajax({type:"get",//獲取數據的方式 get post url:"film.json",//url地址 如果訪問的是php,那么請打開php的服務器 必選async:true,//異步data:"",//獲取數據時的傳參dataType:"json",//返回值類型 jsonp 支持跨域 success:function(data){//成功的回調函數 必選console.log(data);//jquery返回的數據不需要解析var data = data.data.films;for(var i = 0;i<data.length;i++){var $li = $('<li>'+data[i].name+'</li>');$('#con').append($li);}},error:function(e){console.log(e);}
})
因為 ,瀏覽器同源策略,增加安全性,同源策略又叫同域(域名)策略
只有同一個域名下的數據可以相互訪問,不同域名下進行相互之間訪問時就會被組織,提示你蛞蝓了,子域名不一樣與會存在跨域問題
1.在同一個公司 ,163 ,做不同業務的需要的子域名不一樣,解決跨域問題
2.爬取其他網站的數據, 需要解決跨域問題
注意:微信 用戶不需要考慮跨域問題,ios、安卓沒有跨域問題
出于瀏覽器的同源策略限制。**同源策略**(Sameoriginpolicy)是一種約定,它是瀏覽器最核心也最基本的安全功能,如果缺少了同源策略,則瀏覽器的正常功能可能都會受到影響。可以說Web是構建在同源策略基礎之上的,瀏覽器只是針對同源策略的一種實現。同源策略會阻止一個域的javascript腳本和另外一個域的內容進行交互。所謂同源(即指在同一個域)就是兩個頁面具有相同的協議(protocol),主機(host)和端口號(port)
當一個請求url的協議、域名、端口三者之間任意一個與當前頁面url不同即為跨域
【1】無法讀取非同源網頁的 Cookie、LocalStorage 和 IndexedDB
【2】無法接觸非同源網頁的 DOM
【3】無法向非同源地址發送 AJAX 請求 ***
跨域實例:
演示跨域
<script src="./js/jquery.min.js"></script>
<script>$(function () {$.get("http://127.0.0.1/getNews.php", "", function (data) {console.log(data);});})//實例,需要在 vscode中點擊右鍵菜單打開//打開的地址:http://127.0.0.1:5501/01-ajax-kuayu.html//http://127.0.0.1:5501 請求 http://127.0.0.1/getNews.php ,所以產生了跨域/*報錯:Access to XMLHttpRequest at 'http://127.0.0.1/getNews.php' from origin 'http://127.0.0.1:5501' has been blocked by CORS policy: No 'Access-Control-Allow-Origin' header is present on the requested resource.*/
</script>
2.運行程序,會看到跨域
3.在瀏覽器-開發者工具中會看到
已攔截跨源請求:同源策略禁止讀取位于 http://127.0.0.1:8888/getNews.php 的遠程資源。(原因:CORS 頭缺少 'Access-Control-Allow-Origin')。
說明跨域了
解決跨域的常用方式有以下幾種:
這種前端工程師了解即可
1.原生解決跨域問題的原理
js跨域的原理<script>function success(data) {console.log("拿到數據了");console.log(data);}</script><script>success({ name: "lili", age: 18 })</script>
getdata.js
success({ name: "lili", age: 18 })
html
<!-- script 標簽的 src屬性 天生具備跨域能力 --><script src="https://cdn.jsdelivr.net/npm/axios/dist/axios.min.js"></script><script>function success(data) {console.log("拿到數據了");console.log(data);}</script><script src="./js/getdata.js?callback=success"></script><!-- callback=success 就相當于 success({ name: "lili", age: 18 }) -->
原生js解決跨域問題
/*1. script標簽的src屬性 天生就具備 跨域能力2.js原生跨域必須后臺代碼支持*/window.onload = function () {//創建 script標簽var oScript = document.createElement("script");oScript.src = "http://127.0.0.1/getNewsjs.php?callback=success";var oHeader = document.getElementsByTagName('head')[0];oHeader.appendChild(oScript);}function success(data) {console.log(data);}
百度搜索的實例
<input type="text" name="word" id="word" placeholder="請輸入想要搜索的內容" /><button id="btn">搜索</button><div id="con"></div><script>var oCon = document.getElementById("con");//https://sp0.baidu.com/5a1Fazu8AA54nxGko9WTAnF6hhy/su?wd=js&cb=JSON_yy//需求:輸入關鍵字,點擊 按鈕搜索內容window.onload = function () {//1.獲取domvar oBtn = document.getElementById("btn");var oWord = document.getElementById("word");//2.綁定事件oBtn.onclick = function () {//3.獲取文本框內容var txt = oWord.value;//4.跨域獲取 百度搜索的數據//4.1 創建 標簽var oScript = document.createElement("script");oScript.src = "https://sp0.baidu.com/5a1Fazu8AA54nxGko9WTAnF6hhy/su?wd=" + txt + "&cb=success";//cb 因為 咱百度的后臺工程師定義的接收變量的可以是 cbvar oHead = document.getElementsByTagName("head")[0];oHead.appendChild(oScript);}}function success(data) {console.log(data);var str = "";data.s.forEach(item => {str += `<p>${item}</p>`;})oCon.innerHTML = str;}</script>
<script src="./js/jquery.min.js"></script><script>$(function () {$.ajax({type: "get",url: "http://127.0.0.1/getNewsjs.php",data: "",async: true,dataType: "jsonp",//表示支持跨域 ,success: function (data) {console.log(data);},error: function (err) {console.log(err);}})})//jquery 跨域的原理:和js的跨域的原理一樣,只不過,咱jquery工程師,將 js的跨域封裝到了 dataType: "jsonp"</script>
手寫promise
var pro = new Promise(function(resolve, reject){setTimeout(function(){//resolve('success');reject('fail');}, 2000);});pro.then(function(res){//接收成功的數據console.log(res);}, function(err){//接收失敗的數據console.log(err);})
ajax在使用的時候,如果是多個數據請求,容易產生地獄回調問題,可以使用 promise解決
例如:
$(function () {$.getJSON('./json/01.json', function (data) {console.log(data);var list = data.matchedProducts;for (var i = 0; i < list.length; i++) {var $li = $(`<li>${list[i].collection_num} - ${list[i].pro_title}</li>`);$('#list').append($li);}//調用 第二頁數據$.getJSON('./json/02.json', function (data) {console.log(data);var list = data.matchedProducts;for (var i = 0; i < list.length; i++) {var $li = $(`<li>${list[i].collection_num} - ${list[i].pro_title}</li>`);$('#list').append($li);}//調用 第三頁數據$.getJSON('./json/03.json', function (data) {console.log(data);var list = data.matchedProducts;for (var i = 0; i < list.length; i++) {var $li = $(`<li>${list[i].collection_num} - ${list[i].pro_title}</li>`);$('#list').append($li);}})})})})
以上實例,可以使用promise解決
$(function () {function getJson(page) {//創建peomise對象var p = new Promise(function (resolve, reject) {//獲取數據$.getJSON("./json/0" + page + ".json", function (data) {//將獲取到的后臺數據使用 resolve帶回resolve(data);})});return p;}//渲染頁面的函數function writeHTML(data) {var list = data.matchedProducts;for (var i = 0; i < list.length; i++) {var $li = $(`<li>${list[i].collection_num} - ${list[i].pro_title}</li>`);$('#list').append($li);}}//調用 promisegetJson(1).then(function (data) {console.log(data);// 渲染頁面writeHTML(data);//獲取第二頁數據return getJson(2)}).then(function (data) {// 渲染頁面writeHTML(data);//獲取第二頁數據return getJson(3)}).then(function (data) {// 渲染頁面writeHTML(data);}).catch(function (err) {console.log(err);})})
promise.all的使用
$(function () {const p1 = new Promise(function (resolve, reject) {$.getJSON("./json/01.json", function (data) {resolve(data);})})const p2 = new Promise(function (resolve, reject) {$.getJSON("./json/02.json", function (data) {resolve(data);})})const p3 = new Promise(function (resolve, reject) {$.getJSON("./json/03.json", function (data) {resolve(data);})})//渲染頁面的函數function writeHTML(list) {for (var i = 0; i < list.length; i++) {var $li = $(`<li>${list[i].collection_num} - ${list[i].pro_title}</li>`);$('#list').append($li);}}//調用 Promise.all//如果數據組中的promise有一個返回是錯誤的,那么promise不會繼續進行Promise.all([p1, p2, p3]).then((res) => {//console.log(res);//重組數據var mydata = [];res.forEach((item, index) => {mydata = mydata.concat(item.matchedProducts);})console.log(mydata);writeHTML(mydata)})})
顧名思義,Promse.race就是賽跑的意思,意思就是說,Promise.race([p1, p2, p3])里面哪個結果獲得的快,就返回那個結果,不管結果本身是成功狀態還是失敗狀態。
Promise.allSettled
的使用在多個promise
同時進行時咱們很快會想到使用Promise.all
來進行包裝, 但是由于Promise.all
的短路特性, 三個提交中若前面任意一個提交失敗, 則后面的表單也不會進行提交了, 這就與咱們需求不符合.
Promise.allSettled
跟Promise.all
類似, 其參數接受一個Promise
的數組, 返回一個新的Promise
, 唯一的不同在于, 其不會進行短路, 也就是說當Promise
全部處理完成后我們可以拿到每個Promise
的狀態, 而不管其是否處理成功.
在后續的前后端分離式開發中,常見的增刪改查不再是純粹的GET+POST
的兩種請求方式,而是分的更加細化:
這種對請求方法(請求動詞
)約束的規范叫做restFul
規范(整理什么是restful)。該規范不是硬性要求,但是接口設計的時候一般都會遵守,其規范的不僅僅是請求方式,在請求地址形式、響應狀態碼等方面也存在規范要求(具體的要求項目時再說)。
Axios 是一個基于 promise 的 HTTP 庫,可以用在瀏覽器和 node.js 中。axios對ajax進行了封裝,返回promise對象,比ajax更簡潔好用
axios.get("http://www.51houniao.com/product/product/guessYouLike").then(res => {console.log(res);//渲染頁面var str = "";res.data.forEach((item, index) => {str += `<li>${item.proTitle}</li>`;})document.querySelector('#like').innerHTML = str;})
//參數: 參數一:url地址;參數二: 傳給服務器的json對象數據axios.post("http://www.51houniao.com/requirement/request/getMatchedProducts", {desc: false,orderBy: "outtime",pageSize: 100,product_type: 2,}).then(res => {console.log(res);//渲染頁面var str = "";res.data.matchedProducts.forEach((item, index) => {str += `<li>${item.pro_title}</li>`;})document.querySelector('#like').innerHTML = str;})
6.7.3 //支持多個并發請求
function getData1() {return axios.get("./json/01.json");}function getData2() {return axios.get("./json/02.json");}//axios的并發請求axios.all([getData1(), getData2()]).then(res => {console.log(res);var mydata = [];res.forEach((item, index) => {mydata = mydata.concat(item.data.matchedProducts);})console.log(mydata);//渲染})
6.7.4 axios 通用寫法
axios({method: 'get',url: './json/01.json',data: {}}).then(res => {console.log(res);})
6.7.5 請求方法的別名
為方便起見,為所有支持的請求方法提供了別名
在使用別名方法時, url
、method
、data
這些屬性都不必在配置中指定。
6.7.6 攔截器
在請求或響應被 then
或 catch
處理前攔截它們。
var aa = 123;try{alert(a);}catch(e){ //exceptionalert(e); // 捕獲異常}alert(666);//then
axios.get(url).then(res=>{...
})
參考:http://www.axios-js.com/zh-cn/docs/#axios-API
async await 的語法糖 es7之后才出現 和 promise 、generator都有一定的關系,
async-await
是promise
和generator
的語法糖。只是為了讓我們書寫代碼時更加流暢,當然也增強了代碼的可讀性。
async 表示異步,屬于異步操作的關鍵字
三頁數據順序執行使用 async await
客戶端與服務器之間要實現網頁內容的傳輸,則通信的雙方必須遵守網頁內容的傳輸協議。
網頁內容又叫做超文本,因此網頁內容的傳輸協議又叫做超文本傳輸協議(HyperText Transfer Protocol) ,簡稱 HTTP 協議。
由于 HTTP 協議屬于客戶端瀏覽器和服務器之間的通信協議。因此,客戶端發起的請求叫做 HTTP 請求,客戶端發送到服務器的消息,叫做 HTTP 請求消息。
注意:HTTP 請求消息又叫做 HTTP 請求報文。
HTTP 請求消息由請求行(request line)、請求頭部( header ) 、空行 和 請求體 4 個部分組成。
請求頭部用來描述客戶端的基本信息,從而把客戶端相關的信息告知服務器。比如:
User-Agent 用來說明當前是什么類型的瀏覽器;
Content-Type 用來描述發送到服務器的數據格式;
Accept 用來描述客戶端能夠接收什么類型的返回內容;
Accept-Language 用來描述客戶端期望接收哪種人類語言的文本內容。
請求頭部由多行 鍵/值對 組成,每行的鍵和值之間用英文的冒號分隔。
關于更多請求頭字段的描述,可以查看 MDN 官方文檔:https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Headers
請求體中存放的,是要通過 POST 方式提交到服務器的數據。
注意:只有 POST 請求才有請求體,GET 請求沒有請求體!
響應消息就是服務器響應給客戶端的消息內容,也叫作響應報文。
HTTP響應消息由狀態行、響應頭部、空行 和 響應體 4 個部分組成,如下圖所示:
狀態行由 HTTP 協議版本、狀態碼和狀態碼的描述文本 3 個部分組成,他們之間使用空格隔開;
響應頭部用來描述服務器的基本信息。響應頭部由多行 鍵/值對 組成,每行的鍵和值之間用英文的冒號分隔。
關于更多響應頭字段的描述,可以查看 MDN 官方文檔:https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Headers
響應體中存放的,是服務器響應給客戶端的資源內容。
HTTP 請求方法,屬于 HTTP 協議中的一部分,請求方法的作用是:用來表明要對服務器上的資源執行的操作。最常用的請求方法是 GET 和 POST。
HTTP 響應狀態碼(HTTP Status Code),也屬于 HTTP 協議的一部分,用來標識響應的狀態。
響應狀態碼會隨著響應消息一起被發送至客戶端瀏覽器,瀏覽器根據服務器返回的響應狀態碼,就能知道這次 HTTP 請求的結果是成功還是失敗了。
HTTP 狀態碼由三個十進制數字組成,第一個十進制數字定義了狀態碼的類型,后兩個數字用來對狀態碼進行細分。
HTTP 狀態碼共分為 5 種類型:
完整的 HTTP 響應狀態碼,可以參考 MDN 官方文檔 https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Status
常用的狀態碼:
2**
3**
4** 客戶端錯誤,很大幾率西藥前端工程師 出手
405 請求方式不對
415 請求時傳送給服務器的參數不對
5**
HTTPS (全稱:Hyper Text Transfer Protocol over SecureSocket Layer),是以安全為目標的 HTTP 通道,在HTTP的基礎上通過傳輸加密和身份認證保證了傳輸過程的安全性 [1] 。HTTPS 在HTTP 的基礎下加入SSL,HTTPS 的安全基礎是 SSL,因此加密的詳細內容就需要 SSL。 HTTPS 存在不同于 HTTP 的默認端口及一個加密/身份驗證層(在 HTTP與 TCP 之間)。這個系統提供了身份驗證與加密通訊方法。它被廣泛用于萬維網上安全敏感的通訊,例如交易支付等方面
HTTP雖然使用極為廣泛, 但是卻存在不小的安全缺陷, 主要是其數據的明文傳送和消息完整性檢測的缺乏, 而這兩點恰好是網絡支付, 網絡交易等新興應用中安全方面最需要關注的 [3] 。
關于 HTTP的明文數據傳輸, 攻擊者最常用的攻擊手法就是網絡嗅探, 試圖從傳輸過程當中分析出敏感的數據, 例如管理員對 Web 程序后臺的登錄過程等等, 從而獲取網站管理權限, 進而滲透到整個服務器的權限。即使無法獲取到后臺登錄信息, 攻擊者也可以從網絡中獲取普通用戶的隱秘信息, 包括手機號碼, 身份證號碼, 信用卡號等重要資料, 導致嚴重的安全事故。進行網絡嗅探攻擊非常簡單, 對攻擊者的要求很低。使用網絡發布的任意一款抓包工具, 一個新手就有可能獲取到大型網站的用戶信息 [3] 。
另外,HTTP在傳輸客戶端請求和服務端響應時, 唯一的數據完整性檢驗就是在報文頭部包含了本次傳輸數據的長度, 而對內容是否被篡改不作確認。 因此攻擊者可以輕易的發動中間人攻擊, 修改客戶端和服務端傳輸的數據, 甚至在傳輸數據中插入惡意代碼, 導致客戶端被引導至惡意網站被植入木馬 [3] 。
HTTPS 協議是由 HTTP 加上 TLS/SSL 協議構建的可進行加密傳輸、身份認證的網絡協議,主要通過數字證書、加密算法、非對稱密鑰等技術完成互聯網數據傳輸加密,實現互聯網傳輸安全保護。設計目標主要有三個。
(1)數據保密性:保證數據內容在傳輸的過程中不會被第三方查看。就像快遞員傳遞包裹一樣,都進行了封裝,別人無法獲知里面裝了什么 [4] 。
(2)數據完整性:及時發現被第三方篡改的傳輸內容。就像快遞員雖然不知道包裹里裝了什么東西,但他有可能中途掉包,數據完整性就是指如果被掉包,我們能輕松發現并拒收 [4] 。
(3)身份校驗安全性:保證數據到達用戶期望的目的地。就像我們郵寄包裹時,雖然是一個封裝好的未掉包的包裹,但必須確定這個包裹不會送錯地方,通過身份校驗來確保送對了地方 [4] 。
客戶端和服務端在傳輸數據之前,會通過基于X.509證書對雙方進行身份認證 。具體過程如下 [3] :
客戶端發起 SSL 握手消息給服務端要求連接。
服務端將證書發送給客戶端。
客戶端檢查服務端證書,確認是否由自己信任的證書簽發機構簽發。 如果不是,將是否繼續通訊的決定權交給用戶選擇 ( 注意,這里將是一個安全缺陷 )。如果檢查無誤或者用戶選擇繼續,則客戶端認可服務端的身份。
服務端要求客戶端發送證書,并檢查是否通過驗證。失敗則關閉連接,認證成功則從客戶端證書中獲得客戶端的公鑰,一般為1024位或者 2048位。到此,服務器客戶端雙方的身份認證結束,雙方確保身份都是真實可靠的。
客戶端和服務端在開始傳輸數據之前,會協商傳輸過程需要使用的加密算法。 客戶端發送協商請求給服務端, 其中包含自己支持的非對稱加密的密鑰交換算法 ( 一般是RSA), 數據簽名摘要算法 ( 一般是SHA或者MD5) , 加密傳輸數據的對稱加密算法 ( 一般是DES),以及加密密鑰的長度。 服務端接收到消息之后,選中安全性最高的算法,并將選中的算法發送給客戶端,完成協商。客戶端生成隨機的字符串,通過協商好的非對稱加密算法,使用服務端的公鑰對該字符串進行加密,發送給服務端。 服務端接收到之后,使用自己的私鑰解密得到該字符串。在隨后的數據傳輸當中,使用這個字符串作為密鑰進行對稱加密 [3] 。
SSL使用序列號來保護通訊方免受報文重放攻擊。這個序列號被加密后作為數據包的負載。在整個SSL握手中,都有一個唯一的隨機數來標記SSL握手。 這樣防止了攻擊者嗅探整個登錄過程,獲取到加密的登錄數據之后,不對數據進行解密, 而直接重傳登錄數據包的攻擊手法。
可以看到,鑒于電子商務等安全上的需求,HTTPS對比HTTP,在安全方面已經取得了極大的增強。總結來說,HTTPS的改進點在于創造性的使用了非對稱加密算法,在不安全的網路上,安全的傳輸了用來進行對稱加密的密鑰,綜合利用了非對稱加密的安全性和對稱加密的快速性 [3] 。
HTTPS 主要由兩部分組成:HTTP + SSL / TLS,也就是在 HTTP 上又加了一層處理加密信息的模塊。服務端和客戶端的信息傳輸都會通過 TLS 進行加密,所以傳輸的數據都是加密后的數據。
① 客戶端的瀏覽器首先要通過網絡與服務器建立連接,該連接是通過TCP 來完成的,一般 TCP 連接的端口號是80。 建立連接后,客戶機發送一個請求給服務器,請求方式的格式為:統一資源標識符(URL)、協議版本號,后邊是 MIME 信息包括請求修飾符、客戶機信息和許可內容 [2] 。
② 服務器接到請求后,給予相應的響應信息,其格式為一個狀態行,包括信息的協議版本號、一個成功或錯誤的代碼,后邊是 MIME 信息包括服務器信息、實體信息和可能的內容 [2] 。
① 客戶端將它所支持的算法列表和一個用作產生密鑰的隨機數發送給服務器
② 服務器從算法列表中選擇一種加密算法,并將它和一份包含服務器公用密鑰的證書發送給客戶端;該證書還包含了用于認證目的的服務器標識,服務器同時還提供了一個用作產生密鑰的隨機數
③ 客戶端對服務器的證書進行驗證(有關驗證證書,可以參考數字簽名),并抽取服務器的公用密鑰;然后,再產生一個稱作 pre_master_secret 的隨機密碼串,并使用服務器的公用密鑰對其進行加密(參考非對稱加 / 解密),并將加密后的信息發送給服務器
④ 客戶端與服務器端根據 pre_master_secret 以及客戶端與服務器的隨機數值獨立計算出加密和 MAC密鑰(參考 DH密鑰交換算法
⑤ 客戶端將所有握手消息的 MAC 值發送給服務器
⑥ 服務器將所有握手消息的 MAC 值發送給客戶端
HTTP1.0最早在網頁中使用是在1996年,那個時候只是使用一些較為簡單的網頁上和網絡請求上,而HTTP1.1則在1999年才開始廣泛應用于現在的各大瀏覽器網絡請求中,同時HTTP1.1也是當前使用最為廣泛的HTTP協議。 主要區別主要體現在:
7.7.2 HTTP2.0和HTTP1.X相比的新特性
參看: https://www.cnblogs.com/heluan/p/8620312.html
它的最大特點就是,服務器可以主動向客戶端推送信息,客戶端也可以主動向服務器發送信息,是真正的雙向平等對話,屬于服務器推送技術的一種。
其他特點包括:
(1)建立在 TCP 協議之上,服務器端的實現比較容易。
(2)與 HTTP 協議有著良好的兼容性。默認端口也是80和443,并且握手階段采用 HTTP 協議,因此握手時不容易屏蔽,能通過各種 HTTP 代理服務器。
(3)數據格式比較輕量,性能開銷小,通信高效。
(4)可以發送文本,也可以發送二進制數據。
(5)沒有同源限制,客戶端可以與任意服務器通信。
(6)協議標識符是ws
(如果加密,則為wss
),服務器網址就是 URL。
簡單實例:
var ws = new WebSocket("wss://echo.websocket.org");ws.onopen = function(evt) { console.log("Connection open ..."); ws.send("Hello WebSockets!");
};ws.onmessage = function(evt) {console.log( "Received Message: " + evt.data);ws.close();
};ws.onclose = function(evt) {console.log("Connection closed.");
};
參看:
http://www.ruanyifeng.com/blog/2017/05/websocket.html
版权声明:本站所有资料均为网友推荐收集整理而来,仅供学习和研究交流使用。
工作时间:8:00-18:00
客服电话
电子邮件
admin@qq.com
扫码二维码
获取最新动态