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

@titan-design/eslint-plugin

v0.4.0

Published

ESLint rules that enforce the titan code-quality limits: functions of at most 30 non-blank lines, opt-in code lines of at most 200 characters, opt-in no wall clock in beat and motion code, comments that hold code, and TODO comments without a tracking task

Readme

@titan-design/eslint-plugin

ESLint rules for the titan code-quality limits. Each message tells the reader what to do next, so an agent that hits the rule can fix the code without asking.

  • max-function-lines: a function may have at most 30 non-blank lines (option max). Blank lines are not counted; comment lines are.
  • max-line-length (opt-in, not in recommended): a code line may have at most 200 characters (option max). Comment lines, import and re-export declarations, and lines where string, template or regex literals make up at least half the characters after the indent are skipped. A line holding a short literal among long logic is still reported, unlike core max-len's ignoreStrings.
  • todo-needs-issue: every TODO in a comment must carry its task right after the marker: TODO(TP-123), TODO(#123), or a bare TODO: TP-123 / TODO #123 that ends the sentence. TODO UTF-8 support, TODO ES-2022 (keys with a standards prefix such as UTF, ES, ISO, RFC, SHA, MD, TLS, SSL, IPV, ECMA, HTTP are prose), and a key that sits later in the comment or inside a URL are reported. FIXME is deliberately not checked; the rule is about TODO.
  • no-commented-code: a comment whose text parses as statements with a code signal (a declaration or control statement, an assignment, a call, ;) is reported; a lone expression such as read-only or 100 - 75 is prose. JSDoc and directive comments pass.
  • no-chained-type-assertions: a type assertion applied to another one, such as x as unknown as T or <T>(x as unknown), is reported once at the outermost assertion. A chain made only of as const passes. In tests, build the fake with partialFake<T>() from @titan-design/test-kit. It reads syntax only, so it cannot see a double cast split across two statements (const u: unknown = x; u as T); type-aware @typescript-eslint/no-unsafe-type-assertion covers that.
  • no-internal-module-mock: vi.mock, vi.doMock, jest.mock, jest.doMock and jest.unstable_mockModule may not target this repo's own code: a relative, absolute or # specifier, or one under an internal prefix (option internalPrefixes, default ["@titan-design/"]). node: builtins and third-party packages stay mockable. It matches the vi and jest names only, so a renamed import (import { vi as t }) is not seen, and it skips a specifier built at run time.
  • no-wall-clock-motion (opt-in, not in recommended): in beat and motion code, Date.now, performance.now, Math.random, setTimeout, setInterval, setImmediate and requestAnimationFrame are reported, bare or behind window, self or globalThis, so a seek or a second render shows the same frames. It applies only to files whose path contains one of the option paths (default ["/ui/beats/", "/motion/"]) and never to *.test.*, *.spec.* or __tests__/ files. It reads call syntax only, so an aliased import (const now = Date.now) is not seen.
  • no-test-clock-budget (opt-in, not in recommended): in a test file, an expect(x) compared with toBeLessThan, toBeGreaterThan or their OrEqual forms is reported when x comes from a clock (Date.now, performance.now, process.hrtime, process.cpuUsage, process.threadCpuUsage), followed through arithmetic and local names and functions by scope. A loaded CI runner misses such a limit or ratio; assert counted work instead, or gate the timing on a condition that names a bench flag. It cannot follow a time through an imported helper (TP-4262).
  • recipe-step-in-loop (opt-in, not in recommended): ctx.dispatch, ctx.seed, ctx.assisted, ctx.authorize, step(ctx, …) and codeStep(ctx, …) are reported inside a for, while or do loop or a map/forEach/flatMap/reduce/filter/some/every callback, unless it is in a .map or .flatMap callback written directly as an argument of an all(...) that is itself in no loop (a loop deeper in that callback is still reported). A mapItems callback is a fan-out, not a loop. It matches the name ctx and reads one function at a time, so a helper that holds the step op and is called in a loop is not seen; the runtime orphan trap (TP-3108 S5) covers that.
  • recommended: a flat config enabling the five rules other than max-line-length, no-test-clock-budget, no-wall-clock-motion and recipe-step-in-loop at error under the titan namespace.

Tier 0 of the titan-platform DAG. May import only packages in the same tier or below; the package-layers rule in .codewatch/check.json enforces this in CI. eslint 9 is a peer dependency.

// eslint.config.js
import titan from "@titan-design/eslint-plugin";

export default [
  {
    plugins: { titan },
    rules: { "titan/max-function-lines": "error", "titan/todo-needs-issue": "error" },
  },
];

Status: unpublished (private). The first publish follows in a later TP-897 slice.