Skip to main content

FHIR Integration Guide

This guide covers the Fast Healthcare Interoperability Resources (FHIR) integration capabilities in LyfeAI Provider, enabling standardized healthcare data exchange.

Overview

LyfeAI Provider implements FHIR R4 standards for healthcare data interoperability. The system can import, export, and process FHIR resources, making it compatible with modern healthcare systems and HIEs (Health Information Exchanges).

FHIR Service Architecture

The core FHIR functionality is implemented in lib/enhanced-fhir-service.ts:

import { EnhancedFHIRService } from '@/lib/enhanced-fhir-service';

const fhirService = new EnhancedFHIRService();

// Parse FHIR Bundle
const parsedData = await fhirService.parseFHIRBundle(fhirBundle);

// Parse individual Patient resource
const patient = await fhirService.parseFHIRPatient(fhirPatientResource);

Supported FHIR Resources

Core Resources

Patient

  • Demographics (name, gender, birth date)
  • Identifiers (MRN, SSN, driver's license)
  • Contact information (address, phone, email)
  • Communication preferences
  • Extensions for race, ethnicity, birth sex

Condition

  • Clinical conditions and diagnoses
  • ICD-10 coding
  • Onset dates and abatement
  • Clinical status and verification
  • Severity assessments

MedicationStatement

  • Current medications
  • Dosage instructions
  • Date ranges
  • Status (active, completed, on-hold)
  • Reason for medication

AllergyIntolerance

  • Allergens (medication, food, environmental)
  • Reaction manifestations
  • Severity levels
  • Criticality assessments
  • Verification status

Observation

  • Vital signs
  • Laboratory results
  • Clinical measurements
  • Reference ranges
  • Interpretation codes

Encounter

  • Visit information
  • Encounter class and type
  • Period and duration
  • Participants (providers)
  • Diagnoses and procedures

Immunization

  • Vaccine codes (CVX)
  • Administration dates
  • Sites and routes
  • Lot numbers
  • Performer information

DocumentReference

  • Clinical documents
  • Document type and class
  • Content attachments
  • Author and custodian
  • Security labels

Data Import

Parsing FHIR Bundles

// Import a FHIR Bundle
const fhirBundle = {
resourceType: "Bundle",
type: "collection",
entry: [
{
resource: {
resourceType: "Patient",
id: "example-patient",
name: [{
given: ["John"],
family: "Doe"
}],
gender: "male",
birthDate: "1980-01-15"
}
},
// More resources...
]
};

const result = await fhirService.parseFHIRBundle(fhirBundle);

// Result structure:
{
patient: {
firstName: "John",
lastName: "Doe",
dateOfBirth: "1980-01-15",
gender: "male",
// ... mapped fields
},
conditions: [...],
medications: [...],
allergies: [...],
// ... other resources
}

Import from External Systems

// Via server action
import { importFHIRData } from '@/app/actions/ehr-actions';

const importResult = await importFHIRData({
source: "epic-ehr",
patientId: "12345",
resourceTypes: ["Patient", "Condition", "MedicationStatement"]
});

if (importResult.success) {
console.log(`Imported ${importResult.recordCount} records`);
}

Handling Different FHIR Versions

const fhirData = await fhirService.parseFHIRData(resource, {
version: 'R4', // R4 (default), STU3, DSTU2
strict: false, // Allow minor validation errors
includeExtensions: true // Parse FHIR extensions
});

Data Mapping

FHIR to Internal Model

The service maps FHIR resources to internal data models:

// FHIR Patient → Internal Patient
{
// FHIR
"name": [{
"given": ["John", "James"],
"family": "Doe",
"use": "official"
}],
"telecom": [{
"system": "phone",
"value": "555-123-4567",
"use": "home"
}]
}

// Mapped to:
{
firstName: "John",
middleName: "James",
lastName: "Doe",
phone: "555-123-4567"
}

Code System Mapping

// ICD-10 from FHIR Condition
const condition = {
code: {
coding: [{
system: "http://hl7.org/fhir/sid/icd-10",
code: "E11.9",
display: "Type 2 diabetes mellitus without complications"
}]
}
};

// Mapped to:
{
name: "Type 2 diabetes mellitus without complications",
icd10Code: "E11.9",
codeSystem: "ICD-10"
}

Data Export

Creating FHIR Resources

// Convert internal patient to FHIR
const fhirPatient = fhirService.toFHIRPatient({
id: "123",
firstName: "Jane",
lastName: "Smith",
dateOfBirth: "1975-05-20",
gender: "female",
mrn: "MRN789"
});

// Result:
{
resourceType: "Patient",
id: "123",
identifier: [{
type: {
coding: [{
system: "http://terminology.hl7.org/CodeSystem/v2-0203",
code: "MR"
}]
},
value: "MRN789"
}],
name: [{
given: ["Jane"],
family: "Smith"
}],
gender: "female",
birthDate: "1975-05-20"
}

Creating FHIR Bundles

// Export patient data as FHIR Bundle
const bundle = await fhirService.createFHIRBundle(patient.id, {
includeConditions: true,
includeMedications: true,
includeAllergies: true,
includeEncounters: true,
bundleType: "collection"
});

// Save or transmit bundle
await sendToHIE(bundle);

Advanced Features

FHIR Validation

// Validate FHIR resources
const validation = await fhirService.validateFHIRResource(resource);

if (!validation.valid) {
console.error("Validation errors:", validation.errors);
// Handle validation errors
}

Custom Extensions

// Handle US Core extensions
const patient = {
resourceType: "Patient",
extension: [{
url: "http://hl7.org/fhir/us/core/StructureDefinition/us-core-race",
extension: [{
url: "ombCategory",
valueCoding: {
system: "urn:oid:2.16.840.1.113883.6.238",
code: "2054-5",
display: "Black or African American"
}
}]
}]
};

const parsed = await fhirService.parseFHIRPatient(patient, {
parseExtensions: true,
extensionMappings: {
"us-core-race": "race",
"us-core-ethnicity": "ethnicity"
}
});
// Search for FHIR resources
const searchParams = {
resourceType: "Patient",
params: {
name: "smith",
birthdate: "1975-05-20",
gender: "female"
}
};

const results = await fhirService.searchFHIR(searchParams);

Integration Patterns

EHR Integration

// Sync with Epic MyChart
export async function syncWithEpic(patientMRN: string) {
try {
// 1. Authenticate with Epic
const token = await getEpicAccessToken();

// 2. Fetch patient bundle
const bundle = await fetchEpicPatientBundle(patientMRN, token);

// 3. Parse FHIR data
const parsed = await fhirService.parseFHIRBundle(bundle);

// 4. Update local records
await updatePatientFromFHIR(parsed);

return { success: true, recordsUpdated: parsed.recordCount };
} catch (error) {
console.error("Epic sync failed:", error);
return { success: false, error: error.message };
}
}

HIE Integration

// Submit to Health Information Exchange
export async function submitToHIE(patient: Patient) {
// 1. Convert to FHIR
const bundle = await fhirService.createFHIRBundle(patient.id, {
includeAll: true
});

// 2. Add metadata
bundle.meta = {
lastUpdated: new Date().toISOString(),
source: "lyfeai-provider"
};

// 3. Submit to HIE
const response = await hieClient.submit(bundle);

return response;
}

SMART on FHIR Apps

// Launch context for SMART apps
const smartContext = {
patient: fhirPatient.id,
encounter: currentEncounter?.id,
practitioner: currentUser.fhirId,
fhirServer: process.env.FHIR_SERVER_URL
};

// Launch SMART app
launchSmartApp(appId, smartContext);

Error Handling

Common FHIR Errors

try {
const result = await fhirService.parseFHIRBundle(bundle);
} catch (error) {
if (error.code === 'INVALID_RESOURCE_TYPE') {
// Handle unknown resource type
} else if (error.code === 'MISSING_REQUIRED_FIELD') {
// Handle missing required FHIR fields
} else if (error.code === 'INVALID_REFERENCE') {
// Handle broken references between resources
}
}

Fallback Strategies

const parseFHIRWithFallback = async (resource: any) => {
try {
// Try strict parsing
return await fhirService.parseFHIRResource(resource, { strict: true });
} catch (strictError) {
// Try lenient parsing
try {
return await fhirService.parseFHIRResource(resource, { strict: false });
} catch (lenientError) {
// Manual parsing as last resort
return manualFHIRParse(resource);
}
}
};

Performance Optimization

Batch Processing

// Process multiple FHIR resources efficiently
const resources = await fetchLargeFHIRDataset();

const results = await fhirService.batchParse(resources, {
batchSize: 100,
parallel: true,
maxConcurrency: 5
});

Selective Parsing

// Parse only specific resource types
const parsed = await fhirService.parseFHIRBundle(bundle, {
includeOnly: ['Patient', 'Condition', 'MedicationStatement'],
skipValidation: true // Faster but less safe
});

Caching

// Cache parsed FHIR data
const cacheKey = `fhir_${resourceType}_${resourceId}`;
const cached = await fhirCache.get(cacheKey);

if (cached) {
return cached;
}

const parsed = await fhirService.parseFHIRResource(resource);
await fhirCache.set(cacheKey, parsed, { ttl: 3600 });
return parsed;

Testing FHIR Integration

Unit Tests

describe('FHIR Service', () => {
it('should parse FHIR Patient correctly', async () => {
const fhirPatient = createMockFHIRPatient();
const parsed = await fhirService.parseFHIRPatient(fhirPatient);

expect(parsed.firstName).toBe('John');
expect(parsed.lastName).toBe('Doe');
expect(parsed.dateOfBirth).toBe('1980-01-15');
});

it('should handle missing optional fields', async () => {
const minimalPatient = {
resourceType: 'Patient',
name: [{ family: 'Smith' }]
};

const parsed = await fhirService.parseFHIRPatient(minimalPatient);
expect(parsed.firstName).toBe('Unknown');
expect(parsed.phone).toBeNull();
});
});

Integration Tests

it('should sync with external FHIR server', async () => {
const mockServer = setupMockFHIRServer();

const result = await syncWithFHIRServer('http://mock-fhir.local', {
patientId: 'test-123'
});

expect(result.success).toBe(true);
expect(result.resourcesImported).toBeGreaterThan(0);
});

Security Considerations

Data Privacy

// Remove sensitive extensions before export
const sanitizedBundle = fhirService.sanitizeFHIRBundle(bundle, {
removeExtensions: ['ssn', 'driver-license'],
anonymize: false,
redactNotes: true
});

Access Control

// Check FHIR resource access
const canAccessResource = (user: User, resource: any) => {
if (resource.meta?.security) {
return checkSecurityLabels(user, resource.meta.security);
}
return hasPermission(user, `fhir:${resource.resourceType}:read`);
};

Compliance

US Core Compliance

// Ensure US Core compliance
const usCompCompliant = await fhirService.validateUSCore(resource);

if (!usCompCompliant.valid) {
console.warn('US Core violations:', usCompCompliant.issues);
}

Audit Logging

// Log FHIR operations
await auditLog.record({
action: 'fhir_import',
userId: currentUser.id,
resourceType: resource.resourceType,
resourceId: resource.id,
source: 'external_ehr',
timestamp: new Date()
});

Resources