Create Composition
In this lesson, let’s create our first composition on the openEHR server.
In the previous lessons, we successfully created an EHR and also learnt how to retrieve it. We now have everything we need to start storing actual clinical data. In openEHR, that clinical data is stored as a composition.
Let’s get started.
Generate an example composition
The easiest way to understand how compositions work is to start with an example generated by the server.
EHRbase provides an example endpoint that returns a sample composition for a given template. This is extremely useful because compositions can be long and detailed, and writing one from scratch can be difficult when you’re just getting started.
Understanding composition formats
You’ll commonly encounter compositions in 4 formats:
- Canonical JSON
- XML
- Flat JSON
- Structured JSON Canonical JSON is the most detailed and explicit version, but it can be hard to read because of how long it is. In the same way, XML is also detailed and structured, and many developers find it harder to work with during early testing.
On the other hand, Flat JSON is much more compact and easier to scan because it presents the data in a simpler key-value style and is preferred by developers. Structured JSON sits in between, because it keeps some hierarchy while still being easier to read than Canonical JSON.
All of these formats represent the same underlying composition. The data is the same; only the representation changes.
Create your first composition
Let us begin by looking at an example in your preferred format:
GET {{openehrBaseUrl}}/definition/template/adl1.4/{{templateId}}/example
Replace it with the templateId that you got when you uploaded your template to the openEHR server in lesson 3.
Next, click Send and you should see a 200 OK Status Response. This response returns an example composition for that particular form. With this result, you know that your connection and endpoint are set up correctly.
Copy the example composition response, then open the Create Composition request which looks like:
POST {{openehrBaseUrl}}/ehr/{{ehrId}}/composition
Replace the ehrId with the one you created in Lesson 4, and replace the sample body there with the composition you copied from the example endpoint.
Before sending the request, change a few values so you can clearly see your own data when you retrieve it later.
Here’s an example of what a Canonical JSON composition looks like:
{
"_type": "COMPOSITION",
"name": {
"_type": "DV_TEXT",
"value": "Vital Signs Encounter"
},
"archetype_details": {
"_type": "ARCHETYPED",
"archetype_id": {
"_type": "ARCHETYPE_ID",
"value": "openEHR-EHR-COMPOSITION.encounter.v1"
},
"template_id": {
"_type": "TEMPLATE_ID",
"value": "Vital Signs Template"
},
"rm_version": "1.0.4"
},
"language": {
"_type": "CODE_PHRASE",
"terminology_id": {
"_type": "TERMINOLOGY_ID",
"value": "ISO_639-1"
},
"code_string": "en"
},
"territory": {
"_type": "CODE_PHRASE",
"terminology_id": {
"_type": "TERMINOLOGY_ID",
"value": "ISO_3166-1"
},
"code_string": "US"
},
"category": {
"_type": "DV_CODED_TEXT",
"value": "event",
"defining_code": {
"_type": "CODE_PHRASE",
"terminology_id": {
"_type": "TERMINOLOGY_ID",
"value": "openehr"
},
"code_string": "433"
}
},
"composer": {
"_type": "PARTY_IDENTIFIED",
"name": "Dr. John Smith"
},
"context": {
"_type": "EVENT_CONTEXT",
"start_time": {
"_type": "DV_DATE_TIME",
"value": "2026-02-24T10:30:00Z"
},
"setting": {
"_type": "DV_CODED_TEXT",
"value": "outpatient care",
"defining_code": {
"_type": "CODE_PHRASE",
"terminology_id": {
"_type": "TERMINOLOGY_ID",
"value": "openehr"
},
"code_string": "238"
}
}
},
"content": [
{
"_type": "OBSERVATION",
"name": {
"_type": "DV_TEXT",
"value": "Blood Pressure"
},
"archetype_details": {
"_type": "ARCHETYPED",
"archetype_id": {
"_type": "ARCHETYPE_ID",
"value": "openEHR-EHR-OBSERVATION.blood_pressure.v2"
},
"rm_version": "1.0.4"
},
"data": {
"_type": "HISTORY",
"origin": {
"_type": "DV_DATE_TIME",
"value": "2026-02-24T10:30:00Z"
},
"events": [
{
"_type": "POINT_EVENT",
"time": {
"_type": "DV_DATE_TIME",
"value": "2026-02-24T10:30:00Z"
},
"data": {
"_type": "ITEM_TREE",
"items": [
{
"_type": "ELEMENT",
"name": {
"_type": "DV_TEXT",
"value": "Systolic"
},
"value": {
"_type": "DV_QUANTITY",
"magnitude": 120,
"units": "mm[Hg]"
}
},
{
"_type": "ELEMENT",
"name": {
"_type": "DV_TEXT",
"value": "Diastolic"
},
"value": {
"_type": "DV_QUANTITY",
"magnitude": 80,
"units": "mm[Hg]"
}
}
]
}
}
]
}
}
]
}
Click Send, and you should get a 201 Created response. That means the composition has been successfully stored on the server.
Save the composition UID
After a successful create request, the server returns a composition UID. This UID is the unique identifier for the composition you just created.
Save this value somewhere, because you will need it to retrieve the composition again.
Just like the EHR ID identifies the patient record, the composition UID identifies the specific clinical document stored inside that record.
"uid": {
"_type": "OBJECT_VERSION_ID",
"value": "`7e8f9d2a-1234-4b56-89ab-abcdef123456`::ehrserver.example.com::1"
}
Retrieve the composition
Now that the composition is saved, let’s learn how you can retrieve it again by using the composition UID you saved earlier.
Something that’s interesting, is that you can retrieve the same composition in different formats, even if you created it in only one format. Try this out yourself! The composition itself is still the same, only the response format changes. This is especially helpful when you are learning or debugging.
So, to retrieve the composition use the request “Fetch composition” (choose the format) and then replace the composition UID with the one you saved.
GET {{openehrBaseUrl}}/ehr/{{ehrId}}/composition/{{compositionId}}
Click Send you should get a 200 OK response. It returns the composition with the vital signs that you had created.
Lesson summary
In this lesson, we created our first composition using the openEHR Composition API. We started with EHRbase’s example composition endpoint, used it as a base for our request, edited a few values, and then created a composition inside an EHR.
We also saved the returned composition UID and used it to retrieve the same composition in different formats.
