ajax

什么是ajax?

ajax的全名叫做async javascript and xml,即異步的javascript 和 xml
它的實現(xiàn)過程如下:

  1. 使用 XMLHttpRequest 發(fā)請求
  2. 服務器返回 XML 格式的字符串
  3. JS 解析 XML授账,并更新局部頁面

注:現(xiàn)在的服務器基本上都是返回json類型的數(shù)據(jù)了

ajax的使用

// 后端代碼
  if(path==='/xxx'){    //path為url中的請求路徑
    response.statusCode = 200
    response.setHeader('Content-Type', 'text/json;charset=utf-8')
    response.write(`
    {
      "people":{
        "name": "海山城",
        "age": "25",
        "sex": "male"
      }
    }
    `)
    response.end()
}
//前端ajax的使用
let request = new XMLHttpRequest()
request.open('GET', '/xxx')
request.send()
request.onreadystatechange = function(){
  if(request.readyState === 4){
    if(request.status >= 200 && request.status < 300){
      let string = request.responseText //服務器返回的JSON類型的字符串
      let object = JSON.parse(string )  //通過這個api將JSON類型的字符串轉換成一個對象
    }
  }
}

封裝一個ajax

封裝一個 jQuery.ajax空执,滿足 jQuery.ajax(url, method, body, success, fail)
自己已經(jīng)封裝過一個簡單的jQuery了,詳見實現(xiàn)一個jQuery的api婴梧,接著來為這個jQuery函數(shù)本身(函數(shù)本事也是一個對象)增加一個ajax的函數(shù)


//超簡化版jQuery
window.jQuery = function(nodeOrSelector){
  let nodes = {}
  nodes.addClass = function(){}
  return nodes
}
window.$ = window.jQuery

window.jQuery.ajax = function(options){
  let request = new XMLHttpRequest()
  let url = options.url
  let method = options.method
  let body = options.body
  let successFn = options.successFn
  let failFn = options.failFn
  let headers = options.headers
  
  request.open(method, url)
  //header的設置要在open和send之間
  for(let key in headers){
    request.setRequestHeader(key, headers[key])
  }
  request.send(body)
  request.onreadystatechange = function(){
    if(request.readyState === 4){
      if(request.status >= 200 && request.status < 300){
        successFn.call(undefined, request.responseText)
      } else if(request.status >= 400){
        failFn.call(undefined, request)
      }
    }
  }
}

$.ajax({
  url: 'http://localhost:8000/cors',
  method: 'POST',
  body: 'name=seaMount&age=25',
  headers: {
    'content-type': 'application/x-www-form-urlencoded',
    'accept': 'text/json'
  },
  successFn: function(response){
    console.log(response)
  },
  failFn: function(x){
    console.log('請求失敗')
    console.log(x.responseText)
  }
})

注:上面大段用let定義的代碼下梢,看起來挺丑陋的,可以用es6的解構改進

window.jQuery.ajax = function({url, method, body, successFn, failFn, headers}){名字和傳入的參數(shù)要相同塞蹭,位置無需相同
  let request = new XMLHttpRequest()
  request.open(method, url)
  //header的設置要在open和send之間
  for(let key in headers){
    request.setRequestHeader(key, headers[key])
  }
  request.send(body)
  request.onreadystatechange = function(){
    if(request.readyState === 4){
      if(request.status >= 200 && request.status < 300){
        successFn.call(undefined, request.responseText)
      } else if(request.status >= 400){
        failFn.call(undefined, request)
      }
    }
  }
}

升級 jQuery.ajax 滿足 Promise 規(guī)則

因為調用我寫的這個jQuery.ajax的api給外人用孽江,根本不知道傳入的參數(shù)函數(shù)叫什么,不看文檔你能知道失敗的函數(shù)叫failFn番电?并且每個人寫的命名不相同岗屏。Promise規(guī)范不用取名字辆琅,標準化了操作


//超簡化版jQuery
window.jQuery = function(nodeOrSelector){
  let nodes = {}
  nodes.addClass = function(){}
  return nodes
}
window.$ = window.jQuery

