NUK JavaScript Lesson 05:AJAX 撈取資料

這次要介紹如何用 AJAX 撈取資料

xhr 撈取資料

STEPS

使用資料:Open1999 派工受理案件資料
資料網址:https://data.kcg.gov.tw/dataset/open1999

  1. 起手式,建立一個 XMLHttpRequest
1
let xhr = new XMLHttpRequest();
  1. 傳送一個網路請求到對方伺服器要資料,準備取得 (get) 網址資料
1
2
3
4
xhr.open(
'get',
'https://soweb.kcg.gov.tw/open1999/ServiceRequestsQuery.asmx/ServiceRequestsQuery?startdate=&enddate='
);

此時資料還沒回傳

  1. 對方伺服器確認身分後,回傳資料給我
1
xhr.send();

資料會回傳到 response 跟 responseText

  1. 拿到資料後再看要怎麼處理

readyState

  • 0:已經新增一個 XMLHttpRequest,但是還沒連結到要撈的資料
  • 1:已發出網路請求,準備取得網址資料,但是對方還沒傳資料
  • 2:偵測到你有用 send()
  • 3:資料 loading 中
  • 4:已接收到資料,資料會回傳到 response 跟 responseText

將字串轉型成 JSON 格式

撈到 JSON 資料後,我們要先將字串轉型成 JSON 格式

1
JSON.parse(字串);

範例一:

1
2
let b = JSON.parse(a);
console.log(b[0]);

範例二:

1
2
JSON.parse(xhr.responseText);
console.log(data[1].ZipName_);

onload 非同步

如果有人是用 VSCode 在練習的話
可能會發現資料都跑不出來
但是在瀏覽器的 console 輸入 code 的話卻又可以跑出資料
為什麼會這樣子呢?

原因是 xhr 被放在等待區,資料還沒回傳
但是程式碼編譯很快
所以馬上執行的話,撈出來的資料就還是空值

那要怎麼解決?
有段語法叫做 onload
加上去之後,裡面的程式碼會 等到資料回傳時才會觸發

1
2
3
4
xhr.onload = function () {
let data = JSON.parse(xhr.responseText);
console.log(data[1].ZipName_);
};

小考題:各個 console.log 的顯示順序為何?

1
2
3
4
5
6
7
8
console.log(xhr.responseText);
xhr.onload = function () {
console.log(1);
let data = JSON.parse(xhr.responseText);
console.log(data[0].ZipName_);
};
console.log(xhr.responseText);
console.log(2);

答案是:1, 7, 8, 3, 5
而且前兩個 console.log(xhr.responseText) 所回傳的是空值

總複習

題目:撈出鼓山區總共有多少案件

1999 API:https://data.kcg.gov.tw/dataset/open1999

HTML

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Document</title>
<link rel="stylesheet" href="./css/all.css">
</head>
<body>
<h2>鼓山區有幾筆案件哩 :P</h2>
<p>總共有 <span class="total"></span> 筆案件</p>

<script src="./js/all.js"></script>
</body>
</html>

JavaScript

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
let xhr = new XMLHttpRequest();
xhr.open(
'get',
'https://soweb.kcg.gov.tw/open1999/ServiceRequestsQuery.asmx/ServiceRequestsQuery?startdate=&enddate='
);
xhr.send();

xhr.onload = function () {
let data = JSON.parse(xhr.responseText);
let dataLen = data.length;
let total = document.querySelector('.total');
let totalNum = 0;

for (let i = 0; i < dataLen; i++) {
if (data[i].ZipName_ == '鼓山區') {
totalNum += 1;
}
}

total.innerHTML = totalNum;
console.log('鼓山區總共有' + totalNum + '筆案件');
};

以上資源是我自己整理過後的筆記,若有錯誤歡迎隨時和我聯繫。