[{"data":1,"prerenderedAt":-1},["ShallowReactive",2],{"skill:01M6CF7CSDPKBDCJDXA5HCCP26":3,"skill-same:01M6CF7CSDPKBDCJDXA5HCCP26":85},{"skillNo":4,"name":5,"nameZh":6,"description":7,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":16,"categories":17,"keywords":18,"publishedAt":38,"linkOnly":39,"markdownContent":40,"markdownBody":41,"frontMatter":42,"refName":53,"commitSha":54,"skillDirectory":55,"forksCount":56,"repositoryHtmlUrl":57,"repositoryHomepageUrl":6,"ownerHtmlUrl":58,"ownerBlogUrl":6,"ownerDescription":59,"updatedAt":60,"install":61,"resources":74},"01M6CF7CSDPKBDCJDXA5HCCP26","typescript",null,"Write TypeScript that keeps runtime behavior, type surfaces, and module boundaries aligned. Use when building CLIs, services, tooling, registries, package flows, or browser\u002Fnode apps in TypeScript.","usurobor\u002Fcnos","usurobor","https:\u002F\u002Favatars.githubusercontent.com\u002Fu\u002F182342826?v=4","01M6CEXJCRMYD8HB2315FGB1Q8","Peter Lisovin","01M6CEXJH2RW04GQ2SNXY40F5S",9,"Apache-2.0","https:\u002F\u002Fgithub.com\u002Fusurobor\u002Fcnos\u002Fblob\u002Fmain\u002Fsrc\u002Fpackages\u002Fcnos.eng\u002Fskills\u002Feng\u002Ftypescript\u002FSKILL.md",[],[5,19,20,21,22,23,24,25,26,27,28,29,30,31,32,33,34,35,36,37],"Tools","surfaces","async","tooling","schema","use","behavior","write","node","how","services","package","compile","browser","issues","registry","code","debugging","javascript","2026-11-10 10:12:30",false,"---\nname: typescript\ndescription: Write TypeScript that keeps runtime behavior, type surfaces, and module boundaries aligned. Use when building CLIs, services, tooling, registries, package flows, or browser\u002Fnode apps in TypeScript.\nartifact_class: skill\nkata_surface: embedded\ngoverning_question: How do we write TypeScript that is explicit at runtime, strict at compile time, and hard to lie to?\ntriggers:\n  - implementing cnos-adjacent tools or services in TypeScript\n  - building package\u002Findex\u002Fregistry tooling in TS\n  - reviewing TypeScript code for runtime\u002Ftype drift\n  - debugging async, module, or schema issues in TS\n  - migrating JavaScript into TypeScript\nscope: task-local\n---\n\n# TypeScript\n\n## Core Principle\n\n**Write TypeScript so the runtime truth and the type story stay aligned.**\n\nUse schema-backed validation at external boundaries, discriminated unions for state, and branded primitives where accidental interchange would be costly. Prefer strict compiler settings and explicit runtime checks over `any`, unchecked assertions, and wishful typing.\n\n## Algorithm\n\n1. **Define** — name the runtime model, the module boundary, the async\u002Ferror policy, and the validation boundary.\n2. **Unfold** — design types, modules, runtime validation, branded primitives, async flow, and tests together.\n3. **Rules** — keep the code strict, schema-backed at boundaries, exhaustively handled, and hostile to type\u002Fruntime drift.\n4. **Verify** — compile, lint, test, and check the same boundary cases across the whole surface.\n\n---\n\n## 1. Define\n\n### 1.0. Classify the artifact first\n\nUse this skill for TypeScript code that belongs to:\n\n- CLI\u002Ftools\n- services\n- registries\u002Fmanifests\n- package\u002Findex handling\n- command dispatch\n- orchestrator tooling\n- browser\u002Fnode apps where runtime\u002Ftype drift matters\n\nDo **not** use this skill for:\n\n- prose-only documentation\n- framework style wars with no runtime consequence\n- \"add types later\" JavaScript scaffolding\n\n### 1.1. Identify the parts\n\nA coherent TypeScript subsystem has:\n\n- **Runtime model** — what actually exists at runtime\n- **Type model** — how that reality is represented statically\n- **Boundary validation** — where `unknown` input becomes trusted data\n- **Branded primitives** — distinct identities for easily confused scalar values\n- **Module surface** — what a module exports and what it hides\n- **Async policy** — how promises, cancellation, and retries are handled\n- **Error policy** — how failure is represented and propagated\n- **Build\u002Flint\u002Ftest contract** — what proves the code is safe to ship\n  - ❌ Start with types disconnected from runtime parsing\n  - ✅ Define the runtime payloads and the type model together\n\n### 1.2. Articulate how they fit\n\nExternal values cross boundaries as `unknown`. Validation makes them trusted. Types model trusted shapes. Branded primitives keep distinct runtime meanings from collapsing into one wide scalar type. Modules expose only what callers need. Async flow is explicit. Errors are visible and policy-driven.\n\n- ❌ Parse JSON straight into `any`\n- ✅ Parse as `unknown`, validate, then narrow to the domain type\n\n### 1.3. Name the failure mode\n\nTypeScript fails through **type\u002Fruntime drift**. Typical signs:\n\n- `any` leakage\n- unchecked `as X` at trust boundaries\n- promises started and ignored\n- unions never exhaustively checked\n- optional fields used as if always present\n- raw values standing in for many incompatible identities\n- type-only imports mixed carelessly with runtime imports\n- module surface confusion between ESM\u002FCJS\u002Fruntime shape\n- invisible degraded paths\n- mutation of shared state that changes behavior silently\n  - ❌ `const cfg = JSON.parse(text) as Config`\n  - ✅ `const raw: unknown = JSON.parse(text); const cfg = parseConfig(raw)`\n\n---\n\n## 2. Unfold\n\n### 2.1. Compiler posture\n\nStart strict. Baseline:\n\n- `strict: true`\n\nRecommended where it fits:\n\n- `noUncheckedIndexedAccess`\n- `exactOptionalPropertyTypes`\n- `noImplicitOverride`\n- `useUnknownInCatchVariables`\n  - ❌ Start loose and promise to tighten later\n  - ✅ Start strict and carve out only justified exceptions\n\n### 2.2. Runtime boundary first\n\nEvery external boundary begins as `unknown`. Typical boundaries:\n\n- JSON parse\n- HTTP request\u002Fresponse\n- env\u002Fconfig\n- local storage \u002F database reads\n- message bus \u002F queue payloads\n- plugin\u002Fextension manifests\n\nPrefer a runtime schema library at external trust boundaries. Good examples:\n\n- Zod\n- Valibot\n- ArkType\n- similar runtime-first schema systems\n\nThe rule is not \"use Zod.\" The rule is: use explicit runtime schemas where untrusted data enters the system.\n\n- ❌ `function load(x: any): Settings`\n- ❌ `const manifest = raw as PackageManifest`\n- ✅ `function parseSettings(x: unknown): Settings`\n\n### 2.3. Type design\n\nPrefer:\n\n- concrete object types\n- discriminated unions\n- `readonly` where mutation is not part of the design\n- `keyof`, indexed access, and generics when they reduce duplication without hiding the model\n\nUse discriminated unions for state machines and command\u002Fresult surfaces.\n\n```typescript\ntype RestoreResult =\n  | { kind: \"ok\"; packageName: string; version: string }\n  | { kind: \"missing\"; packageName: string }\n  | { kind: \"checksum-mismatch\"; packageName: string; expected: string; actual: string };\n```\n\n- ❌ One wide object with many optional fields and no discriminant\n- ✅ One discriminated union with one obvious runtime case at a time\n\n### 2.4. Branded primitives\n\nUse branded types for domain primitives that are:\n\n- easily confused\n- semantically distinct\n- costly to interchange accidentally\n\nGood candidates:\n\n- paths\n- checksums\n- package names\n- versions\n- command names\n- IDs\n\n```typescript\ntype Brand\u003CT, B extends string> = T & { readonly __brand: B };\n\ntype AbsolutePath = Brand\u003Cstring, \"AbsolutePath\">;\ntype Checksum = Brand\u003Cstring, \"Checksum\">;\ntype PackageName = Brand\u003Cstring, \"PackageName\">;\n```\n\n- ❌ `function verify(path: string, checksum: string)`\n- ✅ `function verify(path: AbsolutePath, checksum: Checksum)`\n\nDo not brand everything. Brand the primitives where accidental substitution would create real bugs.\n\n### 2.5. `unknown`, guards, and assertions\n\nUse:\n\n- `unknown` at boundaries\n- schema-backed parsing for external input\n- local type predicates \u002F assertion functions where they genuinely clarify internal control flow\n- `satisfies` to check object shapes without widening away useful literal information\n\nDo not use handwritten type guards as the primary trust boundary for external data.\n\n- ❌ `function isConfig(x: unknown): x is Config` as the only protection on arbitrary JSON\n- ✅ `ConfigSchema.parse(x)` at the boundary, then local narrowing helpers inside the trusted domain\n\nAvoid:\n\n- `any`\n- unchecked `as`\n- double assertions (`as unknown as X`)\n\n### 2.6. Errors and fallback\n\nMake the error policy explicit. Use:\n\n- thrown `Error` objects for exceptional failure\n- discriminated result types for expected domain failure\n- `unknown` in catch blocks\n- explicit wrapping\u002Fnormalization at boundaries\n\n```typescript\ntry {\n  await execute();\n} catch (err: unknown) {\n  throw new Error(`execute failed: ${err instanceof Error ? err.message : String(err)}`);\n}\n```\n\n- ❌ `throw \"bad config\"`\n- ❌ `catch (err: any) { ... }`\n- ✅ Throw `Error` instances and inspect caught values explicitly\n\nEvery fallback must be:\n\n- intentional\n- visible\n- testable\n\n### 2.7. Modules and imports\n\nKeep module boundaries explicit. Prefer:\n\n- small modules\n- named exports by default\n- `import type` for type-only imports\n- one clear ESM\u002FCJS strategy per package\n  - ❌ Mix runtime and type-only imports casually\n  - ✅ `import type { PackageLock } from \".\u002Ftypes.js\"`\n\n### 2.8. Async and promises\n\nEvery promise must be:\n\n- awaited\n- returned\n- or intentionally handled\n\nNo floating promises. No async callbacks smuggled into sync-shaped APIs by accident.\n\n- ❌ `doRestore()` and ignore the returned promise\n- ✅ `await doRestore()`\n\nIf concurrency exists, own it explicitly:\n\n- `Promise.all`\n- bounded task groups\n- retries with clear policy\n- `AbortSignal` where cancellation matters\n\n### 2.9. Exhaustiveness\n\nIf a union matters, handle it exhaustively.\n\n```typescript\nfunction assertNever(x: never): never {\n  throw new Error(`unreachable case: ${String(x)}`);\n}\n\nswitch (result.kind) {\n  case \"ok\": return ...;\n  case \"missing\": return ...;\n  case \"checksum-mismatch\": return ...;\n  default: return assertNever(result);\n}\n```\n\n- ❌ Default branch that silently absorbs future cases\n- ✅ Exhaustive switch with `assertNever`\n\n### 2.10. Schema and compatibility\n\nTreat manifests, contracts, and registries as public contracts.\n\nWhen handling:\n\n- package manifests\n- lockfiles\n- indexes\n- runtime contracts\n- orchestrator IR\n- extension manifests\n\nprefer:\n\n- explicit version fields\n- additive evolution\n- strict validation of required fields\n- clear behavior for unknown fields\n  - ❌ Silently coerce malformed manifest data into defaults\n  - ✅ Reject malformed input with repairable errors\n\n### 2.11. Determinism and reproducibility\n\nFor outputs that are:\n\n- hashed\n- compared in tests\n- written to reports\n- stored for later diffing\n\nensure:\n\n- stable ordering\n- canonical serialization\n- no dependence on object key enumeration accidents where that matters\n- no hidden timestamps unless intentionally included\n  - ❌ Render objects in arbitrary order where stability matters\n  - ✅ Sort before rendering\n\n### 2.12. Idempotence, retry, and receipts\n\nAssume package restore, update, command execution, and workflow steps may be retried.\n\nFor state-changing operations, define:\n\n- what happens on interruption\n- whether the operation is idempotent\n- what partial state is left behind\n- how cleanup works\n- what visible receipt\u002Flog\u002Fstatus tells the caller what happened\n  - ❌ Write directly to the final target and hope the process completes\n  - ✅ Write to temp, validate, then atomically move into place\n  - ❌ Degraded path only visible in transient stderr\n  - ✅ Degraded path visible in logs, receipts, or structured state\n\n### 2.13. Side-effect boundaries\n\nKeep parsing\u002Fvalidation\u002Fplanning separate from:\n\n- filesystem\n- HTTP\n- subprocesses\n- archive extraction\n- env access\n  - ❌ Parse package manifests inside the fetcher\n  - ✅ Fetch bytes in one module; parse and validate in the domain module\n\n### 2.14. Node\u002Fbrowser reality\n\nTypes do not exist at runtime. Module systems, globals, file APIs, and network APIs do. Be explicit about:\n\n- environment assumptions\n- polyfills\u002Fshims if any\n- Node vs browser boundaries\n- runtime feature detection where necessary\n  - ❌ Write code that type-checks but assumes a runtime that isn't there\n  - ✅ Make the runtime target obvious in the package and module surface\n\n### 2.15. Testing\n\nUse:\n\n- `tsc --noEmit`\n- linter\n- unit tests\n- boundary tests\n- unhappy-path tests\n\nTest:\n\n- malformed input\n- missing fields\n- unknown union members\n- async failure\n- retry\u002Fdegraded paths\n- deterministic output\n  - ❌ Test only the happy path because \"types prove the rest\"\n  - ✅ Test the runtime boundary and degraded behavior explicitly\n\n---\n\n## 3. Rules\n\n### 3.1. Start strict\n\nUse `strict` mode by default.\n\n### 3.2. External input starts as `unknown`\n\nDo not trust JSON, HTTP, env, storage, or plugin data without validation.\n\n### 3.3. Prefer schema-backed trust boundaries\n\nAt external I\u002FO boundaries, prefer runtime schema parsing over handwritten guards.\n\n### 3.4. Avoid `any`\n\nUse `unknown`, unions, generics, and validation instead. If `any` appears, treat it as debt.\n\n### 3.5. Prefer discriminated unions for state and results\n\nThey keep runtime cases explicit and exhaustiveness possible.\n\n### 3.6. Use branded primitives where confusion is costly\n\nBrand paths, checksums, IDs, package names, and similar domain primitives when accidental interchange would create real bugs.\n\n### 3.7. Use `satisfies` for object-shape validation\n\nUse `satisfies` when you want to validate shape without erasing more specific inferred structure.\n\n### 3.8. Keep imports honest\n\nUse `import type` for type-only imports and keep runtime imports explicit.\n\n### 3.9. Make error policy explicit\n\nChoose clearly between:\n\n- thrown `Error`\n- discriminated result values\n- or a deliberate combination by layer\n\nDo not let failure handling emerge accidentally.\n\n### 3.10. No floating or misused promises\n\nAwait them, return them, or handle them deliberately.\n\n### 3.11. Make fallback explicit\n\nFallback is policy, not accident. If a degraded path exists, it must be visible, testable, and reviewable.\n\n### 3.12. Prefer immutable updates by default\n\nDo not silently mutate shared objects when returning a new state\u002Fvalue is clearer.\n\n- ❌ Mutate shared config or registry objects in-place across module boundaries\n- ✅ Return new values unless local mutation is clearly contained and justified\n\n### 3.13. Preserve cnos boundaries\n\nKeep these concepts distinct:\n\n- **skills** choose\n- **commands** dispatch\n- **orchestrators** execute\n- **extensions** provide capability\n\nPrefer explicit metadata and registries over hidden inference.\n\n### 3.14. Shell, archive, and path safety\n\nWhen touching files, subprocesses, or archives:\n\n- avoid shell string interpolation\n- validate archive extraction paths\n- reject path traversal\n- do not log secrets\n- make destructive operations explicit\n\n### 3.15. Override precedence must be explicit\n\nIf behavior may come from:\n\n- flags\n- environment\n- config\n- runtime discovery\n- defaults\n\ndefine the precedence clearly and test it.\n\n### 3.16. Build and verify before push\n\nRun the equivalent of:\n\n- `tsc --noEmit`\n- linter\n- test suite\n\nbefore claiming the code is ready.\n\n---\n\n## 4. Verify\n\n### 4.1. File-level check\n\n- Is the runtime model explicit?\n- Are boundaries typed honestly?\n- Is validation present where trust begins?\n\n### 4.2. Module check\n\n- Are modules small and specific?\n- Are type-only imports separated cleanly?\n- Is ESM\u002FCJS\u002Fruntime behavior explicit?\n\n### 4.3. Async\u002Ferror check\n\n- Any floating promises?\n- Any swallowed errors?\n- Any degraded path that is invisible?\n\n### 4.4. Schema\u002Fcontract check\n\n- Are manifests\u002Fversioned contracts validated?\n- Are `unknown` and malformed cases handled explicitly?\n- Is output deterministic where it matters?\n\n### 4.5. Build\u002Ftest check\n\n- compile\n- lint\n- test\n- boundary\u002Fdegraded-path tests present\n\n---\n\n## 5. Kata\n\n### 5.1. Kata A — package index client\n\n**Scenario:** Implement a TypeScript client that loads a package index, validates package entries, and resolves name + version to a downloadable artifact.\n\n**Task:** Write code that:\n\n- reads JSON as `unknown`\n- validates it into a domain type\n- resolves a package version\n- returns discriminated result types for missing or malformed cases\n\n**Governing skills:** typescript, design, test\n\n**Inputs:**\n\n- valid package index fixture\n- malformed index fixture\n- missing package fixture\n- missing version fixture\n\n**Expected artifacts:**\n\n- domain types using discriminated unions\n- explicit schema-backed parse layer\n- branded types where domain primitives are easily confused\n- no `any`\n- tests for valid and invalid cases\n\n**Verification:**\n\n- no unchecked assertions at the trust boundary\n- all union results handled exhaustively\n- compile, lint, and tests pass\n\n**Common failures:**\n\n- `JSON.parse(...) as Index`\n- one wide result type with many optional fields\n- missing tests for malformed input\n- swallowed errors on missing packages\n\n**Reflection:**\n\n- Did the type story match the runtime truth?\n- Did invalid input fail explicitly enough to repair?\n\n### 5.2. Kata B — async command runner\n\n**Scenario:** Implement a command runner that downloads an artifact, verifies it, and writes it atomically.\n\n**Task:** Write code that:\n\n- uses explicit async flow\n- never drops promises\n- models success\u002Ffailure as explicit result cases\n- keeps I\u002FO separate from parsing\u002Fvalidation\n\n**Governing skills:** typescript, design, test\n\n**Inputs:**\n\n- successful fetch path\n- checksum mismatch path\n- network failure path\n- atomic replace path\n\n**Expected artifacts:**\n\n- no floating promises\n- clear error\u002Fresult policy\n- deterministic verification flow\n- tests for unhappy paths\n\n**Verification:**\n\n- `no-floating-promises` and `no-misused-promises` would pass\n- atomic path is explicit\n- checksum mismatch is visible and test-covered\n\n**Common failures:**\n\n- fire-and-forget promise\n- mixing validation inside transport\n- broad catch that erases failure detail\n- optional fields used as if required\n\n**Reflection:**\n\n- Did the async flow stay visible and auditable?\n- Did retries\u002Ffailures remain policy-driven rather than accidental?\n","# TypeScript\n\n## Core Principle\n\n**Write TypeScript so the runtime truth and the type story stay aligned.**\n\nUse schema-backed validation at external boundaries, discriminated unions for state, and branded primitives where accidental interchange would be costly. Prefer strict compiler settings and explicit runtime checks over `any`, unchecked assertions, and wishful typing.\n\n## Algorithm\n\n1. **Define** — name the runtime model, the module boundary, the async\u002Ferror policy, and the validation boundary.\n2. **Unfold** — design types, modules, runtime validation, branded primitives, async flow, and tests together.\n3. **Rules** — keep the code strict, schema-backed at boundaries, exhaustively handled, and hostile to type\u002Fruntime drift.\n4. **Verify** — compile, lint, test, and check the same boundary cases across the whole surface.\n\n---\n\n## 1. Define\n\n### 1.0. Classify the artifact first\n\nUse this skill for TypeScript code that belongs to:\n\n- CLI\u002Ftools\n- services\n- registries\u002Fmanifests\n- package\u002Findex handling\n- command dispatch\n- orchestrator tooling\n- browser\u002Fnode apps where runtime\u002Ftype drift matters\n\nDo **not** use this skill for:\n\n- prose-only documentation\n- framework style wars with no runtime consequence\n- \"add types later\" JavaScript scaffolding\n\n### 1.1. Identify the parts\n\nA coherent TypeScript subsystem has:\n\n- **Runtime model** — what actually exists at runtime\n- **Type model** — how that reality is represented statically\n- **Boundary validation** — where `unknown` input becomes trusted data\n- **Branded primitives** — distinct identities for easily confused scalar values\n- **Module surface** — what a module exports and what it hides\n- **Async policy** — how promises, cancellation, and retries are handled\n- **Error policy** — how failure is represented and propagated\n- **Build\u002Flint\u002Ftest contract** — what proves the code is safe to ship\n  - ❌ Start with types disconnected from runtime parsing\n  - ✅ Define the runtime payloads and the type model together\n\n### 1.2. Articulate how they fit\n\nExternal values cross boundaries as `unknown`. Validation makes them trusted. Types model trusted shapes. Branded primitives keep distinct runtime meanings from collapsing into one wide scalar type. Modules expose only what callers need. Async flow is explicit. Errors are visible and policy-driven.\n\n- ❌ Parse JSON straight into `any`\n- ✅ Parse as `unknown`, validate, then narrow to the domain type\n\n### 1.3. Name the failure mode\n\nTypeScript fails through **type\u002Fruntime drift**. Typical signs:\n\n- `any` leakage\n- unchecked `as X` at trust boundaries\n- promises started and ignored\n- unions never exhaustively checked\n- optional fields used as if always present\n- raw values standing in for many incompatible identities\n- type-only imports mixed carelessly with runtime imports\n- module surface confusion between ESM\u002FCJS\u002Fruntime shape\n- invisible degraded paths\n- mutation of shared state that changes behavior silently\n  - ❌ `const cfg = JSON.parse(text) as Config`\n  - ✅ `const raw: unknown = JSON.parse(text); const cfg = parseConfig(raw)`\n\n---\n\n## 2. Unfold\n\n### 2.1. Compiler posture\n\nStart strict. Baseline:\n\n- `strict: true`\n\nRecommended where it fits:\n\n- `noUncheckedIndexedAccess`\n- `exactOptionalPropertyTypes`\n- `noImplicitOverride`\n- `useUnknownInCatchVariables`\n  - ❌ Start loose and promise to tighten later\n  - ✅ Start strict and carve out only justified exceptions\n\n### 2.2. Runtime boundary first\n\nEvery external boundary begins as `unknown`. Typical boundaries:\n\n- JSON parse\n- HTTP request\u002Fresponse\n- env\u002Fconfig\n- local storage \u002F database reads\n- message bus \u002F queue payloads\n- plugin\u002Fextension manifests\n\nPrefer a runtime schema library at external trust boundaries. Good examples:\n\n- Zod\n- Valibot\n- ArkType\n- similar runtime-first schema systems\n\nThe rule is not \"use Zod.\" The rule is: use explicit runtime schemas where untrusted data enters the system.\n\n- ❌ `function load(x: any): Settings`\n- ❌ `const manifest = raw as PackageManifest`\n- ✅ `function parseSettings(x: unknown): Settings`\n\n### 2.3. Type design\n\nPrefer:\n\n- concrete object types\n- discriminated unions\n- `readonly` where mutation is not part of the design\n- `keyof`, indexed access, and generics when they reduce duplication without hiding the model\n\nUse discriminated unions for state machines and command\u002Fresult surfaces.\n\n```typescript\ntype RestoreResult =\n  | { kind: \"ok\"; packageName: string; version: string }\n  | { kind: \"missing\"; packageName: string }\n  | { kind: \"checksum-mismatch\"; packageName: string; expected: string; actual: string };\n```\n\n- ❌ One wide object with many optional fields and no discriminant\n- ✅ One discriminated union with one obvious runtime case at a time\n\n### 2.4. Branded primitives\n\nUse branded types for domain primitives that are:\n\n- easily confused\n- semantically distinct\n- costly to interchange accidentally\n\nGood candidates:\n\n- paths\n- checksums\n- package names\n- versions\n- command names\n- IDs\n\n```typescript\ntype Brand\u003CT, B extends string> = T & { readonly __brand: B };\n\ntype AbsolutePath = Brand\u003Cstring, \"AbsolutePath\">;\ntype Checksum = Brand\u003Cstring, \"Checksum\">;\ntype PackageName = Brand\u003Cstring, \"PackageName\">;\n```\n\n- ❌ `function verify(path: string, checksum: string)`\n- ✅ `function verify(path: AbsolutePath, checksum: Checksum)`\n\nDo not brand everything. Brand the primitives where accidental substitution would create real bugs.\n\n### 2.5. `unknown`, guards, and assertions\n\nUse:\n\n- `unknown` at boundaries\n- schema-backed parsing for external input\n- local type predicates \u002F assertion functions where they genuinely clarify internal control flow\n- `satisfies` to check object shapes without widening away useful literal information\n\nDo not use handwritten type guards as the primary trust boundary for external data.\n\n- ❌ `function isConfig(x: unknown): x is Config` as the only protection on arbitrary JSON\n- ✅ `ConfigSchema.parse(x)` at the boundary, then local narrowing helpers inside the trusted domain\n\nAvoid:\n\n- `any`\n- unchecked `as`\n- double assertions (`as unknown as X`)\n\n### 2.6. Errors and fallback\n\nMake the error policy explicit. Use:\n\n- thrown `Error` objects for exceptional failure\n- discriminated result types for expected domain failure\n- `unknown` in catch blocks\n- explicit wrapping\u002Fnormalization at boundaries\n\n```typescript\ntry {\n  await execute();\n} catch (err: unknown) {\n  throw new Error(`execute failed: ${err instanceof Error ? err.message : String(err)}`);\n}\n```\n\n- ❌ `throw \"bad config\"`\n- ❌ `catch (err: any) { ... }`\n- ✅ Throw `Error` instances and inspect caught values explicitly\n\nEvery fallback must be:\n\n- intentional\n- visible\n- testable\n\n### 2.7. Modules and imports\n\nKeep module boundaries explicit. Prefer:\n\n- small modules\n- named exports by default\n- `import type` for type-only imports\n- one clear ESM\u002FCJS strategy per package\n  - ❌ Mix runtime and type-only imports casually\n  - ✅ `import type { PackageLock } from \".\u002Ftypes.js\"`\n\n### 2.8. Async and promises\n\nEvery promise must be:\n\n- awaited\n- returned\n- or intentionally handled\n\nNo floating promises. No async callbacks smuggled into sync-shaped APIs by accident.\n\n- ❌ `doRestore()` and ignore the returned promise\n- ✅ `await doRestore()`\n\nIf concurrency exists, own it explicitly:\n\n- `Promise.all`\n- bounded task groups\n- retries with clear policy\n- `AbortSignal` where cancellation matters\n\n### 2.9. Exhaustiveness\n\nIf a union matters, handle it exhaustively.\n\n```typescript\nfunction assertNever(x: never): never {\n  throw new Error(`unreachable case: ${String(x)}`);\n}\n\nswitch (result.kind) {\n  case \"ok\": return ...;\n  case \"missing\": return ...;\n  case \"checksum-mismatch\": return ...;\n  default: return assertNever(result);\n}\n```\n\n- ❌ Default branch that silently absorbs future cases\n- ✅ Exhaustive switch with `assertNever`\n\n### 2.10. Schema and compatibility\n\nTreat manifests, contracts, and registries as public contracts.\n\nWhen handling:\n\n- package manifests\n- lockfiles\n- indexes\n- runtime contracts\n- orchestrator IR\n- extension manifests\n\nprefer:\n\n- explicit version fields\n- additive evolution\n- strict validation of required fields\n- clear behavior for unknown fields\n  - ❌ Silently coerce malformed manifest data into defaults\n  - ✅ Reject malformed input with repairable errors\n\n### 2.11. Determinism and reproducibility\n\nFor outputs that are:\n\n- hashed\n- compared in tests\n- written to reports\n- stored for later diffing\n\nensure:\n\n- stable ordering\n- canonical serialization\n- no dependence on object key enumeration accidents where that matters\n- no hidden timestamps unless intentionally included\n  - ❌ Render objects in arbitrary order where stability matters\n  - ✅ Sort before rendering\n\n### 2.12. Idempotence, retry, and receipts\n\nAssume package restore, update, command execution, and workflow steps may be retried.\n\nFor state-changing operations, define:\n\n- what happens on interruption\n- whether the operation is idempotent\n- what partial state is left behind\n- how cleanup works\n- what visible receipt\u002Flog\u002Fstatus tells the caller what happened\n  - ❌ Write directly to the final target and hope the process completes\n  - ✅ Write to temp, validate, then atomically move into place\n  - ❌ Degraded path only visible in transient stderr\n  - ✅ Degraded path visible in logs, receipts, or structured state\n\n### 2.13. Side-effect boundaries\n\nKeep parsing\u002Fvalidation\u002Fplanning separate from:\n\n- filesystem\n- HTTP\n- subprocesses\n- archive extraction\n- env access\n  - ❌ Parse package manifests inside the fetcher\n  - ✅ Fetch bytes in one module; parse and validate in the domain module\n\n### 2.14. Node\u002Fbrowser reality\n\nTypes do not exist at runtime. Module systems, globals, file APIs, and network APIs do. Be explicit about:\n\n- environment assumptions\n- polyfills\u002Fshims if any\n- Node vs browser boundaries\n- runtime feature detection where necessary\n  - ❌ Write code that type-checks but assumes a runtime that isn't there\n  - ✅ Make the runtime target obvious in the package and module surface\n\n### 2.15. Testing\n\nUse:\n\n- `tsc --noEmit`\n- linter\n- unit tests\n- boundary tests\n- unhappy-path tests\n\nTest:\n\n- malformed input\n- missing fields\n- unknown union members\n- async failure\n- retry\u002Fdegraded paths\n- deterministic output\n  - ❌ Test only the happy path because \"types prove the rest\"\n  - ✅ Test the runtime boundary and degraded behavior explicitly\n\n---\n\n## 3. Rules\n\n### 3.1. Start strict\n\nUse `strict` mode by default.\n\n### 3.2. External input starts as `unknown`\n\nDo not trust JSON, HTTP, env, storage, or plugin data without validation.\n\n### 3.3. Prefer schema-backed trust boundaries\n\nAt external I\u002FO boundaries, prefer runtime schema parsing over handwritten guards.\n\n### 3.4. Avoid `any`\n\nUse `unknown`, unions, generics, and validation instead. If `any` appears, treat it as debt.\n\n### 3.5. Prefer discriminated unions for state and results\n\nThey keep runtime cases explicit and exhaustiveness possible.\n\n### 3.6. Use branded primitives where confusion is costly\n\nBrand paths, checksums, IDs, package names, and similar domain primitives when accidental interchange would create real bugs.\n\n### 3.7. Use `satisfies` for object-shape validation\n\nUse `satisfies` when you want to validate shape without erasing more specific inferred structure.\n\n### 3.8. Keep imports honest\n\nUse `import type` for type-only imports and keep runtime imports explicit.\n\n### 3.9. Make error policy explicit\n\nChoose clearly between:\n\n- thrown `Error`\n- discriminated result values\n- or a deliberate combination by layer\n\nDo not let failure handling emerge accidentally.\n\n### 3.10. No floating or misused promises\n\nAwait them, return them, or handle them deliberately.\n\n### 3.11. Make fallback explicit\n\nFallback is policy, not accident. If a degraded path exists, it must be visible, testable, and reviewable.\n\n### 3.12. Prefer immutable updates by default\n\nDo not silently mutate shared objects when returning a new state\u002Fvalue is clearer.\n\n- ❌ Mutate shared config or registry objects in-place across module boundaries\n- ✅ Return new values unless local mutation is clearly contained and justified\n\n### 3.13. Preserve cnos boundaries\n\nKeep these concepts distinct:\n\n- **skills** choose\n- **commands** dispatch\n- **orchestrators** execute\n- **extensions** provide capability\n\nPrefer explicit metadata and registries over hidden inference.\n\n### 3.14. Shell, archive, and path safety\n\nWhen touching files, subprocesses, or archives:\n\n- avoid shell string interpolation\n- validate archive extraction paths\n- reject path traversal\n- do not log secrets\n- make destructive operations explicit\n\n### 3.15. Override precedence must be explicit\n\nIf behavior may come from:\n\n- flags\n- environment\n- config\n- runtime discovery\n- defaults\n\ndefine the precedence clearly and test it.\n\n### 3.16. Build and verify before push\n\nRun the equivalent of:\n\n- `tsc --noEmit`\n- linter\n- test suite\n\nbefore claiming the code is ready.\n\n---\n\n## 4. Verify\n\n### 4.1. File-level check\n\n- Is the runtime model explicit?\n- Are boundaries typed honestly?\n- Is validation present where trust begins?\n\n### 4.2. Module check\n\n- Are modules small and specific?\n- Are type-only imports separated cleanly?\n- Is ESM\u002FCJS\u002Fruntime behavior explicit?\n\n### 4.3. Async\u002Ferror check\n\n- Any floating promises?\n- Any swallowed errors?\n- Any degraded path that is invisible?\n\n### 4.4. Schema\u002Fcontract check\n\n- Are manifests\u002Fversioned contracts validated?\n- Are `unknown` and malformed cases handled explicitly?\n- Is output deterministic where it matters?\n\n### 4.5. Build\u002Ftest check\n\n- compile\n- lint\n- test\n- boundary\u002Fdegraded-path tests present\n\n---\n\n## 5. Kata\n\n### 5.1. Kata A — package index client\n\n**Scenario:** Implement a TypeScript client that loads a package index, validates package entries, and resolves name + version to a downloadable artifact.\n\n**Task:** Write code that:\n\n- reads JSON as `unknown`\n- validates it into a domain type\n- resolves a package version\n- returns discriminated result types for missing or malformed cases\n\n**Governing skills:** typescript, design, test\n\n**Inputs:**\n\n- valid package index fixture\n- malformed index fixture\n- missing package fixture\n- missing version fixture\n\n**Expected artifacts:**\n\n- domain types using discriminated unions\n- explicit schema-backed parse layer\n- branded types where domain primitives are easily confused\n- no `any`\n- tests for valid and invalid cases\n\n**Verification:**\n\n- no unchecked assertions at the trust boundary\n- all union results handled exhaustively\n- compile, lint, and tests pass\n\n**Common failures:**\n\n- `JSON.parse(...) as Index`\n- one wide result type with many optional fields\n- missing tests for malformed input\n- swallowed errors on missing packages\n\n**Reflection:**\n\n- Did the type story match the runtime truth?\n- Did invalid input fail explicitly enough to repair?\n\n### 5.2. Kata B — async command runner\n\n**Scenario:** Implement a command runner that downloads an artifact, verifies it, and writes it atomically.\n\n**Task:** Write code that:\n\n- uses explicit async flow\n- never drops promises\n- models success\u002Ffailure as explicit result cases\n- keeps I\u002FO separate from parsing\u002Fvalidation\n\n**Governing skills:** typescript, design, test\n\n**Inputs:**\n\n- successful fetch path\n- checksum mismatch path\n- network failure path\n- atomic replace path\n\n**Expected artifacts:**\n\n- no floating promises\n- clear error\u002Fresult policy\n- deterministic verification flow\n- tests for unhappy paths\n\n**Verification:**\n\n- `no-floating-promises` and `no-misused-promises` would pass\n- atomic path is explicit\n- checksum mismatch is visible and test-covered\n\n**Common failures:**\n\n- fire-and-forget promise\n- mixing validation inside transport\n- broad catch that erases failure detail\n- optional fields used as if required\n\n**Reflection:**\n\n- Did the async flow stay visible and auditable?\n- Did retries\u002Ffailures remain policy-driven rather than accidental?\n",{"name":5,"scope":43,"triggers":44,"description":7,"kata_surface":50,"artifact_class":51,"governing_question":52},"task-local",[45,46,47,48,49],"implementing cnos-adjacent tools or services in TypeScript","building package\u002Findex\u002Fregistry tooling in TS","reviewing TypeScript code for runtime\u002Ftype drift","debugging async, module, or schema issues in TS","migrating JavaScript into TypeScript","embedded","skill","How do we write TypeScript that is explicit at runtime, strict at compile time, and hard to lie to?","main","fb527e6c4bfb75c71fa75d6471b3aa3da32106d4","src\u002Fpackages\u002Fcnos.eng\u002Fskills\u002Feng\u002Ftypescript",0,"https:\u002F\u002Fgithub.com\u002Fusurobor\u002Fcnos","https:\u002F\u002Fgithub.com\u002Fusurobor","Coherence engineer. Building git-CN.","2026-11-07 14:25:44",{"source":8,"skillName":5,"commands":62,"prompt":72,"zipAvailable":73},[63,66,69],{"tool":64,"command":65},"npx","npx skills add usurobor\u002Fcnos --skill typescript",{"tool":67,"command":68},"bunx","bunx skills add usurobor\u002Fcnos --skill typescript",{"tool":70,"command":71},"pnpm","pnpm dlx skills add usurobor\u002Fcnos --skill typescript","安装技能，技能地址：https:\u002F\u002Fgithub.com\u002Fusurobor\u002Fcnos\u002Fblob\u002Fmain\u002Fsrc\u002Fpackages\u002Fcnos.eng\u002Fskills\u002Feng\u002Ftypescript\u002FSKILL.md",true,[75,81],{"path":76,"resourceType":77,"resourceTypeDesc":78,"sizeBytes":79,"sourceHtmlUrl":80},"SOURCE.md","REFERENCE","参考文档",200,"https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fexchanges\u002Flighter-mcp\u002FSOURCE.md",{"path":82,"resourceType":77,"resourceTypeDesc":78,"sizeBytes":83,"sourceHtmlUrl":84},"TRUST.auto.yaml",2217,"https:\u002F\u002Fgithub.com\u002Fjiayaoqijia\u002Fcryptoskill\u002Fblob\u002Fmain\u002Fskills\u002Fexchanges\u002Flighter-mcp\u002FTRUST.auto.yaml",[86,102,118,146,162,182],{"skillNo":87,"name":88,"nameZh":6,"description":89,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":90,"categories":91,"keywords":92,"publishedAt":38},"01M6CF8RWQPM0VXZG06XMR0FFX","issues\u002Ftriage","Issue triage doctrine pointer. Use when classifying a new issue, deciding dispatch eligibility, or deciding whether to close\u002Fsupersede\u002Fdefer.","https:\u002F\u002Fgithub.com\u002Fusurobor\u002Fcnos\u002Fblob\u002Fmain\u002Fsrc\u002Fpackages\u002Fcnos.issues\u002Fskills\u002Ftriage\u002FSKILL.md",[],[93,33,94,95,96,28,97,98,24,99,100,101],"triage","issues triage","issue triage","SET","decision","public","dispatch","issue","doctrine",{"skillNo":103,"name":104,"nameZh":6,"description":105,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":106,"categories":107,"keywords":108,"publishedAt":38},"01M6CF8PJ812DD4APZ3WE8X67B","issues\u002Ftaxonomy","Issue label taxonomy pointer. Use when classifying an issue's kind\u002Farea\u002Fpriority\u002Feffort\u002Fstatus\u002Fprotocol\u002Fdispatch labels, or when the board needs to interpret them.","https:\u002F\u002Fgithub.com\u002Fusurobor\u002Fcnos\u002Fblob\u002Fmain\u002Fsrc\u002Fpackages\u002Fcnos.issues\u002Fskills\u002Ftaxonomy\u002FSKILL.md",[],[33,109,110,111,112,113,96,114,98,115,24,99,116,100,117],"taxonomy","issues taxonomy","github","status","protocol","open","board","github issue","issue labels",{"skillNo":119,"name":120,"nameZh":6,"description":121,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":122,"categories":123,"keywords":134,"publishedAt":38},"01M6CF8KBMZ4D0CDJQ3PF1YVTP","issues\u002Fmap","Issue-board (Issue Pivot) generation domain. Use when reasoning about `cn issues map`'s fetch, taxonomy-parse, effort-computation, and render pipeline, or about the board's JSON\u002FHTML output contract.","https:\u002F\u002Fgithub.com\u002Fusurobor\u002Fcnos\u002Fblob\u002Fmain\u002Fsrc\u002Fpackages\u002Fcnos.issues\u002Fskills\u002Fmap\u002FSKILL.md",[124,129],{"categoryNo":125,"categoryName":126,"taxonomyType":127,"taxonomyTypeDesc":128},"01JBSEEDCAT000000000000009","前端开发","SCENARIO","使用场景",{"categoryNo":130,"categoryName":131,"taxonomyType":132,"taxonomyTypeDesc":133},"01JBSEEDCAT000000000000037","律师与法务","PROFESSION","适用职业",[33,135,111,136,137,138,96,139,109,114,28,140,141,115,142,143,144,145,24,100],"issues map","reasoning","data","pipeline","api","json","README","edit","interactive","fetch","generated",{"skillNo":147,"name":33,"nameZh":6,"description":148,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":149,"categories":150,"keywords":151,"publishedAt":38},"01M6CF8CZQH7G7B7RZPANQWR4G","cnos.issues package entrypoint. Use when reasoning about issue taxonomy, the Issue Pivot \u002F issue-board (`cn issues map`), the read-only CDS issue-state evaluator (`cn issues fsm evaluate`), or the current command-dispatch disposition of issue tooling.","https:\u002F\u002Fgithub.com\u002Fusurobor\u002Fcnos\u002Fblob\u002Fmain\u002Fsrc\u002Fpackages\u002Fcnos.issues\u002FSKILL.md",[],[33,111,152,153,154,155,156,30,157,109,114,28,97,158,141,159,24,160,99,161],"pr","current state","run","artifacts","state","boundary","branch","command","only","cds",{"skillNo":163,"name":164,"nameZh":6,"description":165,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":166,"categories":167,"keywords":168,"publishedAt":38},"01M6CF896XKSRQVB1CSHY8GSXB","receipt-stream","Cross-cycle receipt-stream doctrine for protocol-iteration. Use when γ closes a cycle and writes the per-cycle iteration artifact (`cdd-iteration.md`), when γ updates the cross-cycle aggregator at `.cdd\u002Fiterations\u002FINDEX.md`, when ε reads the receipt stream across cycles to surface protocol-gap patterns, when a finding's disposition lands a cross-repo patch and the cross-repo trace bundle attaches, or when a courtesy empty-findings stub is written for a `protocol_gap_count == 0` cycle.","https:\u002F\u002Fgithub.com\u002Fusurobor\u002Fcnos\u002Fblob\u002Fmain\u002Fsrc\u002Fpackages\u002Fcnos.handoff\u002Fskills\u002Fhandoff\u002Freceipt-stream\u002FSKILL.md",[],[169,170,155,113,171,28,172,173,174,98,175,176,177,178,24,50,179,180,181,101],"receipt stream","handoff","index","learning","format","trace","repo","closeout","read","channel","patch","shape","cdd",{"skillNo":183,"name":184,"nameZh":6,"description":185,"descriptionZh":6,"repositoryFullName":8,"ownerLogin":9,"ownerAvatarUrl":10,"ownerAccountNo":11,"ownerDisplayName":12,"repositoryNo":13,"starsCount":14,"licenseSpdxId":15,"licenseFileUrl":6,"sourceHtmlUrl":186,"categories":187,"keywords":188,"publishedAt":38},"01M6CF84VCBME6RK8V6HAVDM8Z","mid-flight","Mid-flight γ→in-flight-α rescue channel. Use when γ needs to change a load-bearing fact (pinned axis, scope, AC, blocker) after α has begun coding, when γ edits the cycle's GitHub issue body mid-cycle, or when a spec change lands on origin\u002Fmain while α\u002Fβ polling sessions are in-flight.","https:\u002F\u002Fgithub.com\u002Fusurobor\u002Fcnos\u002Fblob\u002Fmain\u002Fsrc\u002Fpackages\u002Fcnos.handoff\u002Fskills\u002Fhandoff\u002Fmid-flight\u002FSKILL.md",[],[189,111,190,191,192,193,28,194,195,158,175,177,24,160,99,196,116,197,198,199],"mid flight","change","sessions","file","cache","pin","coordination","up","Legacy","gamma","artifact channel"]