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

@ora-ai/ax

v0.5.3

Published

Score any site's agent readiness and watch real AI agents navigate it — powered by ora

Readme

ax — the ora CLI

Score any site's agent readiness — and watch real AI agents navigate it. Powered by ora's hosted APIs.

npx @ora-ai/ax audit https://stripe.com

Four commands:

  • audit <url> — run ora's hosted agent-readiness audit against a site: live progress, then a layered report of what passed, what's broken, and ora's ranked list of the highest-impact fixes (or --json for the raw contract payload). No account or API key needed. Gate CI with --min-score.
  • deep-journey <url> — run a real AI agent at a site on one of ora's curated tasks through the public journey API: no key, no workspace. A partner API key unlocks free-text tasks (--task) and a larger allowance.
  • journey "<intent>" — send a real AI agent (claude-code, codex, …) at a site and watch its navigation live as a boxed node-graph, then get the scored insight, tokens, and cost. Requires an ORA_API_KEY.
  • skill [name] — list, print, or install ora's agent skills, digest-verified from the public registry.

audit

ax audit <url> [--min-score n] [--max-age s] [--force] [--tunnel-cmd c] [--api-key k] [--json] [--show-passing] [--show-skipped]
  stripe.com  78/100 B+
  Stripe offers strong developer resource discoverability, but lacks an OpenAPI specification.

  Discovery   ██████░░░░ 6/9 passed · 1 skipped
    ✗ Issues (2)
    ┌───┬──────────────┬───────────────────────────┬──────────────────────────────┐
    │   │ Check        │ What's wrong              │ How to fix                   │
    ├───┼──────────────┼───────────────────────────┼──────────────────────────────┤
    │ ✗ │ sitemap.md   │ status 404                │ Publish /sitemap.md listing… │
    ├───┼──────────────┼───────────────────────────┼──────────────────────────────┤
    │ ⚠ │ robots.txt   │ partially restricted      │ Allow AI crawlers in robots… │
    └───┴──────────────┴───────────────────────────┴──────────────────────────────┘

  Top fixes (ranked by ora)
  1. sitemap-md   ≈ +4 pts
  2. robots-txt   ≈ +1.2 pts

  cached result (43 min old) · pass --force for a fresh scan
  Full report: https://ora.ai/stripe.com

| Flag | Effect | |---|---| | --min-score <n> | Exit 1 when the score is below n (0-100) — the CI gate | | --max-age <s> | Accept a cached result up to s seconds old (server default 6h, clamped to 1-24h) | | --force | Bypass the cache and rescan — spends the stricter 6/day force budget | | --tunnel-cmd <c> | Expose a local target through your own tunnel command and audit the public URL it prints (also read from ORA_TUNNEL_CMD) | | --api-key <k> | ora-issued scan API key — lifts every scan rate limit (also read from ORA_SCAN_API_KEY) | | --json | The raw ora audit payload on stdout, exactly as the API served it | | --show-passing | List every passing check, not just the per-layer summary bar | | --show-skipped | Include not-applicable/pending checks with their reason |

The Top fixes list is ranked by ora server-side (non-bonus fixes first, then estimated score uplift) — the CLI renders it verbatim. All ≈ +N pts figures are estimates. Check tiers (required / recommended / emerging) are advisory display metadata and never determine the score.

CI gate

- name: Agent-readiness gate
  run: npx @ora-ai/ax audit https://your-site.com --min-score 70

Exit codes are the contract:

| Code | Meaning | |---|---| | 0 | success (and score ≥ --min-score when given) | | 1 | score below --min-score | | 2 | usage error — bad flags, malformed URL, local target without a tunnel | | 3 | API unreachable, timeout, or rate limit exhausted |

Budget notes: ora allows 30 scans + 6 --force scans per rolling 24h per IP (plus a 10/min burst limit). Results served from the freshness cache cost nothing, so a CI job that audits on every push stays well inside the budget — tune the window with --max-age, and reserve --force for verifying a fix you just deployed. High-volume callers can present an ora-issued scan API key (--api-key or ORA_SCAN_API_KEY), which exempts them from all of these limits; keys are issued manually by ora (no self-serve signup), and an unrecognized key silently falls back to the keyless limits rather than erroring. An auth-gated MCP target reports mcpAuthRequired and scores 0 as "could not evaluate"; --min-score deliberately skips the gate rather than failing on it.

Auditing localhost (--tunnel-cmd)

A local dev server only exists on your machine, so ora can't reach it. The simplest option is to audit a publicly reachable deployment of the same code (e.g. a preview URL). To audit localhost itself, bring your own tunnel: pass --tunnel-cmd (or set ORA_TUNNEL_CMD) with a command that exposes the local server and prints its public https:// URL. The CLI runs it, audits the URL it prints, and tears the tunnel down when done.

