Skip to content

Commit ed95abb

Browse files
committed
chore(rules): sync generated rules and docs for bun testing
1 parent 588a8b4 commit ed95abb

33 files changed

+1644
-427
lines changed
Lines changed: 17 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,37 +1,42 @@
11
---
22
description: Project overview and context for react-router-starter
3+
globs: **/*
34
alwaysApply: true
45
---
56

67
# Project Context
78

89
## What This Repo Is
910

10-
**react-router-starter** is a monorepo starter for React Router 7 apps with best practices from reportory: Storybook, @lambdacurry/forms, Vitest + React Testing Library, and shared Cursor rules.
11+
**react-router-starter** is a monorepo starter for React Router 7 apps with best practices from reportory: Storybook, @lambdacurry/forms, Bun test + React Testing Library, and shared AI rules.
1112

1213
## Structure
1314

1415
- **apps/todo-app** – Reference app (React Router 7, Vite, Tailwind v4, forms, Storybook, tests).
1516
- **packages/** – Shared packages (e.g. `@todo-starter/ui`, `@todo-starter/utils`) used by apps.
16-
- **.cursorrules/** – Cursor AI rules (project context, React Router, Storybook, forms, testing, monorepo, UI).
17+
- **ai-rules/** – Source-of-truth AI rules (project context, React Router, Storybook, forms, testing, monorepo, UI).
18+
- **.cursor/rules/** – Generated Cursor rules (do not edit directly).
19+
- **AGENTS.md / CLAUDE.md / GEMINI.md** – Generated agent rules (do not edit directly).
1720

18-
## Issue Tracking
21+
## Issue Tracking (Beads)
1922

20-
This project uses **Beads (bd)** for issues. See `AGENTS.md` for workflow.
23+
Beads is required **only** when running Ralph loops or when a task explicitly comes from Beads. For ad-hoc work, you can skip Beads.
24+
25+
When Beads is in use, follow `.devagent/plugins/ralph/AGENTS.md` and use the CLI:
2126

2227
```bash
2328
bd ready # Find available work
2429
bd show <id> # View issue details
2530
bd update <id> --status in_progress # Claim work
26-
bd close <id> # Complete work
31+
bd update <id> --status closed # Complete work
2732
bd sync # Sync with git
2833
```
2934

3035
## Quality Gates (todo-app)
3136

3237
From `apps/todo-app/package.json`:
3338

34-
- **Test:** `npm run test:run` or `npm run test:ci` (Vitest)
39+
- **Test:** `bun run test:run` or `bun run test:ci` (Bun test)
3540
- **Lint:** `npm run lint` (Biome)
3641
- **Typecheck:** `npm run typecheck` (tsc)
3742
- **Build:** `npm run build` (react-router build)
@@ -42,10 +47,12 @@ Run these from `apps/todo-app` or via workspace root scripts if defined.
4247
## Conventions
4348

4449
- **Routing:** File-based routes in `app/routes/`; use loaders/actions and route types.
45-
- **Forms:** @lambdacurry/forms + remix-hook-form + Zod; see `.cursorrules/lambda-curry-forms.mdc`.
46-
- **Tests:** Vitest + React Testing Library; use `renderWithRouter` for router-dependent components; see `apps/todo-app/TESTING.md` and `.cursorrules/testing-best-practices.mdc`.
50+
- **Forms:** @lambdacurry/forms + remix-hook-form + Zod; see `ai-rules/lambda-curry-forms.md`.
51+
- **Tests:** Bun test + React Testing Library; use `renderWithRouter` for router-dependent components; see `apps/todo-app/TESTING.md` and `ai-rules/testing-best-practices.md`.
4752
- **Styling:** Tailwind CSS v4; mobile-first; prefer existing UI components.
4853

49-
## Rule Order
54+
## AI Rules Workflow
5055

51-
Cursor rules in `.cursorrules/` are applied as configured. `00-project-context.mdc` is intended to load first (naming prefix) to establish project context; other rule files add domain-specific guidance (React Router, Storybook, forms, testing, monorepo, UI).
56+
- **Edit source rules** in `ai-rules/`
57+
- **Generate platform files** with `ai-rules generate`
58+
- **Check sync** with `ai-rules status`
File renamed without changes.
Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
---
2+
description: Monorepo structure, package boundaries, and workspace conventions
3+
globs: **/*
4+
alwaysApply: true
5+
---
6+
7+
# Monorepo Rules
8+
9+
## Package Structure
10+
- `apps/` - Applications (todo-app)
11+
- `packages/` - Shared packages (ui, utils)
12+
- Each package has its own package.json with proper exports
13+
14+
## Workspace Dependencies
15+
- Use `workspace:*` for internal package dependencies
16+
- Keep external dependencies in sync across packages
17+
- Use peerDependencies for shared libraries like React
18+
19+
## Import Patterns
20+
```tsx
21+
// Import from workspace packages
22+
import { Button } from '@todo-starter/ui';
23+
import { cn, type Todo } from '@todo-starter/utils';
24+
25+
// Import from local files
26+
import { TodoItem } from '~/components/todo-item';
27+
import type { Route } from './+types/home';
28+
```
29+
30+
## Package Naming
31+
- Use scoped packages: `@todo-starter/package-name`
32+
- Keep names descriptive and consistent
33+
- Use kebab-case for package names
34+
35+
## Scripts and Tasks
36+
- Define scripts at both root and package level
37+
- Use Turbo for orchestrating build tasks
38+
- Prefer package-specific scripts for development
39+
40+
## TypeScript Configuration
41+
- Use Tailwind CSS v4's CSS-first configuration with `@theme` directive
42+
- Use path mapping for workspace packages
43+
- Keep tsconfig.json files minimal and focused
44+
45+
## Best Practices
46+
- Keep packages focused and single-purpose
47+
- Avoid circular dependencies between packages
48+
- Use proper exports in package.json
49+
- Document package APIs and usage patterns
File renamed without changes.
File renamed without changes.
Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
---
2+
description: Bun test and React Testing Library patterns for React Router apps
3+
globs: apps/**/*.test.{ts, tsx}, apps/**/*.spec.{ts, tsx}, apps/**/test/**/*
4+
alwaysApply: false
5+
---
6+
7+
# Testing Best Practices
8+
9+
## Stack
10+
11+
- **Runner:** Bun test (`bun:test`) with JSDOM bootstrap in `test/setup.ts` (loaded via `bunfig.toml`)
12+
- **Component/DOM:** React Testing Library
13+
- **Router:** `createMemoryRouter` + `RouterProvider` via shared `renderWithRouter` helper
14+
15+
## Test Layout (todo-app)
16+
17+
| Pattern | Location | Purpose |
18+
|---------------|-----------------------------------|--------|
19+
| Unit | `app/lib/__tests__/*.test.ts` | Pure utilities, helpers |
20+
| Component | `app/components/__tests__/*.test.tsx` | UI with router/context mocking |
21+
| Integration | `app/routes/__tests__/*.integration.test.tsx` | Full route + provider flows |
22+
23+
Shared setup: `test/setup.ts` (jest-dom, RTL cleanup). Shared helpers: `test/test-utils.tsx`.
24+
25+
## Router-Dependent Components
26+
27+
Use `renderWithRouter` for any component that uses `Link`, `useNavigate`, `useFetcher`, or `useHref`:
28+
29+
```tsx
30+
import { renderWithRouter } from '../../../test/test-utils';
31+
32+
it('renders and submits', () => {
33+
renderWithRouter(<MyComponent />);
34+
});
35+
36+
it('renders at /contact', () => {
37+
renderWithRouter(<Page />, { initialEntries: ['/contact'] });
38+
});
39+
```
40+
41+
For full route trees (loaders, nested layouts), use `createTestRouter` or pass `routes` into `renderWithRouter`.
42+
43+
## Integration Tests
44+
45+
Wrap route components with the same providers as the app (e.g. TodoProvider), then assert user flows:
46+
47+
```tsx
48+
import { renderWithRouter } from '../../test/test-utils';
49+
import { TodoProvider } from '../../lib/todo-context';
50+
import Home from '../home';
51+
52+
renderWithRouter(
53+
<TodoProvider>
54+
<Home />
55+
</TodoProvider>
56+
);
57+
// fire events, assert DOM/state
58+
```
59+
60+
## Bun Config (reference)
61+
62+
- **preload:** `test/setup.ts` via `bunfig.toml`
63+
- **jsdom:** initialized in `test/setup.ts` (globals + `@testing-library/jest-dom`)
64+
- **testTimeout:** Bun default is `5000`; adjust with `bun test --timeout <ms>` when needed
65+
66+
## Commands
67+
68+
- `bun run test` – run tests
69+
- `bun run test:watch` – watch mode
70+
- `bun run test:run` / `bun run test:ci` – single run (CI)
71+
72+
## Best Practices
73+
74+
- Prefer `getByRole`, `getByLabelText`, `getByPlaceholderText` over brittle selectors
75+
- Use `jest.fn()` from `bun:test` for callbacks; assert calls and args
76+
- Hoist repeated regex/selectors to describe scope to satisfy lint rules
77+
- Keep tests focused; use multiple `it` blocks instead of one large test
78+
- For forms: test validation, submit behavior, and error display (see lambda-curry-forms rules for FormError)
Lines changed: 84 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,84 @@
1+
---
2+
description: UI component conventions and shadcn/ui patterns
3+
globs: packages/ui/**/*.tsx, packages/ui/**/*.ts, apps/**/app/**/*.tsx
4+
alwaysApply: true
5+
---
6+
7+
# UI Component Rules
8+
9+
## Component Structure
10+
- Use forwardRef for components that need ref forwarding
11+
- Implement proper TypeScript interfaces
12+
- Use class-variance-authority for variant-based styling
13+
14+
## shadcn/ui Patterns
15+
```tsx
16+
// Component example
17+
import * as React from 'react';
18+
import { cva, type VariantProps } from 'class-variance-authority';
19+
import { cn } from '@todo-starter/utils';
20+
21+
const buttonVariants = cva(
22+
'base-classes',
23+
{
24+
variants: {
25+
variant: {
26+
default: 'default-classes',
27+
destructive: 'destructive-classes'
28+
},
29+
size: {
30+
default: 'default-size',
31+
sm: 'small-size'
32+
}
33+
},
34+
defaultVariants: {
35+
variant: 'default',
36+
size: 'default'
37+
}
38+
}
39+
);
40+
41+
export interface ButtonProps
42+
extends React.ButtonHTMLAttributes<HTMLButtonElement>,
43+
VariantProps<typeof buttonVariants> {
44+
asChild?: boolean;
45+
}
46+
47+
const Button = React.forwardRef<HTMLButtonElement, ButtonProps>(
48+
({ className, variant, size, asChild = false, ...props }, ref) => {
49+
const Comp = asChild ? Slot : 'button';
50+
return (
51+
<Comp
52+
className={cn(buttonVariants({ variant, size, className }))}
53+
ref={ref}
54+
{...props}
55+
/>
56+
);
57+
}
58+
);
59+
Button.displayName = 'Button';
60+
```
61+
62+
## Styling Guidelines
63+
- Use Tailwind CSS classes for styling
64+
- Leverage CSS variables for theming
65+
- Use cn() utility for conditional classes
66+
- Follow shadcn/ui color and spacing conventions
67+
68+
## Accessibility
69+
- Include proper ARIA attributes
70+
- Ensure keyboard navigation works
71+
- Use semantic HTML elements
72+
- Test with screen readers
73+
74+
## Component Organization
75+
- Keep components in `packages/ui/src/components/ui/`
76+
- Export all components from main index file
77+
- Group related components together
78+
- Use consistent naming conventions
79+
80+
## Best Practices
81+
- Prefer composition over complex props
82+
- Keep components focused and reusable
83+
- Document component APIs with TypeScript
84+
- Test components in isolation

.cursorrules/monorepo.mdc

Lines changed: 0 additions & 90 deletions
This file was deleted.

0 commit comments

Comments
 (0)