

기계 번역으로 제공되는 번역입니다. 제공된 번역과 원본 영어의 내용이 상충하는 경우에는 영어 버전이 우선합니다.

# FHIR 리소스 번들링
<a name="managing-fhir-resources-bundle"></a>

FHIR`Bundle`은의 FHIR 리소스 모음을 위한 컨테이너입니다 AWS HealthLake.는 서로 다른 처리 동작을 가진 두 가지 유형의 번들을 AWS HealthLake 지원합니다.

[https://hl7.org/fhir/R4/http.html#transaction](https://hl7.org/fhir/R4/http.html#transaction) 번들은 각 리소스를 독립적으로 처리합니다. 리소스 하나가 실패하더라도 나머지 리소스는 여전히 성공할 수 있습니다. 각 작업은 개별적으로 처리되며 일부 작업이 실패하더라도 처리가 계속됩니다. 관련 없는 여러 환자 레코드를 업로드하는 등 부분적 성공이 허용되는 대량 작업에 배치 번들을 사용합니다.

[https://hl7.org/fhir/R4/http.html#transaction](https://hl7.org/fhir/R4/http.html#transaction) 번들은 모든 리소스를 원자적으로 단일 단위로 처리합니다. 모든 리소스 작업이 성공하거나 커 AWS HealthLake 밋하지 않습니다. 모든 데이터를 함께 기록해야 하는 관련 관찰 및 조건이 있는 환자 생성과 같이 관련 리소스에서 참조 무결성을 보장해야 하는 경우 트랜잭션 번들을 사용합니다.


**배치 번들과 트랜잭션 번들의 차이점**  

| 기능 | 배치 | 트랜잭션 | 
| --- | --- | --- | 
| 처리 모델 | 각 작업은 독립적으로 성공하거나 실패합니다. | 모든 작업은 단일 원자 단위로 성공하거나 실패합니다. | 
| 장애 처리 | 개별 작업이 실패하더라도 처리는 계속됩니다. | 단일 작업이 실패하면 전체 번들이 실패합니다. | 
| 실행 순서 | 실행 순서는 보장되지 않습니다. | 작업은 지정된 순서대로 처리됩니다. | 
| 참조 무결성 | 작업 간에 적용되지 않습니다. | 번들 내에서 로컬로 참조되는 리소스에 적용됩니다. | 
| 가장 적합한 용도 | 부분적 성공이 허용되는 대량 작업. | 함께 생성하거나 업데이트해야 하는 관련 리소스입니다. | 

동일하거나 다른 유형의 FHIR 리소스를 번들링할 수 있으며, `create`, , `read`, 등의 FHIR 작업을 혼합하여 포함할 수 `update` `delete`있습니다`patch`. 자세한 내용은 **FHIR R4 설명서**의 [리소스 번들](https://hl7.org/fhir/R4/Bundle)을 참조하세요.

다음은 각 번들 유형에 대한 사용 사례의 예입니다.

배치 번들  
+ 야간 데이터 동기화 중에 서로 다른 시설에서 관련 없는 여러 환자 레코드를 업로드합니다.
+ 일부 레코드에 검증 문제가 있을 수 있는 과거 약물 레코드를 대량 업로드합니다.
+ 개별 실패가 다른 항목에 영향을 미치지 않는 조직 및 실무자와 같은 참조 데이터를 로드합니다.

트랜잭션 번들  
+ 모든 데이터를 함께 기록해야 하는 응급 부서 승인 중에 관련 관찰 및 조건이 있는 환자를 생성합니다.
+ 환자의 약물 목록과 일관성을 유지해야 하는 관련 알레르기 정보를 업데이트합니다.
+ 환자, 관찰, 절차 및 결제 정보와의 완전한 접촉을 단일 원자 단위로 기록합니다.

**중요**  
배치 번들과 트랜잭션 번들 모두 동일한 `Bundle` 리소스 구조를 사용합니다. 유일한 차이점은 `type` 필드의 값입니다.

다음 예제에서는 여러 리소스 유형 및 작업이 있는 트랜잭션 번들을 보여줍니다.

```
{
  "resourceType": "Bundle",
  "type": "transaction",
  "entry": [
    {
      "fullUrl": "urn:uuid:4f6a30fb-cd3c-4ab6-8757-532101f72065",
      "resource": {
        "resourceType": "Patient",
        "id": "new-patient",
        "active": true,
        "name": [
          {
            "family": "Johnson",
            "given": [
              "Sarah"
            ]
          }
        ],
        "gender": "female",
        "birthDate": "1985-08-12",
        "telecom": [
          {
            "system": "phone",
            "value": "555-123-4567",
            "use": "home"
          }
        ]
      },
      "request": {
        "method": "POST",
        "url": "Patient"
      }
    },
    {
      "fullUrl": "urn:uuid:7f83f473-d8cc-4a8d-86d3-9d9876a3248b",
      "resource": {
        "resourceType": "Observation",
        "id": "blood-pressure",
        "status": "final",
        "code": {
          "coding": [
            {
              "system": "http://loinc.org",
              "code": "85354-9",
              "display": "Blood pressure panel"
            }
          ],
          "text": "Blood pressure panel"
        },
        "subject": {
          "reference": "urn:uuid:4f6a30fb-cd3c-4ab6-8757-532101f72065"
        },
        "effectiveDateTime": "2023-10-15T09:30:00Z",
        "component": [
          {
            "code": {
              "coding": [
                {
                  "system": "http://loinc.org",
                  "code": "8480-6",
                  "display": "Systolic blood pressure"
                }
              ]
            },
            "valueQuantity": {
              "value": 120,
              "unit": "mmHg",
              "system": "http://unitsofmeasure.org",
              "code": "mm[Hg]"
            }
          },
          {
            "code": {
              "coding": [
                {
                  "system": "http://loinc.org",
                  "code": "8462-4",
                  "display": "Diastolic blood pressure"
                }
              ]
            },
            "valueQuantity": {
              "value": 80,
              "unit": "mmHg",
              "system": "http://unitsofmeasure.org",
              "code": "mm[Hg]"
            }
          }
        ]
      },
      "request": {
        "method": "POST",
        "url": "Observation"
      }
    },
    {
      "resource": {
        "resourceType": "Appointment",
        "id": "appointment-123",
        "status": "booked",
        "description": "Annual physical examination",
        "start": "2023-11-15T09:00:00Z",
        "end": "2023-11-15T09:30:00Z",
        "participant": [
          {
            "actor": {
              "reference": "urn:uuid:4f6a30fb-cd3c-4ab6-8757-532101f72065"
            },
            "status": "accepted"
          }
        ]
      },
      "request": {
        "method": "PUT",
        "url": "Appointment/appointment-123"
      }
    },
    {
      "request": {
        "method": "DELETE",
        "url": "MedicationRequest/med-request-456"
      }
    }
  ]
}
```

## FHIR 리소스를 독립 엔터티로 번들링
<a name="bundle-fhir-resources-batch-type"></a>

**FHIR 리소스를 독립 엔터티로 번들링하려면**  


1. HealthLake `region` 및 `datastoreId` 값을 수집합니다. 자세한 내용은 [데이터 스토어 속성 가져오기](managing-data-stores-describe.md) 단원을 참조하십시오.

1. HealthLake `region` 및에 대해 수집된 값을 사용하여 요청에 대한 URL을 구성합니다`datastoreId`. URL에 FHIR 리소스 유형을 지정*하지* 마십시오. 다음 예제에서 전체 URL 경로를 보려면 **복사** 버튼을 스크롤합니다.

   ```
   POST https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/
   ```

1. 각 HTTP 동사를 `method` 요소의 일부로 지정하여 요청에 대한 JSON 본문을 구성합니다. 다음 예제에서는 `Bundle` 리소스와의 `batch` 유형 상호 작용을 사용하여 새 `Patient` 및 `Medication` 리소스를 생성합니다. 그에 따라 모든 필수 섹션에 주석이 추가됩니다. 이 절차의 목적상 파일을 로 저장합니다`batch-independent.json`.

   ```
   {
       "resourceType": "Bundle",
       "id": "bundle-batch",
       "meta": {
           "lastUpdated": "2014-08-18T01:43:30Z"
       },
       "type": "batch",
       "entry": [
           {
               "resource": {
                   "resourceType": "Patient",
                   "meta": {
                       "lastUpdated": "2022-06-03T17:53:36.724Z"
                   },
                   "text": {
                       "status": "generated",
                       "div": "Some narrative"
                   },
                   "active": true,
                   "name": [
                       {
                           "use": "official",
                           "family": "Jackson",
                           "given": [
                               "Mateo",
                               "James"
                           ]
                       }
                   ],
                   "gender": "male",
                   "birthDate": "1974-12-25"
               },
               "request": {
                   "method": "POST",
                   "url": "Patient"
               }
           },
           {
               "resource": {
                   "resourceType": "Medication",
                   "id": "med0310",
                   "contained": [
                       {
                           "resourceType": "Substance",
                           "id": "sub03",
                           "code": {
                               "coding": [
                                   {
                                       "system": "http://snomed.info/sct",
                                       "code": "55452001",
                                       "display": "Oxycodone (substance)"
                                   }
                               ]
                           }
                       }
                   ],
                   "code": {
                       "coding": [
                           {
                               "system": "http://snomed.info/sct",
                               "code": "430127000",
                               "display": "Oral Form Oxycodone (product)"
                           }
                       ]
                   },
                   "form": {
                       "coding": [
                           {
                               "system": "http://snomed.info/sct",
                               "code": "385055001",
                               "display": "Tablet dose form (qualifier value)"
                           }
                       ]
                   },
                   "ingredient": [
                       {
                           "itemReference": {
                               "reference": "#sub03"
                           },
                           "strength": {
                               "numerator": {
                                   "value": 5,
                                   "system": "http://unitsofmeasure.org",
                                   "code": "mg"
                               },
                               "denominator": {
                                   "value": 1,
                                   "system": "http://terminology.hl7.org/CodeSystem/v3-orderableDrugForm",
                                   "code": "TAB"
                               }
                           }
                       }
                   ]
               },
               "request": {
                   "method": "POST",
                   "url": "Medication"
               }
           }
       ]
   }
   ```

1.  요청을 보냅니다. FHIR `Bundle` 배치 유형은 FHIR 권한 부여 시 [AWS 서명 버전 4](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_sigv.html) 또는 SMART로 `POST` 요청을 사용합니다. 다음 코드 예제에서는 데모용으로 `curl` 명령줄 도구를 사용합니다.

------
#### [ SigV4 ]

   SigV4 권한 부여

   ```
   curl --request POST \
     'https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/' \
     --aws-sigv4 'aws:amz:region:healthlake' \
     --user "$AWS_ACCESS_KEY_ID:$AWS_SECRET_ACCESS_KEY" \
     --header "x-amz-security-token:$AWS_SESSION_TOKEN" \
     --header 'Accept: application/json' \
     --data @batch-type.json
   ```

------
#### [ SMART on FHIR ]

   [https://docs.aws.amazon.com/healthlake/latest/APIReference/API_IdentityProviderConfiguration.html](https://docs.aws.amazon.com/healthlake/latest/APIReference/API_IdentityProviderConfiguration.html) 데이터 형식에 대한 SMART on FHIR 권한 부여 예제입니다.

   ```
   {
       "AuthorizationStrategy": "SMART_ON_FHIR",
       "FineGrainedAuthorizationEnabled": true,
       "IdpLambdaArn": "arn:aws:lambda:your-region:your-account-id:function:your-lambda-name",
       "Metadata": "{\"issuer\":\"https://ehr.example.com\", \"jwks_uri\":\"https://ehr.example.com/.well-known/jwks.json\",\"authorization_endpoint\":\"https://ehr.example.com/auth/authorize\",\"token_endpoint\":\"https://ehr.token.com/auth/token\",\"token_endpoint_auth_methods_supported\":[\"client_secret_basic\",\"foo\"],\"grant_types_supported\":[\"client_credential\",\"foo\"],\"registration_endpoint\":\"https://ehr.example.com/auth/register\",\"scopes_supported\":[\"openId\",\"profile\",\"launch\"],\"response_types_supported\":[\"code\"],\"management_endpoint\":\"https://ehr.example.com/user/manage\",\"introspection_endpoint\":\"https://ehr.example.com/user/introspect\",\"revocation_endpoint\":\"https://ehr.example.com/user/revoke\",\"code_challenge_methods_supported\":[\"S256\"],\"capabilities\":[\"launch-ehr\",\"sso-openid-connect\",\"client-public\",\"permission-v2\"]}"
   }
   ```

   호출자는 권한 부여 Lambda에 권한을 할당할 수 있습니다. 자세한 내용은 [OAuth 2.0 범위](reference-smart-on-fhir-oauth-scopes.md) 단원을 참조하십시오.

------

   서버는 `Bundle` 배치 유형 요청의 결과로 생성된 `Patient` 및 `Medication` 리소스를 보여주는 응답을 반환합니다.

## 번들의 조건부 PUTs
<a name="bundle-conditional-PUTs"></a>

AWS HealthLake 는 다음 쿼리 파라미터를 사용하여 번들 내에서 조건부 업데이트를 지원합니다.
+ `_id` (독립 실행형)
+ `_id` 다음 중 하나와 함께 사용할 수 있습니다.
  + `_tag`
  + `_createdAt`
  + `_lastUpdated`

번들에서 조건부 PUTs 사용하는 경우는 쿼리 파라미터를 기존 리소스와 비교하여 AWS HealthLake 평가하고 일치 결과를 기반으로 조치를 취합니다.


**조건부 업데이트 동작**  

| 시나리오 | HTTP 상태 | 취해진 조치 | 
| --- | --- | --- | 
| ID가 제공되지 않은 리소스 | 201 생성됨 | 는 항상 새 리소스를 생성합니다. | 
| 새 ID가 있는 리소스(일치하지 않음) | 201 생성됨 | 지정된 ID로 새 리소스를 생성합니다. | 
| 기존 ID가 있는 리소스(단일 일치) | 200 OK | 일치하는 리소스를 업데이트합니다. | 
| 기존 ID가 있는 리소스(충돌 감지됨) | 409 충돌 | 오류를 반환합니다. 변경 사항이 없습니다. | 
| 기존 ID가 있는 리소스(ID 불일치) | 400 잘못된 요청 | 오류를 반환합니다. 변경 사항이 없습니다. | 
| 여러 리소스 일치 조건 | 412 사전 조건 실패 | 오류를 반환합니다. 변경 사항이 없습니다. | 

조건부 업데이트가 포함된 다음 번들 예제에서는 조건이 충족되는 경우에만 FHIR ID가 인 `Patient` 리소스`_lastUpdated=lt2025-04-20`가 `476` 업데이트됩니다.

```
{
    "resourceType": "Bundle",
    "id": "bundle-batch",
    "meta": {
        "lastUpdated": "2014-08-18T01:43:30Z"
    },
    "type": "batch",
    "entry": [
        {
            "resource": {
                "resourceType": "Patient",
                "id": "476",
                "meta": {
                    "lastUpdated": "2022-06-03T17:53:36.724Z"
                },
                "active": true,
                "name": [
                    {
                        "use": "official",
                        "family": "Jackson",
                        "given": [
                            "Mateo",
                            "James"
                        ]
                    }
                ],
                "gender": "male",
                "birthDate": "1974-12-25"
            },
            "request": {
                "method": "PUT",
                "url": "Patient?_id=476&_lastUpdated=lt2025-04-20"
            }
        },
        {
            "resource": {
                "resourceType": "Medication",
                "id": "med0310",
                "contained": [
                    {
                        "resourceType": "Substance",
                        "id": "sub03",
                        "code": {
                            "coding": [
                                {
                                    "system": "http://snomed.info/sct",
                                    "code": "55452001",
                                    "display": "Oxycodone (substance)"
                                }
                            ]
                        }
                    }
                ],
                "code": {
                    "coding": [
                        {
                            "system": "http://snomed.info/sct",
                            "code": "430127000",
                            "display": "Oral Form Oxycodone (product)"
                        }
                    ]
                },
                "form": {
                    "coding": [
                        {
                            "system": "http://snomed.info/sct",
                            "code": "385055001",
                            "display": "Tablet dose form (qualifier value)"
                        }
                    ]
                },
                "ingredient": [
                    {
                        "itemReference": {
                            "reference": "#sub03"
                        },
                        "strength": {
                            "numerator": {
                                "value": 5,
                                "system": "http://unitsofmeasure.org",
                                "code": "mg"
                            },
                            "denominator": {
                                "value": 1,
                                "system": "http://terminology.hl7.org/CodeSystem/v3-orderableDrugForm",
                                "code": "TAB"
                            }
                        }
                    }
                ]
            },
            "request": {
                "method": "POST",
                "url": "Medication"
            }
        }
    ]
}
```

## FHIR 리소스를 단일 엔터티로 번들링
<a name="bundle-fhir-resources-document-type"></a>

**FHIR 리소스를 단일 엔터티로 번들링하려면**  


1. HealthLake `region` 및 `datastoreId` 값을 수집합니다. 자세한 내용은 [데이터 스토어 속성 가져오기](managing-data-stores-describe.md) 단원을 참조하십시오.

1. HealthLake `region` 및에 대해 수집된 값을 사용하여 요청에 대한 URL을 구성합니다`datastoreId`. FHIR 리소스 유형을 URL의 `Bundle` 일부로 포함합니다. 다음 예제에서 전체 URL 경로를 보려면 **복사** 버튼을 스크롤합니다.

   ```
   POST https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/Bundle
   ```

1. 요청에 대한 JSON 본문을 구성하여 그룹화할 FHIR 리소스를 지정합니다. 다음 예제에서는 HealthLake에서 두 개의 `Patient` 리소스를 그룹화합니다. 이 절차의 목적상 파일을 로 저장합니다`batch-single.json`.

   ```
   {
       "resourceType": "Bundle",
       "id": "bundle-minimal",
       "language": "en-US",
       "identifier": {
           "system": "urn:oid:1.2.3.4.5",
           "value": "28b95815-76ce-457b-b7ae-a972e527db4f"
       },
       "type": "document",
       "timestamp": "2020-12-11T14:30:00+01:00",
       "entry": [
           {
               "fullUrl": "urn:uuid:f40b07e3-37e8-48c3-bf1c-ae70fe12dabf",
               "resource": {
                   "resourceType": "Composition",
                   "id": "f40b07e3-37e8-48c3-bf1c-ae70fe12dabf",
                   "status": "final",
                   "type": {
                       "coding": [
                           {
                               "system": "http://loinc.org",
                               "code": "60591-5",
                               "display": "Patient summary Document"
                           }
                       ]
                   },
                   "date": "2020-12-11T14:30:00+01:00",
                   "author": [
                       {
                           "reference": "urn:uuid:45271f7f-63ab-4946-970f-3daaaa0663ff"
                       }
                   ],
                   "title": "Patient Summary as of December 7, 2020 14:30"
               }
           },
           {
               "fullUrl": "urn:uuid:45271f7f-63ab-4946-970f-3daaaa0663ff",
               "resource": {
                   "resourceType": "Practitioner",
                   "id": "45271f7f-63ab-4946-970f-3daaaa0663ff",
                   
                   "active": true,
                   "name": [
                       {
                           "family": "Doe",
                           "given": [
                               "John"
                           ]
                       }
                   ]                
               }
           }
       ]
   }
   ```

1.  요청을 보냅니다. FHIR `Bundle` 문서 유형은 [AWS 서명 버전 4](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_sigv.html) 서명 프로토콜과 함께 `POST` 요청을 사용합니다. 다음 코드 예제에서는 데모용으로 `curl` 명령줄 도구를 사용합니다.

------
#### [ SigV4 ]

   SigV4 권한 부여

   ```
   curl --request POST \
     'https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/Bundle' \
     --aws-sigv4 'aws:amz:region:healthlake' \
     --user "$AWS_ACCESS_KEY_ID:$AWS_SECRET_ACCESS_KEY" \
     --header "x-amz-security-token:$AWS_SESSION_TOKEN" \
     --header 'Accept: application/json' \
     --data @document-type.json
   ```

------
#### [ SMART on FHIR ]

   [https://docs.aws.amazon.com/healthlake/latest/APIReference/API_IdentityProviderConfiguration.html](https://docs.aws.amazon.com/healthlake/latest/APIReference/API_IdentityProviderConfiguration.html) 데이터 형식에 대한 SMART on FHIR 권한 부여 예제입니다.

   ```
   {
       "AuthorizationStrategy": "SMART_ON_FHIR",
       "FineGrainedAuthorizationEnabled": true,
       "IdpLambdaArn": "arn:aws:lambda:your-region:your-account-id:function:your-lambda-name",
       "Metadata": "{\"issuer\":\"https://ehr.example.com\", \"jwks_uri\":\"https://ehr.example.com/.well-known/jwks.json\",\"authorization_endpoint\":\"https://ehr.example.com/auth/authorize\",\"token_endpoint\":\"https://ehr.token.com/auth/token\",\"token_endpoint_auth_methods_supported\":[\"client_secret_basic\",\"foo\"],\"grant_types_supported\":[\"client_credential\",\"foo\"],\"registration_endpoint\":\"https://ehr.example.com/auth/register\",\"scopes_supported\":[\"openId\",\"profile\",\"launch\"],\"response_types_supported\":[\"code\"],\"management_endpoint\":\"https://ehr.example.com/user/manage\",\"introspection_endpoint\":\"https://ehr.example.com/user/introspect\",\"revocation_endpoint\":\"https://ehr.example.com/user/revoke\",\"code_challenge_methods_supported\":[\"S256\"],\"capabilities\":[\"launch-ehr\",\"sso-openid-connect\",\"client-public\",\"permission-v2\"]}"
   }
   ```

   호출자는 권한 부여 Lambda에 권한을 할당할 수 있습니다. 자세한 내용은 [OAuth 2.0 범위](reference-smart-on-fhir-oauth-scopes.md) 단원을 참조하십시오.

------

   서버는 `Bundle` 문서 유형 요청의 결과로 생성된 두 개의 `Patient` 리소스를 보여주는 응답을 반환합니다.

## 번들에 대한 검증 수준 구성
<a name="validation-level-bundles"></a>

FHIR 리소스를 번들링할 때 선택적으로 `x-amzn-healthlake-fhir-validation-level` HTTP 헤더를 지정하여 리소스에 대한 검증 수준을 구성할 수 있습니다. 이 검증 수준은 번들 내의 모든 생성 및 업데이트 요청에 대해 설정됩니다.는 AWS HealthLake 현재 다음 검증 수준을 지원합니다.
+ `strict`: 리소스는 리소스의 프로필 요소 또는 프로필이 없는 경우 R4 사양에 따라 검증됩니다. 이는의 기본 검증 수준입니다 AWS HealthLake.
+ `structure-only`: 리소스는 R4에 대해 검증되며 참조된 프로파일은 무시합니다.
+ `minimal`: 리소스는 특정 R4 규칙을 무시하면서 최소한으로 검증됩니다. 검색/분석에 필요한 구조 검사에 실패한 리소스는 감사 경고를 포함하도록 업데이트됩니다.

최소 검증 수준으로 번들링된 리소스는 검색 인덱싱에 필요한 검증에 실패하더라도 데이터 스토어에 수집될 수 있습니다. 이 경우 리소스는 해당 실패를 문서화하기 위한 Healthlake별 확장을 포함하도록 업데이트되며 번들 응답 내의 항목에는 다음과 같이 OperationOutcome 리소스가 포함됩니다.

```
{
    "resourceType": "Bundle",
    "type": "batch-response",
    "timestamp": "2025-08-25T22:58:48.846287342Z",
    "entry": [
        {
            "response": {
                "status": "201",
                "location": "Patient/195abc49-ba8e-4c8b-95c2-abc88fef7544/_history/1",
                "etag": "W/\"1\"",
                "lastModified": "2025-08-25T22:58:48.801245445Z",
                "outcome": {
                    "resourceType": "OperationOutcome",
                    "issue": [
                        {
                            "severity": "error",
                            "code": "processing",
                            "details": {
                                "text": "FHIR resource in payload failed FHIR validation rules."
                            },
                            "diagnostics": "FHIR resource in payload failed FHIR validation rules."
                        }
                    ]
                }
            }
        }
    ]
}
```

또한 다음 HTTP 응답 헤더는 "true" 값과 함께 포함됩니다.

```
x-amzn-healthlake-validation-issues : true
```

**참고**  
R4 사양에 따라 잘못된 형식으로 수집된 데이터는 이러한 오류가 있는 경우 예상대로 검색하지 못할 수 있습니다.

## 번들 유형 "메시지"에 대한 제한된 지원
<a name="bundle-message-type-limited-support"></a>

HealthLake는 내부 변환 프로세스를 `message` 통해 FHIR 번들 유형에 대한 제한된 지원을 제공합니다. 이 지원은 레거시 병원 시스템에서 ADT(Admission, Discharge, Transfer) 피드를 수집하는 등 소스에서 메시지 번들을 다시 포맷할 수 없는 시나리오를 위해 설계되었습니다.

**주의**  
이 기능은 명시적 AWS 계정 허용 목록이 필요하며 FHIR R4 메시지 의미 체계 또는 참조 무결성을 적용하지 않습니다. 메시지 번들을 사용하기 전에 계정에 대한 활성화를 요청하려면 AWS Support에 문의하세요.

### 표준 메시지 처리의 주요 차이점
<a name="bundle-message-key-differences"></a>
+ **메시지 번들**(FHIR 사양): 첫 번째 항목은 다른 리소스를 참조`MessageHeader`하는 이어야 합니다. 리소스에는 개별 `request` 객체가 없으며 MessageHeader 이벤트에 따라 처리 작업이 결정됩니다.
+ **HealthLake 처리**: 각 리소스 항목에 PUT 작업을 자동으로 할당하여 메시지 번들을 배치 번들로 변환합니다. 리소스는 메시지 의미 체계 또는 참조 무결성을 적용하지 않고 독립적으로 처리됩니다.

### 중요 제한 사항
<a name="bundle-message-limitations"></a>
+ FHIR R4 메시지별 처리 규칙이 적용되지 않음
+ 리소스 간 트랜잭션 무결성 없음
+ 리소스 간 참조가 검증되지 않음
+ 명시적 계정 허용 목록 지정 필요

### 예제 메시지 번들 구조
<a name="bundle-message-example"></a>

```
{
              "resourceType": "Bundle",
              "type": "message",
              "entry": [
                {
                  "resource": {
                    "resourceType": "MessageHeader",
                    "eventCoding": {
                      "system": "http://hl7.org/fhir/us/davinci-alerts/CodeSystem/notification-event",
                      "code": "notification-admit"
                    },
                    "focus": [{"reference": "Encounter/example-id"}]
                  }
                },
                {
                  "resource": {"resourceType": "Patient", "id": "example-id"}
                },
                {
                  "resource": {"resourceType": "Encounter", "id": "example-id"}
                }
              ]
            }
```

**참고**  
각 리소스는 개별 PUT 작업을 통해 제출된 것처럼 독립적으로 저장됩니다. 전체 FHIR 메시징 의미 체계 또는 참조 무결성 검증이 필요한 경우 제출 전에 메시지 번들을 사전 처리하거나 애플리케이션 수준 검증을 구현합니다.

## 비동기 번들 트랜잭션
<a name="managing-fhir-resources-async-transactions"></a>

AWS HealthLake 는 최대 500개의 리소스가 있는 트랜잭션을 제출할 수 `transaction` 있는 비동기 `Bundle` 유형을 지원합니다. 비동기 트랜잭션을 제출하면 HealthLake는 처리를 위해 이를 대기열에 넣고 즉시 폴링 URL을 반환합니다. 이 URL을 사용하여 상태를 확인하고 응답을 검색할 수 있습니다. 이는 [FHIR 비동기 번들 패턴을](https://hl7.org/fhir/async-bundle.html) 따릅니다.

**비동기 트랜잭션을 사용해야 하는 경우**  

+ 단일 트랜잭션에서 100개 이상의 리소스(동기 제한)를 제출해야 합니다.
+ 트랜잭션 처리가 완료될 때까지 기다리는 동안 애플리케이션을 차단하지 않으려고 합니다.
+ 처리량을 높이려면 대량의 관련 리소스를 처리해야 합니다.

**중요**  
폴링 결과는 트랜잭션이 완료된 후 90일 동안 사용할 수 있습니다. 이 90일 기간이 지나면 폴링 URL이 더 이상 결과를 반환하지 않습니다. 이 기간 내에 결과를 검색하고 저장하도록 통합을 설계합니다.

**참고**  
동기`Bundle`식 유형은 최대 100개의 리소스를 `transaction` 계속 지원하며 기본 처리 모드입니다. `Prefer: respond-async` 헤더 없이 리소스`transaction`가 100개 이상인 `Bundle` 유형을 제출하면 HealthLake가 `422 Unprocessable Entity` 오류를 반환합니다. 유형의 번들`batch`은 비동기 처리에 지원되지 않습니다. `Bundle` 유형만 비동기적으로 제출할 수 `transaction` 있습니다(최대 500개의 작업 사용).

### 비동기 트랜잭션 제출
<a name="async-transactions-submitting"></a>

비동기 트랜잭션을 제출하려면 `Prefer: respond-async` 헤더를 사용하여 데이터 스토어 엔드포인트에 `POST` 요청을 보냅니다. 번들에는 유형이 있어야 합니다`transaction`. 유형의 번들`batch`은 비동기 번들 처리에 지원되지 않습니다.

HealthLake는 제출 시 번들에 대한 초기 검증을 수행합니다. 검증에 성공하면 HealthLake는 폴링 URL이 포함된 `content-location` 응답 헤더와 함께 HTTP 202 Accepted를 반환합니다.

**비동기 `Bundle` 유형을 제출하려면 `transaction`**  


1. HealthLake 데이터 스토어 엔드포인트에 `POST` 요청을 보냅니다.

   ```
   POST https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/
   ```

1. 번들 유형이 인 요청에 대한 JSON 본문을 구성합니다`transaction`. 이 절차의 목적상 파일을 로 저장합니다`async-transaction.json`.

   ```
   {
       "resourceType": "Bundle",
       "type": "transaction",
       "entry": [
           {
               "resource": {
                   "resourceType": "Patient",
                   "active": true,
                   "name": [
                       {
                           "use": "official",
                           "family": "Smith",
                           "given": ["Jane"]
                       }
                   ],
                   "gender": "female",
                   "birthDate": "1990-01-15"
               },
               "request": {
                   "method": "POST",
                   "url": "Patient"
               }
           },
           {
               "resource": {
                   "resourceType": "Observation",
                   "status": "final",
                   "code": {
                       "coding": [
                           {
                               "system": "http://loinc.org",
                               "code": "85354-9",
                               "display": "Blood pressure panel"
                           }
                       ]
                   },
                   "subject": {
                       "reference": "urn:uuid:example-patient-id"
                   }
               },
               "request": {
                   "method": "POST",
                   "url": "Observation"
               }
           }
       ]
   }
   ```

1. `Prefer: respond-async` 헤더와 함께 요청을 전송합니다. FHIR `Bundle` 트랜잭션 유형은 FHIR 권한 부여 시 [AWS 서명 버전 4](https://docs.aws.amazon.com/IAM/latest/UserGuide/reference_sigv.html) 또는 SMART인 `POST` 요청을 사용합니다. 다음 코드 예제에서는 데모용으로 `curl` 명령줄 도구를 사용합니다.

------
#### [ SigV4 ]

   SigV4 권한 부여

   ```
   curl --request POST \
     'https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/' \
     --aws-sigv4 'aws:amz:region:healthlake' \
     --user "$AWS_ACCESS_KEY_ID:$AWS_SECRET_ACCESS_KEY" \
     --header "x-amz-security-token:$AWS_SESSION_TOKEN" \
     --header 'Accept: application/json' \
     --header 'Prefer: respond-async' \
     --data @async-transaction.json
   ```

------
#### [ SMART on FHIR ]

   [https://docs.aws.amazon.com/healthlake/latest/APIReference/API_IdentityProviderConfiguration.html](https://docs.aws.amazon.com/healthlake/latest/APIReference/API_IdentityProviderConfiguration.html) 데이터 형식에 대한 SMART on FHIR 권한 부여 예제입니다.

   ```
   {
       "AuthorizationStrategy": "SMART_ON_FHIR",
       "FineGrainedAuthorizationEnabled": true,
       "IdpLambdaArn": "arn:aws:lambda:your-region:your-account-id:function:your-lambda-name",
       "Metadata": "{\"issuer\":\"https://ehr.example.com\", \"jwks_uri\":\"https://ehr.example.com/.well-known/jwks.json\",\"authorization_endpoint\":\"https://ehr.example.com/auth/authorize\",\"token_endpoint\":\"https://ehr.token.com/auth/token\",\"token_endpoint_auth_methods_supported\":[\"client_secret_basic\",\"foo\"],\"grant_types_supported\":[\"client_credential\",\"foo\"],\"registration_endpoint\":\"https://ehr.example.com/auth/register\",\"scopes_supported\":[\"openId\",\"profile\",\"launch\"],\"response_types_supported\":[\"code\"],\"management_endpoint\":\"https://ehr.example.com/user/manage\",\"introspection_endpoint\":\"https://ehr.example.com/user/introspect\",\"revocation_endpoint\":\"https://ehr.example.com/user/revoke\",\"code_challenge_methods_supported\":[\"S256\"],\"capabilities\":[\"launch-ehr\",\"sso-openid-connect\",\"client-public\",\"permission-v2\"]}"
   }
   ```

   호출자는 권한 부여 Lambda에 권한을 할당할 수 있습니다. 자세한 내용은 [OAuth 2.0 범위](reference-smart-on-fhir-oauth-scopes.md) 단원을 참조하십시오.

------

1. 제출에 성공하면 서버는 HTTP 202 Accepted를 반환합니다. `content-location` 응답 헤더에는 폴링 URL이 포함되어 있습니다. 응답 본문은 `OperationOutcome` 리소스입니다.

   ```
   HTTP/1.1 202 Accepted
   content-location: https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/Transaction/transactionId
   ```

   ```
   {
       "resourceType": "OperationOutcome",
       "issue": [
           {
               "severity": "information",
               "code": "informational",
               "diagnostics": "Submitted Asynchronous Bundle Transaction",
               "location": [
                   "https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/Transaction/transactionId"
               ]
           }
       ]
   }
   ```

### 트랜잭션 상태에 대한 폴링
<a name="async-transactions-polling"></a>

비동기 트랜잭션을 제출한 후 `content-location` 응답 헤더의 폴링 URL을 사용하여 트랜잭션 상태를 확인합니다. 폴링 URL에 `GET` 요청을 보냅니다.

**참고**  
FHIR 지원 데이터 스토어의 SMART의 경우, 권한 부여 토큰에는 트랜잭션 상태를 폴링할 `Transaction` 리소스 유형에 대한 `read` 권한이 포함되어야 합니다. FHIR 범위의 SMART에 대한 자세한 내용은 섹션을 참조하세요[HealthLake에서 지원하는 FHIR OAuth 2.0 범위의 SMART](reference-smart-on-fhir-oauth-scopes.md).

폴링 URL에 `GET` 요청을 보냅니다. 다음 예제에서는 `curl` 명령줄 도구를 사용합니다.

------
#### [ SigV4 ]

SigV4 권한 부여

```
curl --request GET \
  'https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/Transaction/transactionId' \
  --aws-sigv4 'aws:amz:region:healthlake' \
  --user "$AWS_ACCESS_KEY_ID:$AWS_SECRET_ACCESS_KEY" \
  --header "x-amz-security-token:$AWS_SESSION_TOKEN" \
  --header 'Accept: application/json'
```

------
#### [ SMART on FHIR ]

FHIR 권한 부여에 대한 SMART. 권한 부여 토큰에는 `Transaction` 리소스 유형에 대한 `read` 권한이 포함되어야 합니다.

```
curl --request GET \
  'https://healthlake.region.amazonaws.com/datastore/datastoreId/r4/Transaction/transactionId' \
  --header 'Authorization: Bearer $SMART_ACCESS_TOKEN' \
  --header 'Accept: application/json'
```

------

다음 표에서는 가능한 응답을 설명합니다.


**응답 코드 폴링**  

| HTTP 상태 | 의미 | 응답 본문 | 
| --- | --- | --- | 
| 202 수락됨 | 트랜잭션이 대기열에 있음 | OperationOutcome "SUBMITTED" 진단 포함 | 
| 202 수락됨 | 트랜잭션 처리 중 | OperationOutcome 진단 "IN\$1PROGRESS" 사용 | 
| 200 OK | 트랜잭션이 성공적으로 완료되었습니다. | Bundle 유형 포함 transaction-response | 
| 4xx/5xx | 트랜잭션 실패 | OperationOutcome 오류 세부 정보가 있는 | 

다음 예제에서는 각 응답 유형을 보여줍니다.

**트랜잭션 대기 중(202)**  


```
{
    "resourceType": "OperationOutcome",
    "id": "transactionId",
    "issue": [
        {
            "severity": "information",
            "code": "informational",
            "diagnostics": "SUBMITTED"
        }
    ]
}
```

**트랜잭션 처리(202)**  


```
{
    "resourceType": "OperationOutcome",
    "id": "transactionId",
    "issue": [
        {
            "severity": "information",
            "code": "informational",
            "diagnostics": "IN_PROGRESS"
        }
    ]
}
```

**트랜잭션 완료(200)**  


```
{
    "resourceType": "Bundle",
    "type": "transaction-response",
    "entry": [
        {
            "response": {
                "status": "201",
                "location": "Patient/example-id/_history/1",
                "etag": "W/\"1\"",
                "lastModified": "2024-01-15T10:30:00.000Z"
            }
        },
        {
            "response": {
                "status": "201",
                "location": "Observation/example-id/_history/1",
                "etag": "W/\"1\"",
                "lastModified": "2024-01-15T10:30:00.000Z"
            }
        }
    ]
}
```

**트랜잭션 실패(4xx/5xx)**  


```
{
    "resourceType": "OperationOutcome",
    "issue": [
        {
            "severity": "error",
            "code": "exception",
            "diagnostics": "Transaction failed: conflict detected on resource Patient/example-id"
        }
    ]
}
```

### 주문 처리
<a name="async-transactions-processing-order"></a>

유형의 비동기 번들`transaction`은 대기열에 있지만 엄격한 제출 순서로 처리되지 않습니다. HealthLake는 사용 가능한 용량 및 시스템 부하를 기반으로 처리를 최적화합니다.

**중요**  
제출된 순서대로 처리 중인 트랜잭션에 의존하지 마십시오. 예를 들어 오전 10시에 트랜잭션 A를 제출하고 오전 10시 1분에 트랜잭션 B를 제출하는 경우 트랜잭션 B는 트랜잭션 A 이전에 완료될 수 있습니다. 애플리케이션을 다음과 같이 설계하세요.  
out-of-order 처리합니다.
폴링 URL을 사용하여 각 트랜잭션을 독립적으로 추적합니다.
사용 사례에 주문이 중요한 경우 애플리케이션 수준 시퀀싱을 구현합니다.

### 할당량 및 제한
<a name="async-transactions-quotas"></a>

다음 할당량 및 속도 제한은 비동기 트랜잭션에 적용됩니다.


**비동기 트랜잭션 할당량**  

| 할당량 | 값 | 조정 가능 | 
| --- | --- | --- | 
| 비동기 트랜잭션당 최대 작업 수 | 500 | 아니요 | 
| 데이터 스토어당 최대 보류 중인 트랜잭션 수 | 500 | 예 | 
+ 비동기 트랜잭션은에 정의된 것과 동일한 API 속도 제한을 공유합니다[Service Quotas](reference-healthlake-endpoints-quotas.md#reference-healthlake-quotas).
+ 트랜잭션 상태에 대한 폴링은 FHIR 리소스에 대한 읽기(`GET`) 작업과 동일한 API 속도 제한을 공유합니다.
+ 보류 중인 트랜잭션 한도에 도달하면 기존 트랜잭션이 완료될 때까지 후속 제출에서 오류가 반환됩니다.

### 오류 처리
<a name="async-transactions-error-handling"></a>

'트랜잭션' 번들의 경우 번들에 포함된 모든 FHIR 리소스는 원자성 작업으로 처리됩니다. 작업의 모든 리소스가 성공하거나 번들의 작업이 처리되지 않아야 합니다.

오류는 HealthLake가 동기적으로 반환하는 제출 오류와 폴링을 통해 검색하는 처리 오류의 두 가지 범주로 나뉩니다.

**제출 오류**  


HealthLake는 제출 시 번들을 검증하고 트랜잭션이 대기열에 추가되기 전에 동기식으로 오류를 반환합니다. 제출 오류에는 잘못된 FHIR 리소스 검증 오류, 지원되지 않는 리소스 유형, 500개의 작업 제한 초과, 배치 번들과 함께 `Prefer: respond-async` 헤더 사용 등이 포함됩니다. 데이터 스토어에 대해 보류 중인 트랜잭션 한도에 도달하면 HealthLake는를 반환합니다`ThrottlingException`. 제출 오류가 발생하면 트랜잭션이 대기열에 추가되지 않습니다.

**처리 오류**  


처리 오류는 트랜잭션이 대기열에 추가되고 폴링 URL을 통해 반환된 후에 발생합니다. 여기에는 다른 작업이 트랜잭션의 일부인 리소스를 수정한 트랜잭션 충돌과 처리 중 서버 오류가 포함됩니다. 처리 오류가 발생하면 트랜잭션의 리소스에 대해 리소스 변형이 수행되지 않습니다. 폴링 URL은 오류 세부 정보와 `OperationOutcome` 함께를 반환합니다.