Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 5 additions & 5 deletions .fern/metadata.json
Original file line number Diff line number Diff line change
@@ -1,17 +1,17 @@
{
"cliVersion": "5.118.0",
"cliVersion": "5.148.2",
"generatorName": "fernapi/fern-python-sdk",
"generatorVersion": "5.18.1",
"generatorVersion": "5.31.1",
"generatorConfig": {
"client_class_name": "PhenomlClient",
"wire_tests": {
"enabled": true
}
},
"originGitCommit": "26224ef37e22adb507f28c21e8991d4a27822bde",
"originGitCommit": "57c181c052e6a83dea1660396acd7f37d8c336c9",
"originGitCommitIsDirty": true,
"invokedBy": "ci",
"requestedVersion": "AUTO",
"ciProvider": "unknown",
"sdkVersion": "17.0.0"
}
"sdkVersion": "18.0.0"
}
17 changes: 11 additions & 6 deletions .fern/replay.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

41 changes: 41 additions & 0 deletions changelog.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,44 @@
## [18.0.0] - 2026-10-08
### Breaking Changes
- **`phenoml.construe.BadGatewayError`, `phenoml.construe.ContentTooLargeError`, `phenoml.fhir2omop.ServiceUnavailableError`, `phenoml.lang2fhir_batch.ContentTooLargeError`, and `phenoml.voice.ContentTooLargeError`** — removed exported error classes; replace their imports and catches with `phenoml.core.api_error.ApiError` and inspect `status_code`.
- **FHIR-to-OMOP backend output** — clinical `*_source_value` fields now contain the selected bare code instead of `system#code`; read the coding system from `mappings[].source_system`. For `MedicationRequest`, `drug_type_concept_id` changes from `32817` (EHR) to `32838` (EHR prescription). Update loaders and comparisons that depend on the previous values; these server-side changes also affect clients using older SDK versions.

### Added
- **`phenoml.fhir2omop.MappingEntry.selected`** — identifies whether a source coding was selected for the linked row's `*_source_value`; returned on every mapping entry and false for alternate codings and text-only rows.
- **`client.fhir2omop.create(..., vocab_version=...)`** — accepts an optional OMOP vocabulary release for reproducible coded-concept resolution in sync and async clients.
- **`phenoml.fhir2omop.CreateOmopResponse.provider_role_contexts` and `.diagnostics`** — add practitioner-role provenance and reference-resolution diagnostics with `ProviderRoleContext`, its supporting models, `Coding`, and `ReferenceDiagnostic`.
- **`phenoml.fhir2omop.MappingEntry.omop_field`, `PersonRow`, `DrugExposureRow`, `ConditionOccurrenceRow`, and `ProcedureOccurrenceRow`** — add concept-field provenance, person provider/care-site and demographic source-concept fields, drug route/refill/supply/lot/end-date fields, and condition/procedure end timestamps.
- **`client.implementation_guides.implementation_guides.create_version(...)` and `.get_version(...)`** — create and retrieve exact canonical implementation-guide packages using `FhirImplementationGuide` and `ImplementationGuideVersionDetail`, with a new `phenoml.implementation_guides.ConflictError` for HTTP 409.
- **`phenoml.implementation_guides.ImplementationGuideSummary.canonical_url` and `.version_count`** — expose an implementation-guide family's canonical URL and retained version count.
- **`client.lang2fhir.create_multi(..., primary_patient=...)` and `.document_multi(..., primary_patient=...)`** — accept optional `PrimaryPatient` / `PrimaryPatientName` context with identifier, name, birth date, and gender to identify the primary patient.
- **`CreateRequestResource`** — adds `familymemberhistory`, `medicationadministration`, and `medicationstatement` extraction targets.
- **`ResourceReviewResult.remediated`, `ResourceReviewRemediated`, and `ResourceReviewFinding.unaudited`** — report safe coding removals and distinguish fields without an audit verdict.
- **`BaseHttpResponse.response`** — exposes the underlying `httpx.Response` on raw response wrappers.
- **`phenoml.core.http_client.get_keepalive_socket_options()`** — returns platform-appropriate TCP keepalive socket options for custom HTTP transports.
- **`client.lang2fhir.document(...)` and `.document_multi(...)`** — now throw `phenoml.lang2fhir.ForbiddenError` on HTTP 403, including dedicated-instance format restrictions; previously these responses used the generic SDK error.
- **`client.construe.codes.crosswalk(...)`** — now throws `phenoml.construe.InternalServerError` on HTTP 500.

