Agent skill

Convex Schema Validator

by waynesutton in waynesutton/builder-skills

Designs convex/schema.ts tables, validators, indexes, and relationships, and keeps the schema honest as data evolves.

Apache-2.0Auto-check passed

Install Convex Schema Validator

skills CLI
$ npx skills add waynesutton/builder-skills --skill convex-schema-validator -a claude-code

Project install by default; add -g for ~/.claude/skills/.

GitHub CLI
$ gh skill install waynesutton/builder-skills convex-schema-validator --agent claude-code

Project scope by default; add --scope user for a personal install. Needs GitHub CLI 2.90.0 or later (public preview).

Manual copy
$ git clone --depth 1 https://github.com/waynesutton/builder-skills.git skills-src && mkdir -p .claude/skills && cp -r skills-src/skills/convex-schema-validator .claude/skills/convex-schema-validator && rm -rf skills-src

Use ~/.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/

Facts

Skill name
convex-schema-validator
GitHub stars
404
Token cost
~2.4k tokens
SKILL.md length
887 words
Files
4 (incl. assets)
Skills in repo
17
Repo updated
First seen
Licence
Apache-2.0

At a glance

Designs convex/schema.ts tables, validators, indexes, and relationships, and keeps the schema honest as data evolves.

  • Creating tables
  • SKILL.md covers When to reach for this, Schema skeleton, Validators and Optional versus nullable, plus 8 more sections
  • Calls npx
  • Choosing index fields

What it does

Convex Schema Validator is an agent skill from waynesutton/builder-skills. Designs convex/schema.ts tables, validators, indexes, and relationships, and keeps the schema honest as data evolves. Use when creating tables, adding fields, choosing index fields, modeling relationships, or when a validator error appears at deploy time.

Its SKILL.md is about 2.4k tokens, which your agent loads only when the skill is triggered. The skill folder holds 5 other files, including assets (for example `agents/openai.yaml`).

The repository describes itself as: Builder skills for Convex apps. Convex patterns plus a PRD, task.md, changelog, and files.md workflow for Claude Code, Codex, Cursor, and OpenCode. The licence is Apache-2.0.

When your agent uses it

  • Creating tables
  • Choosing index fields
  • Modeling relationships
  • A validator error appears at deploy time

Example prompts

  • “Use the convex-schema-validator skill to design convex/schema.ts tables, validators, indexes, and relationships, and keeps the schema honest as data…”
  • “/convex-schema-validator”

Requirements

  • Node.js

What it can do on your machine

Read from SKILL.md and the folder at commit 82d1ce2. It shows what the files ask for, not the result of running them.

  • Tool permissions

    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.

  • Runs code

    Shell commands in SKILL.md call:

    • npx

    From the folder's file list and the shell code blocks in SKILL.md.

  • Network

    Links to these hosts (documentation or services it may open):

    • docs.convex.dev

    From URLs in SKILL.md, links to its own repository left out.

  • Credentials

    Names no API keys, tokens, secrets or passwords.

    From names ending in _API_KEY, _TOKEN, _SECRET, _KEY or _PASSWORD in SKILL.md.

Context cost

Convex Schema Validator loads about 2.4k tokens when it runs. Until then it costs about 70 tokens; SKILL.md has 887 words of instructions outside code blocks.

Always · name and description, kept in context so the agent knows when to use it
~70
When it runs · the whole SKILL.md, loaded when a task matches
~2.4k

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.

Safety

Auto-check passed

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.

SKILL.md

The full file from waynesutton/builder-skills at commit 82d1ce2, republished under its Apache-2.0 licence (© waynesutton). 887 words, ~2,386 tokens.

