---
title: Bill
summary: API reference for Bill.
status: draft
owner: SAIF Doc Gen
last_reviewed: 2026-09-24
library: SAIF.Domain
reference_type: package
---

# Bill

`Bill` is the central domain wrapper for a `CbpBill` entity and the type most of the other members in this namespace group are built to serve: it exposes the bill's audit, claim, status, and services, implements the audit-queue routing and status-transition behaviour of [OP-DOM-13](../../operations-processes.md#op-dom-13), and drives EOB generation, payment-option changes, and duplicate detection. `BillRegenerator`, `AuditNote`, and SAIF.Services all construct and drive `Bill` instances to change a bill's lifecycle state.

## Purpose
- Routes a bill to the correct audit review level (LEVEL1/LEVEL2) based on bill type, charge amount, and nurse-review requirement ([DOM-BR-130](../../business-rules.md#dom-br-130-audit-routing)).
- Implements the bill status transitions — send to audit, pend, approve, and the underlying `ModifyStatus` used by all of them — recording an audit note and a new `CbpBillStatus` row for each change ([DOM-BR-030](../../business-rules.md#dom-br-030-status-change), [DOM-BR-131](../../business-rules.md#dom-br-131-send-to-audit), [DOM-BR-132](../../business-rules.md#dom-br-132-pend-approve)).
- Generates the bill's explanation of benefits via `EobGenerator`, requiring the bill to have a resolved claim first ([DOM-BR-134](../../business-rules.md#dom-br-134-generate-eob)).
- Detects full-duplicate bills and updates payment options, tagging the update user to flag manual changes ([DOM-BR-133](../../business-rules.md#dom-br-133-payment-option-change), [DOM-BR-135](../../business-rules.md#dom-br-135-duplicate-check)).

## Context
- Namespace: `SAIF.Domain.Model.Claims.Bills`
- Assembly/package: `SAIF.Domain` (packaged in `SAIF.SAIFCode.Core`)

## Public members
| Member | Signature | Purpose |
| --- | --- | --- |
| Bill (constructor by id) | `public Bill(IRepositoryFactory factory, IUserProfileService profile, IBillQueryProvider billQueryProvider, IClaimQueryProvider claimQueryProvider, IAuditNoteQueryProvider auditNoteQueryProvider, IWorkerQueryProvider workerQueryProvider, ICCClaimApiService claimApiService, long billId, IClaimDataApiClient gwClaimDataApiClient)` | Loads the bill by `billId` and, when it has a claim reference, eagerly resolves that claim from `claimQueryProvider`. |
| Bill (constructor from entity) | `public Bill(IRepositoryFactory factory, IUserProfileService profile, CbpBill bill, IBillQueryProvider billQueryProvider, IClaimQueryProvider claimQueryProvider, IAuditNoteQueryProvider auditNoteQueryProvider, IWorkerQueryProvider workerQueryProvider, ICCClaimApiService claimApiService, IClaimDataApiClient gwClaimDataApiClient)` | Wraps an already-loaded `CbpBill` entity (used by `BillRegenerator` for the cloned bill). |
| Data | `public CbpBill Data { get; }` | Exposes the underlying `CbpBill` entity. |
| Audit | `public Audit Audit { get; }` | The bill's first `CbpAudit` wrapped as an `Audit` domain object, or `Audit.Empty()` when the bill has no data. |
| Claim | `public Claim Claim { get; }` | The bill's associated claim, constructed fresh from the bill's `Claim` navigation property on each access. |
| ClaimApiClient | `public Claim ClaimApiClient { get; }` | Identical construction to `Claim`; a second accessor for the same claim data*. |
| OriginalBillIds | `public IEnumerable<long> OriginalBillIds { get; }` | The IDs of the bills this bill duplicates, returned only when the bill `IsFullDuplicate`; otherwise empty. |
| PhysicalMedicineCount | `public int PhysicalMedicineCount { get; }` | The count of physical-medicine services recorded against the bill's claim, `0` when the bill has no data. |
| GenrateEob | `public ExplanationOfBenefits GenrateEob()` | Builds the bill's explanation of benefits via `EobGenerator.GenerateEob`, throwing when the bill's claim does not exist in ClaimCenter ([DOM-BR-134](../../business-rules.md#dom-br-134-generate-eob)). |
| Status | `public BillStatusCode Status { get; }` | The bill's current status code, wrapped from `DataItem.BillStatus`. |
| AuditQueue | `public string AuditQueue { get; }` | The audit review level (`{LEVEL1}` or `{LEVEL2}`) the bill should route to, based on bill type, charge threshold, and nurse-review flag ([DOM-BR-130](../../business-rules.md#dom-br-130-audit-routing)). |
| IsFullDuplicate | `public bool IsFullDuplicate { get; }` | `true` when the bill's non-duplicate service count is zero, meaning every service on it duplicates another bill ([DOM-BR-135](../../business-rules.md#dom-br-135-duplicate-check)). |
| SendToAudit | `public void SendToAudit(string noteText)` | Moves the bill to status Audited, using `AuditQueue` as the responsible party and attaching `noteText` as a B/AU audit note ([DOM-BR-131](../../business-rules.md#dom-br-131-send-to-audit)). |
| SendPend | `public void SendPend(DateTime pendDate, string pendUserId)` | Sets the bill's next review date to `pendDate` and responsible party to `pendUserId`, keeping the current status ([DOM-BR-132](../../business-rules.md#dom-br-132-pend-approve)). |
| Approve | `public void Approve(DateTime nextReviewDate)` | Moves the bill to status Approved with responsible party `"SYSTEM"` and the given next review date ([DOM-BR-132](../../business-rules.md#dom-br-132-pend-approve)). |
| ModifyPaymentOptions | `public void ModifyPaymentOptions(PaymentOptionsRequest data)` | Updates the current status's next review date and the audit's chargeable-cost/special-handling settings from `data`, appending `"@"` to the update user to flag a manual payment-option change ([DOM-BR-133](../../business-rules.md#dom-br-133-payment-option-change)); no-ops when the bill has no data. |
| GetOtherServices | `public IEnumerable<Core.Contracts.Claims.Bills.AuditedService> GetOtherServices(DateTime fromDate, DateTime thruDate)` | Returns the audited-service contracts for the bill's claim (excluding this bill) within the given date range, for duplicate/overlap comparisons. |
| Procedures | `public IEnumerable<BillProcedure> Procedures { get; }` | The bill's procedures wrapped as `BillProcedure` domain objects; empty when the bill has no data. |

## Inherited public members

Members in this section are inherited from `DomainBase<TItem>` in `SAIF.Domain`. They are available on this type through inheritance (via the intermediate `DomainRepositoryBase<TItem>` base).

| Member | Signature | Purpose | Origin |
| --- | --- | --- | --- |
| HasData | `public virtual bool HasData { get; }` | Reports whether the wrapped `CbpBill` entity is present, evaluated as `!DataItem.IsNull()`. | `SAIF.Domain` — `DomainBase<TItem>` |

## Behavioral notes
- `ModifyStatus` (internal) is the single choke point every public status-changing method funnels through: it resolves the target `CbpBillStatus` via `BillStatusCode.GetStatusCode` ([DOM-BR-030](../../business-rules.md#dom-br-030-status-change)), adds a new status row, and optionally attaches a category-B audit note.
- `SendPend` and `Approve` both look up the current user through `IUserProfileService.GetCurrentUser()` rather than accepting the acting user as a parameter, so the caller's ambient identity determines `CurrentUser` on the resulting status row.
- `Claim` and `ClaimApiClient` construct a new `Claim` wrapper on every access rather than caching one, so repeated access re-reads `DataItem.Claim`*.

## Constraints and usage notes
- `GenrateEob` throws a plain `Exception` (not a domain-specific type) when `Data.Claim` is null, so callers must be prepared to catch a generic exception for this specific failure mode.
- `AuditQueue`, `OriginalBillIds`, and `PhysicalMedicineCount` all issue their own query-provider calls on each access; repeated reads re-query rather than reusing a cached value*.

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

## Sources
- `Domain/SAIF.Domain/Model/Claims/Bills/Bill.cs`
- `Domain/SAIF.Domain/DomainBase.cs`
- `Domain/SAIF.Domain/DomainRepositoryBase.cs`
