IKJ-API overview
Informasjon fra Kommunal Journal (IKJ) provides endpoints for submitting and retrieving patient information. Patient resources are represented using the FHIR standard, version R4.
Available environments
| Environment | FQDN |
|---|---|
| Test | api.ikj.test.nhn.no |
Access control
Accessing the IKJ API requires clients to be authenticated using HelseID and DPoP (Demonstrating Proof-of-Possession):
- Scope: Clients must request the appropriate scope (
nhn:ikj/api.readornhn:ikj/api.write). - Claim: Access token must include claim
helseid://claims/client/claims/orgnr_parent. - DPoP required: Only requests including DPoP tokens are accepted.
- Authorization header: Access token must be sent using the
DPoPprefix (i.e., notBearer). - DPoP-Proof: Requests must include a
DPoPheader with a signed proof generated by the client.
See HelseID Dokumentasjon - DPoP for implementation details.
Submitting patient resources
Patient resources are submitted by making POST requests to the Patient endpoint.
Endpoint format: POST /v1/Patient
A successful submission returns 202 Accepted. Processing is asynchronous — the resource is queued for
internal processing after being accepted. The server assigns the resource ID, but it is not included in this
initial response — it only becomes available once the Task resource reports the processing as successfully
completed. The Location header contains the URL of the Task resource that can be polled to check the processing
status; this URL is identified by an internal event ID that the server generates for this specific request, not
by the (not yet known) resource ID.
Note
There is a request size limit of approximately 900 KB for this endpoint.
Updating patient resources
Existing patient resources are replaced by making PUT requests to the Patient endpoint.
Endpoint format: PUT /v1/Patient/{resourceId}
The {resourceId} must be the system-generated resource ID of a previously submitted Patient resource, obtained
from the Task resource of an earlier successful POST (or PUT) once its processing completed — it cannot be
chosen by the client. The value in the URL is authoritative; if the request body includes an id field that
differs from the URL value, the request is rejected with 400 Bad Request immediately.
A successful request returns 202 Accepted. Processing is asynchronous — the same status mechanism used for
POST applies here: the Location header contains the URL of the Task resource, identified by a new internal
event ID generated for this request (distinct from the {resourceId} being updated). Because processing is
asynchronous, the outcome (success or failure) must be checked via the Task endpoint using that event ID. A PUT
to a resource that does not exist will result in a failed processing status.
Note
There is a request size limit of approximately 900 KB for this endpoint.
Retrieving patient resources
Patient resources are retrieved by making GET requests to the Patient endpoint.
Endpoint format: GET /v1/Patient
There are three ways of invoking this endpoint:
- By submitting the resource id in the URL, e.g.
GET /v1/Patient/12345 - By submitting a single query parameter indicating the requested identifier to search for, e.g.
GET /v1/Patient?identifier=a|b - By submitting a set of search parameters restricting the result set, e.g.
GET /v1/Patient?_lastUpdated=ge2024-01-01T12:00Z
The three use cases will be elaborated in the subsections below. Note taht the three use cases are mutually exclusive: It is not allowed to combine query parameters from the three use cases in a single query, this will result in an Operation Outcome with the appropriate error message.
Search for a single patient by resource id
The response is single FHIR Patient if there is a match, or otherwise, an Operation Outcome.
When a Patient is submitted, the returned content location can be used to query the status of the submission. Eventually,
upon successful completion, the Task returned will contain a value reference indicating the resource id of the submitted Patient,
e.g. Patient/12345. This resource id can then be submitted using the GET /v1/Patient/12345 endpoint to retrieve the Patient resource.
Search for a single patient by identifier
The response is single FHIR Patient if there is a match, or otherwise, an Operation Outcome.
A Patient resource is submitted with one or more identifiers, which are composed by a system and a value. The combination of
parentOrgNo, system and value is unique, and since a query will only be able to access data belonging to the parentOrgNo
for which the client is authorized, there will never be more than one match for a requested identifier.
The Patient endpoint can be used to search for a Patient with a given identifier by accessing the endpoint like GET /v1/Patient?identifier=a|b.
Search for a set of patients by query parameters
The response is a FHIR Bundle containing matching Patient resources, possibly none.
Filtering
_lastUpdatedlimits results based on when resources were last updated in IKJ. Requires a prefix (gt,ge,lt,le) with at least minute precision. Example:ge2024-01-01T12:00Z.
Pagination
Keyset pagination (also known as seek pagination) limits the number of resources returned per request.
An opaque cursor parameter is used to retrieve the next page of results. The response Bundle includes a next
link containing the cursor value.
_countcontrols the page size (1–50, default 20)._sortcontrols the sort order:_lastUpdatedfor ascending (default) or-_lastUpdatedfor descending.
Cursor constraints:
- Treat the
cursorvalue as completely opaque — do not attempt to decode or modify it. - Combining filter parameters (
_lastUpdated) with a cursor is not allowed and will result in a400error. - When a cursor is provided, the
_sortparameter is ignored.
Pagination example
GET /v1/Patient?_count=10&_sort=-_lastUpdated
The response Bundle includes self and next link elements:
{
"resourceType": "Bundle",
"type": "searchset",
"link": [
{
"relation": "self",
"url": "https://api.ikj.test.nhn.no/v1/Patient?_count=10&_sort=-_lastUpdated"
},
{
"relation": "next",
"url": "https://api.ikj.test.nhn.no/v1/Patient?cursor=ZXlKTVlYTjB..."
}
]
}
To fetch the next page, follow the next link via GET.