# ProcessManufacturingHandoff

## Permission Scope

subledgerHandoff

## Overview

processManufacturingHandoff receives cost settlement events from the manufacturing module and creates corresponding Miscellaneous-type journal entries in the general ledger. The entry debits finished goods and variance accounts (material price variance, labor efficiency variance, overhead variance) and credits the WIP (work-in-progress) account. The command enforces idempotency and returns a ManufacturingCostSettlementAcknowledgment upon successful posting.

## Business Rules

- Receives a handoff event containing cost settlement data with WIP, finished goods, and variance account references
- Creates a journal entry classified as Miscellaneous journal type
- Debits finished goods account and applicable variance accounts (material price, labor efficiency, overhead)
- Credits the WIP account
- Variance entries are separately recorded for each applicable variance type
- The journal entry must be balanced (total debits equal total credits in functional currency)
- The journal entry carries a source document reference linking to the originating manufacturing settlement
- Idempotent processing: duplicate events with the same source document reference return the original acknowledgment without re-posting
- Validates that the target accounting period is in OPEN or FUTURE_ENTERABLE status
- Validates that all referenced GL accounts are active in the Chart of Accounts
- Handles deprecated GL accounts with successor mappings by redirecting to the successor
- Supports multi-currency: foreign currency amounts are converted to base currency using the provided exchange rate
- Rejects events with zero or negative amounts
- Events are scoped to a company
- Returns a ManufacturingCostSettlementAcknowledgment with journal entry ID and settlement reference
- Emits an audit event recording the source module, document reference, and journal entry created

## Process Flow

```mermaid
flowchart TD
    A[Receive manufacturing handoff event] --> B{Idempotency check: already posted?}
    B -->|Yes| C[Return existing acknowledgment]
    B -->|No| D{Accounting period OPEN or FUTURE_ENTERABLE?}
    D -->|No| E[Return error: invalid period status]
    D -->|Yes| F{GL accounts valid and active?}
    F -->|No| G[Return error: account validation failed]
    F -->|Yes| H[Create entry: debit finished goods + variances, credit WIP]
    H --> I[Post journal entry]
    I --> J[Emit audit event]
    J --> K[Return ManufacturingCostSettlementAcknowledgment]
```

## External Dependencies

- [coa-management::getAccount](../../../coa-management/docs/queries/GetAccount.md) - Validates that WIP, finished goods, and variance GL accounts are active
- [primitives::getCurrency](../../../primitives/docs/queries/GetCurrency.md) - Validates currency for multi-currency transactions

## Error Scenarios

- **INVALID_PERIOD_STATUS**: Target accounting period is not in OPEN or FUTURE_ENTERABLE status
- **ACCOUNT_NOT_FOUND**: Referenced GL account does not exist
- **ACCOUNT_NOT_ACTIVE**: Referenced GL account is not in active status
- **INVALID_AMOUNT**: Handoff event contains zero or negative amounts
- **COMPANY_MISMATCH**: Handoff event company does not match the GL account company scope

## Test Cases

- returns existing entry for idempotent duplicate
- returns error when amount is zero or negative
- returns error when amount is negative
- returns error when period is not OPEN or FUTURE_ENTERABLE
- returns error when period is CLOSED
- returns error when company does not match period company
- returns error when debit account is not found
- returns error when credit account is not found
- returns error when debit account is not active
- returns error when credit account is not active
- creates journal entry with correct type and amounts
- handles multi-currency with exchange rate
