Skip to content
Back to skills

Component Patterns

ASecurity

Guidelines for organizing React components in Shadow Master. Use when creating new components, deciding between single-file vs subfolder structure, or understanding the component architecture.

  • 666 stars
  • 0 votes
  • 0 copies
  • 3 views
  • Added February 8, 2026
developmenttypescriptgobashreactapidocumentation

Works with

  • terminal
  • api

Security analysis

A100/100

Scanned February 12, 2026

npx -y skills add majiayu000/claude-skill-registry --skill component-patterns --agent claude-code

Installs into .claude/skills of the current project.

Are you the author of Component Patterns?

Add the live security badge to your README. It updates with every re-scan.

Security grade badge for Component Patterns
[![Security: A — Skills Directory](https://www.skillsdirectory.com/api/skills/majiayu000-component-patterns/badge)](https://www.skillsdirectory.com/skills/majiayu000-component-patterns)

More formats (shields.io, HTML) on the badges page. Keep it an A: scan every change in CI with Pro.

Download with Pro
SKILL.md
---
name: component-patterns
description: Guidelines for organizing React components in Shadow Master. Use when creating new components, deciding between single-file vs subfolder structure, or understanding the component architecture.
allowed-tools: Read, Grep, Glob
---

# Component Organization Patterns

Guidelines for structuring React components in the Shadow Master codebase.

## Component Directory Overview

```
/components/                    # 130+ components total
├── index.ts                    # Root exports (DiceRoller only)
├── *.tsx                       # 6 standalone utility components
├── action-resolution/          # 3 components - dice pool building
├── auth/                       # 1 component - email verification
├── character/                  # 12 components - character sheet display
├── combat/                     # 4 components - combat tracking UI
├── creation/                   # 83 components - character creation
│   ├── *.tsx                   # 14 top-level cards
│   ├── shared/                 # 14 reusable utilities
│   └── {feature}/              # 17 feature subfolders
├── cyberlimbs/                 # 6 components - augmentation UI
├── sync/                       # 2 components - ruleset sync status
└── ui/                         # 2 components - BaseModal, Tooltip
```

---

## Decision Flowchart

```
Does the component have modals?
├─ Yes → Create subfolder, extract modals
└─ No → Does it have reusable Row/ListItem components?
        ├─ Yes, used elsewhere → Create subfolder
        └─ No → Keep as single file with internal helpers
```

---

## When to Use a Subfolder

Create a subfolder with `index.ts` when:

- Component has one or more **modals** (selection dialogs, forms, etc.)
- Component has **reusable row/list item** components used in multiple places
- Component exceeds ~600 lines with clear separable concerns
- Component has distinct UI pieces that could be tested independently

**Subfolder structure:**

```
/components/{area}/{feature}/
├── FeatureCard.tsx           # Main component
├── FeatureModal.tsx          # Selection/edit modal
├── FeatureRow.tsx            # Optional: if row is complex/reusable
├── constants.ts              # Optional: magic values, options arrays
├── types.ts                  # Optional: feature-specific types
├── utils.ts                  # Optional: feature-specific helpers
├── index.ts                  # Re-exports public API
```

**Index file pattern:**

```typescript
// index.ts - export only public API
export { FeatureCard } from "./FeatureCard";
export { FeatureModal } from "./FeatureModal"; // Only if used externally
```

---

## When to Keep as Single File

Keep as a single file when:

- Component is self-contained with only **internal helper components**
- Internal components are tightly coupled and only make sense within the parent
- Component is under ~400 lines with straightforward structure
- No modals or independently reusable pieces

---

## Component Areas

### Root-Level Components (6 files)

Standalone utility components that don't fit a specific feature area:

| Component              | Purpose                             |
| ---------------------- | ----------------------------------- |
| `DiceRoller.tsx`       | Dice rolling UI with edge rerolls   |
| `AugmentationCard.tsx` | Generic augmentation display        |
| `EssenceDisplay.tsx`   | Essence tracking visualization      |
| `ThemeProvider.tsx`    | Dark/light mode context             |
| `EnvironmentBadge.tsx` | Environment indicator (dev/staging) |
| `NotificationBell.tsx` | Notification center UI              |

---

### `/components/ui/` - Shared UI Primitives

Low-level accessible components used across the app. Built on React Aria.

| Component       | Exports                                              |
| --------------- | ---------------------------------------------------- |
| `BaseModal.tsx` | BaseModal, ModalHeader, ModalBody, ModalFooter       |
| `Tooltip.tsx`   | Tooltip, TooltipTrigger, TooltipContent, InfoTooltip |

**When to add here:** Generic UI primitives with no business logic.

---

### `/components/auth/` - Authentication Components

| Component                     | Purpose                      |
| ----------------------------- | ---------------------------- |
| `EmailVerificationBanner.tsx` | Prompts user to verify email |

---

### `/components/action-resolution/` - Dice Pool Building

Components for building and displaying action resolution dice pools.

| Component               | Purpose                          |
| ----------------------- | -------------------------------- |
| `ActionHistory.tsx`     | List of past action rolls        |
| `ActionPoolBuilder.tsx` | Construct dice pools for actions |
| `EdgeTracker.tsx`       | Edge point tracking and spending |

**Note:** No index.ts - import directly from files.

---

### `/components/character/` - Character Sheet Display

Components for viewing active characters (not creation). No index file - import directly.

| Component                 | Purpose                           |
| ------------------------- | --------------------------------- |
| `AdeptPowerList.tsx`      | Display adept powers and PP       |
| `AutosoftManager.tsx`     | Manage vehicle/drone autosofts    |
| `CyberdeckConfig.tsx`     | Cyberdeck attribute configuration |
| `DroneNetworkManager.tsx` | RCC drone network management      |
| `JumpInControl.tsx`       | Vehicle/drone jump-in interface   |
| `MagicSummary.tsx`        | Magic rating, tradition, drain    |
| `MatrixActions.tsx`       | Matrix action buttons and state   |
| `MatrixSummary.tsx`       | Matrix attributes and programs    |
| `ProgramManager.tsx`      | Running programs management       |
| `RiggingSummary.tsx`      | Rigging stats and VCR mode        |
| `Spellbook.tsx`           | Spell list with casting interface |
| `VehicleActions.tsx`      | Vehicle action buttons            |

---

### `/components/combat/` - Combat Tracking

Components for running combat encounters. Has index.ts and co-located tests.

| Component                 | Purpose                              |
| ------------------------- | ------------------------------------ |
| `CombatTracker.tsx`       | Initiative order and turn management |
| `ActionSelector.tsx`      | Action selection with categories     |
| `ConditionMonitor.tsx`    | Health/damage tracking               |
| `OpposedTestResolver.tsx` | Opposed test dice rolling            |

---

### `/components/cyberlimbs/` - Cyberlimb Management

Components for cyberlimb augmentation display and modification.

| Component                       | Purpose                       |
| ------------------------------- | ----------------------------- |
| `CyberlimbCard.tsx`             | Individual cyberlimb display  |
| `CyberlimbList.tsx`             | List all installed cyberlimbs |
| `CyberlimbDetailPanel.tsx`      | Detailed cyberlimb info panel |
| `CyberlimbInstallModal.tsx`     | Install new cyberlimb         |
| `CyberlimbEnhancementModal.tsx` | Add attribute enhancements    |
| `CyberlimbAccessoryModal.tsx`   | Add accessories to limb       |

---

### `/components/sync/` - Ruleset Synchronization

Components for displaying ruleset sync status and migration.

| Component             | Purpose                              |
| --------------------- | ------------------------------------ |
| `StabilityShield.tsx` | Visual sync status indicator         |
| `MigrationWizard.tsx` | Guide user through ruleset migration |

---

### `/components/creation/` - Character Creation

The largest component area (83 components). Organized by feature with shared utilities.

#### Top-Level Cards (14 files)

Single-file cards without complex modals:

| Card                    | Purpose                       |
| ----------------------- | ----------------------------- |
| `PrioritySelectionCard` | Priority table selection      |
| `AttributesCard`        | Attribute allocation          |
| `SkillsCard`            | Active skills management      |
| `SpellsCard`            | Spell selection for mages     |
| `AdeptPowersCard`       | Adept power selection         |
| `ComplexFormsCard`      | Technomancer complex forms    |
| `AugmentationsCard`     | Cyberware/bioware selection   |
| `VehiclesCard`          | Vehicle/drone acquisition     |
| `WeaponsPanel`          | Weapon purchases              |
| `GearTabsCard`          | Tabbed gear interface         |
| `DerivedStatsCard`      | Calculated stats display      |
| `CharacterInfoCard`     | Name, background, description |
| `EditionSelector`       | Edition selection dropdown    |
| `CreationErrorBoundary` | Error boundary for creation   |

#### Feature Subfolders (17 directories)

| Folder                 | Components | Pattern                                 |
| ---------------------- | ---------- | --------------------------------------- |
| `/armor`               | 4          | Panel + Row + PurchaseModal + ModModal  |
| `/augmentations`       | 4          | 4 specialized modals                    |
| `/contacts`            | 3          | Card + Modal + KarmaConfirm             |
| `/foci`                | 2          | Card + Modal                            |
| `/gear`                | 4          | Panel + Row + 2 Modals                  |
| `/identities`          | 6          | Card + Identity + 3 modal types         |
| `/knowledge-languages` | 5          | Card + 2 Row types + 2 Modals           |
| `/magic-path`          | 2          | Card + Modal + utilities                |
| `/matrix-gear`         | 2          | Card + Modal                            |
| `/metatype`            | 2          | Card + Modal                            |
| `/qualities`           | 3          | Card + SelectionModal + DetailCard      |
| `/shared`              | 14         | Reusable utilities and hooks            |
| `/skills`              | 10         | Panel + ListItem + 8 specialized modals |
| `/spells`              | 2          | ListItem + Modal                        |
| `/vehicles`            | 4          | 4 specialized modals                    |
| `/weapons`             | 4          | Row + 3 Modals                          |

#### Shared Utilities (`/creation/shared/`)

| Component                       | Purpose                         |
| ------------------------------- | ------------------------------- |
| `CreationCard.tsx`              | Standard card wrapper           |
| `BudgetIndicator.tsx`           | Resource budget display         |
| `CardSkeleton.tsx`              | Loading skeleton                |
| `EmptyState.tsx`                | Empty list state                |
| `KarmaConversionModal.tsx`      | Nuyen ↔ Karma conversion        |
| `RatingSelector.tsx`            | 1-6 rating picker               |
| `Stepper.tsx`                   | +/- increment control           |
| `SummaryFooter.tsx`             | Card summary footer             |
| `ValidationBadge.tsx`           | Validation status indicator     |
| `BulkQuantitySelector.tsx`      | Quantity picker for bulk items  |
| `LifestyleModificationSelector` | Lifestyle mod picker            |
| `LifestyleSubscriptionSelector` | Lifestyle subscription picker   |
| `useKarmaConversionPrompt.ts`   | Hook for karma conversion modal |

---

## Adding Components by Area

### Adding a Creation Card

1. **Determine structure** using the decision flowchart
2. **Create in** `/components/creation/` or `/components/creation/{feature}/`
3. **Use `CreationCard` wrapper** from `/components/creation/shared/`
4. **Add to `SheetCreationLayout.tsx`** in appropriate column
5. **Update `CreationState` type** in `/lib/types/creation.ts` if needed
6. **Export from `/components/creation/index.ts`**

### Adding a Combat Component

1. Create in `/components/combat/`
2. Export from `/components/combat/index.ts`
3. Add co-located test in `/components/combat/__tests__/`

### Adding a Character Sheet Component

1. Create in `/components/character/`
2. Import directly from file (no index.ts)
3. Add to relevant page in `/app/characters/[id]/`

### Adding a Cyberlimb Component

1. Create in `/components/cyberlimbs/`
2. Export from `/components/cyberlimbs/index.ts`
3. Export types if needed for external use

### Adding a UI Primitive

1. Create in `/components/ui/`
2. Build on React Aria for accessibility
3. Export from `/components/ui/index.ts`
4. No business logic - pure presentation

---

## Adding a New API Endpoint

1. Create `/app/api/{path}/route.ts`
2. Export HTTP method handlers (GET, POST, PUT, DELETE)
3. Follow authentication pattern (getSession → validate user)
4. Call storage layer functions
5. Return JSON responses

---

## Adding a New Ruleset Module

1. Define module type in `/lib/types/edition.ts`
2. Add module to book payload in `/data/editions/{editionCode}/`
3. Update merge logic in `/lib/rules/merge.ts` if special handling needed
4. Create hook in `RulesetContext.tsx` for easy access

---

## Key Reference Files

- `components/ui/BaseModal.tsx` - Accessible modal foundation
- `components/creation/shared/CreationCard.tsx` - Card wrapper pattern
- `components/creation/SkillsCard.tsx` - Modal-based editing example
- `components/combat/CombatTracker.tsx` - Combat component with tests
- `components/cyberlimbs/index.ts` - Feature folder export pattern
- `app/characters/create/sheet/components/SheetCreationLayout.tsx` - Three-column layout

---

## Component Diagram Generation

Mermaid diagrams are auto-generated from the component structure.

### Commands

```bash
# Preview all areas to stdout
pnpm generate-diagrams

# Generate specific area
pnpm generate-diagrams --area=combat
pnpm generate-diagrams --area=creation

# Update documentation files
pnpm generate-diagrams --output=files

# Verbose mode with component counts
pnpm generate-diagrams --verbose
```

### Output Locations

| Mode              | Location                                   |
| ----------------- | ------------------------------------------ |
| `--output=stdout` | Prints to terminal (default)               |
| `--output=files`  | Writes to `/docs/architecture/components/` |

### Diagram Color Key

| Color  | Hex       | Component Type | Naming Pattern                            |
| ------ | --------- | -------------- | ----------------------------------------- |
| Blue   | `#3b82f6` | Container      | `*Card.tsx`, `*Panel.tsx`, `*Tracker.tsx` |
| Purple | `#8b5cf6` | Modal          | `*Modal.tsx`                              |
| Green  | `#22c55e` | Row            | `*Row.tsx`, `*ListItem.tsx`               |
| Orange | `#f59e0b` | Hook           | `use*.ts`, `*Context.tsx`                 |
| Gray   | `#6b7280` | Shared         | Everything else                           |

### When to Regenerate

Run `pnpm generate-diagrams --output=files` after:

- Adding a new component folder
- Adding/removing modals or cards
- Reorganizing component structure
- Before major documentation updates

### Validation

```bash
# Validate creation docs structure (doesn't regenerate)
pnpm validate-creation-docs --verbose
```

---

## Documentation Structure

### Hand-Written (detailed)

`/docs/architecture/creation-components/` - Detailed creation component docs with:

- Component descriptions
- Props documentation
- Usage patterns
- Context dependencies

### Auto-Generated (overview)

`/docs/architecture/components/` - Generated hierarchy diagrams:

- Mermaid component trees
- Summary tables
- Color-coded by type

---

## Index File Conventions

| Area                 | Has index.ts? | Reason                           |
| -------------------- | ------------- | -------------------------------- |
| `/ui`                | Yes           | Stable public API                |
| `/combat`            | Yes           | Cohesive feature set             |
| `/cyberlimbs`        | Yes           | Cohesive feature set             |
| `/sync`              | Yes           | Cohesive feature set             |
| `/creation`          | Yes           | Organized by phases              |
| `/character`         | No            | Loosely coupled, import directly |
| `/action-resolution` | No            | Loosely coupled, import directly |
| `/auth`              | No            | Single component                 |

Attribution

Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.

Comments

Loading comments…

Newsletter

Get the weekly list of safe new skills, and the ones we pulled.