# GetPunch

## Overview

Retrieves a single `TimeClockEvent` (raw punch) by its id. Used to inspect one punch directly, including a voided punch; the event row is unchanged and its void state lives in `TimeClockEventVoid` (ADR-023).

## Business Rules

- Returns the event regardless of void status; a voided event is never deleted, so it remains individually retrievable
- `eventType` and `source` are returned with normalized enum naming
- `occurredAt` is returned as recorded; no computed workday is attached (the day-breaker assigns workday later, downstream)
- Effective void state is not on this row; it is resolved from the highest-sequence `TimeClockEventVoid` record for the event

## Process Flow

```mermaid
flowchart TD
    A[Caller supplies eventId] --> B{Event exists?}
    B -- No --> C[Return PUNCH_NOT_FOUND]
    B -- Yes --> D[Return TimeClockEvent with eventType, occurredAt, source]
```

## External Dependencies

- [time-tracking::TimeClockEvent](../model/TimeClockEvent.md) model — entity being queried

## Error Scenarios

- **PUNCH_NOT_FOUND**: no TimeClockEvent exists for the given id

## Test Cases

- returns the punch event when found by id, including eventType, occurredAt, and source
- returns PUNCH_NOT_FOUND when the id does not exist
- returns a voided punch: the event row is unchanged; void state lives in TimeClockEventVoid
