---
title: External identifier resolution (auditor, MCO, RTW, group, policy, injured worker)
summary: Resolves external source-system identifiers (auditor, MCO, return-to-work, group, policy, injured worker) into local customer records, using a consistent lookup-or-create pattern per identifier type.
status: draft
owner: SAIF
last_reviewed: 2026-07-30
library: SAIF.Business.CustomerContact
reference_type: package
operation_id: OP-CC-10
trigger: Caller invokes one of the GetCustomerIDFor* resolution functions with an external source-system identifier
---

# External identifier resolution (auditor, MCO, RTW, group, policy, injured worker)

`mdlCustomerContact` exposes six resolution functions that map an external source-system identifier to a local `clsCustomer`, creating the customer and a `CUSTOMER_SOURCE`/type-specific mapping row on first use. All six follow the same lookup-or-create shape, differing only in the source reference table(s) they read and the `CustomerTypeCode` they assign, so they are documented together as one operation.

| Field | Value |
| --- | --- |
| **Operation ID** | OP-CC-10 |
| **Trigger** | `GetCustomerIDForAuditor`, `GetCustomerIDForMCO`, `GetCustomerIDForRTW`, `GetCustomerIDForGroup`, `GetCustomerIDForPolicy`, or `GetCustomerIDForInjuredWorker` |
| **Inputs** | An external source-system identifier appropriate to the type (auditor ID, MCO source ID, RTW source ID, group ID, policy ID, or worker ID) |
| **Outputs** | Resolved `CustomerID` (or a populated `WorkerInfo` for the injured-worker path); newly created `COMPANY` row and mapping row when no mapping existed |
| **Primary components** | `mdlCustomerContact.GetCustomerIDForAuditor`, `GetCustomerIDForMCO`, `GetCustomerIDForRTW`, `GetCustomerIDForGroup`, `GetCustomerIDForPolicy`, `GetCustomerIDForInjuredWorker` |
| **Entry point** | `Business\SAIF.Business.CustomerContact\mdlCustomerContact.vb` |

## Steps

