Chuyển đến nội dung chính

第 8 課:FHIR RESTful API - CRUD、搜尋、歷史記錄和版本控制

REST 互動的詳細資訊:建立 (POST)、讀取 (GET)、更新 (PUT)、修補 (PATCH)、刪除 (DELETE)、vread、歷史記錄。內容協商 (JSON/XML)、ETag、If-Match、條件操作、CapabilityStatement。

🏗️ 建築 — 第 8 課 第 8 課:FHIR RESTful API - CRUD、搜尋、 歷史和版本控制

HL7 FHIR - 基礎到進階醫療資料標準

第 3 部分:FHIR RESTful API 和資料交換

亞洲開發網

1.FHIR RESTful API 概述

FHIR 用途 RESTful API 作為主要的互動範式。每個資源類型都有自己的端點,遵循 HTTP 標準。

基本網址

https://fhir-server.example.com/fhir/r5
        ├── base URL ──────────────────┘
        
GET [base]/Patient/123           → Đọc Patient có id=123
POST [base]/Patient              → Tạo Patient mới
PUT [base]/Patient/123           → Cập nhật Patient 123
DELETE [base]/Patient/123        → Xóa Patient 123

互動概述

互動HTTP方法網址描述
讀獲取[基礎]/[類型]/[id]閱讀資源
讀取獲取[基礎]/[類型]/[id]/_history/[vid]閱讀具體版本
更新。更新放置[基礎]/[類型]/[id]更新資源
補丁。補丁補丁[基礎]/[類型]/[id]部分更新
刪除刪除[基礎]/[類型]/[id]刪除資源
創造後處理[基礎]/[類型]建立新資源
搜尋。搜尋獲取/發布[基數]/[型]?參數搜尋
歷史。歷史獲取[基礎]/[類型]/[id]/_歷史記錄歷史變遷
能力獲取[基礎]/元數據能力聲明

2. 創建(發布)

POST /fhir/r5/Patient HTTP/1.1
Host: fhir-server.example.com
Content-Type: application/fhir+json
Prefer: return=representation

{
  "resourceType": "Patient",
  "name": [
    {
      "family": "Nguyễn",
      "given": ["Văn", "A"],
      "text": "Nguyễn Văn A"
    }
  ],
  "gender": "male",
  "birthDate": "1990-05-15"
}
HTTP/1.1 201 Created
Location: /fhir/r5/Patient/newly-assigned-id/_history/1
ETag: W/"1"
Last-Modified: 2025-01-15T10:00:00Z
Content-Type: application/fhir+json

{
  "resourceType": "Patient",
  "id": "newly-assigned-id",
  "meta": {
    "versionId": "1",
    "lastUpdated": "2025-01-15T10:00:00.000Z"
  },
  ...
}

條件創建

POST /fhir/r5/Patient HTTP/1.1
If-None-Exist: identifier=http://hospital.vn/mrn|MRN12345

{...}

僅在沒有符合條件的患者時才建立 → 避免重複。

3. 讀取(取得)

GET /fhir/r5/Patient/patient-001 HTTP/1.1
Accept: application/fhir+json

版本讀取(vread)

GET /fhir/r5/Patient/patient-001/_history/3 HTTP/1.1

內容協商

接受標頭格式
應用程式/fhir+jsonJSON(推薦)
應用程式/fhir+xmlXML
或使用 _format 參數?_format=json

4. 更新(放置)

PUT /fhir/r5/Patient/patient-001 HTTP/1.1
Content-Type: application/fhir+json
If-Match: W/"3"

{
  "resourceType": "Patient",
  "id": "patient-001",
  "name": [
    {
      "family": "Nguyễn",
      "given": ["Văn", "A"],
      "text": "Nguyễn Văn A"
    }
  ],
  "gender": "male",
  "birthDate": "1990-05-15",
  "telecom": [
    {
      "system": "phone",
      "value": "0901234567",
      "use": "mobile"
    }
  ]
}

如果匹配:W/“3” → 樂觀鎖定。僅噹噹前版本為 3 時才更新。如果已更改 → 409 衝突。

有條件更新

PUT /fhir/r5/Patient?identifier=http://hospital.vn/mrn|MRN12345 HTTP/1.1

