install
source · Clone the upstream repo
git clone https://github.com/Intense-Visions/harness-engineering
Claude Code · Install into ~/.claude/skills/
T=$(mktemp -d) && git clone --depth=1 https://github.com/Intense-Visions/harness-engineering "$T" && mkdir -p ~/.claude/skills && cp -r "$T/agents/skills/claude-code/css-css-modules" ~/.claude/skills/intense-visions-harness-engineering-css-css-modules-422ba7 && rm -rf "$T"
manifest:
agents/skills/claude-code/css-css-modules/SKILL.mdsource content
CSS Modules
Scope CSS to components with CSS Modules for collision-free class names and co-located styles
When to Use
- Writing traditional CSS but needing guaranteed scoped class names
- Projects that prefer CSS files over utility classes
- Combining with Tailwind for component-specific styles that utilities cannot express
- Next.js or Vite projects where CSS Modules work out of the box
Instructions
- Name files with
suffix:.module.css
. The bundler generates unique class names.Button.module.css - Import styles as an object:
.import styles from './Button.module.css' - Apply classes via the styles object:
.className={styles.button} - Use
to inherit styles from other classes or modules.composes - For dynamic classes, use bracket notation:
.styles[variant] - CSS Modules are locally scoped by default. Use
to escape scoping.:global(.class)
/* Button.module.css */ .button { display: inline-flex; align-items: center; justify-content: center; padding: 0.5rem 1rem; border-radius: 0.375rem; font-weight: 500; transition: all 0.2s; } .primary { composes: button; background-color: var(--color-primary); color: white; } .primary:hover { filter: brightness(1.1); } .secondary { composes: button; background-color: var(--color-gray-100); color: var(--color-gray-900); } .large { padding: 0.75rem 1.5rem; font-size: 1.125rem; } .fullWidth { width: 100%; }
// Button.tsx import styles from './Button.module.css'; import clsx from 'clsx'; interface ButtonProps { variant?: 'primary' | 'secondary'; size?: 'default' | 'large'; fullWidth?: boolean; children: React.ReactNode; } function Button({ variant = 'primary', size = 'default', fullWidth, children }: ButtonProps) { return ( <button className={clsx( styles[variant], size === 'large' && styles.large, fullWidth && styles.fullWidth )} > {children} </button> ); }
Details
How it works: The bundler (Webpack, Vite, Next.js) transforms class names from
.button to .Button_button_a1b2c (component name + class name + hash). This guarantees no collisions between components.
TypeScript support: Generate type declarations for CSS Modules:
# typed-css-modules npm install -D typed-css-modules tcm src/ # Or use the Vite plugin npm install -D vite-plugin-css-modules-typescript
This creates
.module.css.d.ts files:
// Button.module.css.d.ts declare const styles: { readonly button: string; readonly primary: string; readonly secondary: string; readonly large: string; readonly fullWidth: string; }; export default styles;
composes keyword: Inherit styles from other classes:
.base { padding: 1rem; border-radius: 0.5rem; } .error { composes: base; border: 2px solid red; } /* .error gets both base and error styles */ /* Compose from another module */ .card { composes: surface from './shared.module.css'; }
:global escape hatch: Apply a class globally (useful for overriding library styles):
.wrapper :global(.third-party-class) { color: red; }
CSS Modules + Tailwind: Use CSS Modules for complex styles and Tailwind for utilities:
<div className={clsx(styles.card, 'p-4 flex gap-2')}>
When to use CSS Modules vs Tailwind: CSS Modules are better for complex pseudo-selectors, animations with many keyframes, and teams that prefer traditional CSS. Tailwind is better for rapid iteration and design consistency.
Source
https://github.com/css-modules/css-modules
Process
- Read the instructions and examples in this document.
- Apply the patterns to your implementation, adapting to your specific context.
- Verify your implementation against the details and edge cases listed above.
Harness Integration
- Type: knowledge — this skill is a reference document, not a procedural workflow.
- No tools or state — consumed as context by other skills and agents.
Success Criteria
- The patterns described in this document are applied correctly in the implementation.
- Edge cases and anti-patterns listed in this document are avoided.