# AssignWorkRule

## Permission Scope

`workRule`

## Overview

Binds a `WorkRule` to a `WorkerEmployment`/`Worker`, effective-dated, so the time-tracking engine can resolve exactly which rule generation is in force for that person on any calculated date. The assignment is only permitted when an `EligibilityRule` in force on the assignment date grants the target that `WorkRule`.

## Business Rules

- Assignment is permitted only if an `EligibilityRule` generation in force on the assignment date permits the target to be assigned this `WorkRule`
- For any worker and date, at most one `WorkRule` generation is in force; a new assignment closes the prior assignment and inserts a new effective-dated one, never overlapping it
- A future-dated assignment (`effectiveStart` in the future) is a scheduled change and does not affect calculation until its start date
- The assignment references the `WorkerEmployment`/`Worker` by id and the `WorkRule` by identity, never by display name
- The `targetId` must resolve to an existing workforce entity of its `targetType`; a well-formed but dangling id is rejected before any eligibility or overlap check

## Process Flow

```mermaid
flowchart TD
    A[Receive worker/employment id, WorkRule id, effectiveStart] --> T{Target resolves in workforce?}
    T -- No --> TN[Reject: TARGET_NOT_FOUND]
    T -- Yes --> B{WorkRule exists?}
    B -- No --> C[Reject: WORK_RULE_NOT_FOUND]
    B -- Yes --> D{EligibilityRule in force on effectiveStart permits target -> WorkRule?}
    D -- No --> E[Reject: NOT_ELIGIBLE]
    D -- Yes --> F{New assignment overlaps an existing in-force assignment for this worker?}
    F -- Yes --> G[Reject: ASSIGNMENT_OVERLAP]
    F -- No --> H[Close current assignment at effectiveStart - 1 day, if any]
    H --> I[Insert new WorkRule assignment effective on effectiveStart]
```

## External Dependencies

- [time-tracking::WorkRule](../model/WorkRule.md) model — the entity being assigned
- [time-tracking::EligibilityRule](../model/EligibilityRule.md) model — checked to confirm the target may be assigned this WorkRule
- [time-tracking::WorkRuleAssignment](../model/WorkRuleAssignment.md) model — the effective-dated binding persisted by this command

## Error Scenarios

- **TARGET_NOT_FOUND**: the target does not resolve to an existing workforce entity
- **WORK_RULE_NOT_FOUND**: no WorkRule exists for the given id, or no WorkRule is effective for the relevant date
- **NOT_ELIGIBLE**: no in-force `EligibilityRule` grants the target this `WorkRule` on the assignment date
- **ASSIGNMENT_OVERLAP**: the new assignment's effective range overlaps an existing in-force assignment for the worker

## Test Cases

- rejects when the target id does not resolve to a workforce entity
- rejects when the WorkRule does not exist
- assigning a WorkRule to a target with no in-force eligibility grant is rejected
- rejects when the new assignment overlaps an existing assignment starting on or after its effectiveStart
- closes the current open assignment at effectiveStart minus one day and inserts the new generation
- inserts the initial generation when the target has no prior assignment
- assignment references the worker/employment and WorkRule by id/identity, never by display name
