Find

Article
· Jan 14 14m read

Implementing FHIR Profiles on IRIS

What is a FHIR Profile?

A FHIR profile is a collection of rules and constraints used to customize and refine a base Fast Healthcare Interoperability Resources (FHIR) resource. Profiling is a vital process that adapts the base FHIR resource standard to satisfy the unique requirements of a specific use case, geographic region, medical institution, or clinical workflow.

While the base FHIR specification provides generic, flexible definitions for resources (such as Patient, Observation, or Medication), profiles transform these generic resources into more precise ones. This ensures consistent and interoperable data exchange tailored for a particular community or implementation.

FHIR is designed to cover various healthcare scenarios globally. Profiles allow implementers to adapt this general platform without losing the benefits of standardization.

When to Use FHIR Profiles?

FHIR profiles act as computable rules used by systems to validate data. You should implement them whenever you need to ensure that exchanged data is not only technically valid FHIR, but also clinically relevant and compliant with local regulations for a specific task.

Use Cases of Profiles

There are two primary methods within the FHIR RESTful API to declare the use of a profile

1. Via Query Parameter (?_profile or $validate)

  1. _profile = Search Filter (It is NOT used for validation, but is effective for retrieving stored resources). Used only for searching resources that already claim conformance. Example:

GET /Patient?_profile=http://example.org/fhir/StructureDefinition/MyProfile

Wrong: /Patient/$validate?_profile=http://example.org/fhir/StructureDefinition/MyProfile

  1. $validate = Validation Operation (It is correct for profile validation, and it is an Operation Parameter for the $validate operation.) It is utilized to ask the server to validate a resource against a specific profile. Example:

POST /Patient/$validate?profile=http://example.org/fhir/StructureDefinition/MyProfile

  1. IRIS-specific validation – InterSystems IRIS requires version numbers when performing $validate. Example:

POST /Patient/$validate?profile=http://examples.com/fhir/StructureDefinition/aktestpatient|1.0.0

Bear in mind that without the version number, IRIS returns an error:

"Profile URI ... does not include a version number. Version number is required for profile validation."

Note: Standard FHIR allows a canonical URL without a version, but IRIS enforces it for determinism and safety.

2. Via Resource Content (meta.profile) [Preferred]

You can specify the profile inside the resource itself:

{
	"resourceType": "Patient",
	"meta": {
		"profile": [
			"http://hl7.org/fhir/us/core/StructureDefinition/us-core-patient"
		]
	}
}

 

Key FHIR Artifacts for Profiling

1. StructureDefinition (The Profile Itself)

The StructureDefinition resource is the core artifact of a FHIR profile. It serves as a blueprint or schema that the data must follow. It describes the rules and constraints for a resource or datatype, specifying the next:

  • Mandatory or optional fields.
  • Cardinality (minimum/maximum repetitions).
  • Fixed values or patterns.
  • Permissible terminologies (ValueSets).
  • Applicable Extensions.

Key Contents:

  • url (Canonical URL): A stable, unique identifier used in the meta.profile of a resource instance.
  • baseDefinition: A link to the resource (or profile) being constrained.
  • snapshot: A comprehensive, "flattened" view of the resource with all the restrictions being applied.
  • differential: A list of changes or constraints applied to the base definition (the profile creator determines it).

2. ValueSet

It specifies a set of permissible codes for a field

  • Purpose: It indicates which values are allowed for a particular element.

3. CodeSystem

It defines a list of codes and their meanings (it is essentially a dictionary).

  • Purpose: It provides building blocks for ValueSets.
  • Relationship: 
    • CodeSystem = "all possible codes"
    • ValueSet = "subset used for this profile"

4. OperationDefinition

It describes custom operations or functions on FHIR resources.

  • It is optional and used for special endpoints only (e.g., $submit, $calculate-risk, $aggregate).

5. Extension

FHIR resources have a fixed schema that follows the 80/20 rule (the most common elements are predefined).

  • Extensions provide a safe, standardized way to add fields that are not present in the base resource.
  • They are defined using StructureDefinition with kind set for "complex-type" or "datatype".

Types of Extensions:

  1. Simple Extension: It is a single value (e.g., valueString, valueBoolean, valueDate).
  2. Complex Extension: It consists of nested elements similar to mini-resources.

Example: Adding nationality to a Patient:

{
  "resourceType": "Patient",
  "id": "123",
  "extension": [
    {
      "url": "http://example.org/fhir/StructureDefinition/patient-nationality",
      "valueString": "Indian"
    }
  ]
}

Servers that do not recognize an extension can safely ignore it.

Profile example requiring an extension comes below:

