Build Features
Real scenarios for building new features.
CRUD Module
Goal: Create a complete products module with list, create, edit, delete.
Command:
Create a products module with CRUD for /api/productsWhat happens:
- Creates folder structure
- Generates TypeScript types
- Creates API service
- Builds data adapter
- Creates list and form components
- Adds tests
Result:
src/modules/products/
├── types/
│ ├── products.types.ts # API response types
│ └── products.contracts.ts # App interfaces
├── services/
│ └── products-service.ts # HTTP calls
├── adapters/
│ └── products-adapter.ts # Data transformation
├── components/
│ ├── ProductList.tsx # List view
│ ├── ProductForm.tsx # Create/Edit form
│ └── ProductCard.tsx # Item display
├── hooks/
│ ├── useProducts.ts # List query
│ └── useProductMutations.ts # Create/Update/Delete
└── __tests__/
└── products-adapter.test.tsAPI Endpoint
Goal: Add a new endpoint to fetch user orders.
Command:
Create a service for GET /api/users/:id/orders with paginationWhat happens:
- Creates types matching the API response
- Creates service with the HTTP call
- Creates adapter for data transformation
- Creates hook/composable for easy use
Result:
typescript
// services/user-orders-service.ts
export const userOrdersService = {
list(userId: string, params: { page: number; limit: number }) {
return api.get(`/api/users/${userId}/orders`, { params })
}
}
// hooks/useUserOrders.ts
export function useUserOrders(userId: string) {
return useQuery({
queryKey: ['users', userId, 'orders'],
queryFn: () => userOrdersService.list(userId, { page: 1, limit: 20 })
})
}Form with Validation
Goal: Create a registration form with email and password validation.
Command:
Create a registration form with email, password, and confirm password fieldsWhat happens:
- Creates Zod validation schema
- Creates form component with fields
- Adds field-level error display
- Connects to registration mutation
- Handles loading and success states
Result:
typescript
// schemas/registration.schema.ts
export const registrationSchema = z.object({
email: z.string().email('Invalid email'),
password: z.string().min(8, 'At least 8 characters'),
confirmPassword: z.string()
}).refine(data => data.password === data.confirmPassword, {
message: 'Passwords must match',
path: ['confirmPassword']
})Form handles:
- Real-time validation
- Field error messages
- Submit loading state
- Success redirect
Pagination and Filters
Goal: Add pagination and status filter to orders list.
Command:
Add pagination and status filter to the orders listWhat happens:
- Updates query hook to accept page and filter params
- Creates filter component
- Creates pagination component
- Connects everything in the view
Result:
typescript
// Using the list
const { orders, totalPages, isLoading } = useOrders({
page: currentPage,
status: selectedStatus,
limit: 20
})
// Filter changes reset to page 1
function onStatusChange(status: string) {
setStatus(status)
setPage(1)
}Quick Tips
Be Specific
Good:
Create a products module with CRUD for GET/POST/PATCH/DELETE /api/v2/productsBetter:
Create a products module:
- List with pagination (20 per page)
- Create form with name, price, description, category
- Edit form (same fields)
- Delete with confirmation
- Filter by category
- Sort by name or priceIncremental Building
Start small, add features:
1. "Create products types and service for /api/products"
2. "Add the products list component"
3. "Add create product form"
4. "Add edit functionality"
5. "Add delete with confirmation"Test as You Go
"Create tests for the products adapter"
"Create tests for the products list component"Related Scenarios
- Code Review — Review the code you built
- Debug Issues — When something doesn't work
- API Design — Design the backend first