ax audit localhost:3000 --tunnel-cmd 'ngrok http 3000 --log stdout'
  • The CLI ships no tunnel vendor and never downloads executables at runtime — any tunnel tool you already have works, as long as it prints its public URL to stdout or stderr.
  • The result is stored as ephemeral: excluded from ora's rankings and deleted after a few days.
  • Off-site checks (registry listings, brand search) usually fail for a throwaway tunnel hostname — the report says so. Use tunnel audits to iterate on your on-site surface, not to compare scores.
  • Free tiers of some tunnel vendors serve an interstitial warning page to browser-like requests, which can distort what the scanner sees — prefer a vendor/plan that serves your origin directly.

deep-journey

ax deep-journey <url> [--intent id | --task text] [--agent id] [--api-key k] [--no-stream] [--json]
ax deep-journey stripe.com --intent pricing
ax deep-journey zapier.com --task "Find how to build a Slack → Sheets zap"   # needs a partner key

Runs a real AI agent at a site through ora's public journey API — no key, no workspace needed for curated tasks. The agent's trajectory streams live as progress lines; the terminal output is ora's verdict, the billable step count, and the generated insight:

  ✓ task satisfied  stripe.com
  14 steps · 6 turns · 41.2s

  The agent found the pricing page in two hops via llms.txt and correctly
  summarised the standard and custom tiers.
    - llms.txt was load-bearing: it linked /pricing directly
    - no web search was needed; every path came from on-site links

  For the 4-layer readiness audit, run: ax audit stripe.com

Anonymous callers run curated intents (pricing, signup, api-docs, integrate, support, …) — list them with GET https://ora.ai/api/journey/intents, and the accepted agents with GET https://ora.ai/api/journey/agents. The public caps are 100 runs per rolling 24h per target and 200 runs per 24h per IP (plus a 20/min burst limit); a target at its cap answers with the most recent stored run (rate_limited: true) instead of an error, so repeat CI invocations are cheap. Verdict and step count come from ora's contract as-is — the CLI never re-judges a run.

Keyed tier: an ora-issued partner API key (--api-key, or ORA_PARTNER_API_KEY / ORA_SCAN_API_KEY in the environment) unlocks --task — a free-text task of 4–300 characters that replaces the curated intent — and moves the caller to an allowance of 1000 runs per rolling 24h per key with no per-target cap and no burst guard. Keys are issued manually by ora (no self-serve signup). A wrong or unrecognized key with a curated intent silently degrades to the anonymous tier; --task without a recognized key is an error.

If the live stream goes quiet (no frames for 120s) the CLI does not abandon the run — it switches to polling the run detail until the server reports a terminal state.

