# Portfolio Project Development Rules ## Code Style & Formatting ### TypeScript - **Tab indentation** (not spaces), **double quotes**, **semicolons** required - **Explicit function return types** for all functions (except inline expressions) - **Never use `any` type** - always provide proper typing - Prefix **interfaces with `I`** (e.g., `IProps`), **PascalCase** for type aliases - Underscore prefix for unused variables (e.g., `_unusedParam`) - Avoid non-null assertions (`!`) - use proper null checks ### React & JSX - Components return `JSX.Element`, functional components with hooks only - Self-closing tags for components without children: `` - No prop-types (using TypeScript) ### Spacing & Formatting - **Object curly spacing**: `{ foo }`, **no array bracket spacing**: `[1, 2]` - **No trailing commas**, arrow spacing: `() => {}` - Max **1 empty line** between blocks, end files with newline, no trailing spaces ### Imports - Use path alias `@/*` (configured in tsconfig) - Group: external deps first, then internal modules - Import from `@/src/portfolio/...` and `@/src/styles/...` ## Project Structure ### File Organization - **Pages**: `/pages/*.tsx` (pages router, not app router) - **Components**: `/src/portfolio/sections/*.tsx` - **Styles**: `/src/styles/*.scss` with helpers - **Data**: `/src/portfolio/data/`, **Helpers**: `/src/portfolio/helpers/` - **Public**: `/public/` (PDFs, images, icons) ### Component Structure - Section components in `/src/portfolio/sections/`, main page in `/src/portfolio/MainPage.tsx` - Each section has single responsibility ## Styling & Libraries ### SCSS - Import helpers: `@import "helpers";`, use variables: `$accent_colour` - BEM-like naming, `!important` only for library overrides (Splide) ### Animations - **AOS** (scroll), **Anime.js** (complex), **react-transition-group** (transitions) - Respect `prefers-reduced-motion` ### Tech Stack - **Next.js 15** (pages router), **React 18.2**, **TypeScript 5.1**, **SASS** - **@splidejs/react-splide**, **react-icons**, **Sharp** - Dev server on **port 4000**: `npm run dev` ## Development Workflow ### Commands - `pnpm dev` - Start dev server (port 4000) - `pnpm build` - Production build - `pnpm start` - Start production server - `pnpm lint` - Check for linting issues - `pnpm lintfix` - Auto-fix linting issues - `pnpm typecheck` - Run TypeScript type checking - `pnpm security:audit` - Run security vulnerability scan - `pnpm security:check` - Generate security report (JSON) - `pnpm security:outdated` - Check for outdated dependencies ### Windsurf Commands Helper Script The project includes `windsurf-commands.sh` for common development tasks: ```bash ./windsurf-commands.sh lint # Run ESLint to check for code issues ./windsurf-commands.sh lintfix # Run ESLint with auto-fix enabled ./windsurf-commands.sh typecheck # Run TypeScript type checking ./windsurf-commands.sh security:audit # Run security vulnerability scan ./windsurf-commands.sh security:check # Generate security report (JSON) ./windsurf-commands.sh security:outdated # Check for outdated dependencies ./windsurf-commands.sh help # Show available commands ``` **Usage:** - Script provides consistent interface for development commands - All commands use `pnpm` internally - Includes error handling and user-friendly output with emojis - Can be used interchangeably with direct `pnpm run` commands ### Before Committing 1. Run `pnpm run lintfix` and `pnpm run lint` (or use `./windsurf-commands.sh lintfix` and `./windsurf-commands.sh lint`) 2. Run `pnpm run typecheck` (or `./windsurf-commands.sh typecheck`) to ensure TypeScript compiles 3. Run `pnpm run security:audit` (or `./windsurf-commands.sh security:audit`) to check for vulnerabilities 4. Test changes in browser ## File Naming - **Components**: PascalCase (`MainPage.tsx`) - **Utilities**: camelCase (`helpers.ts`) - **Styles**: kebab-case/camelCase (`main.scss`) ## Common Patterns ```typescript // Component const ComponentName = (): JSX.Element => { return
{/* content */}
; }; export default ComponentName; // Interface interface IComponentProps { title: string; isActive: boolean; } ``` ```scss // SCSS @import "helpers"; .component { color: $accent_colour; } ``` ## Code Complexity Constraints ### Strict Limits (ESLint Enforced) - **Max line length**: 120 characters (ignores URLs, strings, template literals) - **Max file length**: 300 lines (excluding blank lines and comments) - **Max function length**: 50 lines (excluding blank lines and comments) - **Max cyclomatic complexity**: 10 per function - **Max nesting depth**: 4 levels - **Max parameters**: 4 per function - **Max nested callbacks**: 3 levels - **Max statements**: 20 per function ### Refactoring Strategies When files exceed limits, use these approaches: 1. **Split by logical sections**: Break large files into feature folders with main component, sub-components, helpers, types, and index.ts 2. **Extract helper functions**: Move utility functions to separate `helpers.ts` files 3. **Extract types**: Move interfaces/types to separate `types.ts` files 4. **Break down complex functions**: Use sub-functions, early returns, extract conditionals, use lookup objects **Folder structure example:** ``` /src/portfolio/sections/Experience/ Experience.tsx, ExperienceCard.tsx, helpers.ts, types.ts, index.ts ``` **Handling violations:** 1. Analyze what limit was exceeded 2. Choose appropriate strategy 3. Plan folder structure 4. Execute incrementally (create files, move code, update imports, test) 5. Verify with `npm run lint` **Line length fixes:** Break strings, split chains, extract variables, reformat JSX **Parameter count fixes:** Use object parameters, configuration objects, or split function ## QA and Testing ### Pre-Testing Checklist Before running any tests, verify the development server is running: 1. **Check if dev server is running** using `lsof`: ```bash lsof -i :4000 ``` - If output shows a process, server is running - If no output, start the server with `npm run dev` 2. **Verify server accessibility**: ```bash curl -I http://localhost:4000 ``` - Should return HTTP 200 OK - If connection refused, server needs to be started ### Playwright MCP Testing Workflow When testing changes or new features, follow this systematic approach: #### Step 1: Environment Setup 1. Ensure dev server is running on port 4000 2. Install Playwright browsers if needed (use `mcp0_browser_install` if errors occur) 3. Navigate to `http://localhost:4000` #### Step 2: Visual Testing Use Playwright MCP to verify visual elements: 1. **Take accessibility snapshot** (`mcp0_browser_snapshot`): - Captures page structure and content - Better than screenshots for testing - Use this to verify all sections are present 2. **Check key sections are visible**: - Intro section with name/title - Achievements section - Experience section with carousel - Projects section - Skills and Links section - Footer 3. **Verify responsive behavior**: - Test at different viewport sizes using `mcp0_browser_resize` - Common breakpoints: 375px (mobile), 768px (tablet), 1920px (desktop) - Check that content adapts properly #### Step 3: Functional Testing Test interactive elements: 1. **Navigation and scrolling**: - Verify smooth scroll behavior (if `prefers-reduced-motion: no-preference`) - Test anchor links if present - Check scroll-triggered animations (AOS) 2. **Carousel functionality** (Splide): - Click next/previous arrows using `mcp0_browser_click` - Verify slides change correctly - Check pagination dots are clickable - Ensure carousel is responsive 3. **Interactive elements**: - Test any buttons, links, or accordions - Verify hover states work - Check click handlers fire correctly - Test form inputs if present 4. **External links**: - Verify PDF links open correctly (CV, research papers) - Check social media links - Ensure `target="_blank"` and `rel="noopener noreferrer"` where needed #### Step 4: Accessibility Testing 1. **Contrast ratios**: - Use `mcp0_browser_evaluate` to check computed styles - Verify text has sufficient contrast against backgrounds - Check accent color (`$accent_colour`) meets WCAG AA standards (4.5:1 for normal text) 2. **Keyboard navigation**: - Use `mcp0_browser_press_key` to test Tab navigation - Verify focus indicators are visible - Check all interactive elements are keyboard accessible - Test Escape key for modals/overlays 3. **ARIA labels and semantic HTML**: - Check snapshot for proper heading hierarchy (h1, h2, h3) - Verify buttons have accessible names - Check images have alt text - Ensure landmarks are properly labeled 4. **Screen reader compatibility**: - Verify meaningful content order in accessibility snapshot - Check that hidden decorative elements are properly hidden - Ensure dynamic content updates are announced #### Step 5: Performance Checks 1. **Console errors**: - Use `mcp0_browser_console_messages` to check for errors - Verify no React warnings in development - Check for missing image errors - Look for failed network requests 2. **Network requests**: - Use `mcp0_browser_network_requests` to inspect requests - Verify images are optimized (using Next.js Image) - Check for unnecessary requests - Ensure no 404s or failed requests 3. **Animation performance**: - Verify AOS animations trigger smoothly - Check Anime.js animations don't cause jank - Test on reduced motion preference #### Step 6: Cross-Section Integration 1. **Section transitions**: - Scroll through all sections - Verify spacing between sections is consistent - Check that animations don't overlap or conflict 2. **Data consistency**: - Verify project data displays correctly - Check experience timeline is accurate - Ensure skills list is complete and categorized 3. **Asset loading**: - Verify all images load (profile, project screenshots) - Check PDFs are accessible - Ensure icons render correctly (react-icons) ### Testing Checklist Template When testing a new feature or change, use this checklist: - [ ] Dev server running on port 4000 - [ ] Page loads without errors (check console) - [ ] All sections render correctly (accessibility snapshot) - [ ] Responsive at mobile (375px), tablet (768px), desktop (1920px) - [ ] Interactive elements work (carousels, buttons, links) - [ ] Keyboard navigation functional (Tab, Enter, Escape) - [ ] Contrast ratios meet WCAG AA standards - [ ] No console errors or warnings - [ ] Network requests successful (no 404s) - [ ] Animations smooth and respect reduced motion - [ ] External links open correctly - [ ] Images optimized and load properly ### Common Test Scenarios #### Testing a New Section Component ```typescript // 1. Check server is running lsof -i :4000 // 2. Navigate and snapshot mcp0_browser_navigate → http://localhost:4000 mcp0_browser_snapshot // 3. Verify section appears // Look for section in snapshot output // 4. Test responsiveness mcp0_browser_resize → 375x667 (mobile) mcp0_browser_snapshot mcp0_browser_resize → 1920x1080 (desktop) mcp0_browser_snapshot // 5. Check console mcp0_browser_console_messages ``` #### Testing Accessibility ```typescript // 1. Check contrast mcp0_browser_evaluate → function: () => { const el = document.querySelector('.your-element'); const styles = window.getComputedStyle(el); return { color: styles.color, backgroundColor: styles.backgroundColor }; } // 2. Test keyboard navigation mcp0_browser_press_key → Tab mcp0_browser_snapshot → verify focus mcp0_browser_press_key → Enter mcp0_browser_snapshot → verify action // 3. Check ARIA mcp0_browser_snapshot → review for proper labels ``` ### When to Run Tests - **Before committing**: Run basic visual and console checks - **After adding new section**: Full section integration test - **After styling changes**: Visual + contrast + responsive tests - **After adding interactivity**: Functional + keyboard + accessibility tests - **Before production build**: Complete checklist + all scenarios ### Debugging Failed Tests 1. **Visual issues**: Take screenshot with `mcp0_browser_take_screenshot` for detailed inspection 2. **Functional issues**: Use `mcp0_browser_evaluate` to inspect element state 3. **Network issues**: Check `mcp0_browser_network_requests` for failed requests 4. **Console errors**: Review `mcp0_browser_console_messages` for stack traces 5. **Timing issues**: Use `mcp0_browser_wait_for` to wait for elements/animations ## CI/CD Pipelines The project includes automated GitHub Actions workflows for code quality and security: ### Lint Check Workflows - **Push Lint Check** (`.github/workflows/push-lint-check.yml`) - Runs on every push to any branch - Executes ESLint checks - Uses pnpm v10 with caching for faster builds - Fails if linting errors are found - **PR Lint Check** (`.github/workflows/pr-lint-check.yml`) - Runs on pull requests to main/master/develop - Executes ESLint checks - Posts comment on PR if linting fails - Uses pnpm v10 with caching ### TypeScript Type Check Workflow - **TypeScript Type Check** (`.github/workflows/typecheck.yml`) - Runs on every push and pull request - Executes `tsc --noEmit` to check for type errors - Uses pnpm v10 with caching - Fails if type errors are found ### Security Audit Workflow - **Security Audit** (`.github/workflows/security-audit.yml`) - Runs on push to main/master/develop - Runs on all pull requests - Runs weekly on Monday at 00:00 UTC (scheduled) - Executes `pnpm audit` for vulnerability scanning - Generates security report (JSON) as artifact - Checks for outdated dependencies - Uses pnpm v10 with caching - Continues on error but uploads report for review ### Pipeline Requirements All workflows require: - Node.js 18 - pnpm v10 (matches lockfile version) - Frozen lockfile (`pnpm install --frozen-lockfile`) - Proper caching of pnpm store for performance ### Docker Deployment - **Dockerfile**: Multi-stage build with Alpine Linux base - Uses pnpm v10.30.1 - Non-root user (UID 1001) - Read-only filesystem with security hardening - Standalone Next.js output (~150MB image) - **docker-compose.yml**: One-command deployment ```bash docker-compose up -d ``` - Includes health checks - Security options (no-new-privileges, dropped capabilities) - Runs on port 4000 ## Notes - This is a **portfolio website** showcasing projects, experience, achievements, and skills - Runs on **port 4000** (not default 3000) - Uses **pages router** (not app router) - Strict TypeScript and ESLint configuration for code quality - Tab-based indentation is non-negotiable (project standard) - **Code complexity limits are strictly enforced** - refactor proactively - **Always test changes with Playwright MCP** before committing - **IMPORTANT: Always use Windsurf rules** - they are allowed by default and enable much faster AI development progress