iT邦幫忙

2026 iThome 鐵人賽

DAY 2
0

前言

在上一篇文章中,我們深入認識了FHIR Resource,了解Resource是FHIR交換資料的基本單位,也釐清了ididentifiermetaReference等概念。

從今天開始,我們要實際閱讀一份FHIR Resource。

第一個要認識的是最常見的Patient Resource。

Patient Resource用來記錄接受健康照護服務的人,也就是病人的基本行政資料,例如姓名、出生日期、聯絡方式和地址。

今天會先展示一份完整的虛構Patient JSON,再將內容分段拆解,看看每個欄位分別代表什麼。

本文中的姓名、病歷號、電話、地址及醫療機構全部都是虛構的教學資料,請勿在公開測試環境中使用真實病人的個人資料。


Patient Resource負責記錄什麼?

Patient Resource主要記錄與病人身分及行政管理有關的資料,例如:

  • 病歷號等識別資料
  • 姓名
  • 生理性別或行政管理用途的性別
  • 出生日期
  • 聯絡方式
  • 地址
  • 婚姻狀態
  • 聯絡人
  • 慣用語言
  • 管理這筆病人資料的醫療機構

Patient不適合拿來記錄所有醫療資訊。

例如:

資料內容 適合使用的Resource
病人姓名與生日 Patient
本次門診或住院 Encounter
血壓與體溫 Observation
疾病或診斷 Condition
用藥醫令 MedicationRequest
過敏紀錄 AllergyIntolerance

因此,Patient比較像是病人基本資料的核心,而不是一份包含所有看診內容的完整病歷。


今天使用的Patient JSON

以下是一份FHIR R4 Patient Resource範例:

{
  "resourceType": "Patient",
  "id": "patient-example",
  "identifier": [
    {
      "use": "usual",
      "system": "https://hospital.example.org/mrn",
      "value": "MRN0001"
    }
  ],
  "active": true,
  "name": [
    {
      "use": "official",
      "text": "王小明",
      "family": "王",
      "given": [
        "小明"
      ]
    }
  ],
  "telecom": [
    {
      "system": "phone",
      "value": "0900-000-001",
      "use": "mobile"
    }
  ],
  "gender": "male",
  "birthDate": "2000-01-01",
  "address": [
    {
      "use": "home",
      "type": "both",
      "text": "桃園市中壢區範例路100號",
      "city": "中壢區",
      "district": "桃園市",
      "country": "TW"
    }
  ],
  "maritalStatus": {
    "coding": [
      {
        "system": "http://terminology.hl7.org/CodeSystem/v3-MaritalStatus",
        "code": "S",
        "display": "Never Married"
      }
    ],
    "text": "未婚"
  },
  "communication": [
    {
      "language": {
        "coding": [
          {
            "system": "urn:ietf:bcp:47",
            "code": "zh-TW",
            "display": "Chinese (Taiwan)"
          }
        ],
        "text": "繁體中文"
      },
      "preferred": true
    }
  ],
  "managingOrganization": {
    "reference": "Organization/hospital-example",
    "display": "範例醫院"
  }
}

這份範例使用FHIR R4的基本Patient結構,主要目的是學習欄位。它沒有宣告符合TW Core Profile,因此不能直接視為一份完整的TW Core Patient資料。

接下來從第一個欄位開始閱讀。


resourceType:表示Resource類型

"resourceType": "Patient"

resourceType告訴系統這是一筆Patient Resource。

FHIR中有許多Resource,因此接收方必須先知道資料類型,才能依照正確規則解析後面的欄位。

這個值的大小寫需要符合規範,應寫成:

Patient

而不是:

patient

或:

PATIENT

id:FHIR Server中的邏輯識別碼

"id": "patient-example"

id是這筆Resource在FHIR Server中的邏輯識別碼。

假設FHIR Server的基礎網址是:

https://hospital.example.org/fhir

這筆Patient Resource的網址可能是:

