# CancelGoodsIssue

## Permission Scope

inventoryOperation

## Overview

cancelGoodsIssue transitions a DRAFT goods issue InventoryExecution to CANCELLED. It is a soft cancel: the InventoryExecution and InventoryExecutionLine rows remain for traceability, but no stock, ledger, lot, serial, reservation, or valuation changes occur. Posted goods issues cannot be cancelled.

## Business Rules

- The target InventoryExecution must exist and have `executionType=GOODS_ISSUE`
- Only DRAFT goods issue executions can be cancelled
- Cancellation transitions status from DRAFT to CANCELLED
- Cancellation does not delete the InventoryExecution or InventoryExecutionLine rows
- Cancellation does not create InventoryLedger rows or update StockLevel, LotStockLevel, SerialNumber, StockReservation, or valuation records
- POSTED executions cannot be cancelled; future correction is represented by a separate reversal execution when introduced

## Process Flow

```mermaid
flowchart TD
    A[Cancel goods issue request] --> B[Lock InventoryExecution]
    B --> C{GOODS_ISSUE and DRAFT?}
    C -->|No| D[Return error: INVALID_STATUS]
    C -->|Yes| E[Transition InventoryExecution to CANCELLED]
    E --> F[Return cancelled execution]
```

## External Dependencies

- [inventory::InventoryExecution](../model/InventoryExecution.md) - Validates existence, execution type, and current status, then updates status to CANCELLED
- [inventory::InventoryExecutionLine](../model/InventoryExecution.md) - Retained as the draft line snapshot; not deleted

## Error Scenarios

- **INVALID_STATUS**: Target entity is not in a valid status for this operation

## Test Cases

- returns error when issue execution is missing
- returns error when execution is not a goods issue
- returns error when issue execution is posted
- transitions draft issue execution to CANCELLED without deleting lines