{
  "id": "Patient.nationality",
  "path": "Patient.extension",
  "sliceName": "patientNationality",
  "min": 1,
  "max": "1",
  "type": [
    {
      "code": "Extension",
      "profile": [
        "http://example.org/fhir/StructureDefinition/patient-nationality"
      ]
    }
  ]
}

Example of StructureDefinition:

 
Spoiler

 

FHIR Extensions: Best Practices

Although FHIR resources have a fixed structure, real-world implementations often require additional data fields. Extensions provide a standardized way to add this extra information without modifying the base resource. To maintain interoperability and avoid unnecessary complexity, follow the best practices listed below:

  1. Reuse Before Creating – First, check if a suitable, community-approved extension already exists.
  2. Create New Extensions Only When Necessary – Generate custom extensions only if existing fields or extensions cannot meet your requirements.
  3. Keep Extensions Simple and Modular – Opt for simple extensions (e.g., valueString, valueDate, valueBoolean) whenever possible. Use complex extensions only when needed.
  4. Document and Share – Clearly define your extension in a StructureDefinition and provide examples for others to understand and reuse it.

FHIR Profile Slicing (Summary with an Example)

In FHIR, some elements of a resource can be repeated (e.g., Patient.identifier or Observation.component). Slicing is a mechanism that allows you to apply different rules or constraints to different subsets of a repeating element (each slice is validated independently according to its own rule).  For instance, a patient may have multiple identifiers: a Social Security Number (SSN) and a Medical Record Number (MRN). Without slicing, you could only enforce generic rules for all identifiers, but you cannot distinguish between the types or apply separate constraints. With slicing, you can define each type of identifier as a distinct “slice" with its own cardinality, data type, and fixed values.

  • Key points:
    • Each slice has its own sliceName, cardinality (min/max), and constraints (ValueSets, fixed codes, etc.).
    • Single-valued elements (max=1) do not require slicing, since constraints can be applied directly in the differential.

A sample slicing definition for a patient profile might look like the following:

[
	{
		"id": "Patient.identifier",
		"path": "Patient.identifier",
		"sliceName": "ssn",
		"min": 1,
		"max": "1",
		"type": [
			{
				"code": "Identifier"
			}
		],
		"fixedSystem": "http://hl7.org/fhir/sid/us-ssn"
	},
	{
		"id": "Patient.identifier",
		"path": "Patient.identifier",
		"sliceName": "mrn",
		"min": 0,
		"max": "1",
		"type": [
			{
				"code": "Identifier"
			}
		],
		"fixedSystem": "http://hospital.org/mrn"
	}
]

 

Constraints and ValueSet Bindings in FHIR Profiles

In FHIR profiles, multiple elements use coded values, e.g., Patient.gender or Observation.code. While the base FHIR specification may already define allowed codes, profiles can further constrain these values to meet specific use cases, regions, or organizational rules. This can be achieved by either binding the element to a ValueSet, which defines the set of permissible codes, or by specifying a binding strength (required, extensible, or preferred) to control how strictly the codes must be followed.

For instance, the Patient.gender field globally allows four codes: male, female, other, and unknown. A local system may choose to accept only male or female. With the help of a profile, you can bind Patient.gender to a ValueSet containing only those two codes with the required binding strength. It will ensure that any resource not using one of the allowed codes will fail profile validation.

Sample Binding in a Profile:

{
  "id": "Patient.gender",
  "path": "Patient.gender",
  "min": 1,
  "max": "1",
  "type": [{ "code": "code" }],
  "binding": {
    "strength": "required",
    "valueSet": "http://example.org/fhir/ValueSet/local-gender"
  }
}

 

Cardinality in FHIR Profiles

Cardinality defines how many times an element can appear in a resource. It is specified with the min (minimum) and max (maximum) values in a profile’s differential.

  • min → the minimum number of times the element must appear.
  • max → the maximum number of times the element can appear. Use "*" to indicate unlimited repetitions
{
  "id": "Patient.telecom",
  "path": "Patient.telecom",
  "min": 0,
  "max": "*"
}

 

Profile Hierarchy and Inheritance

FHIR profiles do not have to constrain only the base resources. They can also build on other existing profiles. This means a profile can inherit all the rules, constraints, and bindings from another profile and then add extra requirements for a specific use case. This hierarchical approach helps promote reuse, consistency, and modular design.

For example, the US-Core-Patient profile defines such mandatory fields as name and gender. A hospital could create a custom profile that will build on US-Core-Patient by adding a national identifier or insurance information. By setting the US-Core-Patient as its baseDefinition, the custom profile will automatically inherits all constraints from the base, while also enforcing its own additional rules:

