萌新

  • 主页
所有文章 关于我

萌新

  • 主页

vue.JS第二天

2017-06-21

主入口 main.js

src目录中的main.js—程序的主入口

其中使用了ES6语法,使用import来导入包,这里导入了vue包,还有两个文件,分别是router.js和App.vue,.js和.vue后缀可省略

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
import Vue from 'vue'
import App from './App'
import router from './router'

Vue.config.productionTip = false

/* eslint-disable no-new */
new Vue({
el: '#app',
router,
template: '<App/>',
components: { App }
})

//可以看到在new Vue()时传入了一个对象,但是这个对象却不是键值对,
是这样,这是ES6的一种语法,当引用的变量名和键名相同时,就可以简写成这样

new Vue({
router: router,
render: h => h(App)
}).$mount('app')

// 被简写成了
new Vue({
router, // 这是ES6对象的简写,扩展开就是router: router
// 箭头函数(=>)是ES6的新语法
render: h => h(App) // 这里扩展开就是render: (h) => { return h(App) }
}).$mount('app')

router

router—index.js

1
2
3
4
5
6
7
8
9
10
// 告诉vue要使用router
Vue.use(VueRouter)

// 实例化router对象
const router = new VueRouter({

routes // 挂载路由集合

// 导出router对象
export default router

  • Vue.JS

展开全文 >>

Vue.JS 第一天

2017-06-20

1.安装 nrm,用于管理npm镜像源。

安装
$ npm install -g nrm

列出可选的源
nrm ls

切换源
nrm use cnpm

测试源
nrm test

2.全局安装Vue.JS

npm install --global vue-cli

3.创建项目目录,初始化项目

vue init webpack my-project  //my-project是文件夹名称

cd my-project    //进入文件夹

npm install
npm run dev
  • Vue.JS

展开全文 >>

Ajax 梳理

2017-05-31

XMLHttpRequest对象

XHR为向服务器发送请求和解析服务器响应提供了接口, 能够以异步方式从服务器获取新数据。
可以在浏览器console打印一个new XMLHttpRequest() 对象来查看该对象的属性和方法

试运行以下代码.

1
2
3
4
5
6
7
8
9
var xhr = new XMLHttpRequest(),
i=0;
for(var key in xhr){
if(xhr.hasOwnProperty(key)){
i++;
}
}
console.log(i);//0
console.log(XMLHttpRequest.prototype.hasOwnProperty('timeout'));//true

可见, XMLHttpRequest 实例对象没有自有属性. 实际上, 它的所有属性均来自于 XMLHttpRequest.prototype .
追根溯源, XMLHttpRequest 实例对象具有如下的继承关系. (下面以a<<b表示a继承b)
xhr << XMLHttpRequest.prototype << XMLHttpRequestEventTarget.prototype << EventTarget.prototype << Object.prototype

主要属性:

  1. Number readyState 状态值( 整数), 可以确定请求 / 响应过程的当前活动阶段
  • 0: 请求已建立,未初始化。 未调用open() 方法
  • 1: 请求已建立, 但未发送。 已经调用open() 方法
  • 2: 请求已发送。 已经调用send() 方法, 未接收到响应
  • 3: 接收。 已经接收到部分数据
  • 4: 完成。 已经接收到全部数据, 可以在客户端使用
  1. Function onreadystatechange 当readyState的值改变时自动触发执行其对应的函数( 回调函数)

  2. String responseText 作为响应主体被返回的文本( 字符串类型)

  3. XmlDocument responseXML 服务器返回的数据( Xml对象)

  4. Number states 状态码( 整数), 如: 200、 404…

  5. String statesText 状态文本( 字符串), 如: OK、 NotFound…

主要方法:

  1. void open(String method, String url, Boolen async)
    用于创建请求
    参数:
    method: 请求方式( 字符串类型), 如: POST、 GET、 DELETE…
    url: 要请求的地址( 字符串类型)
    async: 是否异步( 布尔类型)

  2. void send(String body)
    用于发送请求
    参数:
    body: 要发送的数据( 字符串类型)

  3. void setRequestHeader(String header, String value)
    用于设置请求头
    参数:
    header: 请求头的key( 字符串类型)
    vlaue: 请求头的value( 字符串类型)

  4. String getAllResponseHeaders()
    获取所有响应头
    返回值:
    响应头数据( 字符串类型)

  5. String getResponseHeader(String header)
    获取响应头中指定header的值
    如果 readyState 小于 3, 这个方法返回 null, 否则, 它返回服务器发送的所有 HTTP 响应的头部。
    头部作为单个的字符串返回, 一行一个头部。 每行用换行符 “\r\n”
    隔开
    参数:
    header: 响应头的key( 字符串类型)
    返回值:
    响应头中指定的header对应的值

  6. void abort()
    终止请求
    这个方法把 XMLHttpRequest 对象的readyState属性重置为0

MSXML, IE7及更高版本浏览器可以直接使用BOM的 XMLHttpRequest 对象.IE6及更低版本浏览器只能使用 ActiveXObject 对象来创建 XMLHttpRequest 对象实例.创建时需要指明一个类似” Microsoft.XMLHTTP” 这样的ProgID.

IE5, IE5 .5, IE6, IE7, IE8, IE9, IE10, IE edge等浏览器, IE5及之后的浏览器均可以通过如下语句获取xhr对象: var xhr = new ActiveXObject(“Msxml2.XMLHTTP”);

全平台兼容的XMLHttpRequest对象

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
function getXHR() {
var xhr = null;
if (window.XMLHttpRequest) {
xhr = new XMLHttpRequest();
} else if (window.ActiveXObject) {
try {
xhr = new ActiveXObject("Msxml2.XMLHTTP");
} catch (e) {
try {
xhr = new ActiveXObject("Microsoft.XMLHTTP");
} catch (e) {
alert("您的浏览器暂不支持Ajax!");
}
}
}
return xhr;
}

一、新建XHR对象、发出http请求

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
function getXHR() {
var xhr = null;
if (window.XMLHttpRequest) {
xhr = new XMLHttpRequest();
} else if (window.ActiveXObject) {
try {
xhr = new ActiveXObject("Msxml2.XMLHTTP");
} catch (e) {
try {
xhr = new ActiveXObject("Microsoft.XMLHTTP");
} catch (e) {
alert("您的浏览器暂不支持Ajax!");
}
}
}
return xhr;
}

//发送请求 requset
xmlHttpRequest.open("GET", url, true)
//参数1,http request请求方法,要大写。
//参数2,请求页面的url,
//参数3,决定此request是否不同步进行,设定为true表示即使服务器未传回资料也会继续执行其他程序
xmlHttpRequest.send(data);
//send以POST发出请求时,资料以查询字符串的方式列出:name=value&anothername=othervalue&so=on
//如果想用POST方式传送资料,必须先将MIME形态改好,否則伺服器就不會理你傳過來的資料了。
httpRequest.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');

二、处理服务器传回的资料

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
//傳出 request 時必須提供處理傳回值的函數名稱,這個函數是用來處理服务器的回應。
xmlHttpRequest.onreadystatechange = function() {
//这个函数首先该做什么?必须检查request目前的状态,如果状态为4代表服务器已经传回所有资料了,便可以开始解析所有资料
if (xmlHttpRequest.readyState == 4) {
//一切ok,继续解析
} else {
//还没完成
}
//readyState所有可能的值:0 (還沒開始) 1 (讀取中) 2 (已讀取) 3 (資訊交換中) 4 (一切完成)

//接下来检查HTTP状态码,我们只要200 OK这种状态
if (xmlHttpRequest.status >= 200 && xhr.status < 300) || xmlHttpRequest.status == 304) {
//万事俱备
} else {
// 似乎有點問題,或許伺服器傳回了 404 (查無此頁) 或者 500 (內部錯誤) 什麼的
}

//檢查傳回的 HTTP 狀態碼後,要怎麼處理傳回的資料就由你決定了。有兩種存取資料的方式:
httpRequest.responseText //這樣會把傳回值視為字串用
httpRequest.responseXML //這樣會把傳回值視為 XMLDocument 物件, 而後可用 JavaScript DOM 相關函式處理
};

对于一个ajax请求, js引擎首先生成 XMLHttpRequest 实例对象, open过后再调用send方法. 至此, 所有的语句都是同步执行. 但从send方法内部开始, 浏览器为将要发生的网络请求创建了新的http请求线程, 这个线程独立于js引擎线程, 于是网络请求异步被发送出去了. 另一方面, js引擎并不会等待 ajax 发起的http请求收到结果, 而是直接顺序往下执行.

当ajax请求被服务器响应并且收到response后, 浏览器事件触发线程捕获到了ajax的回调事件 onreadystatechange (当然也可能触发onload, 或者 onerror等等) . 该回调事件并没有被立即执行, 而是被添加到 任务队列 的末尾. 直到js引擎空闲了, 任务队列 的任务才被捞出来, 按照添加顺序, 挨个执行, 当然也包括刚刚append到队列末尾的 onreadystatechange 事件.

通过这样的一种方式, ajax并没有破坏js的单线程机制.

XHR一级

XHR1 即 XMLHttpRequest Level 1. XHR1时, xhr对象具有如下缺点:

  • 仅支持文本数据传输, 无法传输二进制数据.
  • 传输数据时, 没有进度信息提示, 只能提示是否完成.
  • 受浏览器 同源策略 限制, 只能请求同域资源.
  • 没有超时机制, 不方便掌控ajax请求节奏.
    XHR二级
    XHR2 即 XMLHttpRequest Level 2. XHR2针对XHR1的上述缺点做了如下改进:
  • 支持二进制数据, 可以上传文件, 可以使用FormData对象管理表单.
  • 提供进度提示, 可通过 xhr.upload.onprogress 事件回调方法获取传输进度.
  • 依然受 同源策略 限制, 这个安全机制不会变. XHR2新提供 Access-Control-Allow-Origin 等headers, 设置为 * 时表示允许任何域名请求, 从而实现跨域CORS访问(有关CORS详细介绍请耐心往下读).
  • 可以设置timeout 及 ontimeout, 方便设置超时时长和超时后续处理.

目前, 主流浏览器基本上都支持XHR2, 除了IE系列需要IE10及更高版本. 因此IE10以下是不支持XHR2的.
那么问题来了, IE7, 8,9的用户怎么办? 很遗憾, 这些用户是比较尴尬的. 对于IE8,9而言, 只有一个阉割版的 XDomainRequest 可用,IE7则没有. 估计IE7用户只能哭晕在厕所了.

XDomainRequest

XDomainRequest 对象是IE8,9折腾出来的, 用于支持CORS请求非成熟的解决方案. 以至于IE10中直接移除了它, 并重新回到了 XMLHttpRequest 的怀抱.
XDomainRequest 仅可用于发送 GET和 POST 请求. 如下即创建过程.
var xdr = new XDomainRequest();
xdr具有如下属性:
timeout
responseText

如下方法:
open: 只能接收Method,和url两个参数. 只能发送异步请求.
send
abort

如下事件回调:
onprogress
ontimeout
onerror
onload

除了缺少一些方法外, XDomainRequest 基本上就和 XMLHttpRequest 的使用方式保持一致.
必须要明确的是:
XDomainRequest 不支持跨域传输cookie.
只能设置请求头的Content-Type字段, 且不能访问响应头信息.

jQuery中的Ajax

  1. jQuery.get(…)
    所有参数:
    url: 待载入页面的URL地址
    data: 待发送 Key / value 参数。
    success: 载入成功时回调函数。
    dataType: 返回内容格式, xml, json, script, text, html

  2. jQuery.post(…)
    所有参数:
    url: 待载入页面的URL地址
    data: 待发送 Key / value 参数
    success: 载入成功时回调函数
    dataType: 返回内容格式, xml, json, script, text, html

  3. jQuery.getJSON(…)
    所有参数:
    url: 待载入页面的URL地址
    data: 待发送 Key / value 参数。
    success: 载入成功时回调函数。

  4. jQuery.getScript(…)
    所有参数:
    url: 待载入页面的URL地址
    data: 待发送 Key / value 参数。
    success: 载入成功时回调函数。

  5. jQuery.ajax(…)
    部分参数:
    url: 请求地址
    type: 请求方式, GET、 POST( 1.9 .0 之后用method)
    headers: 请求头
    data: 要发送的数据
    contentType: 即将发送信息至服务器的内容编码类型(默认: “application/x-www-form-urlencoded; charset=UTF-8”)
    async: 是否异步
    timeout: 设置请求超时时间( 毫秒)
    beforeSend: 发送请求前执行的函数(全局)
    complete: 完成之后执行的回调函数(全局)
    success: 成功之后执行的回调函数(全局)
    error: 失败之后执行的回调函数(全局)
    accepts: 通过请求头发送给服务器, 告诉服务器当前客户端课接受的数据类型
    dataType: 将服务器端返回的数据转换成指定类型
    “xml”: 将服务器端返回的内容转换成xml格式 “text”: 将服务器端返回的内容转换成普通文本格式 “html”: 将服务器端返回的内容转换成普通文本格式, 在插入DOM中时, 如果包含JavaScript标签, 则会尝试去执行。 “script”: 尝试将返回值当作JavaScript去执行, 然后再将服务器端返回的内容转换成普通文本格式 “json”: 将服务器端返回的内容转换成相应的JavaScript对象 “jsonp”: JSONP 格式使用 JSONP 形式调用函数时, 如 “myurl?callback=?”
    jQuery 将自动替换 ? 为正确的函数名, 以执行回调函数

同源策略

同源策略限制了一个源(origin)中加载文本或脚本与来自其它源(origin)中资源的交互方式。

比如说,浏览器的两个tab页中分别打开了http://www.baidu.com/index.html和http: //www.google.com/index.html,其中,JavaScript1和JavaScript3是属于百度的脚本,而 JavaScript2是属于谷歌的脚本,当浏览器的tab1要运行一个脚本时,便会进行同源检查,只有和www.baidu.com同源的脚本才能被执 行,所谓同源,就是指域名、协议、端口相同。所以,tab1只能执行JavaScript1和JavaScript3脚本,而JavaScript2不能 执行,从而防止其他网页对本网页的非法篡改。

如果两个页面拥有相同的协议(protocol),端口(如果指定),和主机,那么这两个页面就属于同一个源(origin)。

IE 例外
当涉及到同源策略时,Internet Explorer有两个主要的例外:
授信范围(Trust Zones):两个相互之间高度互信的域名,如公司域名(corporate domains),不遵守同源策略的限制。
端口:IE未将端口号加入到同源策略的组成部分之中,因此 http://company.com:81/index.html 和http://company.com/index.html 属于同源并且不受任何限制。
这些例外是非标准的,其它浏览器也未做出支持,但会助于开发基于window RT IE的应用程序。

跨域

由于浏览器存在同源策略机制, 同源策略阻止从一个源加载的文档或脚本获取或设置另一个源加载的文档的属性。 所以ajax本身是不可以跨域的, 通过产生一个script标签来实现跨域。 因为script标签的src属性是没有跨域的限制的。

浏览器同源策略并不是对所有的请求均制约:
制约: XmlHttpRequest
不制约: img、 iframe、 script等具有src属性的标签

一、 JSONP实现跨域请求
JSONP是一个非官方的协议, 它允许在服务器端集成Script tags返回至客户端, 通过javascript callback的形式实现跨域访问。 jsonp只能通过get方式进行跨域请求

二、 CORS
这种方法就可以突破浏览器限制来进行传输。 当数据发送给对方域名的时候, 对方已经收到, 但是在返回的时候被浏览器给阻挡, 我们可以写一串类似于身份证的字符串, 通过浏览器的预检, 从而达到数据的传输。实际上, 浏览器不会拦截不合法的跨域请求, 而是拦截了他们的响应, 因此即使请求不合法, 很多时候, 服务器依然收到了请求.(Chrome和Firefox下https网站不允许发送http异步请求除外)

CORS有关的headers

1) HTTP Response Header(服务器提供):
Access-Control-Allow-Origin: 指定允许哪些源的网页发送请求.
Access-Control-Allow-Credentials: 指定是否允许cookie发送.
Access-Control-Allow-Methods: 指定允许哪些请求方法.
Access-Control-Allow-Headers: 指定允许哪些常规的头域字段, 比如说 Content-Type.
Access-Control-Expose-Headers: 指定允许哪些额外的头域字段, 比如说 X-Custom-Header.
该字段可省略. CORS请求时, xhr.getResponseHeader() 方法默认只能获取6个基本字段: Cache-Control、Content-Language、Content-Type、Expires、Last-Modified、Pragma . 如果需要获取其他字段, 就需要在Access-Control-Expose-Headers 中指定. 如上, 这样xhr.getResponseHeader(‘X-Custom-Header’) 才能返回X-Custom-Header字段的值.(该部分摘自阮一峰老师博客)
Access-Control-Max-Age: 指定preflight OPTIONS请求的有效期, 单位为秒.