### Changed
- **`phenoml.fhir2omop.MappingEntryMappingStatus`** — describes response mapping statuses with named literal values while retaining an `Any` fallback for unknown future values; this is a response typing improvement.
- **FHIR-to-OMOP conversion / `phenoml.fhir2omop.Summary`** — documentation describes expanded resource coverage, source-supported dates, clinical-event eligibility, demographic resolution, and outcome-based summary counts.
- **`client.lang2fhir.create_multi(..., patient_reference=...)`, `.document_multi(..., patient_reference=...)`, and Lang2FHIR `detection_effort` parameters** — marked deprecated with existing call sites retained; use `primary_patient.identifier` for patient identifiers and do not combine it with `patient_reference`.
- **`client.lang2fhir.document(...)` and `.document_multi(...)`** — TIFF support is now restricted to dedicated instances; TIFF was already supported by the previous SDK. RTF and XML/C-CDA are also dedicated-instance formats. Documentation specifies a 20 MiB decoded-file limit and a 1 MiB extracted-text limit for RTF/XML.
- **`ResourceReview`** — documentation describes retaining resources after safe removal of unsupported codings and quarantining findings that cannot be safely repaired; read retained resources from the returned bundle.
- **`client.construe.codes.crosswalk(...)`, `client.lang2fhir_batch.create(...)`, `client.lang2fhir_batch.upload_item(...)`, and `client.voice.voice.transcribe(...)`** — removed typed status handling now falls back to `ApiError`: crosswalk HTTP 413/501/502/503, batch create HTTP 409, and upload/transcribe HTTP 413. Batch upload still raises `phenoml.lang2fhir_batch.ConflictError` on HTTP 409; batch creation no longer documents the four-active-jobs limit.
- **`client.profiles.profiles.delete(...)` and `client.profiles.versions.delete(...)`** — explicitly raise `phenoml.profiles.ConflictError` for profiles pinned by an implementation-guide package.
- **`client.lang2fhir.create(...)`, `.create_multi(...)`, `.document(...)`, `.document_multi(...)`, and `client.voice.voice.transcribe(...)`** — documentation now specifies a 32 MiB request-body limit, including the full JSON envelope and base64 content for document methods and the raw audio body for transcription.
- **`BatchError.kind`** — removes `budget_exceeded` from documented values; the field remains a string.
- **`PhenomlClient(token=...)` and `AsyncPhenomlClient(token=...)`** — type hints and documentation now include token strings alongside callable suppliers; strings already worked at runtime.
- **`aiohttp` extra** — loosens `httpx-aiohttp` from exactly `0.1.8` to `^0.1.8`, allowing compatible updates before `0.2.0`.

### Fixed
- **`PhenomlClient(base_url=..., instance_url=...)` and `AsyncPhenomlClient(base_url=..., instance_url=...)`** — preserve an explicitly supplied base URL when an instance hostname is also provided.
- **`OAuthTokenProvider` and `AsyncOAuthTokenProvider`** — credential-based token refresh explicitly sends `grant_type=client_credentials`.
- **`client.agent.chat.stream(...)`** — skips empty SSE events; the async usage example now calls the stream factory without `await` before iterating.

### Compatibility notes
- **`client.fhir2omop.create(...)`** — Python validates server responses and raises `ParsingError` if a mapping lacks `selected`; dedicated instances must include the backend change introduced on 2026-09-30 before adopting 18.0.0.