window.jQuery.ajax = function({url, method, body, headers}){
  return new Promise(function(resolve, reject){
    let request = new XMLHttpRequest()
    request.open(method, url)
    //header的設置要在open和send之間
    for(let key in headers){
      request.setRequestHeader(key, headers[key])
    }
    request.send(body)
    request.onreadystatechange = function(){
      if(request.readyState === 4){
        if(request.status >= 200 && request.status < 300){
          resolve.call(undefined, request.responseText)
        } else if(request.status >= 400){
          reject.call(undefined, request)
        }
      }
    }
  })
}

let promise = $.ajax({
  url: 'http://localhost:8000/cors',
  method: 'POST',
  body: 'name=seaMount&age=25',
  headers: {
    'content-type': 'application/x-www-form-urlencoded',
    'accept': 'text/json'
  }
})

promise.then(
  function(response){
    console.log(response)
  },
  function(x){
    console.log('請求失敗')
    console.log(x.responseText)
  }
)
  • then里面?zhèn)魅雰蓚€函數(shù),第一個是指success的回調函數(shù)这刷,第二個是指fail的回調函數(shù)
  • then可以通過鏈式操作透傳婉烟,下一個then中的函數(shù)的參數(shù)對應的是上一個中的return值。這樣可以多次對結果進行處理
?著作權歸作者所有,轉載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末暇屋,一起剝皮案震驚了整個濱河市似袁,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌咐刨,老刑警劉巖昙衅,帶你破解...
    沈念sama閱讀 211,376評論 6 491
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異定鸟,居然都是意外死亡而涉,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 90,126評論 2 385
  • 文/潘曉璐 我一進店門联予,熙熙樓的掌柜王于貴愁眉苦臉地迎上來啼县,“玉大人,你說我怎么就攤上這事沸久〖揪欤” “怎么了?”我有些...
    開封第一講書人閱讀 156,966評論 0 347
  • 文/不壞的土叔 我叫張陵麦向,是天一觀的道長瘟裸。 經(jīng)常有香客問我,道長诵竭,這世上最難降的妖魔是什么话告? 我笑而不...
    開封第一講書人閱讀 56,432評論 1 283
  • 正文 為了忘掉前任,我火速辦了婚禮卵慰,結果婚禮上沙郭,老公的妹妹穿的比我還像新娘。我一直安慰自己裳朋,他們只是感情好病线,可當我...
    茶點故事閱讀 65,519評論 6 385
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著鲤嫡,像睡著了一般送挑。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上暖眼,一...
    開封第一講書人閱讀 49,792評論 1 290
  • 那天惕耕,我揣著相機與錄音,去河邊找鬼诫肠。 笑死司澎,一個胖子當著我的面吹牛欺缘,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播挤安,決...
    沈念sama閱讀 38,933評論 3 406
  • 文/蒼蘭香墨 我猛地睜開眼谚殊,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了蛤铜?” 一聲冷哼從身側響起嫩絮,我...
    開封第一講書人閱讀 37,701評論 0 266
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎昂羡,沒想到半個月后絮记,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體摔踱,經(jīng)...
    沈念sama閱讀 44,143評論 1 303
  • 正文 獨居荒郊野嶺守林人離奇死亡虐先,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 36,488評論 2 327
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了派敷。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片蛹批。...
    茶點故事閱讀 38,626評論 1 340
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖篮愉,靈堂內(nèi)的尸體忽然破棺而出腐芍,到底是詐尸還是另有隱情,我是刑警寧澤试躏,帶...
    沈念sama閱讀 34,292評論 4 329
  • 正文 年R本政府宣布猪勇,位于F島的核電站,受9級特大地震影響颠蕴,放射性物質發(fā)生泄漏泣刹。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點故事閱讀 39,896評論 3 313
  • 文/蒙蒙 一犀被、第九天 我趴在偏房一處隱蔽的房頂上張望椅您。 院中可真熱鬧,春花似錦寡键、人聲如沸掀泳。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,742評論 0 21
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽员舵。三九已至,卻和暖如春藕畔,著一層夾襖步出監(jiān)牢的瞬間马僻,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 31,977評論 1 265
  • 我被黑心中介騙來泰國打工劫流, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留巫玻,地道東北人丛忆。 一個月前我還...
    沈念sama閱讀 46,324評論 2 360
  • 正文 我出身青樓,卻偏偏與公主長得像仍秤,于是被迫代替她去往敵國和親熄诡。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 43,494評論 2 348

推薦閱讀更多精彩內(nèi)容