{
  "resourceType": "StructureDefinition",
  "url": "http://example.org/fhir/StructureDefinition/HospitalPatient",
  "name": "HospitalPatient",
  "status": "draft",
  "fhirVersion": "4.0.1",
  "kind": "resource",
  "abstract": false,
  "type": "Patient",
  "baseDefinition": "http://hl7.org/fhir/us/core/StructureDefinition/us-core-patient",
  "derivation": "constraint",
  "differential": {
    "element": [
      {
        "id": "Patient.identifier",
        "path": "Patient.identifier",
        "sliceName": "nationalId",
        "min": 1,
        "max": "1",
        "type": [{"code": "Identifier"}],
        "fixedSystem": "http://example.org/fhir/sid/national-id"
      }
    ]
  }
}

 

The "baseDefinition" field determines the profile or resource that your profile constrains, creating hierarchical or inheritance relationships. This means your HospitalPatient profile inherits all constraints from the US-Core-Patient profile.

Using $validate with Parameters vs Direct Resource

The FHIR standard allows the $validate operation to accept a resource in two ways: either directly in the POST body or wrapped inside a Parameters resource. The Parameters resource is a standard FHIR resource type designed to pass named input values to operations. Using it is optional for simple validations but recommended when multiple parameters are needed (e.g., specifying a profile version, validation mode, or additional inputs).

Example – Direct Resource:

POST /Patient/$validate?_profile=...|1.0.0
Content-Type: application/fhir+json

{
  "resourceType": "Patient",
  "id": "123",
  "name": [{"family": "Doe", "given": ["John"]}],
  "gender": "male"
}

 
Example – Parameters Wrapper (Recommended for Flexibility):

{
  "resourceType": "Parameters",
  "parameter": [
    {
      "name": "resource",
      "resource": { "resourceType": "Patient", "id": "123", "name": [{"family": "Doe", "given": ["John"]}], "gender": "male" }
    }
  ]
}

 

IRIS supports both methods. Using the Parameters wrapper ensures future-proofing and flexibility when additional parameters are required.

Implementing FHIR Profiles in InterSystems IRIS

Prerequisites for Implementing FHIR Profiles in InterSystems IRIS

Before beginning your FHIR profile implementation, make sure that your environment meets the following requirements and architectural constraints:

  • Version Compatibility: Profile validation is currently optimized for FHIR R4. Support for FHIR R5 is planned for future releases.
  • Runtime Environment: The system must have Java 11 installed. This is a strict requirement for executing validation logic against FHIR resources.
  • Service Configuration: The FHIR Validation Server must be active. This component is essential for processing and verifying profiles within the IRIS ecosystem.

 

Importing FHIR Profiles into InterSystems IRIS

Before you can perform resource validation, you must first import the relevant FHIR profiles into the IRIS platform. To ensure a successful import, your profile package must adhere to a specific directory structure.

Profile Package Structure

The import utility requires two critical files to be located within the same directory:

  1. package.json: This manifest file determines the metadata, dependencies, and versioning for your FHIR profile.
  2. StructureDefinition: This file (in JSON format) contains the actual constraints and rules for the FHIR resources you are defining.

Note: Both files are mandatory. The import process will fail if the package.json and the StructureDefinition files are not stored together in the same source folder.

Package.json:

{
  "name": "finalpatient.profile",
  "version": "1.0.0",
  "description": "Example finalpatient snapshot profile validation package",
  "dependencies": {
    "hl7.fhir.r4.core":"4.0.1"
  }
}


StructureDefinition:

 
Spoiler

Step-by-Step: Importing the FHIR Profile

Once your package files are prepared and organized, follow these steps within the Management Portal (SMP) to ingest the profile into your InterSystems IRIS environment:

Navigation Path

  1. Open the Management Portal: Log in and navigate to the Health section.
  2. Select Your Namespace: Choose the specific namespace where your FHIR server is configured.
  3. Access FHIR Configuration: Go to FHIR Server Management > Package Management.
  4. Once you are in the Package Management dashboard, do the following:
  5. Click Import: Select the Import button.
  6. Specify Source: Point the system to the directory containing your package.json and StructureDefinition files.
  7. Confirm: Complete the wizard to load the definitions into your instance.

After the import finishes, check the Package Management list. Your new profile should appear under the FHIR core package:

 

 

Associating Profiles with FHIR Endpoints

Importing a package into InterSystems IRIS makes the definitions available to the system, but it does not automatically apply them to your FHIR endpoints. To enable profile validation, you must manually link the imported package to your specific endpoint.