## [17.0.0] - 2026-09-09
### Breaking Changes
- **`ProfileSummary`** — `id`, `source`, `resource_type`, `url`, `version`, `fhir_version`, `implementation_guide`, `created_at`, and `updated_at` are now required; remove `None` guards for these fields.
Expand Down
156 changes: 139 additions & 17 deletions code-examples.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@
"metadata": {
"language": "python",
"packageName": "phenoml",
"sdkVersion": "17.0.0",
"specCommit": "26224ef37e22adb507f28c21e8991d4a27822bde",
"sdkVersion": "18.0.0",
"specCommit": "57c181c052e6a83dea1660396acd7f37d8c336c9",
"generatorName": "fernapi/fern-python-sdk"
},
"renderRules": {
Expand Down Expand Up @@ -1873,6 +1873,7 @@
"resourceType": "MedicationRequest",
"id": "medreq-1",
"status": "active",
"intent": "order",
"subject": {
"reference": "Patient/patient-1"
},
Expand Down Expand Up @@ -1909,15 +1910,26 @@
"person": [
{
"person_id": 1,
"gender_concept_id": 0,
"gender_concept_id": 8532,
"year_of_birth": 1985,
"month_of_birth": 7,
"day_of_birth": 22,
"birth_datetime": "1985-07-22",
"race_concept_id": 0,
"ethnicity_concept_id": 0,
"person_source_value": "patient-1",
"gender_source_value": "female"
"gender_source_value": "female",
"gender_source_concept_id": 0,
"race_source_concept_id": 0,
"ethnicity_source_concept_id": 0
}
],
"observation_period": [
{
"observation_period_id": 1,
"person_id": 1,
"observation_period_start_date": "2024-01-15",
"observation_period_end_date": "2024-01-16",
"period_type_concept_id": 32817
}
],
"condition_occurrence": [
Expand All @@ -1926,9 +1938,8 @@
"person_id": 1,
"condition_concept_id": 201826,
"condition_start_date": "2024-01-15",
"condition_start_datetime": "2024-01-15",
"condition_type_concept_id": 32817,
"condition_source_value": "http://snomed.info/sct#44054006",
"condition_source_value": "44054006",
"condition_source_concept_id": 201826
}
],
Expand All @@ -1938,47 +1949,66 @@
"person_id": 1,
"drug_concept_id": 40163924,
"drug_exposure_start_date": "2024-01-16",
"drug_exposure_start_datetime": "2024-01-16",
"drug_type_concept_id": 32817,
"drug_source_value": "http://www.nlm.nih.gov/research/umls/rxnorm#860975",
"drug_type_concept_id": 32838,
"drug_source_value": "860975",
"drug_source_concept_id": 40163924
}
]
},
"mappings": [
{
"resource_type": "Patient",
"resource_id": "patient-1",
"omop_table": "person",
"omop_field": "gender_concept_id",
"omop_id": 1,
"source_system": "http://hl7.org/fhir/administrative-gender",
"source_code": "female",
"source_name": "female",
"target_vocabulary": "Gender",
"target_code": "F",
"target_name": "FEMALE",
"mapping_status": "MAPPED",
"selected": true,
"note": "FHIR administrative gender; assumed sex at birth"
},
{
"resource_type": "Condition",
"resource_id": "condition-1",
"omop_table": "condition_occurrence",
"omop_field": "condition_concept_id",
"omop_id": 1,
"source_system": "http://snomed.info/sct",
"source_code": "44054006",
"source_name": "Type 2 diabetes mellitus",
"target_vocabulary": "SNOMED",
"target_code": "44054006",
"target_name": "Type 2 diabetes mellitus",
"mapping_status": "ALREADY_STANDARD"
"mapping_status": "ALREADY_STANDARD",
"selected": true
},
{
"resource_type": "MedicationRequest",
"resource_id": "medreq-1",
"omop_table": "drug_exposure",
"omop_field": "drug_concept_id",
"omop_id": 1,
"source_system": "http://www.nlm.nih.gov/research/umls/rxnorm",
"source_code": "860975",
"source_name": "metformin hydrochloride 500 MG",
"target_vocabulary": "RXNORM",
"target_code": "860975",
"target_name": "metformin hydrochloride 500 MG",
"mapping_status": "ALREADY_STANDARD"
"mapping_status": "ALREADY_STANDARD",
"selected": true
}
],
"vocab_version": "v20240229",
"vocab_version": "v20260227",
"summary": {
"codes_already_standard": 2,
"codes_normalized": 0,
"codes_normalized": 1,
"codes_unmapped": 0,
"off_vocab_rate": 0
"off_vocab_rate": 0.3333333333333333
}
}
},
Expand All @@ -1993,6 +2023,12 @@
"fieldTemplate": "fhir_resources={{value}}",
"kind": "object",
"required": true
},
{
"jsonKey": "vocab_version",
"fieldTemplate": "vocab_version={{value}}",
"kind": "string",
"required": false
}
]
}
Expand Down Expand Up @@ -3008,7 +3044,10 @@
"auto",
"appointment",
"condition-encounter-diagnosis",
"familymemberhistory",
"medicationadministration",
"medicationrequest",
"medicationstatement",
"careplan",
"condition-problems-health-concerns",
"coverage",
Expand Down Expand Up @@ -3124,6 +3163,12 @@
"kind": "string",
"required": false
},
{
"jsonKey": "primary_patient",
"fieldTemplate": "primary_patient={{value}}",
"kind": "object",
"required": false
},
{
"jsonKey": "patient_reference",
"fieldTemplate": "patient_reference={{value}}",
Expand Down Expand Up @@ -3250,7 +3295,7 @@
"body": {
"version": "R4",
"resource": "questionnaire",
"content": "JVBERi0xLjQKJeLjz9MK...(base64-encoded PDF or image bytes)"
"content": "JVBERi0xLjQKJeLjz9MK...(base64-encoded document bytes)"
}
},
"response": {
Expand Down Expand Up @@ -3312,7 +3357,7 @@
"request": {
"body": {
"version": "R4",
"content": "JVBERi0xLjQKJeLjz9MK...(base64-encoded PDF or image bytes)",
"content": "JVBERi0xLjQKJeLjz9MK...(base64-encoded document bytes)",
"provider": "medplum",
"config": {
"split_classifications": [
Expand Down Expand Up @@ -3494,6 +3539,12 @@
"kind": "string",
"required": false
},
{
"jsonKey": "primary_patient",
"fieldTemplate": "primary_patient={{value}}",
"kind": "object",
"required": false
},
{
"jsonKey": "patient_reference",
"fieldTemplate": "patient_reference={{value}}",
Expand Down Expand Up @@ -3957,6 +4008,77 @@
]
}
},
"POST /fhir/implementation-guides/{name}/versions": {
"httpMethod": "POST",
"httpPath": "/fhir/implementation-guides/{name}/versions",
"request": {
"body": null
},
"response": {
"body": null
},
"render": {
"callTemplate": "client.implementation_guides.implementation_guides.create_version(name={{name}}, {{__body__}})",
"params": [
{
"name": "name",
"kind": "string"
}
],
"body": {
"fieldSeparator": ", ",
"fields": [
{
"jsonKey": "implementation_guide",
"fieldTemplate": "implementation_guide={{value}}",
"kind": "object",
"required": true
},
{
"jsonKey": "profile_refs",
"fieldTemplate": "profile_refs={{value}}",
"kind": "list",
"required": true,
"items": {
"jsonKey": "",
"fieldTemplate": "{{value}}",
"kind": "string",
"required": true
}
},
{
"jsonKey": "profile_context",
"fieldTemplate": "profile_context={{value}}",
"kind": "string",
"required": false
}
]
}
}
},
"GET /fhir/implementation-guides/{name}/versions/{version}": {
"httpMethod": "GET",
"httpPath": "/fhir/implementation-guides/{name}/versions/{version}",
"request": {
"body": null
},
"response": {
"body": null
},
"render": {
"callTemplate": "client.implementation_guides.implementation_guides.get_version(name={{name}}, version={{version}})",
"params": [
{
"name": "name",
"kind": "string"
},
{
"name": "version",
"kind": "string"
}
]
}
},
"GET /fhir/profiles": {
"httpMethod": "GET",
"httpPath": "/fhir/profiles",
Expand Down
Loading
Loading