https://hospital.example.org/fhir/Patient/patient-example

其中:

  • Patient是Resource類型。
  • patient-example是Resource的id

之後如果要讀取這筆資料,可以使用:

GET https://hospital.example.org/fhir/Patient/patient-example

identifier:病歷號等實務識別資料

"identifier": [
  {
    "use": "usual",
    "system": "https://hospital.example.org/mrn",
    "value": "MRN0001"
  }
]

identifier用來表示實務流程中使用的識別資料,例如病歷號。

這裡包含三個欄位:

use

"use": "usual"

use表示這個identifier的用途。

usual可以理解為一般或慣用的識別資料。

system

"system": "https://hospital.example.org/mrn"

system不是指電腦作業系統,而是用來表示這個編號屬於哪一套識別系統。

不同醫院都可能有MRN0001這個病歷號,因此只看value不一定能確定病人來自哪家機構。

搭配system後,就能表達:

這是由特定醫院病歷號系統所核發的MRN0001。

value

"value": "MRN0001"

value是實際的識別碼內容,在這個範例中是虛構病歷號。


再次比較id與identifier

欄位 範例 用途
id patient-example 識別FHIR Server裡的Resource
identifier.value MRN0001 表示醫院實務使用的病歷號
identifier.system https://hospital.example.org/mrn 說明病歷號由哪套識別系統定義

一位病人在不同FHIR Server中可能擁有不同的id,也可能同時具有一個以上的identifier

例如,同一位病人可能同時有院內病歷號及其他醫療行政識別資料。


active:這筆病人紀錄是否有效

"active": true

active是一個布林值,只有兩種結果:

  • true
  • false

true表示這筆Patient紀錄目前被視為有效使用中的紀錄。

false則表示這筆紀錄不再被積極使用,可能與紀錄合併、重複建檔或其他行政原因有關。

需要注意的是:

active: false不代表病人已經死亡。

病人是否死亡在Patient中有其他欄位可以表示,例如deceasedBooleandeceasedDateTime


name:病人姓名

"name": [
  {
    "use": "official",
    "text": "王小明",
    "family": "王",
    "given": [
      "小明"
    ]
  }
]

name使用HumanName資料型別。

它不是一個單純的字串,而是可以將姓名拆成不同部分。

use

"use": "official"

official表示這是正式姓名。

FHIR也能使用其他代碼表示暱稱、舊名或匿名使用的名稱等不同用途。

text

"text": "王小明"

text是適合直接顯示給人看的完整姓名。

family

"family": "王"

family通常用來記錄姓氏或家族名稱。

given

"given": [
  "小明"
]

given用來記錄名字。

因為不同文化的姓名可能包含一個以上的given name,所以它使用陣列表示。

FHIR需要支援不同國家及文化的姓名結構,因此姓名的設計會比單一name文字欄位更有彈性。


為什麼name外面有中括號?

name的內容使用:

[
  {
    ...
  }
]

中括號[]表示這是一個陣列,可以放入多筆姓名。

例如,一個人可能同時具有正式姓名和暱稱:

"name": [
  {
    "use": "official",
    "text": "王小明"
  },
  {
    "use": "nickname",
    "text": "小明"
  }
]

第一筆是正式姓名,第二筆則是暱稱。

因此,即使目前只有一筆姓名,name仍然使用陣列結構。

JSON中的Object與Array會在下一篇文章中進一步說明。


telecom:電話與電子郵件

"telecom": [
  {
    "system": "phone",
    "value": "0900-000-001",
    "use": "mobile"
  }
]

telecom用來記錄聯絡方式,常見內容包括:

  • 電話
  • 電子郵件
  • 傳真
  • 其他通訊方式

這個範例包含:

system

"system": "phone"

表示聯絡方式是電話。

如果是電子郵件,可能寫成:

"system": "email"

value

"value": "0900-000-001"

表示實際的聯絡內容。本文使用的是虛構電話號碼。

