staleness-gate
# TRD Staleness Gate
What this skill does
# TRD Staleness Gate
Detect whether a TRD is stale before implementation begins. If stale, invoke
`/ensemble:refine-trd` to refresh it, then proceed. If refinement fails, halt.
---
## Inputs
| Variable | Type | Description |
|-------------|---------|-------------|
| `TRD_PATH` | string | Absolute or repo-relative path to the TRD `.md` file |
| `IS_RESUME` | boolean | `true` when implementation is resuming an existing scaffold; `false` on first invocation |
| `FLAVOR` | string | Calling command name (for diagnostic messages): `implement-trd-beads`, `implement-trd`, or `beads-build` |
---
## Resume Detection by Flavor
| Flavor | `IS_RESUME = true` when |
|--------|------------------------|
| `implement-trd-beads` | `ROOT_EPIC_ID` found in `br list --json` for this TRD slug (Preflight step 6 — Resume Detection) |
| `implement-trd` | `git branch --list feature/<TRD_SLUG>-sprint-1` returns a branch name (checked before branch creation) |
| `beads-build --trd` | `ROOT_EPIC_ID` found in Epic Discovery step (Preflight step 4) |
---
## Algorithm
### Step 1 — Resume Check
```
IF IS_RESUME == true:
print "Staleness check: skipped (resume detected)"
RETURN
```
Staleness detection does not apply to resuming an existing scaffold. The TRD was
already validated on first invocation; checking it again mid-session would block
legitimate resume operations.
---
### Step 2 — Get TRD mtime
Determine the last-modified time of the TRD file as a Unix epoch integer.
```bash
# macOS
TRD_MTIME=$(stat -f %m "<TRD_PATH>")
# Linux
TRD_MTIME=$(stat -c %Y "<TRD_PATH>")
# Fallback (cross-platform, if stat not available or fails)
TRD_MTIME=$(python3 -c "import os; print(int(os.path.getmtime('<TRD_PATH>')))")
```
Try macOS form first; if it fails (non-zero exit or empty output), try Linux form;
if that fails, try the Python fallback.
```
IF all three methods fail:
print "WARNING: Cannot determine TRD file age — skipping staleness check."
RETURN
```
---
### Step 3 — Age Check
```bash
CURRENT_TIME=$(date +%s)
AGE_SECONDS=$(( CURRENT_TIME - TRD_MTIME ))
AGE_HOURS=$(( AGE_SECONDS / 3600 ))
```
```
IF AGE_HOURS > 24:
STALE_AGE=true
ELSE:
STALE_AGE=false
```
The threshold is 24 hours. A TRD created more than 24 hours ago may no longer
accurately reflect the current state of the codebase.
---
### Step 4 — Source File Drift Check
**This step ALWAYS runs, even if `STALE_AGE=true`.** Both conditions are evaluated
independently so the staleness message can report both age and drift when both apply.
List all tracked source files (respecting `.gitignore`) and exclude generated
artifacts that do not constitute meaningful code drift:
```bash
git ls-files --exclude-standard \
| grep -vE "^packages/[^/]+/commands/ensemble/|^packages/pi/prompts/|^packages/codex/\.codex/"
```
**Exclusion rationale:**
| Excluded pattern | Reason |
|-----------------|--------|
| `packages/*/commands/ensemble/` | Generated markdown command files — updated by `npm run generate` after YAML edits; not meaningful drift |
| `packages/pi/prompts/` | Generated pi prompt files |
| `packages/codex/.codex/` | Generated codex skill files |
| Any path in `.gitignore` | Covered by `--exclude-standard`: `dist/`, `build/`, `node_modules/`, `coverage/`, `.beads.bd/`, `.bv/`, `.ntm/`, `.opencode/`, `.dolt/` |
For each file in the filtered list, retrieve its mtime (same platform-aware stat
as Step 2). Collect all files where `file_mtime > TRD_MTIME`:
```
NEWER_FILES = [ file for file in filtered_list if mtime(file) > TRD_MTIME ]
NEWER_COUNT = len(NEWER_FILES)
IF NEWER_COUNT > 0:
STALE_DRIFT=true
ELSE:
STALE_DRIFT=false
```
---
### Step 5 — Gate Decision
```
STALE = (STALE_AGE OR STALE_DRIFT)
```
**If not stale:**
```
print "Staleness check: TRD is current"
RETURN
```
**If stale:** build a combined diagnostic message and invoke refinement.
Message construction:
```
MESSAGE = ""
IF STALE_AGE:
MESSAGE += "TRD is ${AGE_HOURS}h old (threshold: 24h).\n"
IF STALE_DRIFT:
MESSAGE += "${NEWER_COUNT} source file(s) are newer than the TRD:\n"
FOR file IN NEWER_FILES[0:10]:
MESSAGE += " - ${file}\n"
IF NEWER_COUNT > 10:
MESSAGE += " (and ${NEWER_COUNT - 10} more)\n"
MESSAGE += "Running /ensemble:refine-trd before implementation."
```
Print the message, then invoke:
```
/ensemble:refine-trd <TRD_PATH>
```
---
### Step 6 — Post-Refinement Decision
```
IF refine-trd exits 0:
print "Staleness gate satisfied — TRD refreshed. Proceeding with implementation."
RETURN
# No re-check: the refinement is trusted. A second staleness check would create
# an infinite loop if the refine-trd command itself touches source files.
IF refine-trd exits non-zero:
print "STALENESS GATE FAILURE: TRD refinement failed. Fix the TRD manually and re-run."
HALT
```
**RETURN** means: resume execution at the next Preflight step in the calling command.
**HALT** means: do not proceed with any implementation. The calling command stops.
---
## Known Limitation
**Git clone/checkout resets file mtimes.**
After `git clone`, `git checkout`, or `git pull`, all files receive the current
wall-clock time as their mtime. This means:
- A freshly-cloned repository will show all files as "newer than" the TRD — even
if no actual changes were made relative to the TRD's last update.
- Checking out an old branch on a recent working tree will not reliably detect
semantic staleness introduced by the branch switch.
This limitation is accepted and documented in PRD-2026-022 non-goals. Semantic
staleness detection (git log-based, content-aware) is out of scope for this release.
**Workaround:** If you encounter false-positive staleness after a fresh clone,
either run `/ensemble:refine-trd` manually (it will confirm the TRD is current and
re-touch its mtime), or proceed past the gate — the refinement step is designed to
be safe to run even when the TRD is already accurate.
Related in General
modeling-omnistudio-epc-catalog
IncludedSalesforce Industries CME EPC product-modeling skill for Product2-based catalog creation. Use when creating EPC products, configuring product attributes, building offer bundles with Product Child Items, or reviewing EPC DataPack JSON metadata for product catalog changes. TRIGGER when: user creates or updates Product2 EPC records, AttributeAssignment payloads, AttributeMetadata/AttributeDefaultValues, Offer bundles, or ProductChildItem relationships. DO NOT TRIGGER when: designing OmniScripts/FlexCards/Integration Procedures (use building-omnistudio-omniscript, building-omnistudio-flexcard, or building-omnistudio-integration-procedure), implementing Apex business logic (use generating-apex), or troubleshooting deployment pipelines (use deploying-metadata).
relationship-science-coach
IncludedUse this skill for direct, practical adult relationship coaching: couples conflict, repair, trust, marriage, dating, flirting, attachment patterns, emotional connection, sex, desire differences, eroticism, kink negotiation, affection, love languages, breakups, and long-term passion. Draw on Gottman, EFT and Hold Me Tight, attachment science, modern sex research, Perel, Nagoski, Kerner, Schnarch, Love and Stosny, and flexible love-language tools. Be concrete and low-hedge. Redirect only for imminent danger, abuse, coercive control, minors, non-consent, self-harm, stalking, or medical/legal/psychiatric decisions.
building-sf-integrations
IncludedSalesforce integration architecture and runtime plumbing with 120-point scoring. Use this skill to set up Named Credentials, External Credentials, External Services, REST/SOAP callout patterns, Platform Events, and Change Data Capture. TRIGGER when: user sets up Named Credentials, External Services, REST/SOAP callouts, Platform Events, CDC, or touches .namedCredential-meta.xml files. DO NOT TRIGGER when: Connected App/OAuth config (use configuring-connected-apps), Apex-only logic (use generating-apex), or data import/export (use handling-sf-data).
venue-templates
IncludedAccess comprehensive LaTeX templates, formatting requirements, and submission guidelines for major scientific publication venues (Nature, Science, PLOS, IEEE, ACM), academic conferences (NeurIPS, ICML, CVPR, CHI), research posters, and grant proposals (NSF, NIH, DOE, DARPA). This skill should be used when preparing manuscripts for journal submission, conference papers, research posters, or grant proposals and need venue-specific formatting requirements and templates.
let-fate-decide
IncludedDraws the 12 Houses of the Zodiac Tarot spread to inject entropy into planning when prompts are vague, ambiguous, or casually delegated. Interprets the spread to guide next steps. Use when the user says 'let fate decide', 'YOLO', 'whatever', 'idk', or other nonchalant phrases, makes Yu-Gi-Oh references, or when you are about to arbitrarily pick between multiple reasonable approaches. Prefer over ask-questions-if-underspecified when the user's tone is casual or playful rather than precision-seeking.
net-ops
IncludedCross-platform network troubleshooting (Windows, macOS, Linux) via local or remote shell. Use for: DNS broken, can't resolve hostnames, nslookup/dig works but apps fail, NRPT, WFP, scutil, /etc/resolver, systemd-resolved, /etc/resolv.conf, NetworkManager, VPN DNS leak residue (ProtonVPN/Mullvad/WireGuard/AnyConnect), AV/firewall blocking DNS or DoH, Tailscale DNS interaction, intermittent connectivity, remote diagnostics over SSH.