Download SKILL.mdSave it as .claude/skills/convex-schema-validator/SKILL.md (or your agent's skills folder). This skill also uses 3 other files; get the full folder from GitHub.
name
convex-schema-validator
description
Designs convex/schema.ts tables, validators, indexes, and relationships, and keeps the schema honest as data evolves. Use when creating tables, adding fields, choosing index fields, modeling relationships, or when a validator error appears at deploy time.

Convex schema validator

Produces a convex/schema.ts that types every document, indexes every query path, and passes validation against the data already in the database. The one rule: every withIndex in a function needs a matching .index() here, named after its fields, queried in field order.

When to reach for this

  • Creating a new table or adding a field to an existing one
  • A query uses .filter() and needs an index instead
  • Deciding whether to embed an object or link with v.id
  • Modeling a document that comes in several shapes
  • npx convex dev fails with a schema validation error

Schema skeleton

typescript
// convex/schema.ts
import { defineSchema, defineTable } from "convex/server";
import { v } from "convex/values";

export default defineSchema({
  users: defineTable({
    name: v.string(),
    email: v.string(),
    avatarUrl: v.optional(v.string()),
  }).index("by_email", ["email"]),

  tasks: defineTable({
    userId: v.id("users"),
    title: v.string(),
    completed: v.boolean(),
    priority: v.union(v.literal("low"), v.literal("medium"), v.literal("high")),
  })
    .index("by_userId", ["userId"])
    .index("by_userId_and_completed", ["userId", "completed"]),
});

defineTable takes either an object of field validators or a single v.union of v.object validators (see discriminated unions). Every table gets _id and _creationTime for free. Do not declare them.

Validators

ValidatorTypeScript typeNote
v.string()stringUTF-8, under 1 MB
v.number()numberFloat64. Use for timestamps and counts
v.boolean()boolean
v.null()nullundefined is not a Convex value. Return null instead
v.int64()bigintNot v.bigint(), which is deprecated
v.bytes()ArrayBufferUnder 1 MB
v.id("table")Id<"table">Typed reference. Convex does not enforce that the target exists
v.array(t)T[]At most 8192 items
v.object({...}){...}At most 1024 entries. Keys cannot start with $ or _
v.record(k, t)Record<K, T>Dynamic ASCII keys. No v.map or v.set
v.union(a, b)A | BUse v.literal members for enums
v.literal("x")"x"
v.optional(t)T | undefinedField may be absent
v.any()anyLast resort. Loses type safety and validation

Optional versus nullable

v.optional means the key may be missing from the document. v.union(t, v.null()) means the key is always present and may hold null. They are different at validation time.

typescript
items: defineTable({
  description: v.optional(v.string()),           // may be absent
  deletedAt: v.union(v.number(), v.null()),       // always present, may be null
  notes: v.optional(v.union(v.string(), v.null())), // either
}),

Use v.optional for fields added after the table had data. Use v.union(..., v.null()) when "explicitly cleared" carries meaning.

Discriminated unions

For a table whose documents come in several shapes, pass a v.union of v.object validators to defineTable. Each member has the same literal key so TypeScript narrows on it.

typescript
events: defineTable(
  v.union(
    v.object({
      kind: v.literal("signup"),
      userId: v.id("users"),
      email: v.string(),
    }),
    v.object({
      kind: v.literal("purchase"),
      userId: v.id("users"),
      orderId: v.id("orders"),
      amount: v.number(),
    }),
  ),
).index("by_kind", ["kind"]),

Put the discriminant (kind) first in any index on a union table so queries can scope to one shape. Prefer this over one wide object full of v.optional fields.

Indexes

Naming and field order

Name the index after its fields in order: by_field1_and_field2. Querying must follow the same order: equality on a prefix of the fields, then at most one range on the next field.

typescript
messages: defineTable({
  channelId: v.id("channels"),
  authorId: v.id("users"),
  sentAt: v.number(),
})
  .index("by_channelId", ["channelId"])
  .index("by_channelId_and_authorId", ["channelId", "authorId"])
  .index("by_channelId_and_sentAt", ["channelId", "sentAt"]),
typescript
// Valid: equality on channelId, range on sentAt
await ctx.db
  .query("messages")
  .withIndex("by_channelId_and_sentAt", (q) =>
    q.eq("channelId", args.channelId).gt("sentAt", args.since),
  )
  .order("desc")
  .take(50);

You cannot skip channelId and filter on sentAt alone with that index. Add by_sentAt if that query exists. _creationTime is appended to every index automatically, so results within an equal prefix sort by creation time.

Reserved names: by_id and by_creation_time. Limits: 32 indexes per table, 16 fields per index.

When to add one
  • Any field a function passes to withIndex, .eq, or a range comparison
  • Every foreign key (userId, channelId, orgId) on the child table
  • The sort field for a paginated list, prefixed by the scoping field
  • Not for fields you only read after fetching the document
  • Not for tiny tables where a .collect() then in memory filter is fine

If a query uses .filter(), that is the signal to add an index and switch to withIndex.

Show full SKILL.md (375 more words)Show less

Relationships

Link documents with v.id("table") on the child. Do not nest growing arrays of objects inside the parent.

typescript
// Good: one to many via a foreign key
posts: defineTable({
  authorId: v.id("users"),
  title: v.string(),
}).index("by_authorId", ["authorId"]),

comments: defineTable({
  postId: v.id("posts"),
  authorId: v.id("users"),
  body: v.string(),
}).index("by_postId", ["postId"]),

// Many to many via a join table
postTags: defineTable({
  postId: v.id("posts"),
  tagId: v.id("tags"),
})
  .index("by_postId", ["postId"])
  .index("by_tagId", ["tagId"]),

Embed with v.object or a small v.array only when the data is bounded, always loaded with the parent, and updated together. A user's settings object is a good embed. A user's posts array is not: it hits the 8192 item cap and every post edit rewrites the user document.

System fields

_id: Id<"table"> and _creationTime: number (ms since epoch) exist on every document. Include them in return validators when a function returns whole documents:

typescript
returns: v.array(
  v.object({
    _id: v.id("tasks"),
    _creationTime: v.number(),
    userId: v.id("users"),
    title: v.string(),
    completed: v.boolean(),
  }),
),

Do not add your own createdAt unless you need a value that differs from insertion time.

Search and vector indexes

Declared on the table like regular indexes. filterFields must be top level fields.

typescript
articles: defineTable({
  title: v.string(),
  body: v.string(),
  category: v.string(),
  embedding: v.array(v.number()),
})
  .searchIndex("search_body", {
    searchField: "body",
    filterFields: ["category"],
  })
  .vectorIndex("by_embedding", {
    vectorField: "embedding",
    dimensions: 1536,
    filterFields: ["category"],
  }),

Query search indexes with withSearchIndex in queries. Vector search runs only in actions via ctx.vectorSearch.

Common mistakes

MistakeWhy it breaksDo instead
withIndex("by_userId") with no matching .index()Deploy failsDeclare the index in the schema first
Index named by_user on ["userId", "status"]Hides what it covers, easy to misuseby_userId_and_status
Querying status on by_userId_and_status without userIdIndex prefix ruleAdd by_status or include userId
Adding newField: v.string() to a table with rowsExisting documents fail validationv.optional, backfill, then require
posts: v.array(v.object(...)) on users8192 cap, write conflicts on every editSeparate posts table with by_authorId
v.bigint()Deprecatedv.int64()
Declaring _id or _creationTime in defineTableRejectedThey are automatic
v.any() to move fastNo validation, no typesModel the shape, or a v.union of the real cases
v.union(v.string(), v.null()) for a new fieldOld documents lack the key entirelyv.optional(v.string())
Storing a DateNot a Convex valuev.number() ms timestamp

Checklist

  • Schema lives in convex/schema.ts and exports defineSchema(...) as default
  • Every table has explicit field validators, no v.any() unless justified
  • Every withIndex call in convex/ has a matching .index() with fields in the name
  • Foreign keys are v.id("table") with an index on the child table
  • No unbounded arrays of objects embedded in a parent document
  • Fields added to tables with data are v.optional
  • Enums and polymorphic shapes use v.union of v.literal or v.object members
  • Return validators include _id and _creationTime when returning whole documents
  • npx convex dev pushes without a schema validation error

Docs

© waynesutton, 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

Files

SKILL.md and 3 other files (assets) in skills/convex-schema-validator of waynesutton/builder-skills.

  • SKILL.md
  • agents/openai.yaml
  • assets/large-logo.png
  • assets/small-logo.svg

Open the folder on GitHubat commit 82d1ce2

Compare with similar skills

Convex Schema Validator 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.

Convex Schema Validator compared with similar skills
SkillStarsUsed inTokensAuto-checkLicenceRepo updated
Convex Schema Validator this skillwaynesutton/builder-skills404—~2.4kAutomated safety check: PassApache-2.0
Convex Designopenclaw/clawhub9.5k1 repos~967Automated safety check: NotesMIT
Design Systemaffaan-m/ECC275k—~698Automated safety check: PassMIT
Design Guidepaperclipai/paperclip99k1 repos~3.1kAutomated safety check: PassMIT
Convexdavila7/claude-code-templates32k3 repos~6.4kAutomated safety check: NotesMIT
Postgresql Table Designwshobson/agents40k—~2kAutomated safety check: PassMIT

Similar skills

  • Convex Design

    openclaw/clawhub

    Design and build reactive, type-safe, production-grade backends on Convex.

    9.5k GitHub starsUsed in 1 repo~967 tokens
    Backend & APIsAuto-check: notes
  • Design System

    affaan-m/ECC

    Generate a design system from an existing codebase or audit one for visual consistency: extract tokens (colors, typography, spacing, shadows) into design-tokens.json and CSS custom properties with…

    275k GitHub stars~698 tokensUpdated 3 days ago
    Frontend & DesignAuto-check passed
  • Design Guide

    paperclipai/paperclip

    Paperclip UI design system guide for building consistent, reusable frontend components.

    99k GitHub starsUsed in 1 repo~3.1k tokens
    Frontend & DesignAuto-check passed
  • Convex

    davila7/claude-code-templates

    Convex reactive backend expert: schema design, TypeScript functions, real-time subscriptions, auth, file storage, scheduling, and deployment.

    32k GitHub starsUsed in 3 repos~6.4k tokens
    DatabasesAuto-check: notes
  • A skill your agent uses when designing or reviewing a PostgreSQL-specific schema.

    40k GitHub stars~2k tokensUpdated 3 days ago
    DatabasesAuto-check passed
  • Audits a design against Dieter Rams' ten principles of good design, scores each with evidence, and hands off a make-plan prompt for a new, refined or redesigned outcome.

    98k GitHub stars~4.6k tokensUpdated yesterday
    Frontend & DesignAuto-check passed

More from waynesutton/builder-skills

All 17 skills in this repo
  • Convex Agents

    waynesutton/builder-skills

    Builds AI agents on the Convex agent component: threads, messages, tools that call queries and mutations, streaming, RAG with vector search, and workflows for multi step jobs.

    404 GitHub stars~2.2k tokensUpdated 10 days ago
    Auto-check passed
  • Convex Best Practices

    waynesutton/builder-skills

    Production patterns for Convex apps and the rules the @convex-dev/eslint-plugin enforces: validators, indexes, idempotent mutations, avoiding OCC conflicts, thin function wrappers, error handling.

    404 GitHub stars~2.6k tokensUpdated 10 days ago
    Auto-check passed
  • Convex Component Authoring

    waynesutton/builder-skills

    Creates reusable Convex components with defineComponent, a clean client wrapper, their own schema, and an npm publish setup.

    404 GitHub stars~2.6k tokensUpdated 10 days ago
    Auto-check passed
  • Convex Cron Jobs

    waynesutton/builder-skills

    Schedules work in Convex: cron jobs in convex/crons.ts, one off scheduled functions with runAfter and runAt, batching large jobs, and cancelling or inspecting the queue.

    404 GitHub stars~2k tokensUpdated 10 days ago
    Auto-check passed
  • Convex HTTP Actions

    waynesutton/builder-skills

    Adds HTTP endpoints in convex/http.ts: webhook receivers with signature checks, REST style routes, CORS, auth headers, streaming responses, and file uploads over HTTP.

    404 GitHub stars~2.6k tokensUpdated 10 days ago
    Auto-check passed
  • Convex Migrations

    waynesutton/builder-skills

    Changes a live Convex schema without downtime: make a field optional, backfill in batches, flip the validator, then clean up.

    404 GitHub stars~2.1k tokensUpdated 10 days ago
    Auto-check passed

Questions about Convex Schema Validator

What does Convex Schema Validator do?

Designs convex/schema.ts tables, validators, indexes, and relationships, and keeps the schema honest as data evolves. Convex Schema Validator is an agent skill from waynesutton/builder-skills.ts tables, validators, indexes, and relationships, and keeps the schema honest as data evolves.

When should I use Convex Schema Validator?

Convex Schema Validator fits situations like: creating tables; choosing index fields; modeling relationships; A validator error appears at deploy time.

How do I install Convex Schema Validator in Claude Code?

Run `npx skills add waynesutton/builder-skills --skill convex-schema-validator -a claude-code`. Or copy the skill folder (skills/convex-schema-validator in waynesutton/builder-skills) into .claude/skills/convex-schema-validator in your project. Claude Code loads it when a task matches its description.

How do I install Convex Schema Validator in Codex?

Run `npx skills add waynesutton/builder-skills --skill convex-schema-validator -a codex`. Or copy the skill folder (skills/convex-schema-validator in waynesutton/builder-skills) into .agents/skills/convex-schema-validator in your project. Codex loads it when a task matches its description.

Can I use Convex Schema Validator in Cursor, Gemini CLI or GitHub Copilot?

Cursor, Gemini CLI, GitHub Copilot and OpenCode also load SKILL.md folders. With the skills CLI, run `npx skills add waynesutton/builder-skills --skill convex-schema-validator -a cursor` (or -a gemini-cli, github-copilot or opencode for the others). To copy it by hand, put the folder in .cursor/skills/convex-schema-validator, .gemini/skills/convex-schema-validator, .github/skills/convex-schema-validator and .opencode/skills/convex-schema-validator in your project.

What does Convex Schema Validator need to run?

Going by SKILL.md and its folder, Convex Schema Validator needs the command-line tools its instructions call (npx). Our summary lists: Node.js.

Does Convex Schema Validator access the network?

SKILL.md names 1 domain. As links in the text: docs.convex.dev. This is read from the text; nothing was executed.

Is Convex Schema Validator safe to install?

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.

What licence does Convex Schema Validator use?

Convex Schema Validator 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.

How many tokens does Convex Schema Validator use?

About 2.4k tokens (SKILL.md is roughly 9.5k characters). Agents keep only the skill's name and description in context until a task matches; then they load SKILL.md in full.

What are the alternatives to Convex Schema Validator?

Skills that share tags, products or a category with Convex Schema Validator: Convex Design (openclaw/clawhub, 9.5k stars), Design System (affaan-m/ECC, 275k stars), Design Guide (paperclipai/paperclip, 99k stars) and Convex (davila7/claude-code-templates, 32k stars). The comparison table on this page puts their stars, adoption, token cost, safety result and licence side by side.

Who maintains Convex Schema Validator?

waynesutton (a GitHub user) maintains it in waynesutton/builder-skills, which has 404 GitHub stars. The repository holds 17 skills in this directory. The repository was last updated on September 28, 2026.

Source: waynesutton/builder-skills on GitHub. Facts on this page come from the repository at the commit we read; the author's words are quoted as theirs.