Appearance
HTTP
HTTP简介
HTTP协议是用于从服务器传输超文本到本地浏览器的传送协议。
HTTP基于TCP/IP通信协议进行传送输数据(HTML文件、图片文件、查询结果等)。
HTTP是一个属于应用层的面向对象的协议,由于其简捷、快速的方式,适用于分布式超媒体信息系统。
HTTP协议工作于客户端-服务器架构之上。浏览器作为HTTP客户端通过URL向HTTP服务器端即WEB服务器发送请求。WEB服务器根据接收到的请求,向客户端发送响应消息。
HTTP请求报文
格式
行 GET /media/channel/get_off_channel?accesstoken=TOKEN50001002 HTTP/1.1 头 Accept: */* Accept-Encoding: gzip, deflate Accept-Language: zh-CN,zh;q=0.9,en;q=0.8 Connection: keep-alive Host: slave.homed.tv 空行 体 字符串,FromData请求行 : 请求方法 请求目标(URL)HTTP版本
请求头
1. HTTP 请求头是 HTTP 请求中的一部分,用于向服务器传递附加的信息。它包含在 HTTP 请求的第一行和第一个空行之间 2. 常用请求头介绍 1. User-Agent:指定客户端的用户代理标识,用于告诉服务器所使用的客户端类型和版本号。 2. Accept:指定客户端能够接受的媒体类型。可以是一个具体的媒体类型,如 text/html,也可以是通配符,如 /,表示接受所有类型。 3. **Content-Type:指定请求体的媒体类型。常见的类型有 application/json,application/x-www-form-urlencoded,multipart/form-data 等** 4. Content-Length:指定请求体的长度。如果请求体为空,则该字段值为 0。 5. Host:指定服务器的主机名和端口号。 6. Referer:指定引用页面的 URL。常用于防止链接盗用或者统计分析。 7. Cookie:指定服务器返回的 Cookie 值,用于存储客户端的状态信息。 8. Authorization:指定客户端的身份验证信息,常用于发送 Basic 或 Bearer 令牌。 9. Cache-Control:指定请求和响应的缓存行为。 10. Connection:指定是否需要持久连接。 11. If-None-Match:指定一个实体标记,用于告诉服务器只有在实体标记不匹配时才返回资源。 12. 其他,以及自定义的请求头请求体
1. HTTP请求体是HTTP请求的一部分,用于在请求中携带数据。它通常用于POST、PUT等方法,用于向服务器提交数据或更新资源。 2. 请求体的格式取决于请求中的Content-Type头部字段。以下是几种常见的Content-Type和请求体的格式: 1. application/x-www-form-urlencoded:这是最常见的请求体格式。数据被编码为键值对,通过&符号连接。例如:key1=value1&key2=value2。这种格式的请求体适用于简单的表单提交。 2. application/json:这种格式通常用于传输结构化的数据,如JSON对象。请求体是一个JSON字符串,包含了键值对或嵌套的数据结构。 3. text/plain:这种格式通常用于传输纯文本数据。请求体可以是任意文本内容。 4. multipart/form-data:这种格式通常用于上传文件。请求体被划分为多个部分,每个部分包含一个表单字段或一个文件。每个部分有自己的Content-Disposition头部字段,指定了字段的名称和文件名。 3. 在请求体中,数据被发送到服务器并由服务器解析和处理。服务器可以根据Content-Type头部字段来解析请求体,并根据请求体中的数据执行相应的操作。
HTTP响应报文
格式
行 HTTP/1.1 200 OK 头 Date: Tue, 06 Aug 2024 07:54:39 GMT Content-Type: application/json;charset=utf-8 Transfer-Encoding: chunked Connection: keep-alive Access-Control-Allow-Origin: * Server: iPanel Access-Control-Allow-Headers: * 空行 体 { ret: 0, data: [] }状态行:版本 状态码 状态信息(Reason)
响应头
Date:服务器封装对象并发送响应报文的时间。 Last-Modified:对象创建或最后修改的时间。 Content-Type:实体中对象类型。对应客户端的Accept Content-Length:HTTP 协议通过设置回车符、换行符作为 HTTP header 的边界,通过 Content-Length 字段作为 HTTP body 的边界,这两个方式都是为了解决“粘包”的问题。 Set-cookie:对应客户端Cookie Location:告诉客户端资源的重定向位置/(URL)路径。 Cache-Control :控制缓存的相关信息。 Etag:用于协商缓存,返回一个摘要值。 Connection:告诉客户,发送完报文TCP连接关闭/保持。keep-alive/close响应体(实体)
常用HTTP请求方法
GET:请求指定的页面信息,并返回实体主体。
POST:表示向指定资源提交数据,数据包含在请求体中。有可能导致新的资源建立或原有资源修改。
HEAD:类似get,服务器会发出http响应报文,但不返回请求对象,仅有HTTP的头信息
PUT:允许用户上传对象到服务器。
DELETE:允许用户删除服务器上的对象。
OPTIONS: 返回服务器针对特殊资源所支持的 HTML 请求方式 或 允许客户端查看服务器的性能。
HTTP状态码
1**:信息,服务器收到请求,需要请求者继续执行操作
2**:成功,操作被成功接收并处理
3**:重定向,需要进一步的操作以完成请求
4**:客户端错误,请求包含语法错误或无法完成请求
5**:服务器错误,服务器在处理请求的过程中发生了错误
常见的状态码
100——客户必须继续发出请求
101——客户要求服务器根据请求转换HTTP协议版本
200——表示请求成功并返回所请求的数据
201——表示请求成功并在服务器上创建了新资源
202——接受和处理、但处理未完成
203——返回信息不确定或不完整
204——表示请求成功,但响应中无返回的内容
205——服务器完成了请求,用户代理必须复位当前已经浏览过的文件
206——服务器已经完成了部分用户的GET请求
300——请求的资源可在多处得到
301——删除请求数据
302——在其他地址发现了请求数据
303——建议客户访问其他URL或访问方式
304——客户端已经执行了GET,但文件未变化
305——请求的资源必须从服务器指定的地址得到
306——前一版本HTTP中使用的代码,现行版本中不再使用
307——申明请求的资源临时性删除
400——表示请求有语法错误或参数错误,服务器无法理解
401——表示请求未经授权,需要用户进行身份验证
402——保留有效ChargeTo头响应
403——表示服务器拒绝请求,通常是因为请求的资源没有访问权限
404——表示请求的资源不存在
405——用户在Request-Line字段定义的方法不允许
406——根据用户发送的Accept拖,请求资源不可访问
407——类似401,用户必须首先在代理服务器上得到授权
408——客户端没有在用户指定的饿时间内完成请求
409——对当前资源状态,请求不能完成
410——服务器上不再有此资源且无进一步的参考地址
411——服务器拒绝用户定义的Content-Length属性请求
412——一个或多个请求头字段在当前请求中错误
413——请求的资源大于服务器允许的大小
414——请求的资源URL长于服务器允许的长度
415——请求资源不支持请求项目格式
416——请求中包含Range请求头字段,在当前请求资源范围内没有range指示值,请求也不包含If-Range请求头字段
417——服务器不满足请求Expect头字段指定的期望值,如果是代理服务器,可能是下一级服务器不能满足请求
500——表示服务器内部发生错误,无法完成请求
501——服务器不支持请求的函数
502——服务器暂时不可用,有时是为了防止发生系统过载
503——服务器过载或暂停维修
504——关口过载,服务器使用另一个关口或服务来响应用户,等待时间设定值较长
505——服务器不支持或拒绝支请求头中指定的HTTP版本
Ajax
Ajax请求与获取数据 ( POST / GET ) 五个步骤
创建XMLHttpRequest()对象
初始化,设置请求方法和url
设置请求的HTTP请求头
发送
事件绑定,处理服务器的返回
在回调函数里根据返回的不同状态进行操作
XMLHttpRequest对象的常用属性和方法
open方法
1. xhr.open(method, url, async, user, password) 2. method : 就是HTTP请求方法,如GET,POST url : HTTP请求URL async : 就是指是否异步发送,默认为true,即异步发送,设为false的话,则表示同步发送 user,password : 用于身份认证 ,较少使用setRequestHeader方法
1. 该方法用于设置HTTP请求头,有两个参数,第一个参数是请求头字段名,第二个是请求头字段值 2. xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencode')send方法
1. GET请求一般不需要设置HTTP请求体,因为GET请求参数都加载URL中,而POST请求需要设置HTTP请求体 2. 该方法用于设置HTTP请求体,只有一个参数,接收的数据作为HTTP请求体。数据必须是字符串类型的,如果不是字符串类型,则会被强转成字符串类型 3. 字符串数据也有格式要求,需要和请求头的Content-Type指定的类型匹配 1. application/x-www-form-urlencode , 查询格式字符串 , exp : "key1=value1&key2=value2" 2. application/json, json格式字符串, exp: "{'key1':value1, 'key2':value2}" 3. text/plain, 纯文本字符串格式, exp : "123" 4. multipart/form-data, fromdata格式, exp: new FromData()readyState属性
1. hr对象本身有一个属性readyState,有五个值,分别对应xhr对象得五种状态: 2. 取值: 0:xhr对象刚被创建,但是还没有open初始化 1:xhr已经被open初始化,但是还没有send 2:xhr已经send,但是还没有收到响应体 3:xhr已经收到部分响应体数据,代表的是请求还在处理当中 4:xhr已经收到全部响应体数据,代表的是响应已经完成onreadystatechange 方法
1. 事件处理程序属性,浏览器会监听xhr对象的readystate值的变化 2. 一般只处理readyState === 4status属性 、 statusText属性
1. xhr.status属性对应HTTP响应报文的状态码【http状态码】,xhr.statusText对应响应报文的状态码描述。 2. 一般只关注成功的响应,即状态码2xx的响应getRespnseHeader方法 、xhr.getAllResponseHeaders方法
1. xhr.getRespnseHeader用于获取指定HTTP响应报文头字段的值 2. xhr.getAllResponseHeaders用于获取所有HTTP响应报文头xhr.response属性、xhr.responseText属性、xhr.responseXML属性
1. xhr.response、xhr.responseText、xhr.responseXML都对应于HTTP响应报文中的响应体。 2. xhr.response 用于接收HTTP响应体,但是数据类型不定(可能是JSON类型,HTML对应的DOM元素类型,二进制数据ArrayBuffer类型等....) 3. xhr.responseText 存放文本格式HTTP响应体,或者没有值 4. xhr.responseXML 存放XML或HTML格式的响应体,或者没有值responseType属性
1. 用于指定xhr.response的数据类型。可读可写。默认text 2. 取值: text , json , blob , document , arraybuffertimeout属性、ontimeout回调方法、onerror回调方法
1. timeout表示设置超时时间 2. ontimeout超时完成后回调函数 3. onerror网络异常回调函数abort方法
1. 终止请求
跨域问题
为什么会跨域?
1. ajax需要满足同源策略,即 同协议,同域名,同端口,三者其一不满足则会产生跨域问题。 2. 跨域是浏览器的问题,而不是服务器问题。 3. 浏览器基于安全考虑,当发现跨域时会进行校验,校验不通过则会报跨域安全问题。跨域如何解决
1. JSONP,JSONP只支持GET请求 - 比较少使用 2. 服务器端设置CORS,设置哪些源访问是容许的, "Access-Control-Allow-Origin", "*" - 最常用方式 3. 浏览器端设置代理【一些框架react,vue等都有比较方便的设置代理的方法】设置CORS响应头实现跨越
1. CORS是一个W3C标准,全称是"跨域资源共享",它允许浏览器向跨源服务器,发出XMLHttpRequest请求,从而克服了AJAX只能同源使用的限制。 2. CORS是通过设置一个响应头来告诉浏览器,该请求容许跨域,浏览器收到该响应头则会放行。CORS预检请求 1. 浏览器将CORS请求分成两类:简单请求(simple request)和非简单请求(not-so-simple request)。
2. 简单请求,同时满足以下两大条件,就属于简单请求,凡是不同时满足下面两个条件,就属于非简单请求 1. 请求方式是 get/post/head 2. 请求头包含字段可以有:Accept,Accept-Language,content-Language,Last-Event-ID,Content-Type,其中Content-Type的值只能是 application/x-www-form-urlencoded,text/plain,multipart/form-data。 3. 简单请求和复杂请求的主要区别在于它们是否触发CORS预检请求 4. 非简单请求的CORS请求,会在正式通信之前,增加一次HTTP查询请求,称为"预检"请求(preflight)。 5. 浏览器先询问服务器,当前网页所在的域名是否在服务器的许可名单之中,以及可以使用哪些HTTP动词和头信息字段。只有得到肯定答复,浏览器才会发出正式的XMLHttpRequest请求,否则就报错 6. 如果服务器否定了"预检"请求,会返回一个正常的HTTP回应,但是没有任何CORS相关的头信息字段。这时,浏览器就会认定,服务器不同意预检请求,因此触发一个错误参考资料
1. https://www.ruanyifeng.com/blog/2016/04/same-origin-policy.html 2. https://www.ruanyifeng.com/blog/2016/04/cors.html
axios
什么是axios
axios是前端最流行的ajax请求库
axios是通过Promise实现对ajax技术的一种封装
react/vue 官方都推荐使用 axios 发 ajax 请求
axios API
axios(config): 通用的发任意类型请求的方式
axios(url[, config]): 可以只指定 url 发 get 请求
axios 请求方法别名
axios.request(config): 等同于 axios(config)
axios.get(url[, config]): 发 get 请求
axios.post(url[, data[, config]]): 发 post 请求
axios.delete(url[, config])
axios.head(url[, config])
axios.options(url[, config])
axios.put(url[, data[, config]])
axios.patch(url[, data[, config]])
并发请求
axios.all(iterable)
axios.spread(callback)
创建实例
- axios.create([config])
请求配置
整体配置说明
javascript{ // `url` 是用于请求的服务器 URL url: '/user', // `method` 是创建请求时使用的方法 method: 'get', // default // `baseURL` 将自动加在 `url` 前面,除非 `url` 是一个绝对 URL。 // 它可以通过设置一个 `baseURL` 便于为 axios 实例的方法传递相对 URL baseURL: 'https://some-domain.com/api/', // `transformRequest` 允许在向服务器发送前,修改请求数据 // 只能用在 'PUT', 'POST' 和 'PATCH' 这几个请求方法 // 后面数组中的函数必须返回一个字符串,或 ArrayBuffer,或 Stream transformRequest: [function (data, headers) { // 对 data 进行任意转换处理 return data; }], // `transformResponse` 在传递给 then/catch 前,允许修改响应数据 transformResponse: [function (data) { // 对 data 进行任意转换处理 return data; }], // `headers` 是即将被发送的自定义请求头 headers: {'X-Requested-With': 'XMLHttpRequest'}, // `params` 是即将与请求一起发送的 URL 参数 // 必须是一个无格式对象(plain object)或 URLSearchParams 对象 params: { ID: 12345 }, // `paramsSerializer` 是一个负责 `params` 序列化的函数 // (e.g. https://www.npmjs.com/package/qs, http://api.jquery.com/jquery.param/) paramsSerializer: function(params) { return Qs.stringify(params, {arrayFormat: 'brackets'}) }, // `data` 是作为请求主体被发送的数据 // 只适用于这些请求方法 'PUT', 'POST', 和 'PATCH' // 在没有设置 `transformRequest` 时,必须是以下类型之一: // - string, plain object, ArrayBuffer, ArrayBufferView, URLSearchParams // - 浏览器专属:FormData, File, Blob // - Node 专属: Stream data: { firstName: 'Fred' }, // `timeout` 指定请求超时的毫秒数(0 表示无超时时间) // 如果请求话费了超过 `timeout` 的时间,请求将被中断 timeout: 1000, // `withCredentials` 表示跨域请求时是否需要使用凭证 withCredentials: false, // default // `adapter` 允许自定义处理请求,以使测试更轻松 // 返回一个 promise 并应用一个有效的响应 (查阅 [response docs](#response-api)). adapter: function (config) { /* ... */ }, // `auth` 表示应该使用 HTTP 基础验证,并提供凭据 // 这将设置一个 `Authorization` 头,覆写掉现有的任意使用 `headers` 设置的自定义 `Authorization`头 auth: { username: 'janedoe', password: 's00pers3cret' }, // `responseType` 表示服务器响应的数据类型,可以是 'arraybuffer', 'blob', 'document', 'json', 'text', 'stream' responseType: 'json', // default // `responseEncoding` indicates encoding to use for decoding responses // Note: Ignored for `responseType` of 'stream' or client-side requests responseEncoding: 'utf8', // default // `xsrfCookieName` 是用作 xsrf token 的值的cookie的名称 xsrfCookieName: 'XSRF-TOKEN', // default // `xsrfHeaderName` is the name of the http header that carries the xsrf token value xsrfHeaderName: 'X-XSRF-TOKEN', // default // `onUploadProgress` 允许为上传处理进度事件 onUploadProgress: function (progressEvent) { // Do whatever you want with the native progress event }, // `onDownloadProgress` 允许为下载处理进度事件 onDownloadProgress: function (progressEvent) { // 对原生进度事件的处理 }, // `maxContentLength` 定义允许的响应内容的最大尺寸 maxContentLength: 2000, // `validateStatus` 定义对于给定的HTTP 响应状态码是 resolve 或 reject promise 。如果 `validateStatus` 返回 `true` (或者设置为 `null` 或 `undefined`),promise 将被 resolve; 否则,promise 将被 rejecte validateStatus: function (status) { return status >= 200 && status < 300; // default }, // `maxRedirects` 定义在 node.js 中 follow 的最大重定向数目 // 如果设置为0,将不会 follow 任何重定向 maxRedirects: 5, // default // `socketPath` defines a UNIX Socket to be used in node.js. // e.g. '/var/run/docker.sock' to send requests to the docker daemon. // Only either `socketPath` or `proxy` can be specified. // If both are specified, `socketPath` is used. socketPath: null, // default // `httpAgent` 和 `httpsAgent` 分别在 node.js 中用于定义在执行 http 和 https 时使用的自定义代理。允许像这样配置选项: // `keepAlive` 默认没有启用 httpAgent: new http.Agent({ keepAlive: true }), httpsAgent: new https.Agent({ keepAlive: true }), // 'proxy' 定义代理服务器的主机名称和端口 // `auth` 表示 HTTP 基础验证应当用于连接代理,并提供凭据 // 这将会设置一个 `Proxy-Authorization` 头,覆写掉已有的通过使用 `header` 设置的自定义 `Proxy-Authorization` 头。 proxy: { host: '127.0.0.1', port: 9000, auth: { username: 'mikeymike', password: 'rapunz3l' } }, // `cancelToken` 指定用于取消请求的 cancel token // (查看后面的 Cancellation 这节了解更多) cancelToken: new CancelToken(function (cancel) {}) }重点掌握以下几个配置
1. url 2. method 3. baseURL 4. headers 5. params 6. data 7. timeout
响应结构
javascript
{
// `data` 由服务器提供的响应
data: {},
// `status` 来自服务器响应的 HTTP 状态码
status: 200,
// `statusText` 来自服务器响应的 HTTP 状态信息
statusText: 'OK',
// `headers` 服务器响应的头
headers: {},
// `config` 是为请求提供的配置信息
config: {},
// 'request'
// `request` is the request that generated this response
// It is the last ClientRequest instance in node.js (in redirects)
// and an XMLHttpRequest instance the browser
request: {}
}配置默认值
全局的 axios 默认值
javascriptaxios.defaults.method = 'GET';//设置默认的请求类型为 GET axios.defaults.baseURL = 'http://localhost:3000';//设置基础 URL axios.defaults.params = {id:100}; axios.defaults.timeout = 3000; ...自定义实例默认值
javascript
const instance = axios.create({
baseURL: 'https://api.example.com'
});
// Alter defaults after instance has been created
instance.defaults.baseURL = 'http://localhost:3000';
...拦截器
拦截器函数/ajax 请求/请求的回调函数的调用顺序
1. 说明: 调用 axios()并不是立即发送 ajax 请求, 而是需要经历一个较长的流程 2. 流程: 请求拦截器 => 发ajax请求 => 响应拦截器 => 请求的回调 3. 注意: 此流程是通过 promise 串连起来的, 请求拦截器传递的是 config, 响应拦截器传递的是 response拦截器使用
javascript// 添加请求拦截器 axios.interceptors.request.use(function (config) { // 在发送请求之前做些什么 return config; }, function (error) { // 对请求错误做些什么 return Promise.reject(error); }); // 添加响应拦截器 axios.interceptors.response.use(function (response) { // 对响应数据做点什么 return response; }, function (error) { // 对响应错误做点什么 return Promise.reject(error); });
fetch
fetch简介
Fetch()是Fetch API中JavaScript window对象的一部分。它是内置的,因此用户不必安装它,axios则使用的是xml对象去封装的
fetch()使用 Promise,不使用回调函数
fetch()采用模块化设计,API 分散在多个对象上(Response 对象、Request 对象、Headers 对象)
fetch()通过数据流(Stream对象)处理数据,可以分块读取,有利于提高网站性能表现,减少内存占用,对于请求大文件或者网速慢的场景相当有用,XMLHTTPRequest对象不支持数据流,所有的数据必须放在缓存里,不支持分块读取,必须等待全部拿到后,再一次性吐出来。
fetch的语法 和 入参
语法: fetch(url[, options]).then(...).catch(...)
javascriptfetch('http://') // fetch()接收到的response是一个 Stream 对象 // response.json()是一个异步操作,取出所有内容,并将其转为 JSON 对象 .then(response => response.json()) .then(json => console.log(json))//获取到的json数据 .catch(err => console.log('Request Failed', err)); // 等价于以下写法 async function getJSON() { let url = '网址'; try { let response = await fetch(url); return await response.json(); } catch (error) { console.log('Request Failed', error); } } console.log(getJSON()); // 获取到的json数据入参: fetch(url[, options])
第一个参数是请求url
第二个参数的完整API
javascriptconst response = fetch(url, { method: "POST",//请求方式 headers: {// 定制http请求的标头 "Content-Type": "application/json" }, body: body: JSON.stringify({ name: "John", age: 30 }),//post请求的数据体 referrer: "about:client", referrerPolicy: "no-referrer-when-downgrade",//用于设定fetch请求的referer标头 mode: "cors", // 指定请求模式 credentials: "same-origin",// 发送cookie cache: "default",// 指定如何处理缓存 redirect: "follow", integrity: "", keepalive: false, signal: null });- 参数详解:
javascriptmethod:HTTP 请求的方法,POST、DELETE、PUT都在这个属性设置。 headers:一个对象,用来定制 HTTP 请求的标头。 body:POST 请求的数据体。 signal:指定一个 AbortSignal 实例,用于取消fetch()请求 cache:指定如何处理缓存。可能的取值如下: /* default:默认值,先在缓存里面寻找匹配的请求。 no-store:直接请求远程服务器,并且不更新缓存。 reload:直接请求远程服务器,并且更新缓存。 no-cache:将服务器资源跟本地缓存进行比较,有新的版本才使用服务器资源,否则使用缓存。 force-cache:缓存优先,只有不存在缓存的情况下,才请求远程服务器。 only-if-cached:只检查缓存,如果缓存里面不存在,将返回504错误。 */ mode: 指定请求的模式。可能的取值如下: /* cors:默认值,允许跨域请求。 same-origin:只允许同源请求。 no-cors:请求方法只限于 GET、POST 和 HEAD,并且只能使用有限的几个简单标头,不能添加跨域的复杂标头,相当于提交表单所能发出的请求。 */ credentials:指定是否发送 Cookie。可能的取值如下: /* same-origin:默认值,同源请求时发送 Cookie,跨域请求时不发送。 include:不管同源请求,还是跨域请求,一律发送 Cookie。 omit:一律不发送。 */ keepalive:用于页面卸载时,告诉浏览器在后台保持连接,继续发送数据。 /* 一个典型的场景就是,用户离开网页时,脚本向服务器提交一些用户行为的统计信息。 这时,如果不用keepalive属性,数据可能无法发送,因为浏览器已经把页面卸载了。 */ redirect: 指定 HTTP 跳转的处理方法。可能的取值如下: /* follow:默认值,fetch()跟随 HTTP 跳转。 error:如果发生跳转,fetch()就报错。 manual:fetch()不跟随 HTTP 跳转,但是response.url属性会指向新的 URL,response.redirected属性会变为true,由开发者自己决定后续如何处理跳转。 */ integrity:指定一个哈希值,用于检查 HTTP 回应传回的数据是否等于这个预先设定的哈希值。 /* 比如,下载文件时,检查文件的 SHA-256 哈希值是否相符,确保没有被篡改 fetch('http://site.com/file', { integrity: 'sha256-abcdef' }); */ referrer: 用于设定fetch请求的referer标头。 /* 这个属性可以为任意字符串,也可以设为空字符串(即不发送referer标头)。 */ referrerPolicy: 用于设定Referer标头的规则。可能的取值如下: /* no-referrer-when-downgrade:默认值,总是发送Referer标头,除非从 HTTPS 页面请求 HTTP 资源时不发送。 no-referrer:不发送Referer标头。 origin:Referer标头只包含域名,不包含完整的路径。 origin-when-cross-origin:同源请求Referer标头包含完整的路径,跨域请求只包含域名。 same-origin:跨域请求不发送Referer,同源请求发送。 strict-origin:Referer标头只包含域名,HTTPS 页面请求 HTTP 资源时不发送Referer标头。 strict-origin-when-cross-origin:同源请求时Referer标头包含完整路径,跨域请求时只包含域名,HTTPS 页面请求 HTTP 资源时不发送该标头。 unsafe-url:不管什么情况,总是发送Referer标头。 */
fetch的Response对象
fetch的Response对象
fetch()请求成功以后,得到的是一个 Response 对象。它对应服务器的 HTTP 回应
Response 包含的数据通过 Stream 接口异步读取,但是它还包含一些同步属性,对应 HTTP 回应的标头信息(Headers),可以立即读取。
标头信息的属性有:
javascriptconst response = await fetch(url); - response.ok:返回一个布尔值,表示请求是否成功 例如:true对应 HTTP 请求的状态码 200 到 299,false对应其他的状态码。 - response.status:返回一个数字,表示 HTTP 回应的状态码 例如:200,表示成功请求 - response.statusText属性返回一个字符串,表示 HTTP 回应的状态信息 例如:请求成功以后,服务器返回"OK" - response.url:返回请求的 URL。 如果: URL 存在跳转,该属性返回的是最终 URL。 - response.redirected:返回一个布尔值,表示请求是否发生过跳转。 - response.type:返回请求的类型。可能的值如下: basic:普通请求,即同源请求。 cors:跨域请求。 error:网络错误,主要用于 Service Worker。
判断请求是否成功发出
fetch()发出请求以后,只有网络错误或者无法连接时,fetch()才会报错,其他情况都不会报错,而是认为请求成功。
通过Response.status属性,得到HTTP 回应的真实状态码,可以判断请求是否成功,也可以判断response.ok是否为true。
exp
javascriptasync function getfetchText() { let response = await fetch('网址'); if (response.status >= 200 && response.status < 300) { return await response.text(); } else { throw new Error(response.statusText); } } 或者 if (response.ok) { // 请求成功 console.log('请求成功') } else { // 请求失败 console.log('请求失败') }操作标头
Response 对象还有一个Response.headers属性,指向一个 Headers 对象,对应 HTTP 回应的所有标头。
Headers 对象可以使用for…of循环进行遍历
javascriptconst response = await fetch(url); for (let [key, value] of response.headers) { console.log(`${key} : ${value}`); } // 或者 for (let [key, value] of response.headers.entries()) { //response.heasers.entries()方法返回一个遍历器,可以依次遍历所有键值对([key,value]) console.log(`${key} : ${value}`); }- 操作标头的方法(不常用)
javascriptconst response = await fetch(url); response.headers.get():根据指定的键名,返回键值。 response.headers.has(): 返回一个布尔值,表示是否包含某个标头。 response.headers.set():将指定的键名设置为新的键值,如果该键名不存在则会添加。 response.headers.append():添加标头。 response.headers.delete():删除标头。 response.headers.keys():返回一个遍历器,可以依次遍历所有键名。 response.headers.values():返回一个遍历器,可以依次遍历所有键值。 response.headers.entries():返回一个遍历器,可以依次遍历所有键值对([key, value])。 response.headers.forEach():依次遍历标头,每个标头都会执行一次参数函数。读取Response对象内容的方法
javascriptconst response = await fetch(url); response.text():得到文本字符串,用于获取文本数据,比如 HTML 文件。 response.json():得到 JSON 对象。 response.blob():得到二进制 Blob 对象,例如读取图片文件,显示在网页上。 response.formData():得到 FormData 表单对象,主要用在 Service Worker 里面,拦截用户提交的表单,修改某些数据以后,再提交给服务器。 response.arrayBuffer():得到二进制 ArrayBuffer 对象,主要用于获取流媒体文件。创建副本(clone)
Stream 对象只能读取一次,读取完就没了,这意味着上面五个读取方法,只能使用一个,否则会报错
Response 对象提供Response.clone()方法,创建Response对象的副本,实现多次读取。
exp
javascriptconst response1 = await fetch('图片地址'); // response.clone()复制了一份 Response 对象,然后将同一张图片读取了两次 const response2 = response1.clone(); const myBlob1 = await response1.blob(); const myBlob2 = await response2.blob(); image1.src = URL.createObjectURL(myBlob1); image2.src = URL.createObjectURL(myBlob2);Response.body
Response.body是 Response 对象暴露出的底层接口,返回一个 ReadableStream 对象,供用户操作
ex: 用来分块读取内容,显示下载的进度
javascriptconst response = await fetch('图片地址'); // response.body.getReader()方法返回一个遍历器 const reader = response.body.getReader(); while(true) { // 这个遍历器的read()方法每次返回一个对象,表示本次读取的内容块 const {done, value} = await reader.read(); // done属性是一个布尔值,用来判断有没有读完 if (done) { break; } // value属性是一个 arrayBuffer 数组,表示内容块的内容,而value.length属性是当前块的大小 console.log(`Received ${value.length} bytes`) }
例子
作业
完成使用homed接口从登录到请求各类数据的完整流程
接口请求所需要的参数
javascript{ deviceno: 00-23-b8-2e-0b-df devicetype: 1 }成功请求到的数据均打印输出到控制台
整体流程和接口:
1. 使用fetch 请求用户列表 1. GET http://access.homed.tv/account/user/get_list 2. 入参 deviceno , devicetype 2. 使用fetch 登录 1. 利用第一步的返回列表中 is_super_user=1 的超级用户登录 2. GET http://access.homed.tv/account/login 3. 入参 deviceno , devicetype , accounttype=1 , account(超级用户的user_id) 3. 使用axios 设置请求拦截器, 针对get和post请求,拦截器中统一处理第二步中返回的token 4. 使用axios 请求两份数据 1. 请求首页瀑布流 1. GET http://slave.homed.me/homed/programtype/get_patch_list 2. 入参 :label=0 , num=2 (这里没有token,因为第三步中会处理) 2. 请求天气预报 1. POST http://slave.homed.me/application/weather/get_weather_forecast 2. 请求头: content-type : application/x-www-form-urlencoded 3. 请求体: json格式字符串 , {"code":["440303"],"type":[1,6],"resource":0} (这里没有token,因为第三步中会处理) 5. axios 设置响应拦截器,处理所有的data.ret === 0则正确返回,否则统一alert弹出请求错误