Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.encoreos.io/llms.txt

Use this file to discover all available pages before exploring further.

Created: 2025-12-18
Status: Architecture Decision Record
Related Specs: RH-06 (Compliance & Staff Operations)

Overview

This document explains the architectural decision regarding the integration between the Recovery Housing (RH) core and Human Resources (HR) core, specifically around staff employee references.

Architecture Decision: No Foreign Key Constraints for staff_employee_id

Context

RH-06 introduces several tables that reference staff employees:
  • rh_staff_assignments.staff_employee_id
  • rh_staff_trainings.staff_employee_id
  • rh_shift_notes.staff_employee_id

Decision

These staff_employee_id columns intentionally do not have foreign key constraints to HR tables (hr_employees).

Rationale

Per the Encore Health OS Platform constitution (§1.2, §1.3):
  1. Core Isolation Principle: Cores depend ONLY on Platform Foundation (PF), never on each other directly. Foreign key constraints would create a direct database-level dependency between RH and HR.
  2. Deployment Independence: Each core should be deployable and testable independently. FK constraints would require HR schema to exist for RH migrations to succeed.
  3. Cross-Core Integration Patterns: The constitution mandates that cross-core communication use one of:
    • Platform Integration Layer (hooks, components in @/platform/)
    • Event-based integration (pg_notify/webhooks)
    • API contracts (edge functions)
    Not direct database references.

Implementation Details

Data Integrity Approach

Instead of FK constraints, RH-06 uses:
  1. Application-Level Validation: UI components use @/platform/workforce hooks to look up and validate employee IDs before saving.
  2. UUID Type Enforcement: The staff_employee_id columns are typed as UUID, ensuring only valid UUIDs can be stored.
  3. RLS Policies: Access control is enforced via organization-scoped RLS policies, not FK relationships.

Employee Lookup Pattern

// ✅ CORRECT - Use Platform Integration Layer
import { useWorkforceEmployees } from '@/platform/workforce';

function StaffAssignmentForm() {
  const { employees } = useWorkforceEmployees(organizationId);
  // Use employees for dropdown selection
}

// ❌ WRONG - Direct core import
import { useEmployees } from '@/cores/hr/hooks/useEmployees';

Implications

  1. Orphaned References: If an employee is deleted from HR, RH records referencing that employee will have orphaned staff_employee_id values. This is acceptable because:
    • Historical records should be preserved
    • Soft-delete is the standard pattern (HR uses deleted_at)
    • UI can gracefully handle “Unknown Employee” display
  2. Data Migration: When migrating data, ensure employee IDs exist in HR before creating RH staff records.
  3. Testing: RLS tests can create test users directly in auth.users without needing HR employee records.

Alternative Considered

Option: Add FK constraint to pf_profiles Rejected because:
  • Not all staff may have platform profiles (contractors, external auditors)
  • Would still create cross-table dependency issues in tests
  • pf_profiles is for platform users, not necessarily all staff

Last Updated: 2025-12-18