use

"use": "mobile"

表示這是一組行動電話。

telecom同樣是陣列,因此可以同時記錄行動電話、住家電話及電子郵件。


gender:行政管理用途的性別

"gender": "male"

FHIR R4 Patient的gender使用AdministrativeGender代碼。

常見值包括:

代碼 意義
male 男性
female 女性
other 其他
unknown 未知

這裡使用完整的male,而不是自行寫成M1

使用固定代碼可以減少不同系統對資料產生不同解讀。

不過,Patient的gender屬於行政管理用途,不能直接用一個欄位完整表達所有與性別相關的個人或臨床資訊。


birthDate:出生日期

"birthDate": "2000-01-01"

birthDate使用FHIR的date資料型別,完整日期通常採用:

YYYY-MM-DD

也就是「年-月-日」。

在這個範例中:

  • 年:2000
  • 月:01
  • 日:01

統一日期格式能避免01/02/2000究竟代表1月2日還是2月1日的問題。

如果來源資料只知道出生年份,也可以只記錄:

"birthDate": "2000"

不能因為系統要求完整日期,就自行捏造不知道的月份或日期。


address:地址

"address": [
  {
    "use": "home",
    "type": "both",
    "text": "桃園市中壢區範例路100號",
    "city": "中壢區",
    "district": "桃園市",
    "country": "TW"
  }
]

address使用Address資料型別,也是一個可以放入多筆資料的陣列。

病人可能同時具有:

  • 戶籍地址
  • 居住地址
  • 工作地址
  • 過去地址

範例中的欄位包括:

use

"use": "home"

表示這是住家地址。

type

"type": "both"

表示這個地址可以同時作為實體地址及郵寄地址。

text

"text": "桃園市中壢區範例路100號"

text是適合直接顯示給人閱讀的完整地址。

city、district及country

"city": "中壢區",
"district": "桃園市",
"country": "TW"

這些欄位將地址拆成不同部分,方便系統進行結構化處理。

不同國家的地址結構不完全相同。臺灣地址在FHIR中如何更精確地表示,需要參考TW Core IG的規則,不能只依照英文欄位名稱直接猜測。


maritalStatus:婚姻狀態

"maritalStatus": {
  "coding": [
    {
      "system": "http://terminology.hl7.org/CodeSystem/v3-MaritalStatus",
      "code": "S",
      "display": "Never Married"
    }
  ],
  "text": "未婚"
}

maritalStatus使用CodeableConcept資料型別。

它不只放入一段「未婚」文字,也可以包含標準代碼。

system

"system": "http://terminology.hl7.org/CodeSystem/v3-MaritalStatus"

表示代碼來自哪一套CodeSystem。

code

"code": "S"

是系統實際處理的代碼。

display

"display": "Never Married"

是該代碼適合顯示給人閱讀的名稱。

text

"text": "未婚"

則是這筆資料在目前情境中希望呈現的文字。

這種設計同時兼顧電腦處理及人類閱讀。


communication:慣用語言

"communication": [
  {
    "language": {
      "coding": [
        {
          "system": "urn:ietf:bcp:47",
          "code": "zh-TW",
          "display": "Chinese (Taiwan)"
        }
      ],
      "text": "繁體中文"
    },
    "preferred": true
  }
]

communication表示可以用什麼語言與病人溝通。

範例中的:

"code": "zh-TW"

代表臺灣繁體中文語言標籤。

"preferred": true

表示這是病人偏好的溝通語言。

如果病人會使用多種語言,communication陣列就可以包含多筆資料,再使用preferred指出偏好的語言。


managingOrganization:管理病人紀錄的機構

"managingOrganization": {
  "reference": "Organization/hospital-example",
  "display": "範例醫院"
}

managingOrganization用來表示管理這筆Patient紀錄的醫療機構。

reference

"reference": "Organization/hospital-example"

表示它指向一筆Organization Resource。

display

"display": "範例醫院"