2) HTTP Request Header(浏览器OPTIONS请求默认自带):
Access-Control-Request-Method: 告知服务器,浏览器将发送哪种请求, 比如说POST.
Access-Control-Request-Headers: 告知服务器, 浏览器将包含哪些额外的头域字段.

CORS请求分为简单请求和非简单请求

简单请求只一次请求, 而复杂请求是两次请求, 在发送数据之前会先发一次请求用于做“ 预检”, 只有“ 预检” 通过后才再发送一次请求用于数据传输。

简单请求:
1) 请求是以下三种之一:
1、 请求方式: HEAD、 GET、 POST
2、 http头域不超出以下几种字段:
Accept 浏览器能够处理的内容类型;
Accept - Language 浏览器当前设置的语言;
Content - Language
Last - Event - ID
Content - Type 对应的值是以下三个中的任意一个
application / x - www - form - urlencoded
multipart / form - data
text / plain
注意: 同时满足以上两个条件时, 则是简单请求, 否则为复杂请求

对于简单请求, 浏览器将发送一次http请求, 同时在Request头域中增加 Origin 字段, 用来标示请求发起的源, 服务器根据这个源采取不同的响应策略. 若服务器认为该请求合法, 那么需要往返回的 HTTP Response 中添加 Access-Control- 等字段.( Access-Control- 相关字段解析请阅读我之前写的CORS 跨域访问

复杂请求: 由于复杂请求时, 首先会发送“ 预检” 请求, 如果“ 预检” 成功, 则发送真实数据。

“ 预检” 请求时, 允许请求方式则需服务器设置响应头: Access - Control - Request - Method“
预检” 请求时, 允许请求头则需服务器设置响应头: Access - Control - Request - Headers“
预检” 缓存时间, 服务器设置响应头: Access - Control - Max - Age

对于非简单请求, 比如Method为POST且Content-Type值为 application/json 的请求或者Method为 PUT 或 DELETE 的请求, 浏览器将发送两次http请求. 第一次为preflight预检(Method: OPTIONS),主要验证来源是否合法. 值得注意的是:OPTION请求响应头同样需要包含 Access-Control-* 字段等. 第二次才是真正的HTTP请求. 所以服务器必须处理OPTIONS应答(通常需要返回20X的状态码, 否则xhr.onerror事件将被触发).

跨域传输cookie:
在跨域请求中, 默认情况下, HTTP Authentication信息, Cookie头以及用户的SSL证书无论在预检请求中或是在实际请求都是不会被发送。
如果想要发送:
浏览器端: XMLHttpRequest的withCredentials为true
服务器端: Access - Control - Allow - Credentials为true
注意: 服务器端响应的 Access - Control - Allow - Origin 不能是通配符 *

Axios

如果你仅仅只是想要一个不错的http库, 相比于庞大臃肿的jquery, 短小精悍的Axios可能更加适合你.

Axios支持node, jquery并不支持.
Axios基于promise语法, jq3.0才开始全面支持.
Axios短小精悍, 更加适合http场景, jquery大而全, 加载较慢.

语法上Axios基本就和promise一样, 在then方法中处理回调, 在catch方法中处理异常. 如下:

axios.get("https://api.github.com/users/louiszhai")
  .then(function(response){
    console.log(response);
  })
  .catch(function (error) {
    console.log(error);
  });

参考资料: http: //louiszhai.github.io/2016/11/02/ajax/

  • Ajax

展开全文 >>

« Prev1…1617181920…23Next »
© 2022 萌新
Hexo Theme Yilia by Litten
  • 所有文章
  • 关于我

tag:

  • Ajax
  • Js基础
  • webgl canvas 游戏 引擎
  • es6
  • React.js
  • Sass
  • SQL
  • 分享会
  • Vue.JS
  • webpack
  • webAR
  • 《JavaScript设计模式与开发实践》
  • 《JavaScript面向对象编程指南》
  • 《JavaScript面向对象编程指南》阅读笔记
  • react
  • 《你不知道的JavaScript》
  • this
  • 图解HTTP
  • 读书是一场修行
  • 《实战ES2015》
  • 杂谈
  • 移动前端开发进阶之路
  • 工具
  • 深入理解ES6
  • 疯言疯语
  • HTML5
  • 移动web开发
  • 微信小游戏

    缺失模块。
    1、请确保node版本大于6.2
    2、在博客根目录(注意不是yilia根目录)执行以下命令:
    npm i hexo-generator-json-content --save

    3、在根目录_config.yml里添加配置:

      jsonContent:
        meta: false
        pages: false
        posts:
          title: true
          date: true
          path: true
          text: false
          raw: false
          content: false
          slug: false
          updated: false
          comments: false
          link: false
          permalink: false
          excerpt: false
          categories: false
          tags: true
    

很惭愧

只做了一点微小的工作
谢谢大家