-
Notifications
You must be signed in to change notification settings - Fork 1
docs: add KNOWLEDGE.md with codebase patterns and conventions #174
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: main
Are you sure you want to change the base?
Changes from 1 commit
82e90ec
249a38c
05f858d
baf366c
22ad510
4def0ce
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| @@ -0,0 +1,233 @@ | ||||||||||||||||||||||||||||||||||
| # Knowledge: DocuGen Patterns & Conventions | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| This document captures architectural decisions, patterns, and conventions that are implemented in the codebase but not formally documented elsewhere. | ||||||||||||||||||||||||||||||||||
|
Comment on lines
+1
to
+3
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. 🚩 Significant content overlap with docs/ARCHITECTURE.md KNOWLEDGE.md covers topics that substantially overlap with Was this helpful? React with 👍 or 👎 to provide feedback. |
||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| --- | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ## 1. Centralized Content Management | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| All site copy lives in a single file: **`src/data/content.ts`** | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| - Components import content from this central source rather than containing inline text | ||||||||||||||||||||||||||||||||||
| - Export naming convention: uppercase constants (`SITE`, `NAV_LINKS`, `HERO_COPY`, `FEATURES`, `FAQS`, etc.) | ||||||||||||||||||||||||||||||||||
| - Content is organized by feature/section | ||||||||||||||||||||||||||||||||||
|
shazzar00ni marked this conversation as resolved.
Outdated
|
||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ```typescript | ||||||||||||||||||||||||||||||||||
| // Example structure | ||||||||||||||||||||||||||||||||||
| export const SITE = { name: 'DocuGen', tagline: '...', ... }; | ||||||||||||||||||||||||||||||||||
| export const HERO_COPY = { headline: '...', subheadline: '...', ... }; | ||||||||||||||||||||||||||||||||||
| export const FEATURES = [{ icon: '...', title: '...', ... }, ...]; | ||||||||||||||||||||||||||||||||||
| export const FAQS = [{ question: '...', answer: '...', ... }]; | ||||||||||||||||||||||||||||||||||
| ``` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| **Rationale:** Enables copy updates without touching component logic. Supports i18n migration. | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| --- | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ## 2. CSS Class Utility (`cn()`) | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| **Location:** `src/lib/utils.ts` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ```typescript | ||||||||||||||||||||||||||||||||||
| cn(...classes: (string | undefined | null | false)[]): string | ||||||||||||||||||||||||||||||||||
| ``` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| Filters falsy values and joins class names with spaces. | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ```tsx | ||||||||||||||||||||||||||||||||||
| <button className={cn('base-class', isActive && 'active-class', className)}> | ||||||||||||||||||||||||||||||||||
| ``` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| **Used throughout:** All components use this pattern for conditional styling. | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| --- | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ## 3. Lazy Loading Strategy | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| **Location:** `src/App.tsx` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| - Page-critical sections use static imports: `Hero`, `HowItWorks`, `FAQ`, `Navbar`, `Footer` | ||||||||||||||||||||||||||||||||||
| - Heavy sections are lazy-loaded: `Features`, `Testimonials`, `Preview`, `Pricing`, `Newsletter` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ```typescript | ||||||||||||||||||||||||||||||||||
| const Features = lazy(() => | ||||||||||||||||||||||||||||||||||
| import('./components/Features').then(module => ({ default: module.Features })) | ||||||||||||||||||||||||||||||||||
| ); | ||||||||||||||||||||||||||||||||||
| ``` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| - Each lazy component wrapped in `<Suspense fallback={<Loading />} />` | ||||||||||||||||||||||||||||||||||
| - Custom `Loading` spinner component for consistent loading UI | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| **Rationale:** Improves initial bundle load time. Critical path content renders immediately. | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| --- | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ## 4. UI Component Library | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| **Location:** `src/components/ui/` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ### Button | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| - Variants: `primary` (teal), `secondary` (dark), `ghost` (text) | ||||||||||||||||||||||||||||||||||
| - Sizes: `sm`, `md`, `lg` | ||||||||||||||||||||||||||||||||||
| - Props: `children`, `variant?`, `size?`, `className?`, `onClick?`, `type?` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ### Input | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| - Dark theme styling with teal focus ring | ||||||||||||||||||||||||||||||||||
| - Supports `text` and `email` types | ||||||||||||||||||||||||||||||||||
| - Props: `placeholder?`, `type?`, `className?`, `disabled?`, `value?`, `onChange?`, `onBlur?` | ||||||||||||||||||||||||||||||||||
| - Supports all standard HTML input attributes via spread | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ### Container | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| - Responsive max-width wrapper (`max-w-7xl`) | ||||||||||||||||||||||||||||||||||
| - Horizontal padding: `px-4 sm:px-6 lg:px-8` | ||||||||||||||||||||||||||||||||||
| - Props: `children`, `className?` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ### Skeleton | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| - Base component with variants: `text`, `circular`, `rectangular` | ||||||||||||||||||||||||||||||||||
| - Pre-built composite components: | ||||||||||||||||||||||||||||||||||
| - `SkeletonCard` - user card with avatar | ||||||||||||||||||||||||||||||||||
| - `SkeletonButton` - standard button dimensions | ||||||||||||||||||||||||||||||||||
| - `SkeletonInput` - form input height | ||||||||||||||||||||||||||||||||||
| - `SkeletonFeature` - icon + title + description | ||||||||||||||||||||||||||||||||||
| - `SkeletonTestimonial` - quote + author info | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| --- | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ## 5. Theme System Architecture | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| **Location:** `src/lib/ThemeContext.tsx` | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| ### Components | ||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||
| - `ThemeProvider` - wraps app, manages state | ||||||||||||||||||||||||||||||||||
| - `useTheme()` - hook for components (throws if used outside provider) | ||||||||||||||||||||||||||||||||||
|
shazzar00ni marked this conversation as resolved.
Outdated
|
||||||||||||||||||||||||||||||||||
| **Location:** `src/lib/ThemeContext.tsx` | |
| ### Components | |
| - `ThemeProvider` - wraps app, manages state | |
| - `useTheme()` - hook for components (throws if used outside provider) | |
| **Locations:** | |
| - `src/lib/ThemeContext.tsx` - `ThemeProvider`, `ThemeContext`, `Theme` type | |
| - `src/lib/useTheme.ts` - `useTheme()` hook for components (throws if used outside provider) | |
| ### Components | |
| - `ThemeProvider` - wraps app, manages state | |
| - `ThemeContext` - shared context consumed by the hook | |
| - `useTheme()` - hook for components |
Copilot
AI
Apr 30, 2026
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The environment variable example is formatted like JavaScript/TypeScript and includes spaces/semicolon (VITE_PLAUSIBLE_DOMAIN = your - domain.com;), which is not a valid .env entry and is easy to copy/paste incorrectly. Please change it to a correct .env example (e.g. VITE_PLAUSIBLE_DOMAIN=your-domain.com).
| VITE_PLAUSIBLE_DOMAIN = your - domain.com; | |
| VITE_PLAUSIBLE_DOMAIN=your-domain.com |
Copilot
AI
Apr 30, 2026
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The port details here are internally inconsistent with the repo configuration: vite.config.ts sets the dev server to 3000, but playwright.config.ts configures webServer.port/baseURL as 5173. Also, vite preview does not use server.port by default (it has its own preview port unless configured). Please update this section to reflect the actual ports being used, or adjust the configs so dev/e2e/preview are aligned.
| - Preview command serves production build on same port | |
| - E2E tests target `http://localhost:5173` (Playwright default) | |
| - `vite preview` does **not** automatically reuse `server.port`; its preview port must be configured separately if you want it to match dev | |
| - E2E tests currently target `http://localhost:5173` (per Playwright configuration), so dev and E2E are not using the same port |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Update the “Last updated” date to match this PR change date.
Line 234 shows 2026-04-24, but this PR was created on 2026-04-30.
Proposed fix
- _Last updated: 2026-04-24_
+ _Last updated: 2026-04-30_🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.
In `@KNOWLEDGE.md` at line 234, Update the "Last updated" date string in
KNOWLEDGE.md by replacing the existing "_Last updated: 2026-04-24_" text with
"_Last updated: 2026-04-30_" so the file reflects the PR creation date; locate
the exact string "_Last updated: 2026-04-24_" and change only the date portion.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🚩 KNOWLEDGE.md placed at root rather than docs/ directory
AGENTS.md prescribes
docs/as the directory for "Documentation files" and lists ARCHITECTURE.md, DEVELOPMENT.md, etc. there. KNOWLEDGE.md covers similar content (architectural patterns, conventions) and could arguably belong indocs/. However, there's existing precedent for root-level markdown files (DEPLOYMENT.md, ISSUES.md, SECURITY.md, CODE_OF_CONDUCT.md) that aren't indocs/either. The distinction seems to be project governance/meta files at root vs. detailed technical docs indocs/. KNOWLEDGE.md straddles this line - it's a meta file about how to work in the codebase (like AGENTS.md) but also contains detailed technical documentation (like ARCHITECTURE.md). Not flagged as a rule violation since the AGENTS.md file organization section is descriptive of existing structure rather than an explicit prohibition on root-level docs.Was this helpful? React with 👍 or 👎 to provide feedback.