Option A: Updating an Existing Endpoint

If you already have a FHIR endpoint configured, follow these steps to add your profile:

  1. Navigate to Settings: Open your endpoint configuration and click Edit.
  2. Select Packages: Locate the Custom Packages section. From the list, select the package(s) you imported previously.
  3. Apply Changes: Click Save.

Note: Please be patient after clicking save. It may take several moments for the system to index the new definitions and update the endpoint metadata.

Option B: Creating a New Endpoint

If you are setting up a fresh FHIR service, take the next steps:

  1. Configure Basics: Fill in your endpoint URL and core settings.
  2. Add Custom Definitions: Before clicking save for the first time, navigate to the Custom Packages field and select your imported package.
  3. Finalize: Save the endpoint to initialize it with the profile definitions already in place.

 

Validating Resources Against Your FHIR Profile

With the packages imported and successfully linked to your endpoint, your environment is now fully configured. You can begin validating FHIR resources against your custom profiles.

Executing Validation

You can now send POST requests to your FHIR endpoint using the $validate operation. The server will employ the rules defined in your StructureDefinition to ensure that incoming resources comply with your specific business logic and data requirements.

Get Started with Sample Code

You can find the full codebase and ready-to-use samples in this fhir-profile-demo repo. Clone the repo to quickly test the profile import and validation process in your own IRIS environment.  

1 new Comment
Discussion (1)2
Log in or sign up to continue
Question
· Jan 14

Tips to Get the Best Makkah to Jeddah Taxi Fare

Traveling between Makkah and Jeddah is very common for pilgrims, tourists, and residents. Whether you’re heading to King Abdulaziz International Airport, Jeddah city, or returning after Umrah, taxi services remain one of the most convenient options. However, taxi fares can vary widely depending on timing, demand, and how you book. In this guide, you’ll learn practical tips to get the best Makkah to Jeddah taxi fare without compromising on comfort or safety.

Understand the Average Makkah to Jeddah Taxi Fare

Before booking a Umrah taxi, it’s important to know the average fare range. Typically, a one-way taxi from Makkah to Jeddah costs more than local city rides because of the distance (around 85–95 km).

Why Knowing the Average Fare Matters

  • Helps you avoid overcharging
  • Makes it easier to negotiate prices
  • Allows you to compare online and offline taxi options

Having a fair price range in mind gives you confidence when booking or negotiating with drivers.

Book Your Taxi in Advance Whenever Possible

One of the easiest ways to save money is to book your taxi in advance. Last-minute bookings often cost more, especially during peak seasons.

Benefits of Advance Booking

  • Fixed or pre-agreed fare
  • No surprise charges
  • Better vehicle options

Advance bookings are especially useful during Umrah, Hajj, weekends, and holidays, when demand is high and prices increase.

Avoid Peak Hours and High-Demand Periods

Taxi fares from Makkah to Jeddah fluctuate based on demand. Traveling during peak times usually results in higher prices.

High-Fare Periods to Avoid

  • After Friday prayers
  • Late nights
  • Umrah and Hajj seasons
  • Airport rush hours

If your schedule is flexible, traveling during early morning or mid-day hours can help you secure a lower fare.

Compare Online Taxi Services and Local Drivers

Not all taxi services in Saudi Arabia offer the same prices. Some online providers offer competitive rates, while local drivers may quote higher fares if they sense urgency.

How to Compare Effectively

  • Check multiple taxi websites
  • Ask for price confirmation before booking
  • Compare vehicle types and services included

A quick comparison can save you a significant amount, especially for long-distance travel.

Choose the Right Type of Taxi for Your Needs

Taxi fares depend heavily on the vehicle type you select. Luxury cars cost more than standard sedans.

Common Taxi Options

  • Standard sedan (budget-friendly)
  • SUV or family car
  • Luxury or VIP vehicle

If you’re traveling alone or with minimal luggage, a standard Jeddah taxi is usually the most economical option.

Travel in a Group to Split the Fare

If you’re traveling with family or friends, sharing a taxi can significantly reduce individual costs.

Why Group Travel Is Cost-Effective

  • Same fare split among passengers
  • No need to book multiple taxis
  • More luggage space when choosing SUVs

This is one of the smartest ways to reduce your Makkah to Jeddah taxi fare without sacrificing comfort.

Confirm All Charges Before Starting the Journey

Many travelers end up paying more because they didn’t clarify the fare structure beforehand.

Charges You Should Confirm

  • Total fare (one-way)
  • Toll or parking fees
  • Waiting charges
  • Night or holiday surcharges