{...resource body...}

5.補丁(PATCH)

JSON 補丁(RFC 6902)

PATCH /fhir/r5/Patient/patient-001 HTTP/1.1
Content-Type: application/json-patch+json

[
  {
    "op": "add",
    "path": "/telecom/-",
    "value": {
      "system": "email",
      "value": "[email protected]",
      "use": "home"
    }
  },
  {
    "op": "replace",
    "path": "/active",
    "value": true
  }
]

FHIR路徑補丁

PATCH /fhir/r5/Patient/patient-001 HTTP/1.1
Content-Type: application/fhir+json

{
  "resourceType": "Parameters",
  "parameter": [
    {
      "name": "operation",
      "part": [
        {"name": "type", "valueCode": "add"},
        {"name": "path", "valueString": "Patient"},
        {"name": "name", "valueString": "active"},
        {"name": "value", "valueBoolean": true}
      ]
    }
  ]
}

6. 刪除(DELETE)

DELETE /fhir/r5/Patient/patient-001 HTTP/1.1

FHIR 伺服器通常實現 邏輯刪除 (標記已刪除,保留在歷史記錄中)而不是實體刪除。

7. 歷史

# History của một resource
GET /fhir/r5/Patient/patient-001/_history

# History của tất cả Patient
GET /fhir/r5/Patient/_history

# History toàn server
GET /fhir/r5/_history

# Với parameters
GET /fhir/r5/Patient/patient-001/_history?_count=10&_since=2025-01-01T00:00:00Z

回應返回Bundle類型 歷史。歷史 包含所有版本。

8. 基本搜索

# Tìm Patient theo tên
GET /fhir/r5/Patient?name=Nguyen

# Tìm theo giới tính
GET /fhir/r5/Patient?gender=male

# Kết hợp nhiều tham số (AND)
GET /fhir/r5/Patient?name=Nguyen&gender=male&birthdate=1990-05-15

# Tìm Observation theo Patient
GET /fhir/r5/Observation?subject=Patient/patient-001&category=vital-signs

# POST search (khi query string quá dài)
POST /fhir/r5/Patient/_search
Content-Type: application/x-www-form-urlencoded

name=Nguyen&gender=male

搜尋回應(捆綁搜尋集)

{
  "resourceType": "Bundle",
  "type": "searchset",
  "total": 42,
  "link": [
    {
      "relation": "self",
      "url": "https://fhir-server.example.com/fhir/r5/Patient?name=Nguyen&_count=10"
    },
    {
      "relation": "next",
      "url": "https://fhir-server.example.com/fhir/r5?_getpages=uuid-abc&_pageId=2"
    }
  ],
  "entry": [
    {
      "fullUrl": "https://fhir-server.example.com/fhir/r5/Patient/patient-001",
      "resource": {
        "resourceType": "Patient",
        "id": "patient-001"
      },
      "search": {
        "mode": "match",
        "score": 1
      }
    }
  ]
}

9. 能力聲明

GET /fhir/r5/metadata HTTP/1.1
Accept: application/fhir+json

能力聲明 (舊名稱:一致性)描述了 FHIR 伺服器的功能:它支援哪些資源類型、互動和搜尋參數。

10. FHIR 中的 HTTP 狀態碼

狀態意義
200 好讀取/搜尋/更新成功
201 已建立創建成功
204 沒有內容刪除成功
304 未修改有條件讀取,不改變
400 錯誤請求請求無效
401 未經授權未經驗證
403 禁忌無權利
404 未找到資源不存在
409 衝突版本衝突(If-Match)
410 走了資源已刪除
第412章 前提條件失敗條件操作失敗
422 無法處理的實體驗證失敗(操作結果)

11. 總結

  • FHIR RESTful API 符合 HTTP 標準: 發布/獲取/放置/修補/刪除

  • 版本控制 — 每次更新都會建立一個新版本,可透過 vread 和歷史記錄存取

  • 條件運算 — If-Match、If-None-Exist 用於並發控制

  • 搜尋 — 具有多種參數類型、AND/OR 組合的高靈活性

  • 能力聲明 - 自描述伺服器功能(機器可讀)