Agent skill

Crxjs

by samber in samber/cc-skills

CRXJS Chrome extension development — true HMR for popup, options, content scripts, side panels, manifest-driven builds, dynamic content script imports (?script, ?script&module), and defineManifest…

MITAuto-check passedDevelopment

Install Crxjs

skills CLI
$ npx skills add samber/cc-skills --skill crxjs -a claude-code

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

GitHub CLI
$ gh skill install samber/cc-skills crxjs --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/samber/cc-skills.git skills-src && mkdir -p .claude/skills && cp -r skills-src/skills/crxjs .claude/skills/crxjs && 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
crxjs
GitHub stars
228
Token cost
~2.6k tokens
SKILL.md length
646 words
Files
1
Skills in repo
15
Repo updated
First seen
Licence
MIT

At a glance

CRXJS Chrome extension development — true HMR for popup, options, content scripts, side panels, manifest-driven builds, dynamic content script imports (?script, ?script&module), and defineManifest…

  • The user mentions CRXJS
  • SKILL.md covers Current status, Quick start, Vite config by framework and defineManifest — type-safe…, plus 9 more sections
  • Calls npm
  • @crxjs/vite-plugin

What it does

Crxjs is an agent skill from samber/cc-skills. CRXJS Chrome extension development — true HMR for popup, options, content scripts, side panels, manifest-driven builds, dynamic content script imports (?script, ?script&module), and defineManifest for type-safe manifests. Uses Vite as its build tool. Use when the user mentions CRXJS, crxjs, @crxjs/vite-plugin, 'extension with hot reload', 'HMR for chrome extension', or wants to set up a CRXJS-based Chrome extension project with any framework (React, Vue, Svelte, Solid, Vanilla). Also trigger when the user has an…

Its SKILL.md is about 2.6k tokens, which your agent loads only when the skill is triggered. It is a single SKILL.md file with no bundled scripts. Compatibility notes: Designed for Claude Code, Codex or similar harness. Requires git, node.

It sits in Development, covering Browser extensions and Type safety. It works with Vite, Chrome Extensions, React and Svelte. The repository describes itself as: 🧑🎨 A collection of agentic skills that works. The licence is MIT.

When your agent uses it

  • The user mentions CRXJS
  • @crxjs/vite-plugin
  • Extension with hot reload
  • HMR for chrome extension

Example prompts

  • “extension with hot reload”
  • “HMR for chrome extension”
  • “Use the crxjs skill to crxj Chrome extension development — true HMR for popup, options, content scripts, side panels, manifest-driven builds…”
  • “/crxjs”

Requirements

  • Node.js
  • Compatibility (from SKILL.md): Designed for Claude Code, Codex or similar harness. Requires git, node.
  • Pre-approved tools (allowed-tools): Read, Edit, Write, Glob, Grep, Bash(git:*), Bash(gh:*), Bash(npm:*)

What it can do on your machine

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

  • Tool permissions

    Pre-approves these tools, so the agent can use them without asking each time:

    • Read
    • Edit
    • Write
    • Glob
    • Grep
    • Bash(git:*)
    • Bash(gh:*)
    • Bash(npm:*)

    From allowed-tools in the SKILL.md frontmatter.

  • Runs code

    Shell commands in SKILL.md call:

    • npm

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

  • Network

    No URLs in SKILL.md. Its commands use npm, which can reach the network depending on how they are called.

    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.

  • Compatibility

    Designed for Claude Code, Codex or similar harness. Requires git, node.

    From compatibility in the SKILL.md frontmatter.

Context cost

Crxjs loads about 2.6k tokens when it runs. Until then it costs about 192 tokens; SKILL.md has 646 words of instructions outside code blocks.

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

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 samber/cc-skills at commit 123cb15, republished under its MIT licence (© samber). 646 words, ~2,582 tokens.

