
Component Engineering
- 80 installs
- 125 repo stars
- Updated February 4, 2026
- igorwarzocha/opencode-workflows
Build and review React components against a formal standard for accessibility, composition, and styling with data attributes and CVA.
About
A skill embodying a formal specification for accessible, composable React components. A developer uses it via /component-create and /component-review to build or audit components against composition, accessibility, and styling pillars.
- asChild composition, keyboard/ARIA maps, and cn/data-slot/CVA styling references
- /component-review audits for monolithic patterns vs composition
Component Engineering by the numbers
- 80 all-time installs (skills.sh)
- +4 installs in the week ending Aug 2, 2026 (Skillselion tracking)
- Ranked #1,109 of 2,245 Frontend Development skills by installs in the Skillselion catalog
- Data as of Aug 2, 2026 (Skillselion catalog sync)
npx skills add https://github.com/igorwarzocha/opencode-workflows --skill component-engineeringAdd your badge
Show developers this skill is listed on Skillselion. Paste this into your README.
| Installs | 80 |
|---|---|
| repo stars | ★ 125 |
| Last updated | February 4, 2026 |
| Repository | igorwarzocha/opencode-workflows ↗ |
What it does
Build and review React components against a formal standard for accessibility, composition, and styling with data attributes and CVA.
Files
Component Engineering Specification
<overview> This skill embodies the formal standard for building professional, accessible, and composable React artifacts. </overview>
<context name="Knowledge Deep-Dives"> You MUST read these reference files to perform your duties:
- Architecture:
composition.md- asChild, Taxonomy, Composition. - Accessibility:
accessibility.md- Keyboard maps, ARIA, Focus management. - Styling:
styling.md-cnutility, Data attributes, CVA, Design tokens.
</context>
<workflow>
<phase name="review">
/component-review [file]
Strictly audit the file against the specification pillars. 1. You MUST read all reference files in the references/ directory before proceeding. 2. Classify the artifact using taxonomy.md. 3. Evaluate Accessibility: You MUST check keyboard support and semantic HTML against accessibility.md. 4. Evaluate Architecture: You MUST check for monolithic patterns vs composition against composition.md. 5. Evaluate Styling: Look for data-slot usage and prop spreading against styling.md. </phase>
<phase name="create">
/component-create [name] [intent]
Build a new artifact following the "Architecture First" workflow. 1. You MUST read the relevant references/*.md files to select the correct patterns. 2. Choose the Taxonomy type. 3. Select the base Semantic Element or Headless Primitive. 4. You MUST implement the Keyboard Map. 5. You MUST apply asChild support if the component is an activator/trigger. 6. You MUST expose Data Attributes (data-state, data-slot). 7. Use the cn utility for class merging. </phase>
</workflow>
Accessibility (a11y) & State Reference
<overview> Accessibility is a baseline requirement. All components MUST be usable by everyone, including keyboard-only and screen-reader users. </overview>
<rules>
1. Semantic HTML & Keyboard Maps
- Foundation: You MUST start with native elements (
<button>,<select>). - Keyboard Navigation: All interactive elements MUST be reachable via
Tab. - Keyboard Map Implementation:
const handleKeyDown = (e: React.KeyboardEvent) => {
switch(e.key) {
case 'ArrowDown': focusNext(); break;
case 'Escape': close(); break;
case 'Enter': case ' ': select(); break;
}
};2. ARIA Patterns
- Role: Define what it is (
role="menu",role="dialog"). - State: Describe dynamic status (
aria-expanded,aria-invalid,aria-checked). - Properties: Define relationships (
aria-controls="id",aria-labelledby="id"). - Live Regions: Use
aria-live="polite"for dynamic content updates (e.g., "3 results found").
3. Focus Management
- Focus Trapping: You MUST use for Modals/Dialogs to keep focus inside while open.
- Focus Restoration: You MUST return focus to the trigger element when a component closes.
- Focus Visible: Use
:focus-visiblein CSS to show focus indicators only for keyboard users.
4. Color & Contrast
- WCAG Ratios: 4.5:1 for normal text, 3:1 for large text.
- Color Independence: You MUST NOT convey info with color alone. Use icons or text labels.
5. Controlled vs. Uncontrolled State
Professional components SHOULD support both modes.
- Controlled: Parent owns state via
valueandonChange. - Uncontrolled: Component owns state via
defaultValue. - Implementation: Use
useControllableState(from Radix UI or similar) to merge both paths seamlessly.
const [value, setValue] = useControllableState({
prop: controlledValue,
defaultProp: defaultValue,
onChange: onValueChange,
});</rules>
Composition & Component Architecture Reference
<overview> Composition is the foundation of modern, flexible UI. You MUST distribute responsibility across multiple cooperating components instead of using monolithic "god components" with dozens of props. </overview>
<instructions>
Pillar 1: Composable Components
Break complex UIs into focused sub-components. Follow the Root-Subpart pattern.
Anti-pattern: The Monolith
// ❌ Hard to customize, leads to prop explosion
<Accordion title="Items" data={data} headerClassName="..." contentClassName="..." />Pro-pattern: Composition
// ✅ Flexible, semantic, no wrapper hell
<Accordion.Root value="item-1">
<Accordion.Item value="item-1">
<Accordion.Trigger>Title</Accordion.Trigger>
<Accordion.Content>Content</Accordion.Content>
</Accordion.Item>
</Accordion.Root>Pillar 2: asChild (Slot Pattern)
The asChild prop allows a component to merge its behaviors and props into its immediate child, eliminating extra wrapper elements.
Usage with Radix UI Slot
import { Slot } from "@radix-ui/react-slot";
function Button({ asChild, ...props }) {
const Comp = asChild ? Slot : "button";
return <Comp {...props} />;
}
// Usage: Link styled as a Button
<Button asChild>
<a href="/home">Home</a>
</Button>Pillar 3: Single Element Wrapping
Each exported component SHOULD wrap exactly one HTML or JSX element.
- Why: Allows direct prop spreading, easy styling overrides, and predictable DOM structure.
- Rule: If you need to style a nested part, you MUST export it as a separate component (e.g.,
CardHeader).
Pillar 4: Polymorphism (The 'as' prop)
Allows the consumer to specify the HTML element.
- Preference: You SHOULD prefer
asChildfor interactive components; useasfor simple typographic or layout elements.
</instructions>
<context name="Artifact Taxonomy"> 1. Primitive: Headless, behavior-only foundation (e.g., Radix Dialog). 2. Component: Styled, reusable unit (e.g., Button). 3. Block: Composition solving a specific product use case (e.g., PricingTable). 4. Pattern: Documentation of a recurring composition (e.g., Typeahead). 5. Template: Page-level scaffold with routing/providers. 6. Utility: Non-visual logic (e.g., useId, cn). </context>
Distribution & Ownership Reference
<overview> Choosing the right distribution model depends on the required ownership and customization level. </overview>
<context>
Distribution Models
1. Registry (Source Distribution)
Source code is copied directly into the project (e.g., shadcn/ui).
- Pros: Full ownership, zero runtime overhead, easy customization.
- Cons: Manual updates, code duplication.
2. NPM (Package Distribution)
Pre-built, versioned code installed as a dependency.
- Pros: Version management, simplified installation.
- Cons: Hard to customize, black-box implementation.
</context>
<rules>
Transparency Principle
In open-source, consumers SHOULD benefit from visibility.
- You SHOULD provide source maps and readable code.
- You MUST document project structure and dependencies clearly.
- You MUST include migration guides for breaking changes.
</rules>
Component Patterns Reference
<rules>
Accessibility Checklist
- [ ] You MUST NOT use
onClickon<div>withoutroleandtabIndex. - [ ] SVGs MUST have
aria-hidden="true"or a<title>. - [ ] Focus indicators MUST be visible.
- [ ] Form inputs MUST have associated
<label>oraria-label.
</rules>
<context>
Composition Patterns
- Root: Container with context provider.
- Trigger: Activator using
asChild. - Content: The main displayed part.
Naming Conventions
- You SHOULD use standard suffixes:
Trigger,Content,Header,Footer,Title,Description. - You MUST use kebab-case for
data-slot.
</context>
Styling & Theming Reference
<overview> Modern component libraries SHOULD use a combination of Tailwind CSS, design tokens, and attribute-driven styling. </overview>
<instructions>
1. The cn Utility (Class Merging)
You MUST combine clsx (conditional logic) and tailwind-merge (intelligent override resolution).
import { clsx, type ClassValue } from 'clsx';
import { twMerge } from 'tailwind-merge';
export function cn(...inputs: ClassValue[]) {
return twMerge(clsx(inputs));
}2. Class Variance Authority (CVA)
Declarative API for managing component variants.
const buttonVariants = cva("base-classes", {
variants: {
variant: {
primary: "bg-blue-500 text-white",
destructive: "bg-red-500 text-white",
},
size: {
sm: "h-8 px-3",
md: "h-10 px-4",
}
},
defaultVariants: { variant: "primary", size: "md" }
});3. Attribute-Driven Styling
You MUST use data attributes to expose internal state to CSS.
- data-state: Visual states (
open,closed,active). - data-slot: Stable identifiers for sub-parts (
data-slot="trigger"). - Benefit: No need for
openClassNameprops. Style from outside withdata-[state=open]:opacity-100.
4. Design Tokens (Semantic Variables)
You SHOULD separate theme from usage using CSS variables.
:root {
--background: oklch(1 0 0);
--primary: oklch(0.2 0 0);
}
.dark {
--background: oklch(0.1 0 0);
}</instructions>
<context name="Distribution Principles">
- Registry (Source): Users copy code directly (e.g., shadcn/ui). High ownership, easy customization.
- NPM (Package): Pre-built dependency. Centralized updates, harder to customize.
- Transparency: You MUST always provide source code access or clear documentation.
</context>
Artifact Taxonomy Reference
<overview> Use these heuristics to classify and name UI artifacts. </overview>
<context>
1. Primitive
Headless, unstyled behavioral foundation. You MUST encapsulate semantics, focus, keyboard, and ARIA.
- Example: Radix UI Dialog.
2. Component
Styled, reusable UI unit. You MUST add visual design to primitives.
- Example: shadcn/ui Button.
3. Pattern
Specific composition of primitives/components solving a recurring problem. Independent of implementation.
- Example: Form validation with inline errors.
4. Block
Opinionated, production-ready composition for a specific use case (e.g., Pricing Table). Trades generality for speed.
5. Page
Complete single-route view composed of multiple blocks.
6. Template
Multi-page collection or full-site scaffold.
7. Utility
Non-visual helper for ergonomics or composition (e.g., hooks, class utilities).
</context>