提供方便人類閱讀的機構名稱。

真正讓系統建立資料關係的是reference,而不是display。因為不同機構可能具有相似名稱,單靠顯示文字不一定能準確識別。


Patient沒有放入哪些資料?

今天的Patient範例雖然包含許多欄位,但沒有放入以下內容:

  • 王小明的血壓
  • 王小明的抽血結果
  • 醫師診斷
  • 用藥內容
  • 本次看診日期
  • 檢查報告

這些內容應該分別使用其他Resource,再透過Reference連回Patient。

例如,一筆Observation可以這樣指向Patient:

"subject": {
  "reference": "Patient/patient-example",
  "display": "王小明"
}

這表示該筆Observation屬於patient-example這位病人。

因此,Patient是病人資料的核心之一,但不等於病人的完整電子病歷。


閱讀Patient時可以先看哪些欄位?

第一次面對很長的Patient JSON時,可以先依照以下順序閱讀:

  1. resourceType:確認是不是Patient。
  2. id:確認Resource識別碼。
  3. identifier:查看病歷號等識別資料。
  4. active:確認紀錄是否有效。
  5. name:查看姓名。
  6. gender:查看行政管理用途的性別。
  7. birthDate:查看出生日期。
  8. telecom:查看聯絡方式。
  9. address:查看地址。
  10. managingOrganization:查看管理機構。

不需要第一次就背下所有欄位。先理解常見資料放在哪裡,再搭配官方文件查詢即可。


資料看起來合理,不代表一定符合FHIR

以下是一段合法的JSON:

{
  "resourceType": "Patient",
  "favoriteFood": "蛋糕"
}

從JSON語法來看,這段資料沒有少括號或少逗號。

但是,FHIR R4的Patient Resource並沒有名為favoriteFood的標準欄位,所以它不符合Patient Resource的基本結構。

這表示檢查FHIR資料時,需要分成不同層次:

  1. JSON語法是否正確?
  2. Resource類型是否存在?
  3. 欄位是否屬於該Resource?
  4. 欄位的資料型別是否正確?
  5. 代碼是否符合規定?
  6. 是否符合指定的Profile?

因此,「可以被JSON工具打開」不代表它就是一份正確的FHIR Resource。


今日小結

今天第一次完整閱讀了一份Patient Resource,認識了以下欄位:

  • resourceType
  • id
  • identifier
  • active
  • name
  • telecom
  • gender
  • birthDate
  • address
  • maritalStatus
  • communication
  • managingOrganization

Patient主要負責表示病人的基本行政資料,不會包含病人的所有診斷、檢驗及用藥紀錄。其他醫療資料會使用不同Resource,再透過Reference與Patient連結。

今天的範例中也出現了大括號、中括號、Object、Array、Key及Value等JSON結構。

下一篇將暫時把FHIR放在旁邊,專門補充JSON基礎,讓後續閱讀FHIR Resource時不再被大量括號和逗號困住。

明日預告

Day 9|FHIR資料為什麼使用JSON?

參考資料

  1. HL7 FHIR R4:Patient Resource
    https://hl7.org/fhir/R4/patient.html

  2. HL7 FHIR R4:Patient範例
    https://hl7.org/fhir/R4/patient-examples.html

  3. HL7 FHIR R4:Data Types
    https://hl7.org/fhir/R4/datatypes.html

  4. HL7 FHIR R4:References
    https://hl7.org/fhir/R4/references.html

  5. 衛生福利部臺灣核心實作指引:TW Core Patient
    https://twcore.mohw.gov.tw/ig/twcore/StructureDefinition-Patient-twcore.html


上一篇
Day 7|FHIR的Resource到底是什麼?
下一篇
Day 9|FHIR資料為什麼使用JSON?
系列文
《醫資生的 FHIR 30日入門:用 Postman 讀懂醫療資料交換》30
圖片
  熱門推薦
圖片
{{ item.channelVendor }} | {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言