| Flag | Effect | |---|---| | --intent <id> | Curated task id (server default when omitted) | | --task <text> | Free-text task — needs a partner API key; mutually exclusive with --intent | | --api-key <k> | ora partner API key; also read from ORA_PARTNER_API_KEY (then ORA_SCAN_API_KEY) | | --agent <id> | Agent from the public roster (default: ora's pick) | | --no-stream | Poll for the result instead of streaming the trajectory | | --json | Print the terminal run detail (verdict, step_count, result) as JSON |

deep-journey exit codes: 0 run succeeded (any verdict) · 1 run failed · 2 usage error · 3 API unreachable / rate-limited.

This differs from ax journey (below), which drives the authenticated platform with free-text goals and renders the full trajectory graph; deep-journey is the zero-setup public path.

skill

ax skill                                # list the registry
ax skill agent-ready-website            # print a SKILL.md
ax skill agent-ready-website --install  # write .claude/skills/<name>/SKILL.md
ax skill --json                         # the raw registry index

Skills come from ora's public registry (https://ora.ai/.well-known/agent-skills/) and every byte is verified against the registry's sha256 digest before it is printed or installed. Skill content is never bundled into this package. --dir <path> overrides the install directory, and --json prints the registry index as JSON instead of the formatted list.

journey

ax journey "<intent>" [--domain d] [--harness h] [--model m] [--json]
ax journey "Find the API docs and how to authenticate" --domain stripe.com

Triggers a real agent run on ora's platform and renders the journey live — the whole graph repaints in place as the agent moves:

  ▶ stripe.com  ·  claude-code

  9 steps  ·  3 reasoning  ·  1 search

  ╭────────────────────────────────────────────────────────────────────────────────╮
  │ ◆ Find the API docs and how to authenticate. Fetch the actual pages to verify. │
  ╰─┬──────────────────────────────────────────────────────────────────────────────╯
    │  (…) The user is asking me to find the API documentation for Stripe…
    │  ╭──────────────────────────────────────────────╮
    ╰──┤ 🔍 "Stripe API documentation authentication" │
       ╰─┬────────────────────────────────────────────╯
         │  ╭─────────────────────────────────────────╮
         ├──┤ 🌐 docs.stripe.com/api/authentication ✓ │
         │  ╰─────────────────────────────────────────╯
         │  ╭───────────────────────────╮
         ╰──┤ 🌐 docs.stripe.com/apis ✓ │
            ╰───────────────────────────╯

  ────────────────────────────────────────────────────
  ✓ completed  9 turns · 30.8s · 119.1k tokens · $0.031

  Visibility  █████████████████████░ 95/100   ✓ intent satisfied

Edges come from ora's own per-step attribution (link-follows nest under the page that linked them; searches hang off the intent). (…) markers are the agent's reasoning, placed above the action it led to.

| Flag | Effect | |---|---| | --domain <d> | Site the agent targets (e.g. stripe.com) | | --harness <h> | Agent harness: claude-code (default), codex, openclaw, hermess, claude-agent, eve, … | | --model <m> | Model override (e.g. claude-haiku-4-5-20251001 — cheap and good for demos) | | --json | Full result as JSON: run metadata, usage, insight, and the raw trajectory |

Note: run-to-run variance is real — agents sometimes answer from search snippets without fetching, which scores differently. Run a few journeys before drawing conclusions.

Journey exit codes: 0 run outcome success · 1 non-success outcome · 2 any error.

Setup

journey needs an ora platform API key (scopes runs:read + runs:write):

export ORA_API_KEY=ora_sk_...        # your shell, CI secret store, etc.
ax journey "Find the pricing page" --domain example.com

For local development, copy .env.example to .env — the CLI reads a .env in the working directory on startup (exported variables win over the file).

Library use

The same contract-typed client the CLI uses is importable:

import { audit } from "@ora-ai/ax";

const { result } = await audit("stripe.com");
console.log(result.score, result.grade, result.topFixes);

result is the raw versioned audit payload (AuditScanResult / AuditScoreResult, generated from ora's OpenAPI spec). fetchSkill / fetchSkillIndex expose the digest-verified skill registry.

The public journey client is exported too — the same no-key path as ax deep-journey:

import { deepJourney, fetchJourneyAgents } from "@ora-ai/ax";

const { agents, defaultId } = await fetchJourneyAgents();
const agent = agents.find((a) => a.id === defaultId)!;
const { detail } = await deepJourney("stripe.com", {
	intentId: "pricing",
	harness: agent.harness,
	model: agent.model,
});
console.log(detail.verdict, detail.step_count, detail.result?.insight.summary);

detail is the contract's JourneyRunDetail; fetchJourneyIntents lists the curated intents. The same public caps apply — a capped target resolves with the most recent stored run (cached: true on the outcome), not an error.

Environment variables

All configuration is environment-first: the consumer defines the variables, the CLI only reads them.

A .env in the working directory is read on startup — copy .env.example and fill it in. Anything already exported wins over the file, so a key set for your shell or by CI beats a stale .env.

| Var | Used by | Default | Purpose | |---|---|---|---| | ORA_API_URL | audit, deep-journey, skill | https://ora.ai | Public API base (no auth) | | ORA_PLATFORM_URL | journey | https://api.agentfront.sh | Authenticated platform API base | | ORA_TUNNEL_CMD | audit | — (optional) | Tunnel command for a local target (same as --tunnel-cmd) | | ORA_API_KEY | journey | — (required) | Secret key (ora_sk_…), exchanged for a short-lived bearer token | | ORA_SCAN_API_KEY | audit, deep-journey | — (optional) | ora-issued scan API key; lifts every scan rate limit (issued manually by ora). deep-journey accepts it as a partner-key fallback | | ORA_PARTNER_API_KEY | deep-journey | — (optional) | ora-issued partner API key; unlocks --task and the 1000/24h keyed allowance |

Contract versioning

The audit types are generated from ora's served OpenAPI spec (pnpm contract:gen); the build is pinned to a contract version and CI fails when production drifts from the checked-in types. At runtime, the CLI prints one stderr warning when ora reports a newer contract than the build — upgrade with npm i -g @ora-ai/ax@latest.

Migrating from 0.1.x

  • ax scan is now ax audit (no alias).
  • --json prints the raw ora audit payload instead of the old reshaped envelope: stable check ids, layer ids, grade, topFixes, and contractVersion — key your scripts to those fields.
  • Audit API failures now exit 3 (usage errors stay 2).

Development

pnpm install
pnpm test            # vitest (watch)
pnpm test:ci         # single run + coverage
pnpm typecheck
pnpm lint
pnpm contract:gen    # regenerate src/contract/ from the served OpenAPI spec
pnpm build           # tsup → dist/main.cjs (bin) + dist/index.* (library)
pnpm smoke           # run the built binary the way a user would (needs build)
pnpm verify:pack     # check the tarball npm would publish (needs build)
node dist/main.cjs audit https://example.com

Manual testing without burning the live scan rate limit:

node scripts/mock-scan-server.mjs &
ORA_API_URL=http://localhost:8799 node dist/main.cjs audit https://example.com

To exercise the published-package experience locally: npm pack, then npx ./ora-ai-ax-<version>.tgz audit https://example.com, or pnpm link --global and use ax directly.

Releasing

Publishing runs from GitHub Actions only — Actions → Release → Run workflow, pick a patch/minor/major bump. See RELEASING.md for the runbook, required setup, and failure recovery.

License

MIT