Build a Next.js baby tracking app (diapers, feedings, naps, pumping) with TypeScript, Prisma/SQLite, TailwindCSS, and React Hooks. Designed for future React Native conversion with mobile-first architecture patterns.
Build a baby activity tracker (diapers, feedings, naps, pumping, etc.) using Next.js App Router, TypeScript, Prisma, SQLite, TailwindCSS, and React Hooks. Architecture is designed for future React Native conversion with mobile-first patterns.
1. Use `/src` directory structure with dedicated folders:
- `/components/ui` — Reusable UI primitives
- `/components/features` — Feature-specific components
- `/hooks` — Custom hooks
- `/services` — API services and data fetching
- `/utils` — Utility functions
- `/constants` — Shared constants with type safety
- `/context` — React context providers
- `/types` — Shared TypeScript types
- `/styles` — Global styles and theme
2. Co-locate component files:
- Place component, styles, types, and README.md in the same folder
- Include README.md documenting props, usage, and implementation details
3. Follow consistent naming conventions across all files and components
1. Create "dumb" UI components that are highly configurable through props
2. Implement container/presentational pattern (separate data fetching from UI)
3. Keep components small and focused (under 200 lines of code)
4. Use composition over inheritance for complex components
5. Include props for error and loading states in all data-dependent components
6. Design with accessibility in mind (proper ARIA attributes)
7. Document component APIs thoroughly in component README files
1. Enable strict mode in `tsconfig.json`
2. Create shared types in `/types` directory for domain entities (e.g., feeding events, diaper changes)
3. Use discriminated unions for different event types:
```typescript
type ActivityEvent = FeedingEvent | DiaperEvent | NapEvent | PumpingEvent;
```
4. Implement type guards for safe type narrowing
5. Define constants with type safety using `as const` assertions
6. Create specific error types extending base Error class
7. Use TypeScript generics for reusable components and functions
8. Define readonly properties for immutable data
1. Implement custom hooks for complex state logic
2. Create context providers for global state accessed by multiple components
3. Use React Query for data fetching with proper type definitions
4. Follow immutable update patterns in all state modifications
5. Implement memoization for expensive computations with `useMemo`
6. Include proper error and loading states in all async operations
7. Design state management with offline-first principles in mind (for future mobile support)
1. Define a shared design system with consistent variables:
- Colors, spacing, typography, shadows, borders
2. Use CSS Modules or Styled Components for component styling
3. Keep styles modular and component-specific
4. Implement responsive design using media queries
5. Export theme as TypeScript constants
6. Support light and dark modes through a theme context
7. Create helper functions for complex style logic
1. Use Next.js file-system based routing
2. Define strongly typed route parameters with TypeScript interfaces
3. Create navigation utilities that consolidate route definitions
4. Implement type-safe navigation helpers
5. Create guards for protected routes in middleware
6. Design consistent route structure that will mirror future mobile routes
7. Make routes accessible and SEO-friendly
1. Create a type-safe fetch wrapper with proper error handling
2. Implement domain-specific API services that use the core API layer
3. Use React Query for data fetching with consistent query key patterns
4. Implement error handling that provides clear user feedback
5. Define optimistic updates for better UX
6. Structure API responses with consistent types
7. Design with offline capabilities in mind for future mobile support
1. Use React Hook Form for form state management and validation
2. Create reusable validation rules
3. Implement consistent error message styling
4. Create type-safe form components
5. Consider implementing a form builder pattern for complex forms
6. Handle form submission with loading and error states
7. Make forms accessible with proper labels and ARIA attributes
1. Write tests for all components, custom hooks, and services
2. Test error and loading states
3. Verify accessibility features
4. Test responsive layouts
5. Implement integration tests for complex features
1. Avoid web-specific APIs that won't exist in React Native (e.g., `window`, `document`)
2. Design UI with touch interaction in mind (larger touch targets: 44x44px minimum)
3. Consider offline capabilities from the start
4. Plan for cross-platform navigation patterns
5. Document any web-specific behavior that will need adaptation for mobile
1. Challenge yourself to write as few lines of code as possible
2. When changing existing code, preserve all formatting and styling unless explicitly asked to modify it
3. Make only the changes that have been discussed and approved
4. Maintain all existing functionality when making modifications
5. Ask questions about any ambiguous requirements before implementing changes
6. Perform due diligence to ensure accuracy and minimize rewrites
```typescript
// types/activity.ts
type FeedingEvent = {
type: 'feeding';
amount: number;
unit: 'ml' | 'oz';
method: 'bottle' | 'breast';
};
type DiaperEvent = {
type: 'diaper';
kind: 'wet' | 'dirty' | 'both';
};
type NapEvent = {
type: 'nap';
duration: number; // minutes
};
type PumpingEvent = {
type: 'pumping';
amount: number;
unit: 'ml' | 'oz';
};
export type ActivityEvent = FeedingEvent | DiaperEvent | NapEvent | PumpingEvent;
// Type guard example
export function isFeedingEvent(event: ActivityEvent): event is FeedingEvent {
return event.type === 'feeding';
}
```
```typescript
// hooks/useActivities.ts
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';
import { activityService } from '@/services/activityService';
import type { ActivityEvent } from '@/types/activity';
export function useActivities() {
const queryClient = useQueryClient();
const { data: activities, isLoading, error } = useQuery({
queryKey: ['activities'],
queryFn: activityService.getAll,
});
const addActivityMutation = useMutation({
mutationFn: activityService.create,
onSuccess: () => {
queryClient.invalidateQueries({ queryKey: ['activities'] });
},
});
return {
activities,
isLoading,
error,
addActivity: addActivityMutation.mutate,
isAdding: addActivityMutation.isPending,
};
}
```
```typescript
// components/features/ActivityList/ActivityListContainer.tsx
'use client';
import { useActivities } from '@/hooks/useActivities';
import { ActivityListPresentation } from './ActivityListPresentation';
export function ActivityListContainer() {
const { activities, isLoading, error } = useActivities();
return (
<ActivityListPresentation
activities={activities}
isLoading={isLoading}
error={error}
/>
);
}
// components/features/ActivityList/ActivityListPresentation.tsx
import type { ActivityEvent } from '@/types/activity';
import { ActivityCard } from '@/components/ui/ActivityCard';
import { LoadingSpinner } from '@/components/ui/LoadingSpinner';
import { ErrorMessage } from '@/components/ui/ErrorMessage';
type Props = {
activities?: ActivityEvent[];
isLoading: boolean;
error: Error | null;
};
export function ActivityListPresentation({ activities, isLoading, error }: Props) {
if (isLoading) return <LoadingSpinner />;
if (error) return <ErrorMessage message={error.message} />;
if (!activities?.length) return <p>No activities yet.</p>;
return (
<ul className="space-y-4">
{activities.map((activity) => (
<ActivityCard key={activity.id} activity={activity} />
))}
</ul>
);
}
```
This skill guides you through building a baby activity tracker with Next.js, TypeScript, Prisma, and TailwindCSS using architecture patterns that facilitate future React Native conversion. Focus on type safety, component modularity, accessibility, and offline-first design. Write minimal code, preserve existing formatting, and validate requirements before implementing changes.
Leave a review
No reviews yet. Be the first to review this skill!
# Download SKILL.md from killerskills.ai/api/skills/nextjs-cross-platform-baby-tracker/raw