一键导入
effect-basics
Core Effect patterns for this codebase. Start here for Effect. Covers Effect.gen, tryPromise, typed errors, concurrency.
用 Codex 或 Claude 帮你安装 复制这段 Prompt,粘贴到 Codex、Claude 或其他助手里,让它检查 Skill 页面并帮你完成安装。
菜单
Core Effect patterns for this codebase. Start here for Effect. Covers Effect.gen, tryPromise, typed errors, concurrency.
用 Codex 或 Claude 帮你安装 复制这段 Prompt,粘贴到 Codex、Claude 或其他助手里,让它检查 Skill 页面并帮你完成安装。
基于 SOC 职业分类
Effect service definition, interface design, error types, retries. Use when creating new services or defining error hierarchies.
AXM - Agent Extension Manager: Use for any operation (install/create/new/edit/update/add/remove/delete/publish/find/discover) on agent skills, subagents, slash commands/stored prompts, MCP servers, context packages, rule extensions, hook extensions, or packs — e.g. "create a skill", "make a /command", "add a subagent", "build an MCP server", "publish an extension". Use this BEFORE hand-authoring or editing any SKILL.md, slash-command, subagent, MCP, rule, hook, or extension manifest file: route extension authoring through AXM instead of writing these files directly.
Native skill manifest with two unknown top-level keys.
Effect CLI + Effect architecture. Use when adding commands, defining flags, or wiring handlers. Covers file organization, argument/flag patterns, and testing.
"unterminated
Native skill with an invalid extension name in manifest.
| name | effect-basics |
| description | Core Effect patterns for this codebase. Start here for Effect. Covers Effect.gen, tryPromise, typed errors, concurrency. |
| user-invocable | false |
This project uses Effect for all business logic and I/O. Do NOT use raw Promises or async/await.
Effect<A, E, R>, never Promise<T>E) instead of thrown exceptionsR)Effect<A, E, R> signaturesDefault to simple functions. Services add indirection—only use them when justified.
| Use simple functions when... | Use services when... |
|---|---|
| Operation is stateless | Shared mutable state (caches, pools) |
| No shared configuration beyond dependencies | Complex initialization requiring cleanup |
| Function composes well with other Effects | Configuration shared across multiple methods |
Testing via Effect.provide is sufficient | Need to swap entire implementation in tests |
// Just a function returning an Effect—no service needed
// Let Effect infer the return type (dependencies auto-tracked)
export const computeIntegrity = (dir: string) =>
Effect.gen(function* () {
const fs = yield* FileSystem;
const files = yield* fs.readDirectory(dir);
// ... compute hash
return hash;
});
| Instead of... | Use... |
|---|---|
async function foo() | const foo = Effect.gen(function* () { ... }) |
await promise | yield* Effect.tryPromise(() => promise) |
Promise.all([a, b]) | Effect.all([a, b], { concurrency: "unbounded" }) |
try/catch | Typed errors with Effect.catchTag |
fs.readFile | @effect/platform FileSystem service |
path.join | @effect/platform Path service |
fetch | @effect/platform HttpClient service |
const processFile = (path: string) =>
Effect.gen(function* () {
const fs = yield* FileSystem;
const content = yield* fs.readFileString(path);
const parsed = yield* parseContent(content);
return parsed;
});
const fetchData = (url: string) =>
Effect.tryPromise({
try: () => externalLib.fetch(url),
catch: (error) => new FetchError({ cause: error }),
});
// Run independent operations concurrently
const results =
yield *
Effect.all([fetchUsers(), fetchProducts(), fetchOrders()], {
concurrency: "unbounded",
});
See /effect-errors for comprehensive error modeling (TaggedError, defects, recovery).
// Typed error handling with catchTag
const result =
yield *
fetchData(url).pipe(
Effect.catchTag("FetchError", (error) =>
error.retryable ? Effect.retry(fetchData(url), retryPolicy) : Effect.fail(error),
),
);
| Context | Method |
|---|---|
| CLI entry point | Effect.runPromise or BunRuntime.runMain |
| Tests | Effect.runPromise within test functions |
| Business logic | Never — compose Effects, don't run them |
Let Effect infer return types. Effect's covariant R parameter enables automatic dependency tracking—explicit annotations can impair this.
// Good: dependencies auto-tracked as you add services
const fetchUser = (id: string) =>
Effect.gen(function* () {
const db = yield* Database;
const logger = yield* Logger; // R automatically includes Logger
// ...
});
// Avoid: explicit annotation requires manual updates
const fetchUser = (id: string): Effect.Effect<User, DbError, Database> =>
// Adding Logger above would require updating this annotation
Avoid tacit (point-free) usage:
// Bad: loses type info
Effect.forEach(ids, fetchUser);
// Good: preserves inference
Effect.forEach(ids, (id) => fetchUser(id));
Use explicit annotations when:
Effect.async (TypeScript can't infer callback types)Effect.gen with yield*Effect.tryPromise with error mappingEffect.all with concurrency@effect/platform servicesEffect<A, E, R> signatures