# Badge lifecycle contract

Audience: AI coding agents first.

## Outcome

Add canonical `mount()`, `update(next)`, and idempotent `destroy()` lifecycle to `Badge`. Preserve constructor mounting and current setter behavior.

## Status

IDLE — D5-BADGE-01 is committed in this worktree.

## Task IDs

- D5-BADGE-01 — Badge lifecycle slice

## Source request

Owner requested next smallest independently shippable Delivery 5 lifecycle slice, selected from current architecture inventory. Add tests, run focused test/lint/build, commit. Do not delegate or use external models.

## Acceptance criteria

- Constructor still creates and mounts a usable badge.
- `mount()` is idempotent and does not duplicate DOM.
- `update(next)` applies supported current setter state in place without replacing mounted root.
- `destroy()` is idempotent, removes owned listener and mounted root, and leaves instance remountable.
- Existing setters retain signatures and behavior while mounted.
- Focused lifecycle tests, lint, and production build pass cleanly.
- Commit contains only Badge primitive, its focused tests, generated direct assets, and plan registry receipt.

## Preserved WIP

- Worktree: `/home/user/Projects/Press.zone/wordpress/wp-content/.worktrees/ipz-search-delivery5c/plugins/international-press-zone`
- Baseline: clean at `e65a292d5`.
- Preserve behavior outside canonical Badge primitive.

## Constraints

- Follow `.claude/agents/expert.md` and `.claude/skills/frontend-javascript.md`.
- Delivery 5 lifecycle contract requires independently revertible primitive slices.
- Do not add a second Badge implementation or alter styling.
- Preserve public constructor and setters.

## Execution steps

1. Keep one bound remove listener and define remount-safe lifecycle around current DOM structure.
2. Implement minimal lifecycle using current setter behavior for supported updates.
3. Add focused constructor, idempotent mount, in-place update, listener cleanup, repeated destroy, and remount tests.
4. Run focused test, admin lint, production build, asset completeness, and diff checks.
5. Commit only clean slice and update receipt.

## Current receipt

D5-BADGE-01 implemented. `Badge` now creates its initial element through idempotent `mount()`, exposes in-place `update(next)` for existing text, variant, size, and tooltip setters, and keeps one bound remove listener for idempotent cleanup and remounting. Focused lifecycle tests cover constructor compatibility, repeated mount, in-place update, listener removal, repeated destroy, and remount. Inventory regenerated: 123 modules, 54 components, 16 pages, 0 unclassified, 0 direction violations, 2 duplicate-ID baseline entries.

Verification completed cleanly:

- `npm test -- badge-lifecycle.test.js` — 3/3 pass.
- `npm run lint:js` — pass.
- `npm run build` — pass; regenerated `admin/dist/js/454.js`.
- `node tools/ui-inventory.mjs --check` — pass.
- `node tools/ui-gate.mjs` — 6 changed files, no new violations.
- `git diff --check` — pass.

## Next executable action

The current local commit contains D5-BADGE-01. The pre-commit root check reported JavaScript was not analysed because the monorepo root has no package manifest; this is benign because the affected admin package's focused test, lint, and production build were run successfully before commit. PHP, Trivy, and Composer audit were not applicable to this JavaScript-only slice.

## Next executable action

No action is scheduled within this independently shippable committed slice.