Always ask for a final price confirmation before the trip begins to avoid misunderstandings.

Avoid Booking Taxis Directly from Crowded Areas

Taxi fares are often higher near:

  • Haram exits
  • Busy hotels
  • Tourist hotspots

Drivers in crowded areas know travelers are in a hurry and may quote higher prices.

Smart Alternative

Walk a short distance away or use pre-booked taxi services in Makkah to get better rates.

Use Trusted Taxi Providers Only

Cheap fares are tempting, but safety and reliability matter just as much.

Why Trusted Providers Are Better

  • Professional drivers
  • Clean and insured vehicles
  • Transparent pricing
  • Punctual service

A reliable taxi service ensures peace of mind while still offering competitive prices.

Negotiate Politely with Local Taxi Drivers

Negotiation is common in some Makkah taxi services, especially with independent drivers.

Tips for Successful Negotiation

  • Be calm and respectful
  • Mention average market rates
  • Avoid showing urgency

Polite negotiation can sometimes save you a noticeable amount, especially during off-peak hours.

Check Reviews Before Booking Online

Online taxi services often display customer reviews. These reviews provide insights into pricing fairness and service quality.

What to Look for in Reviews

  • Transparent fares
  • No hidden charges
  • Timely pickups

Choosing a highly rated provider reduces the risk of unexpected costs.

Final Thoughts: Travel Smart and Save Money

Getting the best Makkah to Jeddah taxi fare isn’t difficult if you plan ahead and make informed choices. By understanding average prices, booking in advance, avoiding peak hours, and choosing the right service, you can enjoy a comfortable and affordable journey.

A little research and smart planning go a long way in ensuring a stress-free and budget-friendly trip between these two important cities.

Discussion (0)1
Log in or sign up to continue
Announcement
· Jan 13

Managing InterSystems Servers – Virtual February 2-6, 2026 / Registration space available

Managing InterSystems Servers – Virtual  February 2-6, 2026

  • Configure, manage, plan, and monitor system operations of InterSystems Data Platform technology
  • This 5-day course teaches system and database administrators how to manage InterSystems® Data Platform technology which powers all of our products.
  • Learn to install, configure and secure the data platform, configure for high availability and disaster recovery, and monitor the system.
  • Students also learn troubleshooting techniques.

SELF REGISTER HERE

Discussion (0)1
Log in or sign up to continue
Announcement
· Jan 13

Global Masters: puntos y una insignia por convertir ideas en realidad

¡Hola, comunidad!

A partir de enero de 2026, los desarrolladores que conviertan ideas de producto del Portal de Ideas en soluciones reales y funcionales serán premiados con 7.000 puntos en Global Masters y una insignia.

Lo que obtenéis:
🧙‍♂️ Insignia Idea to Reality Wizard
— otorgada una sola vez a los miembros de la comunidad que implementen una idea de producto propuesta en el Portal de Ideas.
7.000 puntos de Global Masters — otorgados por cada idea implementada de la lista «Community Opportunity».


 

Detalles: 

Como quizá ya sabéis, cualquiera puede enviar ideas o sugerencias de producto en el Portal de Ideas de InterSystems (y ganar puntos e insignias por ello; ved esta publicación relacionada).
Cualquiera puede sumarse, tomar una idea y ayudar a toda la comunidad haciéndola realidad.
Ahora, cuando una idea sea implementada por un miembro de la comunidad, queremos agradecéroslo reconociendo vuestra contribución y otorgándoos puntos de Global Masters y una insignia.

🤝 ¿Trabajáis en equipo?
Si una idea se implementa junto con otros desarrolladores, los 7.000 puntos se reparten a partes iguales entre todos los colaboradores.

La insignia se otorga una sola vez, pero los puntos pueden ganarse una y otra vez a medida que implementáis más ideas.

Gracias a todos los que construís, contribuís y ayudáis a convertir ideas en realidad. Estamos deseando ver en qué trabajáis a continuación 💡

Si aún no sois miembros del Global Masters Advocacy Hub, uníos ahora para manteneros al día, conseguir premios interesantes y dejarnos reconocer vuestra contribución a la comunidad de desarrolladores. 👍

Discussion (0)1
Log in or sign up to continue
Question
· Jan 13

Creating an Analytics Dashboard from SQL Query

New to using Analytics and using Dashboards. We have this Report, SQL Query that lists out the Activity per Data Source in Health Share Provider Directory. Instead of running it as a report, because it takes a while to run, was wondering if there is a way to do this as a Dashboard instead.

How can I take the SQL from this report and create a Dashboard instead?

3 new Comments
Discussion (3)3
Log in or sign up to continue