Download SKILL.mdSave it as .claude/skills/crxjs/SKILL.md (or your agent's skills folder).
name
crxjs
description
CRXJS Chrome extension development — true HMR for popup, options, content scripts, side panels, manifest-driven builds, dynamic content script imports (`?script`, `?script&module`), and `defineManifest` for type-safe manifests. Uses Vite as its build tool. Use when the user mentions CRXJS, crxjs, @crxjs/vite-plugin, 'extension with hot reload', 'HMR for chrome extension', or wants to set up a CRXJS-based Chrome extension project with any framework (React, Vue, Svelte, Solid, Vanilla). Also trigger when the user has an existing CRXJS project and wants to add features, fix HMR issues, or configure content scripts with CRXJS. For general Chrome extension architecture (messaging, CSP, storage, permissions) -> See `samber/cc-skills@chrome-extension` skill.
allowed-tools
Read, Edit, Write, Glob, Grep, Bash(git:*), Bash(gh:*), Bash(npm:*)
compatibility
Designed for Claude Code, Codex or similar harness. Requires git, node.
user-invocable
true
license
MIT
metadata.author
samber
metadata.version
1.1.0

CRXJS

CRXJS is a Chrome extension development tool that provides true HMR for popup, options, content scripts, and side panels. It reads your manifest to auto-generate the extension output, handles content script injection, and manages the service worker build. Under the hood it is a Vite plugin (@crxjs/vite-plugin).

Current status

  • Package: @crxjs/vite-plugin (v2.x stable, latest v2.4.0 as of March 2026)
  • Scaffolding: npm create crxjs@latest (always use @latest)
  • Maintained by: @Toumash and @FliPPeDround (since mid-2025)
  • GitHub: github.com/crxjs/chrome-extension-tools (~4k stars)
  • Vite compatibility: v3 through v8-beta

Quick start

bash
# Scaffold new project (picks framework interactively)
npm create crxjs@latest

# Or add to existing Vite project
npm install @crxjs/vite-plugin -D

Vite config by framework

CRXJS is added as a Vite plugin. The setup varies slightly per framework.

React
typescript
// vite.config.ts
import { defineConfig } from "vite";
import react from "@vitejs/plugin-react";
import { crx } from "@crxjs/vite-plugin";
import manifest from "./manifest.json";

export default defineConfig({
  plugins: [react(), crx({ manifest })],
});

Use @vitejs/plugin-react (not plugin-react-swc) for best HMR compatibility. If you must use SWC, cast the manifest:

typescript
import { ManifestV3Export } from "@crxjs/vite-plugin";
const manifest = manifestJson as ManifestV3Export;
Vue
typescript
import vue from "@vitejs/plugin-vue";
import { crx } from "@crxjs/vite-plugin";
import manifest from "./manifest.json";

export default defineConfig({
  plugins: [vue(), crx({ manifest })],
});
Svelte
typescript
import { svelte } from "@sveltejs/vite-plugin-svelte";
import { crx } from "@crxjs/vite-plugin";
import manifest from "./manifest.json";

export default defineConfig({
  plugins: [svelte(), crx({ manifest })],
});
Vanilla TypeScript
typescript
import { crx } from "@crxjs/vite-plugin";
import manifest from "./manifest.json";

export default defineConfig({
  plugins: [crx({ manifest })],
});

defineManifest — type-safe dynamic manifest

Instead of a static JSON file, use CRXJS's defineManifest for dynamic values and full TypeScript autocompletion:

typescript
// manifest.ts
import { defineManifest } from "@crxjs/vite-plugin";
import pkg from "./package.json";

export default defineManifest((config) => ({
  manifest_version: 3,
  name: config.command === "serve" ? `[DEV] ${pkg.name}` : pkg.name,
  version: pkg.version,
  description: pkg.description,
  permissions: ["storage", "activeTab", "scripting"],
  action: {
    default_popup: "src/popup/index.html",
    default_icon: {
      "16": "public/icons/icon16.png",
      "48": "public/icons/icon48.png",
    },
  },
  background: {
    service_worker: "src/background/index.ts",
    type: "module",
  },
  content_scripts: [
    {
      matches: ["https://*/*"],
      js: ["src/content/index.ts"],
      css: ["src/content/styles.css"],
    },
  ],
  options_page: "src/options/index.html",
  side_panel: { default_path: "src/sidepanel/index.html" },
  icons: {
    "16": "public/icons/icon16.png",
    "48": "public/icons/icon48.png",
    "128": "public/icons/icon128.png",
  },
}));

Import in vite.config.ts:

typescript
import manifest from "./manifest";
// ... crx({ manifest })

Type declarations

Add to a src/vite-env.d.ts or src/crxjs.d.ts:

typescript
/// <reference types="@crxjs/vite-plugin/client" />

This enables types for ?script and ?script&module imports.

HMR behavior by context

ContextHMRHow it works
PopupFull HMRWebSocket-based, state preserved
Options pageFull HMRSame as popup
Side panelFull HMRSame as popup
Content script (manifest)True HMRCRXJS injects loader + HMR client
Content script (dynamic)True HMRVia ?script import
Service workerAuto-reloadChanges trigger full extension reload
Main world scriptsNo HMRSkipped by CRXJS loader

Content script HMR works because CRXJS generates a loader script that imports an HMR preamble, the HMR client, and your actual script — enabling real module-level HMR without full page reload. This is CRXJS's main differentiator.

Dynamic content script imports

For content scripts injected programmatically (not in manifest), CRXJS provides special import suffixes:

typescript
// background.ts — ?script gives you a resolved path for executeScript
import contentScript from "./content?script";

chrome.action.onClicked.addListener(async (tab) => {
  await chrome.scripting.executeScript({
    target: { tabId: tab.id! },
    files: [contentScript],
  });
});

For main world injection (no HMR):

typescript
import mainWorldScript from "./inject?script&module";

await chrome.scripting.executeScript({
  target: { tabId },
  world: "MAIN",
  files: [mainWorldScript],
});

CRXJS plugin options

typescript
crx({
  manifest,
  browser: "chrome", // 'chrome' | 'firefox'
  contentScripts: {
    injectCss: true, // auto-inject CSS for content scripts
    hmrTimeout: 5000, // HMR connection timeout (ms)
  },
});

Development workflow

bash
# Start dev server (outputs to dist/ with HMR)
npm run dev

# 1. Open chrome://extensions
# 2. Enable "Developer mode"
# 3. Click "Load unpacked"
# 4. Select the dist/ directory
# 5. Edit code — popup/content scripts update instantly via HMR
# 6. Service worker changes trigger automatic extension reload

After loading once, subsequent npm run dev sessions reconnect automatically. No need to re-load the extension unless manifest.json changes.

Production build

bash
npm run build    # outputs to dist/

The dist/ directory is ready to zip and upload to Chrome Web Store:

bash
cd dist && zip -r ../extension.zip .

Disable Vite's module preload to avoid CWS rejection of inline scripts:

typescript
build: {
  modulePreload: false;
}

Known issues and workarounds

Tailwind CSS HMR in content scripts

New Tailwind classes may not trigger CSS updates in content scripts. Workaround: restart dev server after adding new utility classes. Improved in v2.4.0 but not fully resolved. Ensure injectCss: true in config.

WebSocket connection errors (ws://localhost:undefined/)

Cause: port mismatch between dev server and HMR config. Fix: explicitly set both to the same value:

typescript
server: {
  port: 5173,
  strictPort: true,
  hmr: { port: 5173 },
}
Show full SKILL.md (249 more words)Show less
"Manifest version 2 is deprecated" warning

If you see this, your manifest is being interpreted as MV2. Fix: ensure "manifest_version": 3 is set.

Content scripts not injecting on file:// URLs

Chrome requires the user to enable "Allow access to file URLs" in the extension settings at chrome://extensions. CRXJS cannot change this.

HMR stops working after Chrome update

CRXJS's HMR relies on injecting a content script that connects to the dev server's WebSocket. Chrome security updates occasionally break this. Fix: update to the latest CRXJS version, which tracks Chrome changes.

CRXJS vs alternatives

FeatureCRXJSWXTPlasmo
Content script HMRTrue HMRFile-based reloadPartial
Framework supportAny Vite frameworkAnyReact-focused
Abstraction levelThin (Vite plugin)Full frameworkFull framework
Messaging helpersNone (use chrome.* directly)Built-inBuilt-in
Storage wrappersNoneBuilt-inBuilt-in
Cross-browserChrome + FirefoxChrome + Firefox + SafariChrome + Firefox
File-based routingNoYesYes
Learning curveLow (know Vite, know CRXJS)MediumMedium

Choose CRXJS when: you want minimal abstraction over raw Chrome APIs and value content script HMR above all. CRXJS stays out of the way — no magic routing, no wrapper APIs, just your code with HMR.

Choose WXT when: you want conventions, built-in utilities, and cross-browser support.

Choose Plasmo when: you're React-focused and want the highest-level abstraction.

my-extension/
├── src/
│   ├── background/
│   │   └── index.ts
│   ├── content/
│   │   ├── index.ts
│   │   └── styles.css
│   ├── popup/
│   │   ├── index.html        <- CRXJS resolves HTML entry points
│   │   ├── App.tsx
│   │   └── main.tsx
│   ├── options/
│   │   ├── index.html
│   │   └── main.tsx
│   ├── sidepanel/
│   │   ├── index.html
│   │   └── main.tsx
│   └── shared/
│       ├── messages.ts
│       └── storage.ts
├── public/
│   └── icons/
├── manifest.ts               <- or manifest.json
├── vite.config.ts
├── tsconfig.json
└── package.json

CRXJS resolves HTML files referenced in the manifest automatically. Your popup.html can use standard <script type="module" src="./main.tsx"> and it works.

If you encounter a bug or unexpected behavior in CRXJS, open an issue at github.com/crxjs/chrome-extension-tools/issues.

© samber, MIT. Rendered from Markdown: HTML in the file is shown as text, images as links, and headings moved down two levels. Raw file

Files

Just SKILL.md in skills/crxjs of samber/cc-skills.

Open the folder on GitHubat commit 123cb15

Compare with similar skills

Crxjs 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.

Crxjs compared with similar skills
SkillStarsUsed inTokensAuto-checkLicenceRepo updated
Crxjs this skillsamber/cc-skills228—~2.6kAutomated safety check: PassMIT
Wxtmengxi-ream/read-frog10k—~500Automated safety check: PassGPL-3.0
Wayfinder Developmentslimani-dev/muraqib1281 repos~622Automated safety check: PassMIT
Wagmi Feature Developmentwevm/wagmi6.8k—~3.8kAutomated safety check: PassMIT
Design StyleCastor6/tactus3761 repos~2.1kAutomated safety check: PassApache-2.0
Deepseek Automationzhu1090093659/deepseek-pp1.9k—~2.1kAutomated safety check: NotesApache-2.0

Similar skills

  • Wxt

    mengxi-ream/read-frog

    Build browser extensions with WXT - a next-gen framework with file-based entrypoints, Vite builds, auto-imports, typed storage with migrations, content script UIs, and multi-browser MV2/MV3 support.

    10k GitHub stars~500 tokensUpdated today
    DevelopmentAuto-check passed
  • Wayfinder Development

    slimani-dev/muraqib

    A skill your agent uses for Laravel Wayfinder which auto-generates typed functions for Laravel controllers and routes.

    128 GitHub starsUsed in 1 repo~622 tokens
    Backend & APIsAuto-check passed
  • Walks through adding a Wagmi feature across its layers: a Viem-based core action, TanStack Query options, and React and Vue bindings.

    6.8k GitHub stars~3.8k tokensUpdated 7 days ago
    DevelopmentAuto-check passed
  • Design Style

    Castor6/tactus

    A skill your agent uses whenever the user asks to build, create, design, develop, improve, or style any frontend interface or visual element.

    376 GitHub starsUsed in 1 repo~2.1k tokens
    Frontend & DesignAuto-check passed
  • Deepseek Automation

    zhu1090093659/deepseek-pp

    A skill your agent uses when implementing, resuming, reviewing, or verifying the DeepSeek++ Codex-style automation feature in this repository.

    1.9k GitHub stars~2.1k tokensUpdated 1 mo ago
    DevelopmentAuto-check: notes
  • Markstream Custom Components

    Simon-He95/markstream-vue

    Override built-in Markstream node renderers and add trusted custom tags across Vue, React, Svelte, and Angular.

    3k GitHub stars~955 tokensUpdated 3 days ago
    DevelopmentAuto-check passed

More from samber/cc-skills

All 15 skills in this repo
  • Interviews you about objective, audience and context, then designs an end-of-article call to action with copy, placement, A/B test plan and accessibility check.

    228 GitHub stars~3.1k tokensUpdated 7 days ago
    Auto-check passed
  • Builds a PROSE.md writing guide that captures how a person or brand writes, such as vocabulary, sentence rhythm and signature moves, separate from emotional tone.

    228 GitHub stars~5.3k tokensUpdated 7 days ago
    Auto-check passed
  • Press Release Writer

    samber/cc-skills

    Drafts press releases that fit the release type, target media and region, after collecting the facts and checking that the story has a real news angle.

    228 GitHub stars~1.8k tokensUpdated 7 days ago
    Auto-check passed
  • Produces a training or workshop report as a Word file, with participant feedback and recommendations, drafted in Markdown first and converted once at the end.

    228 GitHub stars~2.7k tokensUpdated 7 days ago
    Auto-check passed
  • Site Launch Checklist

    samber/cc-skills

    Pre-launch checklist for shipping a new website or web app. An agent skill from samber/cc-skills.

    228 GitHub stars~13k tokensUpdated 7 days ago
    Auto-check: notes
  • Conventional Git

    samber/cc-skills

    Conventional Commits v1.0.0 branch naming, worktree naming, and commit message standards for GitHub and GitLab projects.

    228 GitHub stars~1.8k tokensUpdated 7 days ago
    Auto-check passed

Categories

Questions about Crxjs

What does Crxjs do?

CRXJS Chrome extension development — true HMR for popup, options, content scripts, side panels, manifest-driven builds, dynamic content script imports (?script, ?script&module), and defineManifest…. Crxjs is an agent skill from samber/cc-skills.script&module), and defineManifest for type-safe manifests.

When should I use Crxjs?

Crxjs fits situations like: the user mentions CRXJS; @crxjs/vite-plugin; extension with hot reload; HMR for chrome extension.

How do I install Crxjs in Claude Code?

Run `npx skills add samber/cc-skills --skill crxjs -a claude-code`. Or copy the skill folder (skills/crxjs in samber/cc-skills) into .claude/skills/crxjs in your project. Claude Code loads it when a task matches its description.

How do I install Crxjs in Codex?

Run `npx skills add samber/cc-skills --skill crxjs -a codex`. Or copy the skill folder (skills/crxjs in samber/cc-skills) into .agents/skills/crxjs in your project. Codex loads it when a task matches its description.

Can I use Crxjs 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 samber/cc-skills --skill crxjs -a cursor` (or -a gemini-cli, github-copilot or opencode for the others). To copy it by hand, put the folder in .cursor/skills/crxjs, .gemini/skills/crxjs, .github/skills/crxjs and .opencode/skills/crxjs in your project.

What does Crxjs need to run?

Going by SKILL.md and its folder, Crxjs needs the command-line tools its instructions call (npm). Our summary lists: Node.js. Its frontmatter pre-approves these tools: Read, Edit, Write, Glob, Grep, Bash(git:*), Bash(gh:*), Bash(npm:*). Compatibility (from SKILL.md): Designed for Claude Code, Codex or similar harness. Requires git, node..

Does Crxjs access the network?

SKILL.md contains no URLs. Its commands use npm, which can reach the network depending on how they are called. This is read from the text; nothing was executed.

Is Crxjs 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 Crxjs use?

Crxjs is published under the MIT licence (declared in SKILL.md). It allows redistribution, so the full SKILL.md is shown on this page.

How many tokens does Crxjs use?

About 2.6k tokens (SKILL.md is roughly 10k 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 Crxjs?

Skills that share tags, products or a category with Crxjs: Wxt (mengxi-ream/read-frog, 10k stars), Wayfinder Development (slimani-dev/muraqib, 128 stars), Wagmi Feature Development (wevm/wagmi, 6.8k stars) and Design Style (Castor6/tactus, 376 stars). The comparison table on this page puts their stars, adoption, token cost, safety result and licence side by side.

Who maintains Crxjs?

samber (a GitHub user) maintains it in samber/cc-skills, which has 228 GitHub stars. The repository holds 15 skills in this directory. The repository was last updated on October 1, 2026.

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