Supercheck Architecture
supercheck-io/supercheck
Work on Supercheck system architecture, Next.js routes and actions, React data hooks, Drizzle schemas and migrations, app-worker boundaries, or cross-package contracts.
A skill your agent uses for Convex/kitcn setup and feature work: cRPC, ORM, auth, React.
$ npx skills add udecode/kitcn --skill kitcn -a claude-codeProject install by default; add -g for ~/.claude/skills/.
$ gh skill install udecode/kitcn kitcn --agent claude-codeProject scope by default; add --scope user for a personal install. Needs GitHub CLI 2.90.0 or later (public preview).
$ git clone --depth 1 https://github.com/udecode/kitcn.git skills-src && mkdir -p .claude/skills && cp -r skills-src/.agents/skills/kitcn .claude/skills/kitcn && rm -rf skills-srcUse ~/.claude/skills/ instead of .claude/skills for a personal install. The folder must contain SKILL.md.
Claude Code skills documentation · loads skills from .claude/skills/
Install the "kitcn" agent skill from https://github.com/udecode/kitcn/tree/main/.agents/skills/kitcn into .claude/skills/kitcn/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "kitcn", then confirm the skill loads.Claude Code copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$skill-installer install https://github.com/udecode/kitcn/tree/main/.agents/skills/kitcnType this inside Codex. $skill-installer <name> installs a curated skill from openai/skills. The installer writes to $CODEX_HOME/skills (default ~/.codex/skills). Restart Codex if the skill does not show up.
$ npx skills add udecode/kitcn --skill kitcn -a codexProject install goes to .agents/skills/; add -g for ~/.codex/skills/.
$ gh skill install udecode/kitcn kitcn --agent codexProject scope by default (.agents/skills/); add --scope user for a personal install.
$ git clone --depth 1 https://github.com/udecode/kitcn.git skills-src && mkdir -p .agents/skills && cp -r skills-src/.agents/skills/kitcn .agents/skills/kitcn && rm -rf skills-srcUse ~/.agents/skills/ instead of .agents/skills for a personal install.
Codex skills documentation · loads skills from .agents/skills/
Install the "kitcn" agent skill from https://github.com/udecode/kitcn/tree/main/.agents/skills/kitcn into .agents/skills/kitcn/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "kitcn", then confirm the skill loads.Codex copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$ npx skills add udecode/kitcn --skill kitcn -a cursorProject install goes to .agents/skills/; add -g for ~/.cursor/skills/.
$ gh skill install udecode/kitcn kitcn --agent cursorProject scope by default (.agents/skills/); add --scope user for a personal install.
$ git clone --depth 1 https://github.com/udecode/kitcn.git skills-src && mkdir -p .cursor/skills && cp -r skills-src/.agents/skills/kitcn .cursor/skills/kitcn && rm -rf skills-srcUse ~/.cursor/skills/ instead of .cursor/skills for a personal install.
Cursor skills documentation · loads skills from .cursor/skills/, .agents/skills/, .claude/skills/, .codex/skills/
Install the "kitcn" agent skill from https://github.com/udecode/kitcn/tree/main/.agents/skills/kitcn into .cursor/skills/kitcn/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "kitcn", then confirm the skill loads.Cursor copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$ gemini skills install https://github.com/udecode/kitcn.git --path .agents/skills/kitcn--scope user (default) or --scope workspace; --path is the subfolder of the repo that holds the skill; --consent skips the security confirmation prompt.
$ npx skills add udecode/kitcn --skill kitcn -a gemini-cliProject install goes to .agents/skills/; add -g for ~/.gemini/skills/.
$ gh skill install udecode/kitcn kitcn --agent gemini-cliProject scope by default (.agents/skills/); add --scope user for a personal install.
$ git clone --depth 1 https://github.com/udecode/kitcn.git skills-src && mkdir -p .gemini/skills && cp -r skills-src/.agents/skills/kitcn .gemini/skills/kitcn && rm -rf skills-srcUse ~/.gemini/skills/ instead of .gemini/skills for a personal install, then run /skills reload.
Gemini CLI skills documentation · loads skills from .gemini/skills/, .agents/skills/
Install the "kitcn" agent skill from https://github.com/udecode/kitcn/tree/main/.agents/skills/kitcn into .gemini/skills/kitcn/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "kitcn", then confirm the skill loads.Gemini CLI copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$ gh skill install udecode/kitcn kitcnInstalls for Copilot at project scope by default; add --scope user for a personal install. Preview a skill first with gh skill preview. Needs GitHub CLI 2.90.0 or later (public preview).
$ npx skills add udecode/kitcn --skill kitcn -a github-copilotProject install goes to .agents/skills/; add -g for ~/.copilot/skills/.
$ git clone --depth 1 https://github.com/udecode/kitcn.git skills-src && mkdir -p .github/skills && cp -r skills-src/.agents/skills/kitcn .github/skills/kitcn && rm -rf skills-srcUse ~/.copilot/skills/ instead of .github/skills for a personal install. Commit .github/skills so cloud agent and code review can use it.
GitHub Copilot skills documentation · loads skills from .github/skills/, .claude/skills/, .agents/skills/
Install the "kitcn" agent skill from https://github.com/udecode/kitcn/tree/main/.agents/skills/kitcn into .github/skills/kitcn/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "kitcn", then confirm the skill loads.GitHub Copilot copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
$ npx skills add udecode/kitcn --skill kitcn -a opencodeOpenCode documents no install command of its own. Project install goes to .agents/skills/; add -g for ~/.config/opencode/skills/.
$ gh skill install udecode/kitcn kitcn --agent opencodeProject scope by default (.agents/skills/); add --scope user for a personal install.
$ git clone --depth 1 https://github.com/udecode/kitcn.git skills-src && mkdir -p .opencode/skills && cp -r skills-src/.agents/skills/kitcn .opencode/skills/kitcn && rm -rf skills-srcUse ~/.config/opencode/skills/ instead of .opencode/skills for a personal install.
OpenCode skills documentation · loads skills from .opencode/skills/, .claude/skills/, .agents/skills/
Install the "kitcn" agent skill from https://github.com/udecode/kitcn/tree/main/.agents/skills/kitcn into .opencode/skills/kitcn/ in this project. Copy the whole folder (SKILL.md and every file beside it), keep the folder name "kitcn", then confirm the skill loads.OpenCode copies the folder itself, the same result as the manual copy. Check what it changed before you commit it.
kitcnA skill your agent uses for Convex/kitcn setup and feature work: cRPC, ORM, auth, React.
Kitcn is an agent skill from udecode/kitcn. Use for Convex/kitcn setup and feature work: cRPC, ORM, auth, React.
Its SKILL.md is about 7.9k tokens, which your agent loads only when the skill is triggered. The skill folder holds 25 other files, including reference files (for example `references/features/aggregates.md`, `references/features/auth-admin.md` and `references/features/auth-organizations.md`).
It sits in Databases, covering ORMs and data access. It works with React. The repository describes itself as: Convex + Better Auth + tRPC + Drizzle + TanStack Query + shadcn. The licence is Apache-2.0.
11 steps, taken from the step headings in SKILL.md.
Read from SKILL.md and the folder at commit c6010f5. It shows what the files ask for, not the result of running them.
Pre-approves nothing: there is no allowed-tools line, so your agent's usual permission prompts apply.
From allowed-tools in the SKILL.md frontmatter.
No scripts in the folder and no shell commands in SKILL.md (its code samples are typescript).
From the folder's file list and the shell code blocks in SKILL.md.
No URLs in SKILL.md.
From URLs in SKILL.md, links to its own repository left out.
Names no API keys, tokens, secrets or passwords.
From names ending in _API_KEY, _TOKEN, _SECRET, _KEY or _PASSWORD in SKILL.md.
Kitcn loads about 7.9k tokens when it runs, and up to ~83k if it reads all its reference files. Until then it costs about 19 tokens; SKILL.md has 2,775 words of instructions outside code blocks.
Estimates: characters ÷ 4, the usual rule of thumb; real counts depend on the model's tokenizer. Scripts and assets cost tokens only if the agent reads them.
The automated check found no risky patterns in SKILL.md.
Automated static check — not a guarantee. Review scripts before installing. It scans the text of SKILL.md for risky patterns (piping downloads into a shell, reading credential files, hidden Unicode, destructive commands); files beside SKILL.md are not scanned.
The full file from udecode/kitcn at commit c6010f5, republished under its Apache-2.0 licence (© udecode). 2,775 words, ~7,909 tokens.
.claude/skills/kitcn/SKILL.md (or your agent's skills folder). This skill also uses 22 other files; get the full folder from GitHub.Use this file first for everyday feature delivery in an already configured kitcn app.
references/setup/index.md (then the relevant setup file).In scope:
query, mutation, action, httpAction) with runtime auth + rate limits.useCRPC() + TanStack Query.ctx.orm for app data access.CRPCError for expected failures.create<Module>Handler(ctx) in queries/mutations, create<Module>Caller(ctx) in actions/HTTP routes, caller.actions.* for action procedures, and caller.schedule.* for scheduling. Never call ctx.runQuery/ctx.runMutation/ctx.runAction directly for module procedures.Default assumption:
findMany/findFirst, insert/update/delete).
Only remember these non-parity deltas:z.object(...) (no primitive root args).z.void() outputs; omit .output(...) for no-value mutations..output(...) parses the handler's value as-is and substitutes nothing: a handler must return the schema's input type, so z.string().nullable() needs an explicit null (?? null), not undefined. Model absent values as .nullable(), never a top-level .optional() — Convex wires undefined as null and cannot express top-level optionality, so .output(z.string().optional()) publishes v.string() and the deployment rejects the null whenever the handler returns undefined. .optional() inside an object is fine. The low-level returns: option on zCustomQuery/zCustomMutation/zCustomAction differs — it substitutes null for undefined before parsing..input(...) calls merge input shapes..paginated({ limit, item }) must be before .query() and adds input.cursor, input.endCursor, and input.limit; pass all three to ORM cursor queries so live splits stay bounded.@convex/api leaves (api.namespace.fn.meta) so never put secrets in .meta(...); chaining .meta(...) is shallow merge and supports defaultMeta.auth: "optional" waits for auth load then runs, auth: "required" waits then skips when logged out.ctx.orm enforces constraints + RLS; ctx.db bypasses them.findMany() must be explicitly sized (limit, cursor mode, schema defaultLimit, or explicit allowFullScan).where requires explicit .withIndex(...); no implicit full scan fallback.orderBy field; index that field for stable paging.maxScan applies to cursor mode only; allowFullScan is for non-cursor full-scan opt-in.columns projection / many-relation subfilters can run post-fetch; bound result size early.orderBy; vector mode has stricter limits (no cursor/offset/top-level where/order).where throws unless allowFullScan().count(), aggregate(), and groupBy() require a matching aggregateIndex. Use groupBy({ by, _count, _sum }) instead of multiple .count() calls or findMany + manual JS grouping. Every by field must be finite-constrained (eq/in/isNull) in where. See references/features/aggregates.md.subscribe: true); never use queryClient.invalidateQueries for these subscribed paths.prefetch hydrates client, caller is server-only and not hydrated, preloadQuery hydrates but can cause stale split ownership if also rendered client-side.convexBetterAuth(...); generic server-only shortcut is createCallerFactory(...).createAuthMutations(authClient) wrappers so logout unsubscribes auth queries before sign out. Raw Convex preset keeps a smaller plain authClient.ctx.runQuery/ctx.runMutation/ctx.runAction directly for module-to-module calls. Use the generated runtime helpers from convex/functions/generated/<module>.runtime.create<Module>Handler(ctx) is the default in queries/mutations: zero overhead, query/mutation ctx only, and no redundant validation or middleware.create<Module>Caller(ctx) is for actions and HTTP routes. Action procedures live under caller.actions.*; scheduling lives under caller.schedule.now|after|at|cancel. Use requireActionCtx(ctx) only for true ActionCtx callbacks; use requireSchedulerCtx(ctx) when mutation or action contexts can schedule. Each caller/handler eagerly loads its module, so split large modules.Api, ApiInputs, ApiOutputs, Select, Insert, TableName) import from @convex/api — no manual inferApiInputs<typeof api>.httpRouter (not appRouter) for codegen.convex/functions/generated/ directory: getAuth, defineAuth from generated/auth; initCRPC, QueryCtx, MutationCtx, OrmCtx from generated/server; create<Module>Caller, create<Module>Handler from generated/<module>.runtime. No manual convex/lib/orm.ts.defineAuth(() => ({ ...options, triggers })) replaces split getAuthOptions + authTriggers. Trigger callbacks are doc-first: beforeCreate(data), onCreate(doc), onUpdate(newDoc, oldDoc) — no ctx first param.internal.generated.* (not internal.auth.*).execute({ batchSize, delayMs }). Opt into sync: execute({ mode: 'sync' }) or defineSchema(..., { defaults: { mutationExecutionMode: 'sync' } }). Relevant defaults: mutationBatchSize, mutationLeafBatchSize, mutationMaxRows, mutationScheduleCallCap.actionType: discriminator({ variants, as? }) in convexTable(...). Query config does not include a polymorphic option. Writes stay flat; reads synthesize nested details (or custom alias). Use withVariants: true to auto-load all one() relations on discriminator tables.Use references/setup/ when the task needs:
setup/index.md + setup/server.mdsetup/auth.mdsetup/react.mdsetup/next.md or setup/start.md
For full template-level recreation: start with setup/index.md, then load relevant setup files, then load selected feature refs.Lock these decisions first:
public / optionalAuth / auth / private.Typical feature touches:
convex/functions/schema.tsconvex/functions/<feature>.tsconvex/lib/crpc.ts (only if middleware/procedure builder changes)src/lib/convex/crpc.tsx (only if cRPC context/meta wiring changes)src/** feature UI filesconvex/functions/http.ts or convex/routers/** for HTTP endpointsconvex/functions/crons.ts or scheduled handlers if neededimport {
convexTable,
defineSchema,
id,
integer,
index,
text,
timestamp,
} from "kitcn/orm";
export const project = convexTable(
"project",
{
name: text().notNull(),
ownerId: id("user").notNull(),
updatedAt: timestamp()
.notNull()
.defaultNow()
.$onUpdateFn(() => new Date()),
},
(t) => [index("ownerId_updatedAt").on(t.ownerId, t.updatedAt)]
);
export const task = convexTable(
"task",
{
projectId: id("project").notNull(),
title: text().notNull(),
status: text().notNull().default("open"),
updatedAt: timestamp()
.notNull()
.defaultNow()
.$onUpdateFn(() => new Date()),
},
(t) => [index("projectId_updatedAt").on(t.projectId, t.updatedAt)]
);
export default defineSchema({ project, task })
.relations((r) => ({
project: {
tasks: r.many.task(),
},
task: {
project: r.one.project({ from: r.task.projectId, to: r.project.id }),
},
}))
.triggers({
task: {
change: async (change, ctx) => {
const projectId = change.newDoc?.projectId ?? change.oldDoc?.projectId;
if (!projectId) return;
const open = await ctx.orm.query.task.findMany({
where: { projectId, status: "open" },
columns: { id: true },
limit: 500,
});
await ctx.orm.update(project).set({ openTaskCount: open.length });
},
},
});Schema rules that matter:
many() relation paths need child FK indexes.references/features/orm.md.import { getSession } from "kitcn/auth";
import { CRPCError } from "kitcn/server";
import { initCRPC, type QueryCtx } from "../functions/generated/server";
const c = initCRPC
.meta<{
auth?: "optional" | "required";
role?: "admin";
ratelimit?: string;
}>()
.create();
function requireAuth<T>(user: T | null): T {
if (!user) {
throw new CRPCError({ code: "UNAUTHORIZED", message: "Not authenticated" });
}
return user;
}
async function getSessionUser(ctx: QueryCtx) {
const session = await getSession(ctx);
if (!session) return null;
return await ctx.orm.query.user.findFirst({
where: { id: { eq: session.userId } },
});
}
export const publicQuery = c.query.meta({ auth: "optional" });
export const authQuery = c.query
.meta({ auth: "required" })
.use(async ({ ctx, next }) => {
const user = requireAuth(await getSessionUser(ctx));
return next({ ctx: { ...ctx, user, userId: user.id } });
});
export const authMutation = c.mutation
.meta({ auth: "optional" })
.use(async ({ ctx, next }) => {
const user = await getSessionUser(ctx);
return next({
ctx: { ...ctx, user, userId: user?.id ?? null },
});
});Builder rules that matter:
public, optional, auth, and private procedure families once in convex/lib/crpc.ts. Authenticated action builders live in convex/lib/crpc-action.ts, the only builder module that imports getAuth..meta(...) is client-visible via generated API metadata. Never put secrets there.procedure info. When procedures are built from your app generated/server helper, standard export const queries, mutations, and actions infer module:function automatically from file path + export name. Use .name("module:function") only to override or cover unusual export shapes.getSession(ctx) from kitcn/auth, which reads the session row
directly. Keep getAuth(ctx) out of convex/lib/crpc.ts: it pulls the whole Better Auth
definition and every auth plugin into the static import closure of every procedure module, and
Convex has no dynamic import() to escape it. Import getAuth only in the modules that call
auth.api.* — convex/lib/crpc-action.ts, HTTP routes, and organization/admin mutations.c.middleware() chains preserve mutation writer types on mutation procedures. If the middleware itself performs writes, type it as mutation-only with c.middleware<MutationCtx>(...).references/setup/server.md and references/features/auth*.md.import * as z from "zod";
import { eq } from "kitcn/orm";
import { CRPCError } from "kitcn/server";
import { authMutation, authQuery } from "../lib/crpc";
import { project } from "./schema";
export const listProjects = authQuery
.paginated({ limit: z.number().min(1).max(50).default(20), item: project })
.query(async ({ ctx, input }) =>
ctx.orm.query.project.findMany({
where: { ownerId: ctx.userId },
orderBy: { updatedAt: "desc" },
cursor: input.cursor,
endCursor: input.endCursor,
limit: input.limit,
})
);
export const renameProject = authMutation
.input(z.object({ id: z.string(), name: z.string().min(1).max(120) }))
.mutation(async ({ ctx, input }) => {
const current = await ctx.orm.query.project.findFirst({
where: { id: input.id, ownerId: ctx.userId },
columns: { id: true },
});
if (!current) {
throw new CRPCError({ code: "NOT_FOUND", message: "Project not found" });
}
await ctx.orm
.update(project)
.set({ name: input.name })
.where(eq(project.id, current.id));
return null;
});Procedure rules that matter:
z.object(...)..input(...); add .output(...) only when needed..output(...) for no-value mutations..meta({ ratelimit: ... }) only for named bucket overrides.CRPCError for expected outcomes.limit, cursor, or .paginated(...).references/features/orm.md.Use:
create<Module>Handler(ctx) in queries/mutations.create<Module>Caller(ctx) in actions/HTTP routes.caller.actions.* for action procedures.caller.schedule.* for scheduled procedures.ctx.runQuery / ctx.runMutation / ctx.runAction for module procedures.where.where only when composition reads better than object form..withIndex(...) first plus explicit limit/maxScan.search: { index, query, filters } and does not support orderBy.orderBy field is indexed.pageByKey, vector search, pipelines, aggregate indexes) live in references/features/orm.md..returning(...) on inserts when caller needs created ids.where(...).unsetToken..execute({ mode: "sync" }) only when atomic all-at-once behavior is required.references/features/orm.md.Use this map consistently:
BAD_REQUEST: invalid input or business precondition.UNAUTHORIZED: no session.FORBIDDEN: session exists, permission missing.NOT_FOUND: missing or inaccessible resource.CONFLICT: duplicate or conflicting write.TOO_MANY_REQUESTS: rate limit.INTERNAL_SERVER_ERROR: unexpected failures only. cRPC also raises it for a
failed .output(...) parse, with message Output validation failed and
sanitized structural Zod issues in error.data.ZodError. Custom issue
messages and fields stay server-side because they can contain handler output.data payloads on CRPCError when the client needs
domain metadata like conflicting ids. Read them on the client from
error.data.Required tests:
Preconditions (must be true before writing/using useCRPC() code paths):
@convex/api) from setup bootstrap.CRPCProvider inside QueryClient + Convex provider flow).references/setup/ first..convex/, not ~/.convex.useCRPC() pattern: const crpc = useCRPC(); const projects = useQuery(crpc.project.listProjects.queryOptions({ cursor: null, limit: 20 })); const createProject = useMutation(crpc.project.createProject.mutationOptions());
Key client defaults/deltas:
subscribe: true).queryClient.invalidateQueries for subscribed cRPC query paths.{ subscribe: false } only for one-time fetches; refresh those with explicit refetch/fetchQuery.skipUnauth: true to avoid unauthorized fetch churn.useInfiniteQuery from kitcn/react.queryKey(...) helpers for cache read/write/fetch ops instead of manual keys.createAuthMutations(...) wrappers (not raw auth client calls) to avoid logout race errors. Raw Convex preset keeps the plain auth client path.error.data?.message over error.message; data.message is the clean CRPCError payload.QueryClient mutation onError toast with mutation.meta.errorMessage / skipErrorToast rather than copy-pasting onError in every component.references/features/react.md.Choose one per use case:
prefetch(...) (preferred): non-blocking, hydrated, client owns data.caller.*: blocking server-only logic (redirects/auth checks), not hydrated.preloadQuery(...): blocking + hydrated when server needs data immediately.Do not render preloadQuery result on server and again on client for the same data path.
HydrateClient must wrap all client components that consume prefetched queries.references/setup/next.md and references/features/react.md.import { createTaskCaller } from "../functions/generated/task.runtime";
export const createTaskRoute = authRoute
.post("/api/projects/:projectId/tasks")
.params(z.object({ projectId: z.string() }))
.input(z.object({ title: z.string().min(1) }))
.output(z.object({ id: z.string() }))
.mutation(async ({ ctx, params, input }) => {
const caller = createTaskCaller(ctx);
const id = await caller.createFromHttp({
projectId: params.projectId,
title: input.title,
userId: ctx.userId,
});
return { id };
});HTTP-specific rules:
z.coerce.* for search params.publicRoute / authRoute / optionalAuthRoute builders from convex/lib/crpc.ts.router(...) for feature-level HTTP grouping.{ params, searchParams }; query values are strings.references/features/http.md.Example: const caller = createTaskCaller(ctx); await caller.schedule.now.sendTaskCreated({ taskId: created.id, userId: ctx.userId }); await caller.schedule.at(input.sendAt).sendReminder({ taskId: input.taskId, userId: ctx.userId });
Scheduling rules:
ctx.scheduler.* directly only when you must schedule non-procedure internal.* functions.references/features/scheduling.md.Minimum feature test set:
UNAUTHORIZED)FORBIDDEN where relevant)NOT_FOUND)references/features/testing.md.Before calling a feature done:
limit/cursor).where and avoid accidental full scans.ctx.db is not used on paths that rely on ORM constraints/RLS..paginated(...) + ORM cursor flow (not ad-hoc wrappers)..withIndex(...) + bound (limit/maxScan) is explicit.@ts-nocheck, no global lint-rule downgrades, no unresolved lint warnings in touched files.| Mistake | Correct pattern |
|---|---|
| Raw Convex handler for new feature procedures | cRPC builders (publicQuery, authMutation, etc.) |
| Write-time side effects duplicated across mutations | Schema trigger, or one centralized mutation-side sync helper when trigger path is unsafe |
| Missing bounds on list/search | Add limit + cursor/pagination |
orderBy written as array objects | Use object form: orderBy: { updatedAt: "desc" } |
Using ctx.db for policy-sensitive reads | Use ctx.orm (RLS/constraints path) |
Throwing generic Error for expected outcomes | Throw CRPCError with explicit code |
| Infinite list with TanStack native hook directly | Use useInfiniteQuery from kitcn/react |
Primitive root input (z.string()) | Use root z.object(...) input schema |
Returning nothing with z.void() | Omit explicit output |
Returning a possibly-missing lookup under .output(...nullable()) | Coalesce it: ?? null. .output(...) substitutes nothing for undefined |
| Manual pagination wrappers for infinite endpoints | Use .paginated({ limit, item }) |
Synthetic Convex IDs in tests ("missing-id") | Use inserted IDs or semantic lookup keys |
| Aggregates disabled but helper/config still present | Remove aggregate helper + defineTriggers handlers + app config together |
Putting secrets in .meta(...) | Keep metadata non-sensitive (client-visible) |
Using ctx.runQuery/ctx.runMutation/ctx.runAction directly | Use create<Module>Handler(ctx) in queries/mutations, create<Module>Caller(ctx) in actions/HTTP with caller.actions.* / caller.schedule.* (from generated/<module>.runtime) |
Using createCaller in query/mutation context | Use create<Module>Handler(ctx) — zero overhead, bypasses redundant validation |
Adding // @ts-nocheck to unblock compile | NEVER do this; fix the underlying types using canonical patterns in references/setup/ |
| Relaxing lint rules to pass checks | Keep baseline lint config; fix code-level warnings/errors instead |
Setup (once per project):
references/setup/index.md: bootstrap, env, decision intake, gates, checklist, troubleshootingreferences/setup/server.md: core backend (schema, ORM, cRPC) + optional module gatesreferences/setup/auth.md: auth core bootstrap + plugin setupreferences/setup/react.md: client core (QueryClient, provider, cRPC context)references/setup/next.md: Next.js App Router setupreferences/setup/start.md: TanStack Start setupreferences/setup/doc-guidelines.md: skill/docs sync contractFeatures (per session, self-contained):
references/features/orm.md: full ORM API, constraints, RLS, advanced mutations, filtering/search/composition/paginationreferences/features/react.md: full client, RSC, hydration, error handling matrixreferences/features/http.md: typed REST routes, webhooks, streamingreferences/features/scheduling.md: cron + delayed job patternsreferences/features/testing.md: deeper testing scenariosreferences/features/aggregates.md: aggregate component patternsreferences/features/migrations.md: built-in online data migrations (defineMigration, CLI, deploy, drift). Load when: task involves data backfills, optional→required field hardening, field renames/removals, type narrowing, or kitcn migrate CLI commands. Skip for backward-compatible changes (new optional fields, new tables, code-level defaults).references/features/create-plugins.md: canonical plugin authoring patterns (split package entries, token config, scaffold/lockfile/CLI manifest rules). Load when: creating or refactoring plugins.references/features/ratelimit.md: ratelimit runtime accounting (shard budget dealing, check() vs limit(), snapshot conversion, read accuracy, failure modes). Load when: tuning shards, reading remaining quota, or debugging unexpected denials. Skip for plain ratelimit.middleware() wiring, which setup/server.md owns.references/features/auth.md: full Better Auth core flowreferences/features/auth-admin.md: admin plugin detailsreferences/features/auth-organizations.md: org/multi-tenant plugin details© udecode, Apache-2.0. Rendered from Markdown: HTML in the file is shown as text, images as links, and headings moved down two levels. Raw file
SKILL.md and 22 other files (references) in .agents/skills/kitcn of udecode/kitcn.
Open the folder on GitHubat commit c6010f5
Kitcn next to the 5 skills that share the most tags, products or categories with it. Stars are the repository's; “used in” counts other GitHub owners with a copy.
| Skill | Stars | Used in | Tokens | Auto-check | Licence | Repo updated |
|---|---|---|---|---|---|---|
| Kitcn this skilludecode/kitcn | 450 | — | ~7.9k | Automated safety check: Pass | Apache-2.0 | |
| Supercheck Architecturesupercheck-io/supercheck | 215 | — | ~1.3k | Automated safety check: Pass | AGPL-3.0 | |
| Context7 MCPrtadewald/skills | 180 | — | ~681 | Automated safety check: Pass | None | |
| Documentation Lookupaffaan-m/ECC | 275k | 1 repos | ~670 | Automated safety check: Pass | MIT | |
| Context7 MCPdanielvm-git/bigpowers | 257 | — | ~603 | Automated safety check: Pass | MIT | |
| Vite Flare Starterjezweb/claude-skills | 1.1k | — | ~2.6k | Automated safety check: Pass | MIT |
supercheck-io/supercheck
Work on Supercheck system architecture, Next.js routes and actions, React data hooks, Drizzle schemas and migrations, app-worker boundaries, or cross-package contracts.
rtadewald/skills
This skill should be used when the user asks about libraries, frameworks, API references, or needs code examples.
affaan-m/ECC
通过 Context7 MCP 使用最新的库和框架文档,而非训练数据。当用户提出设置问题、API参考、代码示例或命名框架(例如 React、Next.js、Prisma)时激活。
danielvm-git/bigpowers
Fetch current library docs via Context7 MCP instead of training data.
jezweb/claude-skills
Scaffold a full-stack Cloudflare app from the vite-flare-starter template — React 19 + Hono + D1+Drizzle + better-auth + Tailwind v4+shadcn/ui + TanStack Query + R2 + Workers AI.
JetBrains/skills
Search tool for modern web development best practices. An agent skill from JetBrains/skills.
udecode/kitcn
Create a short annotated visual walkthrough from real final-state screenshots or rendered artifacts.
udecode/kitcn
Prevent feature creep when building software, apps, and AI-powered products.
udecode/kitcn
Repair an unreleased .changeset/.md file so it matches the real branch delta against main.
udecode/kitcn
Audit newer Convex npm releases against kitcn. An agent skill from udecode/kitcn.
udecode/kitcn
A skill your agent uses when working with Jotai X stores (createAtomStore), accessing state in components or callbacks, persisting state to cookies or localStorage
udecode/kitcn
Run a scoped Linear backlog autonomously as a sequence of maximal safe parallel batches by composing orchestrator, autogoal, and task.
Works with
Categories
A skill your agent uses for Convex/kitcn setup and feature work: cRPC, ORM, auth, React. Kitcn is an agent skill from udecode/kitcn. Use for Convex/kitcn setup and feature work: cRPC, ORM, auth, React.
Kitcn fits situations like: convex/kitcn setup and feature work: cRPC; tasks that involve ORMs and data access.
Run `npx skills add udecode/kitcn --skill kitcn -a claude-code`. Or copy the skill folder (.agents/skills/kitcn in udecode/kitcn) into .claude/skills/kitcn in your project. Claude Code loads it when a task matches its description.
Run `npx skills add udecode/kitcn --skill kitcn -a codex`. Or copy the skill folder (.agents/skills/kitcn in udecode/kitcn) into .agents/skills/kitcn in your project. Codex loads it when a task matches its description.
Cursor, Gemini CLI, GitHub Copilot and OpenCode also load SKILL.md folders. With the skills CLI, run `npx skills add udecode/kitcn --skill kitcn -a cursor` (or -a gemini-cli, github-copilot or opencode for the others). To copy it by hand, put the folder in .cursor/skills/kitcn, .gemini/skills/kitcn, .github/skills/kitcn and .opencode/skills/kitcn in your project.
SKILL.md names no scripts, command-line tools or credentials: Kitcn is instructions for the agent only.
SKILL.md contains no URLs. Any network use would come from the scripts or tools the agent runs. This is read from the text; nothing was executed.
Our automated static check of SKILL.md found no risky patterns, such as piping downloads into a shell, reading credential files or hidden Unicode. It is not a guarantee. Review the folder before installing.
Kitcn is published under the Apache-2.0 licence (the repository's licence). It allows redistribution, so the full SKILL.md is shown on this page.
About 7.9k tokens (SKILL.md is roughly 32k characters). Agents keep only the skill's name and description in context until a task matches; then they load SKILL.md in full. Its references folder adds about 76k tokens, read only when the agent opens those files.
Skills that share tags, products or a category with Kitcn: Supercheck Architecture (supercheck-io/supercheck, 215 stars), Context7 MCP (rtadewald/skills, 180 stars), Documentation Lookup (affaan-m/ECC, 275k stars) and Context7 MCP (danielvm-git/bigpowers, 257 stars). The comparison table on this page puts their stars, adoption, token cost, safety result and licence side by side.
udecode (a GitHub organization) maintains it in udecode/kitcn, which has 450 GitHub stars. The repository holds 33 skills in this directory. The repository was last updated on October 1, 2026.
Source: udecode/kitcn on GitHub. Facts on this page come from the repository at the commit we read; the author's words are quoted as theirs.