From jointjs-claude-playground
Creates an interactive data explorer playground for any database schema, API data model, or entity-relationship diagram — an animated JointJS graph with two-tone entity nodes showing PK and field count, field-level search, full field table modal with PK/FK/UQ/NN badges, sample queries, router toggle, and BFS path highlighting. Use when the user wants to visualize data structures, table relationships, JSON schemas, or entity models — from local schema files, ORM models, migration files, or described schemas. Examples: 'visualize my database schema', 'create a data map for our API models', 'show me the entity relationships in our app', 'explore this Postgres schema', 'build a data explorer for this project', 'map out our database', 'explore our migrations', 'build a JointJS data playground', 'create a JointJS schema explorer'.
How this skill is triggered — by the user, by Claude, or both
Slash command
/jointjs-claude-playground:data-explorerThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
Generates a self-contained HTML file with an animated JointJS graph showing database schemas and entity models: two-tone entity nodes with `PK: <field> · N fields` sublabels, field-level search, FK-labeled relationship links, a full field table modal, and a prompt output bar.
Generates a self-contained HTML file with an animated JointJS graph showing database schemas and entity models: two-tone entity nodes with PK: <field> · N fields sublabels, field-level search, FK-labeled relationship links, a full field table modal, and a prompt output bar.
Two modes depending on whether the schema is described/known (use as given) or in local files (read files first).
Use when the user pastes a schema, describes tables, or names a well-known data model.
../graph-explorer/templates/graph-explorer.md — Shared Framework + Data Explorer Speclabel<subject>-data-explorer.htmlopen <filename>-data-explorer.htmlUse when the user says "this project", "our database", "our migrations", or points to a local path. Read schema files first.
Search in priority order — stop when you find a match:
# SQL migrations
Glob('migrations/**/*.sql')
Glob('db/migrate/**/*.rb') # Rails
Glob('database/migrations/**/*.php') # Laravel
# ORM model definitions
Glob('src/**/models/*.{ts,js}') # TypeScript/JS ORMs (TypeORM, Prisma, Mongoose)
Glob('app/models/**/*.rb') # Rails ActiveRecord
Glob('models/**/*.py') # Django, SQLAlchemy
Glob('**/schema.prisma') # Prisma
# Schema dumps / introspection output
Glob('**/*.sql') # schema.sql, dump.sql
Glob('**/schema.{json,yaml,yml}') # JSON Schema, OpenAPI components
Also check: package.json for ORM name (prisma, typeorm, sequelize, mongoose) to guide parsing strategy.
SQL migrations / schema dumps:
CREATE TABLE orders (
id uuid PRIMARY KEY,
user_id uuid NOT NULL REFERENCES users(id), -- → FK link to users, label: 'user_id'
total numeric(10,2) NOT NULL,
created_at timestamptz NOT NULL DEFAULT now()
);
Extract: table name, columns (name + type), PRIMARY KEY, FOREIGN KEY references, UNIQUE constraints, NOT NULL.
Prisma schema:
model User {
id String @id @default(uuid())
email String @unique
orders Order[] -- → relation, emit link Order→User
}
Extract: model name, fields (name + type + attributes), @relation → FK links.
TypeORM / Sequelize / Django models:
@Entity, @Column, @ManyToOne, @OneToMany decorators (TypeORM)models.Model subclasses with field definitions (Django)Rails ActiveRecord:
create_table :orders in migrations → entityt.references :user → FK link to usersbelongs_to :user in model file → confirms relationshipOpenAPI / JSON Schema:
components/schemas → one node per schema object$ref to another schema → link// One node per table/model
{
id: 'orders',
label: 'orders',
sub: 'schema_name_or_file_path',
layer: 'derived_domain_group', // see Phase 4
fields: [
{ name: 'id', type: 'uuid', pk: true, nullable: false },
{ name: 'user_id', type: 'uuid', fk: true, nullable: false },
{ name: 'total', type: 'numeric(10,2)', nullable: false },
{ name: 'created_at', type: 'timestamptz', nullable: false },
],
snippet: `-- generated sample query\nSELECT * FROM orders WHERE id = $1;`,
}
// One connection per FK / relation
{ from: 'orders', to: 'users', type: 'foreignKey', label: 'user_id' }
Group tables into domain layers by name prefix/suffix patterns:
| Pattern | Layer |
|---|---|
user, account, session, role, permission | auth |
product, item, inventory, category, sku | product |
order, cart, checkout, line_item | order |
payment, invoice, charge, refund, transaction | payment |
event, log, audit, metric, stat | analytics |
setting, config, feature_flag | config |
| Uncategorized | core |
Assign one color per layer using the LAYERS palette from the Data Explorer Spec — rename keys to match what was found.
Write the HTML file using the graph-explorer template (Shared Framework + Data Explorer Spec), substituting the extracted NODES, CONNECTIONS, and derived LAYERS. Add presets:
full — alwaysauth, transactions)Filename: <project-name>-data-explorer.html where project name = root directory name or package.json name.
| Problem | Fix |
|---|---|
| Many small lookup/enum tables | Merge into a config or shared layer node; list them in desc |
| No FK constraints in schema (app-level only) | Read model files for belongs_to/@ManyToOne to recover relationships |
| Prisma enums | Skip as nodes — mention in the field's type string |
| Migration files out of order | Read the latest state: prefer a schema.sql dump over individual migration files |
| Too many tables (>25) | One node per domain group — aggregate fields from all tables in the group into a summary node |
PK: <field> · N fields sublabelgetVisibleIds() also matches field names and types (e.g. type "uuid" to find all UUID fields)label property rendered as a small annotation at distance: 0.45https://cdn.jsdelivr.net/npm/@joint/[email protected]/dist/joint.min.js../graph-explorer/templates/graph-explorer.md → Shared Framework + Data Explorer Spec<subject>-data-explorer.htmldatamap.EntityNode, datamap.Linknpx claudepluginhub clientio/jointjs-claude-marketplace --plugin jointjs-claude-playgroundGenerate HTML entity-relationship diagrams (ERDs) and database schema visualizations with clickable tables, relationship paths, and migration before/after views. Use whenever the user has a database schema, data model, or table structure to document, explain, migrate, or explore — even when they call it a "data model", "schema diagram", or just "the tables". Reach for this any time the conversation touches database structure with more than ~3 tables.
Generates ERDs, Mermaid/PlantUML diagrams, schema docs, and insights from SQL dumps, ORM models (Prisma, SQLAlchemy, TypeORM), migrations, or live DBs.
Creates complex multi-entity relational data models with Mermaid classDiagram output. For advanced modeling beyond simple SQL table creation.