npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@thenavidm/design-md-generator

v0.1.0

Published

DESIGN.md generator and checker for AI coding agents. Build a spec-exact DESIGN.md from your CSS variables, Tailwind config or colors, and lint any file against Google's format.

Readme

DESIGN.md Generator

License YouTube X LinkedIn

DESIGN.md generator and checker for AI coding agents. Build a spec-exact DESIGN.md from your CSS variables, Tailwind config or colors, and lint any file against Google's format.

A DESIGN.md tells an AI coding agent what your product looks like: exact colors, type, spacing and corners in a YAML block, then the reasons in plain words. This library writes one to Google Labs' format, reads one back, and checks it the way Google's own linter does, plus a few checks it doesn't make.

Built and maintained by Navid Moazzez.

Use it free on navid.me: the DESIGN.md generator. More in free tools.

npm install @thenavidm/design-md-generator

The library behind the free DESIGN.md generator on navid.me. A CLI and an MCP server come next.

Contents

| | Section | | |---|---|---| | 1 | What it does | Import, write, read, check, export | | 2 | Usage | From CSS variables to a checked file | | 3 | Functions | What each one returns | | 4 | The checks | Google's checks, then this tool's own | | 5 | Getting your agent to read it | Claude Code, Cursor, Codex | | 6 | Notes and gotchas | What surprises people |

1. What it does

| Job | Function | |---|---| | Read tokens from CSS variables, a Tailwind config, token JSON or a list of colors | importTokens | | Write a DESIGN.md: YAML tokens, then the 8 sections in the spec's order | toDesignMd | | Read a DESIGN.md back into tokens and words | parseDesignMd | | Check a file: Google's rules, WCAG contrast, bad values, duplicates | lintDesignMd | | Export the tokens as Tailwind v4 CSS or design tokens JSON | toTailwindCss, toDtcg |

2. Usage

import { importTokens, emptyDesignSystem, toDesignMd, lintDesignMd } from "@thenavidm/design-md-generator";

const tokens = importTokens(`:root { --color-primary: #0b81f7; --color-ink: #0a0c10; --radius-md: 8px; }`);
const ds = { ...emptyDesignSystem("navid.me"), ...tokens };
ds.components = { "button-primary": { backgroundColor: "{colors.primary}", textColor: "#ffffff" } };

const md = toDesignMd(ds);
lintDesignMd(md).issues;
// [{ rule: "contrast-ratio", severity: "warning", path: "components.button-primary", data: { ratio: 3.82 } }, …]

3. Functions

| Function | Returns | |---|---| | importTokens(text) | Colors, text styles, corners, spacing and shadows, with the kind of input it read | | toDesignMd(ds, { title }) | The file: front matter, an optional # Name, then the sections that have something to say | | parseDesignMd(text) | The tokens, each section's words, every heading in order, and whether the front matter parsed | | lintDesignMd(textOrDs) | ok, the issues (rule, severity, path, data), a token count and the file's size | | contrast(a, b) / wcag(ratio) | The WCAG ratio, unrounded, and which levels it meets | | toTailwindCss(ds) / toDtcg(ds) | The tokens as a Tailwind v4 @theme, or design tokens JSON |

Results are data and codes, never sentences, so the app showing them words them in its own language.

4. The checks

The first 23 rows are Google's own checks (@google/design.md lint), with the same names, severities and conditions. Google leaves some findings unnamed; here each has a name.

A test runs Google's linter next to this one on the same files, and they must agree on every finding but one. Google judges contrast on a see-through color as if it were solid, so white glass at 6% counts as white. Here a see-through pair isn't judged, since its contrast depends on what's under it.

| Rule | Severity | When | |---|---|---| | broken-ref | error | A {colors.x} reference points at nothing | | broken-ref | warning | A component property the format doesn't have, like borderColor | | missing-primary | warning | Colors, but no primary | | contrast-ratio | warning | A component's text on its background is under 4.5:1, both solid colors | | orphaned-tokens | warning | A color no component uses, directly or through a reference, unless its family is used or it's a standard role (primary, secondary, tertiary, error, surface, background, outline) | | missing-typography | warning | Colors, but no text styles, and typography isn't in omitted | | section-order | warning | Sections out of the spec's order | | unknown-key | warning | A top-level key 2 letters or fewer from a real one | | token-like-ignored | warning | An unknown key holding tokens an agent will skip | | unknown-omission | warning | omitted names something that isn't a token group | | redundant-omission | warning | omitted names a group that has tokens | | declared-omission | info | A token group left out on purpose | | missing-sections | info | Colors, but no spacing or no corner tokens | | token-summary | info | How many tokens of each kind | | front-matter | warning | No YAML at all, YAML that doesn't parse, or a key set in 2 YAML blocks. Google reports it unnamed | | invalid-color | error | A color that isn't a CSS color | | invalid-dimension | error | A corner, font size, line height or letter spacing that isn't a size | | invalid-typography | warning | A text style written as 1 value, like sans: Inter. Google reports it once per letter | | unknown-type-prop | warning | A text style property the format doesn't have | | invalid-font | error | A font family that's a color | | invalid-weight | error | A font weight that isn't a number | | token-collision | error | Grouped tokens that flatten to a name already taken | | duplicate-section | error | The same section twice; the spec says to reject the file | | invalid-dimension | warning | A spacing value, or a corner as a bare number, that Google skips without a word | | missing-name | warning | No name | | misnamed-section | info | A heading that looks like 1 of the 8 but isn't spelled the spec's way, like ## 04. Color (Colors) | | unwritten-sections | info | Sections not written yet | | duplicate-color | info | One color under 2 names |

