iT邦幫忙

2026 iThome 鐵人賽

DAY 17
0
自我挑戰組

30 天養大一個開源專案:baodao-skill 從零開始系列 第 17 篇

【Day 17】要 37,152 筆只給 1,000 筆:健保院所名錄的靜默截斷

  • 分享至 

  • xImage
  •  

先講結論:健保署的院所 API 有一個不發出任何聲音的陷阱——你帶 limit=40000 去要全台灣的健保特約醫院診所,它回你 HTTP 200、整整 1,000 筆,沒有錯誤、沒有警告。2026-09-24 實測:result.limit 悄悄寫著 1000,result.total 誠實寫著 37,152。只看 records 長度的程式,會以為全台灣只有 1,000 家醫院,然後安心下班。地雷圖鑑裡最危險的一種:靜默截斷。

連我們自己的範例都中過招

這不是假想敵。taiwan-hospital 收錄時的全量下載範例,就是單次把 limit 拉高抓全部——9/20 的硬化工程(0.8.1)做文件程式實測時才抓到:38 頁才能取齊的 37,133 筆,舊寫法永遠只拿到 1,000 筆。修正後的版本先看 result.total,再用 offset 一頁一頁取。文件寫的程式要能被 CI 直接執行,就是為了攔這種「看起來能跑」的程式。

實測:38 頁取齊 37,152 家

import json, urllib.request
UA = {'User-Agent': 'Mozilla/5.0'}
BASE = 'https://info.nhi.gov.tw/api/iode0010/v1/rest/datastore/A21030000I-D2100G-001'
def page(offset):
    req = urllib.request.Request(f'{BASE}?limit=1000&offset={offset}', headers=UA)
    return json.loads(urllib.request.urlopen(req, timeout=40).read())['result']
first = page(0)
total, recs = first['total'], list(first['records'])
for off in range(1000, total, 1000):
    recs += page(off)['records']
print(total, len(recs))

2026-09-24 實測輸出:37152 37152——38 頁,一页不缺。資料源:健保署開放資料 A21030000I-D2100G-001(醫事機構基本資料),免 key、免登入。

37,152 家的分佈長這樣(2026-09-24 實測,依 HOSP_ATTR_NAME):

類型 家數
私立西醫診所 11,970
其他(多為藥局) 11,873
私立牙醫診所 7,711
私立中醫診所 4,636
衛生所 349
私立西醫醫院 235

「其他」那一萬多家,點開名字幾乎都是藥局——富康活力、康是美、安安藥局這些連鎖全在裡面。名稱含「診所」兩字的合計 24,354 家。隨手抽一個生活例子:台北市大同區 224 家,鈞生診所在甘州街 28 號,電話 (02)2557-0048。順帶一個眼熟的細節:地址欄是全形數字(鄭州路145號),Day 11 的教訓繼續適用。

這個數字是活的

文件上寫的是 37,133(2026-09-20 實測),今天早上實測已經是 37,152——四天多了 19 家。更妙的是,同一次實測裡前後兩次呼叫,total 從 37,149 變成 37,152:名錄後台幾乎是即時在更新的。所以回答這類問題一定要附查詢日期,這也是 Day 15 那堂課的續集——基準數字會漂,CI 要每晚重問。只是健保署這站有個小麻煩:它會斷 GitHub Actions 的 IP,CI 上的健保檢查多半只能 WARN 跳過,這種漂移在 CI 上反而是看不見的,得靠不佈署在雲上的眼睛。

錯誤處理(寫進 SKILL 的規矩)

  • limit 封頂 1,000:全量一律分頁,取完比對 result.total,對不上就重取或回報,不把殘缺當全部。
  • 這是名錄不是現場:掛號、即時看診進度、醫師排班都不在裡面,如實說不支援。要看診時段有姊妹資料集 D21006(固定服務時段)、D2100C(診療科別)。
  • 數字會動:回報院所數、家數統計時附查詢日期。
  • 連不上(info.nhi.gov.tw 對部分 IP 不友善)就換網路重試;持續失敗回報資料源異常,不編名錄。

第 17 天。地雷圖鑑給這條的位置很前面:會報錯的 API 不可怕,可怕的是 200 OK 配上悄悄縮水的資料。


上一篇
【Day 16】台電主站 403:官網擋程式,隔壁主機免 key 給 JSON(實測 2,639.7 萬瓩)
下一篇
【Day 18】14.7MB 的實價登錄:下一季回 200 但不是 zip,這一季的中山區一坪 91.9 萬
系列文
30 天養大一個開源專案:baodao-skill 從零開始 共 24 篇
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言