Skip to content

COA KPIs System

Last Updated: 2026-01-19

Overview

The COA KPIs system is a flat, denormalized Chart of Accounts with Key Performance Indicators for construction cost estimation. It replaces the older hierarchical tree-based COA with a tabular approach that embeds all 8 hierarchy levels (L1-L8) directly in each record.

Key Files

Layer File
Frontend Types frontend/src/types/coaKpi.ts
Frontend Hook frontend/src/hooks/resources/useCOAKpis.ts
Frontend API frontend/src/services/api/coaKpis.ts
Backend Router backend/app/api/v1/routers/coa_kpis.py
Backend Schema backend/app/schemas/coa_kpi.py
Backend Repository backend/app/repositories/coa_kpi.py

Data Model

interface COAKPI {
  id: string;                 // Same as kpiCode
  kpiCode: string;            // Dot-separated code (e.g., "11.1.1.2.0.0.0")
  kpiName: string;            // Display name

  group: 'bulk' | 'equipment' | 'indirect';  // Partition key
  discipline?: string;

  // 8-Level Hierarchy (denormalized)
  l1Code: string;
  l1Description: string;
  l2Code?: string;
  l2Description?: string;
  // ... l3 through l8

  // Computed
  depth: number;              // 1-8 based on filled levels
  searchText: string;         // For search optimization

  // KPI Inheritance
  enforceKpi: boolean;        // When true, descendants use this KPI
  effectiveKpiCode?: string;  // The KPI to use (may be from ancestor)
  effectiveKpiName?: string;
  isInherited: boolean;       // True if from enforced ancestor
}

Group Classification

Group Description Examples
bulk Bulk materials Cables, pipes, fittings
equipment Tagged equipment Pumps, motors, valves
indirect Indirect costs Labor overhead, site costs

API Endpoints

Endpoint Method Description
/coa-kpis GET Paginated list with filters
/coa-kpis/{kpi_code} GET Single item
/coa-kpis POST Create
/coa-kpis/{kpi_code} PUT Update
/coa-kpis/{kpi_code} DELETE Soft/hard delete
/coa-kpis/bulk POST Bulk upsert
/coa-kpis/disciplines GET Distinct disciplines

Query Filters

interface COAKPIFilters {
  group?: 'bulk' | 'equipment' | 'indirect';
  discipline?: string;
  depth?: number;
  search?: string;
  isActive?: boolean;
  limit?: number;
  skip?: number;
}

Frontend Usage

const {
  coaKpis,           // Raw items
  options,           // For combobox (value + label)
  optionsWithKpi,    // With inheritance info
  loading,
  hasMore,
  loadMore,
} = useCOAKpis({
  filters: { group: 'bulk' },
});

MTO Integration

When assigning COA to an MTO item:

  1. User selects COA from combobox
  2. Frontend auto-populates KPI using effectiveKpiCode
  3. MTO item updated with coaCode, coaName, kpiCode, kpiName
  4. Q-Flag can mark item for cost-per-unit calculations

MTO Fields

interface MTOItem {
  coaCode?: string;      // Selected COA code
  coaName?: string;
  kpiCode?: string;      // Effective KPI (may differ from COA)
  kpiName?: string;
  qFlag?: boolean;       // Primary quantity for KPI aggregation
}

KPI Inheritance

The effectiveKpiCode is pre-computed:

If enforceKpi = true:
  effectiveKpiCode = own kpiCode
Else if ancestor has enforceKpi = true:
  effectiveKpiCode = ancestor's kpiCode (isInherited = true)
Else:
  effectiveKpiCode = own kpiCode

COA vs COA KPIs

Aspect Legacy COA (Tree) COA KPIs (Flat)
Structure Hierarchical with parentId Flat with L1-L8 embedded
KPI Inheritance Computed at query time Pre-computed
Query Performance Tree traversal Direct lookup
Partition Key /scope /group

Cosmos DB Configuration

  • Container: coa-kpis
  • Partition Key: /group
  • ID: Uses kpiCode as document ID