1. **Auditor resolution (`GetCustomerIDForAuditor`).**
   - Read `PA_AUDITOR` for the source auditor record ([SQL-051](../sql/SQL-051.md), [PA_AUDITOR](../database-tables.md#pa-auditor)).
   - Look up an existing `CUSTOMER_AUDITOR` mapping ([SQL-050](../sql/SQL-050.md), [CUSTOMER_AUDITOR](../database-tables.md#customer-auditor)).
   - If none exists: create a `clsCustomer` with `CustomerTypeCode = "AUDIT"`, save it, then insert the mapping row ([SQL-020](../sql/SQL-020.md)).
   - On a mapping-insert failure: roll back by deleting the newly created customer.
2. **MCO resolution (`GetCustomerIDForMCO`).**
   - Look up an existing mapping by reading `CUSTOMER_SOURCE` directly, filtered to the MCO source type (one of [SQL-054](../sql/SQL-054.md)/[SQL-055](../sql/SQL-055.md)/[SQL-056](../sql/SQL-056.md)/[SQL-062](../sql/SQL-062.md) depending on the specific source-type filter, all against [CUSTOMER_SOURCE](../database-tables.md#customer-source)).
   - Unlike the other five resolution functions, `GetCustomerIDForMCO` performs no customer creation — if no `CUSTOMER_SOURCE` row is found, it returns without creating a new customer.*
3. **RTW resolution (`GetCustomerIDForRTW`).**
   - Read `CUSTOMER_SOURCE` and `RTW_LOAD_CODE` for the source RTW record ([SQL-061](../sql/SQL-061.md), [RTW_LOAD_CODE](../database-tables.md#rtw-load-code)).
   - If no mapping exists: create a `clsCustomer` with `CustomerTypeCode = "RTW"`, save it, then insert a `CUSTOMER_SOURCE` mapping row.
4. **Group resolution (`GetCustomerIDForGroup`).**
   - Look up an existing mapping in `CUSTOMER_GROUP` ([SQL-053](../sql/SQL-053.md), [CUSTOMER_GROUP](../database-tables.md#customer-group)); if not found, fall back to `CUSTOMER_SOURCE`, then read `GROUP_ASSOCIATION` for the source record ([SQL-052](../sql/SQL-052.md), [GROUP_ASSOCIATION](../database-tables.md#group-association)).
   - If none exists: create a `clsCustomer` with `CustomerTypeCode` set to `"GROUP"` or `"LOSSC"` depending on the `GroupTypes` value of the source record, save it, then insert the `CUSTOMER_GROUP` mapping row ([SQL-021](../sql/SQL-021.md)).
   - **Unused-variable oddity:** a second `Sql` object (`sql2`) is declared for this flow but never executed — the code instead reuses `Sql.Execute` for the relevant statement, leaving `sql2` dead in the current source.*
5. **Policy resolution (`GetCustomerIDForPolicy`).**
   - Look up an existing mapping in `CUSTOMER_POLICY` ([SQL-057](../sql/SQL-057.md), [CUSTOMER_POLICY](../database-tables.md#customer-policy)).
   - If none exists: read `POLICY` for the source record ([SQL-058](../sql/SQL-058.md), [POLICY](../database-tables.md#policy)), create a `clsCustomer` with `CustomerTypeCode = "POL"`, save it, then insert the `CUSTOMER_POLICY` mapping row ([SQL-023](../sql/SQL-023.md)).
6. **Injured-worker resolution (`GetCustomerIDForInjuredWorker`).**
   - Read `CUSTOMER_SOURCE` for an existing mapping.
   - If none exists, call the external `CCClaimDataApi` API client (`inDPI.ApiClients.Item("CCClaimDataApi")`) via route `v1/ExternalLogin/PersonDetails/{workerID}` to retrieve the worker's identity details from the external claims data service. This is an external API integration outside the SAIF library dependency graph, not an in-repo project/package reference.
   - Create or update a `clsCustomer` with `CustomerTypeCode = "WORK"` and `IsPerson = True`; insert a `CUSTOMER_SOURCE` mapping row if the customer is new.
   - The returned `WorkerInfo` object only has `CustID`, `PersonID`, and `WorkerID` populated — other fields present in the external API response are read during resolution but are not copied onto `WorkerInfo` or otherwise persisted.*

## Process flow

The following diagram visualizes the shared lookup-or-create shape across all six identifier types.

```mermaid
flowchart TD
	Start([GetCustomerIDFor* called]) --> Type{Identifier type}
	Type -->|Auditor| AuditorLookup[Read PA_AUDITOR;<br>lookup CUSTOMER_AUDITOR]
	Type -->|MCO| MCOLookup[Lookup CUSTOMER_SOURCE only]
	Type -->|RTW| RTWLookup[Read CUSTOMER_SOURCE + RTW_LOAD_CODE]
	Type -->|Group| GroupLookup[Lookup CUSTOMER_GROUP,<br>fallback CUSTOMER_SOURCE;<br>read GROUP_ASSOCIATION]
	Type -->|Policy| PolicyLookup[Lookup CUSTOMER_POLICY;<br>read POLICY]
	Type -->|Injured worker| WorkerLookup[Lookup CUSTOMER_SOURCE]
	AuditorLookup --> Found1{Mapping found?}
	RTWLookup --> Found2{Mapping found?}
	GroupLookup --> Found3{Mapping found?}
	PolicyLookup --> Found4{Mapping found?}
	WorkerLookup --> Found5{Mapping found?}
	MCOLookup --> Found6{Mapping found?}
	Found6 -->|No| ReturnEmpty([Return without creating])
	Found6 -->|Yes| ReturnID([Return existing CustomerID])
	Found1 -->|Yes| ReturnID
	Found2 -->|Yes| ReturnID
	Found3 -->|Yes| ReturnID
	Found4 -->|Yes| ReturnID
	Found5 -->|Yes| ReturnWorker([Return WorkerInfo])
	Found1 -->|No| CallApi1[Create customer;<br>save; insert mapping]
	Found2 -->|No| CallApi2[Create customer;<br>save; insert mapping]
	Found3 -->|No| CallApi3[Create customer;<br>save; insert mapping]
	Found4 -->|No| CallApi4[Create customer;<br>save; insert mapping]
	Found5 -->|No| CallExternalApi[Call CCClaimDataApi<br>PersonDetails endpoint]
	CallExternalApi --> CreateWorker[Create/update customer;<br>insert mapping if new]
	CreateWorker --> ReturnWorker
	CallApi1 --> ReturnID
	CallApi2 --> ReturnID
	CallApi3 --> ReturnID
	CallApi4 --> ReturnID
```

## Failure and edge-case behavior
- `GetCustomerIDForMCO` is the only one of the six functions that never creates a customer; if the `CUSTOMER_SOURCE` lookup misses, the caller receives no customer and must handle that outcome itself.*
- `GetCustomerIDForGroup` declares an apparently-unused `Sql` object (`sql2`) alongside the one actually executed, suggesting either dead code or an incomplete refactor; behavior is unaffected since the executed statement covers the mapping insert.*
- `GetCustomerIDForInjuredWorker` depends on an external API call (`CCClaimDataApi`) rather than another SAIF library, so its availability and correctness depend on that external service; only `CustID`, `PersonID`, and `WorkerID` from the response are retained on the returned `WorkerInfo`, with the remaining response fields discarded after use.*

> **Note:** Statements marked with `*` were inferred from code structure, naming
> conventions, or contextual evidence where direct confirmation was not available
> in source artifacts.

## Related documentation
- [Operations and processes](../operations-processes.md)
- [Business rules](../business-rules.md)
- [SQL catalog](../sql/index.md)
- [Database tables](../database-tables.md)

## Sources
- `Business\SAIF.Business.CustomerContact\mdlCustomerContact.vb`
- `Business\SAIF.Business.CustomerContact\WorkerInfo.vb`
