Skip to main content
typescript-fieldguide This skill should be used when writing TypeScript, eliminating any types, implementing Zod validation, or when strict type safety is needed. Covers modern TS 5.5+ features and runtime validation patterns.
Zur Installation springen Skills Marktplatz Entdecken und erkunden Sie KI-Skills, die von der Community erstellt wurden.
Mit Codex oder Claude installieren Kopieren Sie diesen Prompt, fügen Sie ihn in Codex, Claude oder einen anderen Assistant ein und lassen Sie die Skill-Seite prüfen und installieren.
Prompt kopierenPrompt-Details anzeigen Ein direkter Befehl überspringt den Prüf-Prompt. Prüfen Sie die Quelle, bevor Sie ihn ausführen.
npx skills add https://github.com/outfitter-dev/outfitter --skill typescript-fieldguideDer Befehl bleibt in einer Zeile. Scrollen Sie horizontal, um ihn vor dem Kopieren vollständig zu prüfen.
Sie bevorzugen eine lokale Kopie? Laden Sie die Dateien herunter, die SkillsMP derzeit vorliegen.
ZIP herunterladen Herunterladen... Mehr aus diesem Repository Patterns for @outfitter/daemon including lifecycle management, IPC communication, health checks, and PID files. Use when building background services, daemons, or when "daemon", "IPC", "health check", "background service", or "@outfitter/daemon" are mentioned.
Creates handlers, CLI commands, MCP tools, and daemon services following Outfitter Dev Kit conventions. Use when adding new components to a project, scaffolding code, or when "create handler", "new command", "add tool", or "daemon service" are mentioned.
Deep patterns for @outfitter/mcp including tool registration, Zod schemas, resources, and server configuration. Use when building MCP servers, registering tools, defining resources, or when "MCP server", "MCP tool", "registerTool", or "@outfitter/mcp" are mentioned.
Verwandte Berufe SOC
Basierend auf der SOC-Berufsklassifikation
name typescript-fieldguide description This skill should be used when writing TypeScript, eliminating any types, implementing Zod validation, or when strict type safety is needed. Covers modern TS 5.5+ features and runtime validation patterns. metadata {"version":"1.0.1"}
TypeScript Development
Type-safe code = compile-time errors = runtime confidence.
<when_to_use>
Writing new TypeScript code
Eliminating any types
Using modern TypeScript 5.5+ features
Validating API inputs/outputs with Zod
Implementing Result types and discriminated unions
Creating branded types for domain concepts
NOT for: runtime-only logic unrelated to types, non-TypeScript projects
</when_to_use>
tsconfig.json strict settings:
{
"compilerOptions" : {
"strict" : true ,
"noUncheckedIndexedAccess" : true ,
"exactOptionalPropertyTypes" : true
,
"noImplicitOverride"
:
true
,
"noPropertyAccessFromIndexSignature"
:
true
,
"noFallthroughCasesInSwitch"
:
true
,
"noImplicitReturns"
:
true
,
"forceConsistentCasingInFileNames"
:
true
,
"verbatimModuleSyntax"
:
true
,
"isolatedModules"
:
true
,
"skipLibCheck"
:
false
}
}
Version requirements : TS 5.2+ (using), TS 5.4+ (NoInfer), TS 5.5+ (inferred predicates)
Core Patterns any defeats the type system. Use unknown + guards.
function process (data : any ) {
return data.value ;
}
function process (data : unknown ): string {
if (!hasValue (data)) throw new TypeError ("Invalid" );
return data.value .toString ();
}
function hasValue (v : unknown ): v is { value : unknown } {
return typeof v === "object" && v !== null && "value" in v;
}
async function fetchUser (id : string ): Promise <User > {
const data : unknown = await fetch (`/api/users/${id} ` ).then ((r ) => r.json ());
return UserSchema .parse (data);
}
Exceptions hide errors from types. Result makes them explicit.
type Result <T, E = Error > =
| { readonly ok : true ; readonly value : T }
| { readonly ok : false ; readonly error : E };
type UserError =
| { readonly type : "not-found" ; readonly id : string }
| { readonly type : "network" ; readonly message : string };
async function getUser (id : string ): Promise <Result <User , UserError >> {
try {
const response = await fetch (`/api/users/${id} ` );
if (response.status === 404 )
return { ok : false , error : { type : "not-found" , id } };
if (!response.ok )
return {
ok : false ,
error : { type : "network" , message : response.statusText },
};
return { ok : true , value : await response.json () };
} catch (e) {
return { ok : false , error : { type : "network" , message : String (e) } };
}
}
const result = await getUser (id);
if (!result.ok ) {
switch (result.error .type ) {
case "not-found" :
return showNotFound (result.error .id );
case "network" :
return showError (result.error .message );
}
}
return renderUser (result.value );
Prevent illegal state combinations.
type Request = { status : 'idle' |'loading' |'success' |'error' ; data ?: User ; error ?: string ; };
type RequestState =
| { readonly status : 'idle' }
| { readonly status : 'loading' }
| { readonly status : 'success' ; readonly data : User }
| { readonly status : 'error' ; readonly error : string };
function render (state : RequestState ): JSX .Element {
switch (state.status ) {
case 'idle' : return <div > Ready</div > ;
case 'loading' : return <div > Loading...</div > ;
case 'success' : return <div > {state.data.name}</div > ;
case 'error' : return <div > Error: {state.error}</div > ;
default : return assertNever (state);
}
}
function assertNever (value : never ): never {
throw new Error (`Unhandled: ${JSON .stringify(value)} ` );
}
Prevent mixing incompatible primitives.
declare const __brand : unique symbol ;
type Brand <T, B extends string > = T & { readonly [__brand]: B };
type UserId = Brand <string , "UserId" >;
type ProductId = Brand <string , "ProductId" >;
function createUserId (value : string ): UserId {
if (!/^user-\d+$/ .test (value)) throw new TypeError (`Invalid: ${value} ` );
return value as UserId ;
}
const userId = createUserId ("user-123" );
getUser (userId);
type SanitizedHtml = Brand <string , "SanitizedHtml" >;
function sanitize (raw : string ): SanitizedHtml {
return escapeHtml (raw) as SanitizedHtml ;
}
function render (html : SanitizedHtml ): void {
element.innerHTML = html;
}
Modern TypeScript (5.2+) using for automatic cleanup (TS 5.2+):
class DatabaseConnection implements Disposable {
[Symbol .dispose ]() {
this .close ();
}
}
function query ( ) {
using conn = new DatabaseConnection ();
return conn.query ("SELECT * FROM users" );
}
async function asyncWork ( ) {
await using resource = new AsyncResource ();
}
Use for: connections, file handles, locks, transactions.
Validate type without widening (TS 4.9+):
const config = {
port : 3000 ,
host : "localhost" ,
} satisfies Record <string , string | number >;
config.port ;
const routes = {
home : "/" ,
user : "/user/:id" ,
} as const satisfies Record <string , string >;
type HomeRoute = typeof routes.home ;
Preserve literals through generics (TS 5.0+):
function makeTuple<const T extends readonly unknown []>(...args : T): T {
return args;
}
const result = makeTuple ("a" , "b" , "c" );
TS 5.5+ auto-infers type predicates:
function isString (x : unknown ) {
return typeof x === "string" ;
}
const strings = values.filter (isString);
Pattern matching at type level:
type Route = `/${string } ` ;
type ApiRoute = `/api/v${number } /${string } ` ;
type ExtractParams <T extends string > =
T extends `${string } :${infer P} /${infer R} `
? P | ExtractParams <`/${R} ` >
: T extends `${string } :${infer P} `
? P
: never ;
type Params = ExtractParams <"/user/:id/post/:postId" >;
Zod Validation Schema = runtime validation + TypeScript type.
import { z } from "zod" ;
const UserSchema = z.object ({
id : z.string ().uuid (),
email : z.string ().email (),
name : z.string ().min (1 ).max (100 ),
});
type User = z.infer <typeof UserSchema >;
const result = UserSchema .safeParse (data);
if (!result.success ) {
console .error (result.error .issues );
return ;
}
const user = result.data ;
Discriminated unions (preferred over z.union):
const ApiResponse = z.discriminatedUnion ("type" , [
z.object ({ type : z.literal ("success" ), data : z.unknown () }),
z.object ({ type : z.literal ("error" ), code : z.string (), message : z.string () }),
]);
const EnvSchema = z.object ({
NODE_ENV : z
.enum (["development" , "production" , "test" ])
.default ("development" ),
DATABASE_URL : z.string ().url (),
PORT : z.coerce .number ().int ().positive ().default (3000 ),
});
const env = EnvSchema .parse (process.env );
import { zValidator } from "@hono/zod-validator" ;
app.post ("/users" , zValidator ("json" , UserSchema ), (c ) => {
const user = c.req .valid ("json" );
return c.json (user);
});
Type Guards
function isString (v : unknown ): v is string {
return typeof v === "string" ;
}
function assertString (v : unknown ): asserts v is string {
if (typeof v !== "string" ) throw new TypeError ("Expected string" );
}
const users : User [] = getUsers ();
const first = users[0 ];
if (first !== undefined ) processUser (first);
TSDoc Types show structure. TSDoc shows intent. Critical for AI agents.
export async function authenticate (
credentials : Credentials
): Promise <SessionToken >;
Document: all exports, parameters with constraints, thrown errors, non-obvious returns.
Strict TypeScript config enabled
Type-only imports: import type { User } from './types'
Const assertions for literal types
Exhaustive matching with assertNever
Runtime validation at boundaries (Zod)
Branded types for domain/sensitive data
Result types for error-prone operations
satisfies for literal inference
using for resources with cleanup
TSDoc on all exports
any (use unknown + guards)
@ts-ignore (fix types or document)
TypeScript enums (use const assertions or z.enum)
Non-null assertions ! (use guards)
Loose state (use discriminated unions)
Hidden errors (use Result)
safeParse over parse
z.discriminatedUnion over z.union
Inferred predicates (TS 5.5+)
Const type parameters for literals