Contrast follows WCAG 2.2: 4.5:1 for text, 3:1 for large text, 7:1 for AAA, and the ratio is never rounded, so 4.499:1 fails (W3C).

5. Getting your agent to read it

None of these load a DESIGN.md by themselves. Each has its own way in, read from its docs on 2026-09-25.

| Agent | How | |---|---| | Claude Code | Add @DESIGN.md to your CLAUDE.md. Claude Code imports it at launch (memory docs) | | Cursor | Reference @DESIGN.md in a rule in .cursor/rules, or from AGENTS.md, which Cursor reads (rules docs) | | Codex | Add a line to AGENTS.md saying to follow DESIGN.md for any UI work. Codex reads AGENTS.md files but has no import, and caps them at 32 KiB by default (AGENTS.md docs) | | Stitch | DESIGN.md is Stitch's own format |

6. Notes and gotchas

The tokens are the rules, the words are the reasons. The spec says the YAML values are normative and the prose gives context. Write "Midnight Forest Green" in the words if you like; the agent builds with primary.

The YAML is optional. A file of words alone is valid, and Google's linter only warns. The tokens are what give an agent exact values instead of descriptions.

Tokens can sit in code blocks. Google's linter reads the front matter and every ```yaml block in the file, merged, and rejects a key set in 2 of them. parseDesignMd does the same, and keeps those blocks out of the words.

Nested tokens flatten. ink: { light: "#121715", dark: "#faf8f5" } is 2 colors, ink.light and ink.dark, and {colors.ink.light} points at the first.

Order matters, gaps don't. Leave out a section you have nothing to say about. Never move one: the spec fixes the order.

Headings must match exactly. ## 04. Colors or ## Color isn't the Colors section to an agent reading by the spec. Use the 8 names as the spec writes them, or its 3 aliases: Brand & Style, Layout & Spacing, Elevation.

Extra sections are fine. The spec says a reader keeps a section it doesn't know, like ## Iconography. parseDesignMd keeps them where they stood, and toDesignMd writes them back there.

Say what each token is for. The tokens can't hold a note, so ds.notes goes next to each token in its section: - `primary` (#0B81F7): Links, buttons and focus rings. Reading the file back returns the notes.

States are components. A hover or pressed state is its own component with a related name, like button-primary-hover, as the spec shows.

omitted is for tokens. It lists the token groups you're leaving out on purpose (colors, typography, spacing, rounded, components), never prose sections.

A size needs its unit. fontSize: "42" is an error; 42px is right. Unquoted 42 passes Google's check, but write the unit anyway.

Brand blue behind white text often fails. A mid blue like #0B81F7 behind white text is 3.82:1, under the 4.5:1 AA line. Use it for large text and icons, or darken it for buttons.

Imports are read, never run. A Tailwind config is parsed as text. Values built by code (colors.slate, a spread) are skipped and counted.

Dark mode is a second name. The format has no themes, so a variable set again under a dark selector comes back as <name>-dark.

Dependencies

| Package | License | Used for | |---|---|---| | yaml | ISC | Reading and writing the front matter | | @google/design.md | Apache-2.0 | Tests only: the official linter the checks are compared against |

Questions

Run into a problem or have a question? Open an issue and I will help.

About the author

Navid Moazzez is a leading AI business strategist, and the host of the AI Creator Summit, watched by 100,000+ creators. He helps creators and founders master AI and build their own AI Operating System (AI OS) to automate their business and life. He creates useful free tools, MCP servers and CLIs that creators and founders can use in their own workflows.

Links

License

MIT. Free to use, modify, and share.

DESIGN.md is an open format from Google Labs (Apache-2.0). This project is not affiliated with, endorsed by, or connected to Google.


© 2026 Navid Media. Made with ❤️ by Navid Moazzez.