From beb96dd11cb3c94f2a4de3201cba5031b58c617b Mon Sep 17 00:00:00 2001 From: "google-labs-jules[bot]" <161369871+google-labs-jules[bot]@users.noreply.github.com> Date: Wed, 13 May 2026 18:36:26 +0000 Subject: [PATCH] docs(frontend): autonomous architectural standardization for modularized components Co-authored-by: beginwebdev2002 <102213457+beginwebdev2002@users.noreply.github.com> --- frontend/angular/basics.md | 309 ++++++++++++++++++++++++++++ frontend/angular/readme.md | 296 +------------------------- frontend/design-ui/basics.md | 29 +++ frontend/design-ui/readme.md | 11 +- frontend/javascript/basic-syntax.md | 16 ++ frontend/javascript/readme.md | 16 -- frontend/qwik/basics.md | 53 +++++ frontend/qwik/readme.md | 20 +- frontend/react/basics.md | 71 +++++++ frontend/react/readme.md | 60 +----- frontend/solidjs/basics.md | 29 +++ frontend/solidjs/readme.md | 17 +- frontend/typescript/fundamentals.md | 156 ++++++++++++++ frontend/typescript/readme.md | 147 +------------ 14 files changed, 678 insertions(+), 552 deletions(-) create mode 100644 frontend/angular/basics.md create mode 100644 frontend/design-ui/basics.md create mode 100644 frontend/qwik/basics.md create mode 100644 frontend/react/basics.md create mode 100644 frontend/solidjs/basics.md create mode 100644 frontend/typescript/fundamentals.md diff --git a/frontend/angular/basics.md b/frontend/angular/basics.md new file mode 100644 index 0000000..ce4a380 --- /dev/null +++ b/frontend/angular/basics.md @@ -0,0 +1,309 @@ +--- +technology: Angular +domain: frontend +level: Senior/Architect +version: 20+ +tags: [best-practices, clean-code, architecture-patterns, vibe-coding, cursor-rules, typescript, software-architecture, system-design, solid-principles, production-ready, programming-standards, react-best-practices, node-js, design-patterns, scalable-code, windsurf-rules, ai-coding, fsd, ddd, enterprise-patterns] +ai_role: Senior Angular Performance Expert +last_updated: 2026-03-22 +--- + +# ๐Ÿš€ Angular Basics & Popular Patterns + +[โฌ†๏ธ Back to Top](./readme.md) + +### ๐Ÿšจ 1. Using `@Input()` Decorator +> [!NOTE] +> **Context:** Component Inputs +### โŒ Bad Practice +```typescript +@Input() title: string; +``` +### โš ๏ธ Problem +Using the `@Input()` decorator breaks the functional reactivity of Zoneless applications. +### โœ… Best Practice +```typescript +title = input(); +``` +### ๐Ÿš€ Solution +Use Signal Inputs (`input()`). This allows Angular to precisely know *which* specific component requires an update, paving the way for Zoneless applications. +--- + +### ๐Ÿšจ 2. Using `@Output()` Decorator +> [!NOTE] +> **Context:** Component Outputs +### โŒ Bad Practice +```typescript +@Output() save = new EventEmitter(); +``` +### โš ๏ธ Problem +The classic `EventEmitter` adds an unnecessary layer of abstraction over RxJS Subject and does not integrate with the Angular functional API. +### โœ… Best Practice +```typescript +save = output(); +``` +### ๐Ÿš€ Solution +Use the `output()` function. It provides strict typing, better performance, and a unified API with Signal Inputs. +--- + +### ๐Ÿšจ 3. Two-Way Binding with `@Input()` and `@Output()` +> [!NOTE] +> **Context:** Model Synchronization +### โŒ Bad Practice +```typescript +@Input() value: string; +@Output() valueChange = new EventEmitter(); +``` +### โš ๏ธ Problem +Boilerplate code that is easy to break if you make a mistake in naming the `Change` event. +### โœ… Best Practice +```typescript +value = model(); +``` +### ๐Ÿš€ Solution +> [!IMPORTANT] +> Use `model()`. This creates a Signal that MUST be both read and written to, automatically synchronizing its state with the parent. +--- + +### ๐Ÿšจ 4. Structural Directives (`*ngIf`, `*ngFor`) +> [!NOTE] +> **Context:** Template Control Flow +### โŒ Bad Practice +```html +
+
  • {{ item }}
  • +
    +``` +### โš ๏ธ Problem +Directives require importing `CommonModule` or `NgIf/NgFor`, increasing bundle size. Micro-template syntax is complex for static analysis and type-checking. +### โœ… Best Practice +```html +@if (isLoaded()) { + @for (item of items(); track item.id) { +
  • {{ item.name }}
  • + } +} @else { + +} +``` +### ๐Ÿš€ Solution +Use the built-in Control Flow (`@if`, `@for`). It is built into the compiler, requires no imports, supports improved type-narrowing, and runs faster. +--- + +### ๐Ÿšจ 5. Subscribing in Components (Logic in `ngOnInit`) +> [!NOTE] +> **Context:** Data Fetching +### โŒ Bad Practice +```typescript +data: unknown; +ngOnInit() { + this.service.getData().subscribe(res => this.data = res); +} +``` +### โš ๏ธ Problem +Imperative subscriptions lead to memory leaks (if you forget to `unsubscribe`), "Callback Hell", and state desynchronization. Requires manual subscription management. +### โœ… Best Practice +```typescript +data = toSignal(this.service.getData()); +``` +### ๐Ÿš€ Solution +Use `toSignal()` to convert an Observable into a Signal. This automatically manages the subscription and integrates the data stream into the reactivity system. +--- + +### ๐Ÿšจ 6. `BehaviorSubject` for Local State +> [!NOTE] +> **Context:** Component State Management +### โŒ Bad Practice +```typescript +private count$ = new BehaviorSubject(0); +getCount() { return this.count$.value; } +``` +### โš ๏ธ Problem +RxJS is overkill for simple synchronous state. `BehaviorSubject` requires `.value` for access and `.next()` for writes, increasing cognitive load. +### โœ… Best Practice +```typescript +count = signal(0); +// Access: count() +// Update: count.set(1) +``` +### ๐Ÿš€ Solution +Use `signal()` for local state. It is a primitive designed specifically for synchronizing UI and data. +--- + +### ๐Ÿšจ 7. Derived State with `ngOnChanges` +> [!NOTE] +> **Context:** Reactivity +### โŒ Bad Practice +```typescript +ngOnChanges(changes: SimpleChanges) { + if (changes['firstName']) { + this.fullName = `${this.firstName} ${this.lastName}`; + } +} +``` +### โš ๏ธ Problem +`ngOnChanges` is triggered only when Inputs change, has complex typing, and runs before View initialization. +### โœ… Best Practice +```typescript +fullName = computed(() => `${this.firstName()} ${this.lastName()}`); +``` +### ๐Ÿš€ Solution +Use `computed()`. The signal is recalculated *only* when its dependencies change, and the result is memoized (cached). +--- + +### ๐Ÿšจ 8. Constructor Dependency Injection +> [!NOTE] +> **Context:** DI Pattern +### โŒ Bad Practice +```typescript +constructor(private http: HttpClient, private store: Store) {} +``` +### โš ๏ธ Problem +Constructors become cluttered with many dependencies. When inheriting classes, dependencies must be passed through `super()`. +### โœ… Best Practice +```typescript +private http = inject(HttpClient); +private store = inject(Store); +``` +### ๐Ÿš€ Solution +Use the `inject()` function. It operates in the initialization context (fields or constructor), is type-safe, and does not require `super()` during inheritance. +--- + +### ๐Ÿšจ 9. Modules (`NgModule`) +> [!NOTE] +> **Context:** App Architecture +### โŒ Bad Practice +```typescript +@NgModule({ + declarations: [AppComponent], + imports: [BrowserModule] +}) +export class AppModule {} +``` +### โš ๏ธ Problem +Modules create an unnecessary level of indirection. Components become dependent on the module context, complicating Lazy Loading and testing. +### โœ… Best Practice +```typescript +@Component({ + standalone: true, + imports: [CommonModule] +}) +``` +### ๐Ÿš€ Solution +Use Standalone Components. This is the Angular v14+ standard that makes components self-sufficient and tree-shakable. +--- + +### ๐Ÿšจ 10. String-based Route Loading +> [!NOTE] +> **Context:** Lazy Loading Routing +### โŒ Bad Practice +```typescript +loadChildren: () => import('./module').then(m => m.UserModule) +``` +### โš ๏ธ Problem +Loading modules pulls in transitive dependencies that might not be needed. +### โœ… Best Practice +```typescript +loadComponent: () => import('./user.component').then(c => c.UserComponent) +``` +### ๐Ÿš€ Solution +Use `loadComponent` for routing to Standalone components. This ensures minimal chunk size. +--- + +### ๐Ÿšจ 11. Heavy Logic in Templates +> [!NOTE] +> **Context:** Template Performance +### โŒ Bad Practice +```html +
    {{ calculateTotal(items) }}
    +``` +### โš ๏ธ Problem +The `calculateTotal` function is called during *every* Change Detection (CD) cycle, even if `items` have not changed. This kills UI performance. +### โœ… Best Practice +```typescript +total = computed(() => this.calculateTotal(this.items())); +``` +```html +
    {{ total() }}
    +``` +### ๐Ÿš€ Solution +Extract logic into `computed()` signals or Pure Pipes. They are only executed when input data changes. +--- + +### ๐Ÿšจ 12. Manual Subscription Management (`takeUntil`) +> [!NOTE] +> **Context:** RxJS Memory Leaks +### โŒ Bad Practice +```typescript +destroy$ = new Subject(); +ngOnDestroy() { this.destroy$.next(); } +stream$.pipe(takeUntil(this.destroy$)).subscribe(); +``` +### โš ๏ธ Problem +It's easy to forget `takeUntil` or `unsubscribe`. Requires a lot of boilerplate code in every component. +### โœ… Best Practice +```typescript +stream$.pipe(takeUntilDestroyed()).subscribe(); +``` +### ๐Ÿš€ Solution +Use the `takeUntilDestroyed()` operator. It automatically unsubscribes upon context destruction (component, directive, service). +--- + +### ๐Ÿšจ 13. Deeply Nested Components Passing Data +> [!NOTE] +> **Context:** Prop Drilling +### โŒ Bad Practice +```html + + + + +``` +### โš ๏ธ Problem +"Prop drilling" heavily couples intermediate components to data they don't need, just for the sake of passing it deeper. +### โœ… Best Practice +```typescript +// Service +theme = signal('dark'); +// Grandchild +theme = inject(ThemeService).theme; +``` +### ๐Ÿš€ Solution +Use Signal Stores or services for state sharing, or the new `input()` API with context inheritance (in the future). +--- + +### ๐Ÿšจ 14. Accessing DOM directly (`ElementRef.nativeElement`) +> [!NOTE] +> **Context:** Security & Abstraction +### โŒ Bad Practice +```typescript +el.nativeElement.style.backgroundColor = 'red'; +``` +### โš ๏ธ Problem +Direct DOM access breaks abstraction (doesn't work in SSR/Web Workers) and opens up XSS vulnerabilities. It bypasses Angular Sanitization mechanisms. +### โœ… Best Practice +```typescript +// Use Renderer2 or bindings +
    +``` +### ๐Ÿš€ Solution +Use style/class bindings or `Renderer2`. For direct manipulations, consider directives. +--- + +### ๐Ÿšจ 15. Zone.js overhead +> [!NOTE] +> **Context:** Change Detection +### โŒ Bad Practice +The application relies on Zone.js for any asynchronous event (setTimeout, Promise, XHR). +### โš ๏ธ Problem +Zone.js patches all browser APIs, adding overhead and increasing bundle size. CD triggers more often than necessary. +### โœ… Best Practice +```typescript +bootstrapApplication(App, { + providers: [provideExperimentalZonelessChangeDetection()] +}); +``` +### ๐Ÿš€ Solution +Migrate to Zoneless mode. Use Signals to notify Angular when a re-render is needed. +--- +[โฌ†๏ธ Back to Top](#) diff --git a/frontend/angular/readme.md b/frontend/angular/readme.md index 77107e5..01d2284 100644 --- a/frontend/angular/readme.md +++ b/frontend/angular/readme.md @@ -24,304 +24,10 @@ last_updated: 2026-03-22 Please refer to the specialized guides for detailed best practices: +- [๐Ÿš€ Basics & Popular](./basics.md) - [๐Ÿงฉ Components & Signals](./components-signals.md) - [โšก Reactivity & RxJS](./reactivity.md) -### ๐Ÿšจ 1. Using `@Input()` Decorator -> [!NOTE] -> **Context:** Component Inputs -### โŒ Bad Practice -```typescript -@Input() title: string; -``` -### โš ๏ธ Problem -Using the `@Input()` decorator breaks the functional reactivity of Zoneless applications. -### โœ… Best Practice -```typescript -title = input(); -``` -### ๐Ÿš€ Solution -Use Signal Inputs (`input()`). This allows Angular to precisely know *which* specific component requires an update, paving the way for Zoneless applications. ---- - -### ๐Ÿšจ 2. Using `@Output()` Decorator -> [!NOTE] -> **Context:** Component Outputs -### โŒ Bad Practice -```typescript -@Output() save = new EventEmitter(); -``` -### โš ๏ธ Problem -The classic `EventEmitter` adds an unnecessary layer of abstraction over RxJS Subject and does not integrate with the Angular functional API. -### โœ… Best Practice -```typescript -save = output(); -``` -### ๐Ÿš€ Solution -Use the `output()` function. It provides strict typing, better performance, and a unified API with Signal Inputs. ---- - -### ๐Ÿšจ 3. Two-Way Binding with `@Input()` and `@Output()` -> [!NOTE] -> **Context:** Model Synchronization -### โŒ Bad Practice -```typescript -@Input() value: string; -@Output() valueChange = new EventEmitter(); -``` -### โš ๏ธ Problem -Boilerplate code that is easy to break if you make a mistake in naming the `Change` event. -### โœ… Best Practice -```typescript -value = model(); -``` -### ๐Ÿš€ Solution -> [!IMPORTANT] -> Use `model()`. This creates a Signal that MUST be both read and written to, automatically synchronizing its state with the parent. ---- - -### ๐Ÿšจ 4. Structural Directives (`*ngIf`, `*ngFor`) -> [!NOTE] -> **Context:** Template Control Flow -### โŒ Bad Practice -```html -
    -
  • {{ item }}
  • -
    -``` -### โš ๏ธ Problem -Directives require importing `CommonModule` or `NgIf/NgFor`, increasing bundle size. Micro-template syntax is complex for static analysis and type-checking. -### โœ… Best Practice -```html -@if (isLoaded()) { - @for (item of items(); track item.id) { -
  • {{ item.name }}
  • - } -} @else { - -} -``` -### ๐Ÿš€ Solution -Use the built-in Control Flow (`@if`, `@for`). It is built into the compiler, requires no imports, supports improved type-narrowing, and runs faster. ---- - -### ๐Ÿšจ 5. Subscribing in Components (Logic in `ngOnInit`) -> [!NOTE] -> **Context:** Data Fetching -### โŒ Bad Practice -```typescript -data: unknown; -ngOnInit() { - this.service.getData().subscribe(res => this.data = res); -} -``` -### โš ๏ธ Problem -Imperative subscriptions lead to memory leaks (if you forget to `unsubscribe`), "Callback Hell", and state desynchronization. Requires manual subscription management. -### โœ… Best Practice -```typescript -data = toSignal(this.service.getData()); -``` -### ๐Ÿš€ Solution -Use `toSignal()` to convert an Observable into a Signal. This automatically manages the subscription and integrates the data stream into the reactivity system. ---- - -### ๐Ÿšจ 6. `BehaviorSubject` for Local State -> [!NOTE] -> **Context:** Component State Management -### โŒ Bad Practice -```typescript -private count$ = new BehaviorSubject(0); -getCount() { return this.count$.value; } -``` -### โš ๏ธ Problem -RxJS is overkill for simple synchronous state. `BehaviorSubject` requires `.value` for access and `.next()` for writes, increasing cognitive load. -### โœ… Best Practice -```typescript -count = signal(0); -// Access: count() -// Update: count.set(1) -``` -### ๐Ÿš€ Solution -Use `signal()` for local state. It is a primitive designed specifically for synchronizing UI and data. ---- - -### ๐Ÿšจ 7. Derived State with `ngOnChanges` -> [!NOTE] -> **Context:** Reactivity -### โŒ Bad Practice -```typescript -ngOnChanges(changes: SimpleChanges) { - if (changes['firstName']) { - this.fullName = `${this.firstName} ${this.lastName}`; - } -} -``` -### โš ๏ธ Problem -`ngOnChanges` is triggered only when Inputs change, has complex typing, and runs before View initialization. -### โœ… Best Practice -```typescript -fullName = computed(() => `${this.firstName()} ${this.lastName()}`); -``` -### ๐Ÿš€ Solution -Use `computed()`. The signal is recalculated *only* when its dependencies change, and the result is memoized (cached). ---- - -### ๐Ÿšจ 8. Constructor Dependency Injection -> [!NOTE] -> **Context:** DI Pattern -### โŒ Bad Practice -```typescript -constructor(private http: HttpClient, private store: Store) {} -``` -### โš ๏ธ Problem -Constructors become cluttered with many dependencies. When inheriting classes, dependencies must be passed through `super()`. -### โœ… Best Practice -```typescript -private http = inject(HttpClient); -private store = inject(Store); -``` -### ๐Ÿš€ Solution -Use the `inject()` function. It operates in the initialization context (fields or constructor), is type-safe, and does not require `super()` during inheritance. ---- - -### ๐Ÿšจ 9. Modules (`NgModule`) -> [!NOTE] -> **Context:** App Architecture -### โŒ Bad Practice -```typescript -@NgModule({ - declarations: [AppComponent], - imports: [BrowserModule] -}) -export class AppModule {} -``` -### โš ๏ธ Problem -Modules create an unnecessary level of indirection. Components become dependent on the module context, complicating Lazy Loading and testing. -### โœ… Best Practice -```typescript -@Component({ - standalone: true, - imports: [CommonModule] -}) -``` -### ๐Ÿš€ Solution -Use Standalone Components. This is the Angular v14+ standard that makes components self-sufficient and tree-shakable. ---- - -### ๐Ÿšจ 10. String-based Route Loading -> [!NOTE] -> **Context:** Lazy Loading Routing -### โŒ Bad Practice -```typescript -loadChildren: () => import('./module').then(m => m.UserModule) -``` -### โš ๏ธ Problem -Loading modules pulls in transitive dependencies that might not be needed. -### โœ… Best Practice -```typescript -loadComponent: () => import('./user.component').then(c => c.UserComponent) -``` -### ๐Ÿš€ Solution -Use `loadComponent` for routing to Standalone components. This ensures minimal chunk size. ---- - -### ๐Ÿšจ 11. Heavy Logic in Templates -> [!NOTE] -> **Context:** Template Performance -### โŒ Bad Practice -```html -
    {{ calculateTotal(items) }}
    -``` -### โš ๏ธ Problem -The `calculateTotal` function is called during *every* Change Detection (CD) cycle, even if `items` have not changed. This kills UI performance. -### โœ… Best Practice -```typescript -total = computed(() => this.calculateTotal(this.items())); -``` -```html -
    {{ total() }}
    -``` -### ๐Ÿš€ Solution -Extract logic into `computed()` signals or Pure Pipes. They are only executed when input data changes. ---- - -### ๐Ÿšจ 12. Manual Subscription Management (`takeUntil`) -> [!NOTE] -> **Context:** RxJS Memory Leaks -### โŒ Bad Practice -```typescript -destroy$ = new Subject(); -ngOnDestroy() { this.destroy$.next(); } -stream$.pipe(takeUntil(this.destroy$)).subscribe(); -``` -### โš ๏ธ Problem -It's easy to forget `takeUntil` or `unsubscribe`. Requires a lot of boilerplate code in every component. -### โœ… Best Practice -```typescript -stream$.pipe(takeUntilDestroyed()).subscribe(); -``` -### ๐Ÿš€ Solution -Use the `takeUntilDestroyed()` operator. It automatically unsubscribes upon context destruction (component, directive, service). ---- - -### ๐Ÿšจ 13. Deeply Nested Components Passing Data -> [!NOTE] -> **Context:** Prop Drilling -### โŒ Bad Practice -```html - - - - -``` -### โš ๏ธ Problem -"Prop drilling" heavily couples intermediate components to data they don't need, just for the sake of passing it deeper. -### โœ… Best Practice -```typescript -// Service -theme = signal('dark'); -// Grandchild -theme = inject(ThemeService).theme; -``` -### ๐Ÿš€ Solution -Use Signal Stores or services for state sharing, or the new `input()` API with context inheritance (in the future). ---- - -### ๐Ÿšจ 14. Accessing DOM directly (`ElementRef.nativeElement`) -> [!NOTE] -> **Context:** Security & Abstraction -### โŒ Bad Practice -```typescript -el.nativeElement.style.backgroundColor = 'red'; -``` -### โš ๏ธ Problem -Direct DOM access breaks abstraction (doesn't work in SSR/Web Workers) and opens up XSS vulnerabilities. It bypasses Angular Sanitization mechanisms. -### โœ… Best Practice -```typescript -// Use Renderer2 or bindings -
    -``` -### ๐Ÿš€ Solution -Use style/class bindings or `Renderer2`. For direct manipulations, consider directives. ---- - -### ๐Ÿšจ 15. Zone.js overhead -> [!NOTE] -> **Context:** Change Detection -### โŒ Bad Practice -The application relies on Zone.js for any asynchronous event (setTimeout, Promise, XHR). -### โš ๏ธ Problem -Zone.js patches all browser APIs, adding overhead and increasing bundle size. CD triggers more often than necessary. -### โœ… Best Practice -```typescript -bootstrapApplication(App, { - providers: [provideExperimentalZonelessChangeDetection()] -}); -``` -### ๐Ÿš€ Solution -Migrate to Zoneless mode. Use Signals to notify Angular when a re-render is needed. ---- -[โฌ†๏ธ Back to Top](#) ## ๐Ÿ“š Specialized Topics For further reading, please refer to the following specialized guides: diff --git a/frontend/design-ui/basics.md b/frontend/design-ui/basics.md new file mode 100644 index 0000000..204fdca --- /dev/null +++ b/frontend/design-ui/basics.md @@ -0,0 +1,29 @@ +--- +technology: UI/UX Design +domain: frontend +level: Senior/Architect +version: Latest +tags: [vibe-coding, documentation, best-practices, architecture, design-system, accessibility] +ai_role: Senior Vibe Coding Expert +last_updated: 2026-03-29 +--- + +# ๐Ÿš€ UI/UX Basics & General + +[โฌ†๏ธ Back to Top](./readme.md) + +### ๐Ÿšจ 1. Using Non-semantic HTML Elements +> [!NOTE] +> **Context:** Accessibility +### โŒ Bad Practice +```html +
    Submit
    +``` +### โš ๏ธ Problem +Using non-semantic elements for interactive components breaks keyboard navigation and screen reader support. +### โœ… Best Practice +```html + +``` +### ๐Ÿš€ Solution +Always use native, semantic HTML elements (e.g., `; +``` +### โš ๏ธ Problem +Closures cannot be serialized natively by Qwik, breaking resumability and throwing an error. +### โœ… Best Practice +```tsx +const Component = component$(({ onClick$ }: { onClick$: PropFunction<() => void> }) => ( + +)); +``` +### ๐Ÿš€ Solution +Use the `$` suffix (`onClick$`) to mark the prop as a `PropFunction`, allowing Qwik to serialize the closure and load it lazily. diff --git a/frontend/qwik/readme.md b/frontend/qwik/readme.md index a482088..8f6cf9c 100644 --- a/frontend/qwik/readme.md +++ b/frontend/qwik/readme.md @@ -25,29 +25,11 @@ last_updated: 2026-03-22 - Adhere to the defined [Architectural Patterns](../../architectures/readme.md) when building applications. - Strongly prefer **Feature Sliced Design (FSD)** for applications scaling across multiple teams. -## ๐Ÿš€ I. Basics & Popular -## ๐Ÿšจ 1. Passing Closures as Props -> [!NOTE] -> **Context:** Component Props -### โŒ Bad Practice -```tsx -const Component = ({ onClick }) => ; -``` -### โš ๏ธ Problem -Closures cannot be serialized natively by Qwik, breaking resumability and throwing an error. -### โœ… Best Practice -```tsx -const Component = component$(({ onClick$ }: { onClick$: PropFunction<() => void> }) => ( - -)); -``` -### ๐Ÿš€ Solution -Use the `$` suffix (`onClick$`) to mark the prop as a `PropFunction`, allowing Qwik to serialize the closure and load it lazily. - ## ๐Ÿ“š Specialized Topics For further reading, please refer to the following specialized guides: +- [๐Ÿš€ Basics & Popular](./basics.md) - [๐Ÿš€ Advanced Performance](./performance.md) - [๐Ÿ“ฆ State Management](./state-management.md) - [๐Ÿงช Testing](./testing.md) diff --git a/frontend/react/basics.md b/frontend/react/basics.md new file mode 100644 index 0000000..729faf4 --- /dev/null +++ b/frontend/react/basics.md @@ -0,0 +1,71 @@ +--- +technology: React +domain: frontend +level: Senior/Architect +version: "19+" +tags: [react, best-practices, architecture, clean-code, scalable-code, modern-react, server-components] +ai_role: Senior React Expert +last_updated: 2026-03-22 +--- + +# ๐Ÿš€ React Basics & Popular Patterns + +[โฌ†๏ธ Back to Top](./readme.md) + +### ๐Ÿšจ 1. Direct DOM Manipulation +> [!NOTE] +> **Context:** Updating elements in a React component. +### โŒ Bad Practice +```tsx +function Component() { + const handleClick = () => { + document.getElementById('my-element').style.color = 'red'; + }; + return
    Click me
    ; +} +``` +### โš ๏ธ Problem +Direct DOM manipulation bypasses React's virtual DOM, causing inconsistencies between the actual DOM and React's internal state, leading to forced synchronous layouts and potential XSS vulnerabilities. +### โœ… Best Practice +```tsx +function Component() { + const [isActive, setIsActive] = useState(false); + return ( +
    setIsActive(!isActive)} + > + Click me +
    + ); +} +``` +### ๐Ÿš€ Solution +Always use state and props to drive the UI. React uses a virtual DOM to efficiently update the real DOM based on state changes, ensuring deterministic rendering loops. + +### ๐Ÿšจ 2. Large Component Files +> [!NOTE] +> **Context:** Managing component complexity. +### โŒ Bad Practice +```tsx +function MassiveDashboard() { + // 500 lines of state and hooks + // 1000 lines of JSX layout + return
    ...
    ; +} +``` +### โš ๏ธ Problem +Massive components are difficult to read, test, and maintain. They violate the Single Responsibility Principle and trigger overly broad re-renders when local state changes. +### โœ… Best Practice +```tsx +function Dashboard() { + return ( + + + + + ); +} +``` +### ๐Ÿš€ Solution +Break down the UI into smaller, reusable components. Extract logic into custom hooks and modularize presentational elements into separate, encapsulated files. diff --git a/frontend/react/readme.md b/frontend/react/readme.md index c62e2b8..fdec094 100644 --- a/frontend/react/readme.md +++ b/frontend/react/readme.md @@ -20,69 +20,11 @@ last_updated: 2026-03-22 - Adhere to the defined [Architectural Patterns](../../architectures/readme.md) when building applications. - Strongly prefer **Feature Sliced Design (FSD)** for applications scaling across multiple teams. -## ๐Ÿš€ I. Basics & Popular - -### ๐Ÿšจ 1. Direct DOM Manipulation -> [!NOTE] -> **Context:** Updating elements in a React component. -### โŒ Bad Practice -```tsx -function Component() { - const handleClick = () => { - document.getElementById('my-element').style.color = 'red'; - }; - return
    Click me
    ; -} -``` -### โš ๏ธ Problem -Direct DOM manipulation bypasses React's virtual DOM, causing inconsistencies between the actual DOM and React's internal state, leading to forced synchronous layouts and potential XSS vulnerabilities. -### โœ… Best Practice -```tsx -function Component() { - const [isActive, setIsActive] = useState(false); - return ( -
    setIsActive(!isActive)} - > - Click me -
    - ); -} -``` -### ๐Ÿš€ Solution -Always use state and props to drive the UI. React uses a virtual DOM to efficiently update the real DOM based on state changes, ensuring deterministic rendering loops. - -### ๐Ÿšจ 2. Large Component Files -> [!NOTE] -> **Context:** Managing component complexity. -### โŒ Bad Practice -```tsx -function MassiveDashboard() { - // 500 lines of state and hooks - // 1000 lines of JSX layout - return
    ...
    ; -} -``` -### โš ๏ธ Problem -Massive components are difficult to read, test, and maintain. They violate the Single Responsibility Principle and trigger overly broad re-renders when local state changes. -### โœ… Best Practice -```tsx -function Dashboard() { - return ( - - - - - ); -} -``` -### ๐Ÿš€ Solution -Break down the UI into smaller, reusable components. Extract logic into custom hooks and modularize presentational elements into separate, encapsulated files. ## ๐Ÿ“š Specialized Topics For further reading, please refer to the following specialized guides: +- [๐Ÿš€ Basics & Popular](./basics.md) - [๐Ÿ”„ State Management](./state-management.md) - [โšก Performance](./performance.md) - [๐Ÿ›ก๏ธ Security](./security.md) diff --git a/frontend/solidjs/basics.md b/frontend/solidjs/basics.md new file mode 100644 index 0000000..63e21cc --- /dev/null +++ b/frontend/solidjs/basics.md @@ -0,0 +1,29 @@ +--- +technology: SolidJS +domain: frontend +level: Senior/Architect +version: "1.8+" +tags: [best-practices, clean-code, architecture-patterns, vibe-coding, cursor-rules, typescript, software-architecture, system-design, solid-principles, production-ready, programming-standards, react-best-practices, node-js, design-patterns, scalable-code, windsurf-rules, ai-coding, fsd, ddd, enterprise-patterns] +ai_role: Senior SolidJS Expert +last_updated: 2026-03-22 +--- + +# ๐Ÿš€ SolidJS Basics & Popular Patterns + +[โฌ†๏ธ Back to Top](./readme.md) + +### ๐Ÿšจ 1. Using JSX Map for Lists +> [!NOTE] +> **Context:** Rendering Lists +### โŒ Bad Practice +```tsx +return
      {items().map(item =>
    • {item.name}
    • )}
    ; +``` +### โš ๏ธ Problem +Using `.map` creates the DOM nodes once and does not react to array changes optimally, leading to unnecessary re-renders or lost reactivity. +### โœ… Best Practice +```tsx +return
      {item =>
    • {item.name}
    • }
    ; +``` +### ๐Ÿš€ Solution +Use the `` component. It caches DOM elements and handles granular updates when the array changes. diff --git a/frontend/solidjs/readme.md b/frontend/solidjs/readme.md index 628efdd..f67cd34 100644 --- a/frontend/solidjs/readme.md +++ b/frontend/solidjs/readme.md @@ -26,26 +26,11 @@ last_updated: 2026-03-22 - Adhere to the defined [Architectural Patterns](../../architectures/readme.md) when building applications. - Strongly prefer **Feature Sliced Design (FSD)** for applications scaling across multiple teams. ## ๐Ÿš€ I. Basics & Popular -## ๐Ÿšจ 1. Using JSX Map for Lists -> [!NOTE] -> **Context:** Rendering Lists -### โŒ Bad Practice -```tsx -return
      {items().map(item =>
    • {item.name}
    • )}
    ; -``` -### โš ๏ธ Problem -Using `.map` creates the DOM nodes once and does not react to array changes optimally, leading to unnecessary re-renders or lost reactivity. -### โœ… Best Practice -```tsx -return
      {item =>
    • {item.name}
    • }
    ; -``` -### ๐Ÿš€ Solution -Use the `` component. It caches DOM elements and handles granular updates when the array changes. - ## ๐Ÿ“š Specialized Topics For further reading, please refer to the following specialized guides: +- [๐Ÿš€ Basics & Popular](./basics.md) - [๐Ÿš€ Advanced Performance](./performance.md) - [๐Ÿ“ฆ State Management](./state-management.md) - [๐Ÿงช Testing](./testing.md) diff --git a/frontend/typescript/fundamentals.md b/frontend/typescript/fundamentals.md new file mode 100644 index 0000000..e3208d7 --- /dev/null +++ b/frontend/typescript/fundamentals.md @@ -0,0 +1,156 @@ +--- +technology: TypeScript +domain: frontend +level: Senior/Architect +version: 5.5+ +tags: [typescript, type-safety, clean-code, best-practices, architecture] +ai_role: Senior TypeScript Architecture Expert +last_updated: 2026-03-29 +--- + +# ๐Ÿš€ TypeScript Fundamentals + +[โฌ†๏ธ Back to Top](./readme.md) + +### ๐Ÿšจ 1. `any` vs `unknown` +> [!NOTE] +> **Context:** Handling data of an uncertain type. `any` disables all type-checking, while `unknown` forces safety. +### โŒ Bad Practice +```typescript +function process(data: any) { + console.log(data.name); // No error, but might crash at runtime +} +``` +### โš ๏ธ Problem +`any` is a "get out of jail free" card that propagates through the codebase, effectively turning off TypeScript's benefits and hiding potential runtime exceptions. +### โœ… Best Practice +```typescript +function process(data: unknown) { + if (data && typeof data === 'object' && 'name' in data) { + console.log((data as { name: string }).name); + } +} +``` +### ๐Ÿš€ Solution +Use `unknown` for values whose type is not yet determined. It requires a type check or assertion before usage, ensuring the developer acknowledges the data's structure. + +### ๐Ÿšจ 2. `null` vs `undefined` in APIs +> [!NOTE] +> **Context:** Distinguishing between "value not provided" and "value is empty." +### โŒ Bad Practice +```typescript +interface UserResponse { + bio: string | null | undefined; +} +``` +### โš ๏ธ Problem +Using both creates ambiguity. In JSON, `undefined` properties are often stripped, while `null` is preserved. Mixing them increases complexity in conditional checks. +### โœ… Best Practice +```typescript +interface UserResponse { + bio?: string | null; // Optional if missing, null if explicitly empty +} +``` +### ๐Ÿš€ Solution +Standardize: use `undefined` (optional properties) for missing keys and `null` for intentional absence of value. Avoid using both for the same field unless strictly required by a legacy API. + +### ๐Ÿšจ 3. `Array` vs `T[]` +> [!NOTE] +> **Context:** Visual consistency in array declarations. +### โŒ Bad Practice +```typescript +const users: Array = []; +const complex: Array = []; +``` +### โš ๏ธ Problem +`Array` is more verbose and can be confused with other generic types. It is harder to scan in complex signatures. +### โœ… Best Practice +```typescript +const users: User[] = []; +const complex: (string | number)[] = []; +``` +### ๐Ÿš€ Solution +Prefer the shorthand `T[]`. It is idiomatic, more readable, and clearly distinguishes arrays from other generic containers like `Record` or `Promise`. + +### ๐Ÿšจ 4. `interface` vs `type` +> [!NOTE] +> **Context:** Defining object structures and aliases. +### โŒ Bad Practice +```typescript +type Point = { x: number; y: number; }; // Bad: Using type for object structure +interface Status { status: "active" | "inactive"; } // Bad: Trying to use interface for a union-like structure +``` +### โš ๏ธ Problem +Using `type` for object structures prevents declaration merging and reduces performance in TS compiler caching. Using `interface` for unions is impossible or leads to awkward wrapper objects. +### โœ… Best Practice +```typescript +interface Point { x: number; y: number; } +type Status = "active" | "inactive"; +``` +### ๐Ÿš€ Solution +> [!IMPORTANT] +> Prefer `interface` for structure, `type` for unions. Interfaces provide better error messages and performance for structural types in TypeScript 5.x. + +### ๐Ÿšจ 5. Function Overloads vs Union Types +> [!NOTE] +> **Context:** Handling functions with different input/output combinations. +### โŒ Bad Practice +```typescript +function format(input: string): string; +function format(input: number): string; +function format(input: any): string { + return String(input); +} +``` +### โš ๏ธ Problem +Overloads are verbose and can be harder to implement correctly. They often require `any` or complex type-casting in the implementation body. +### โœ… Best Practice +```typescript +function format(input: string | number): string { + return String(input); +} +``` +### ๐Ÿš€ Solution +Prefer Union types when the implementation logic is identical for all types. Reserve overloads only for cases where the return type strictly depends on the input type and cannot be expressed via generics. + +### ๐Ÿšจ 6. Global Scope Pollution (Legacy Namespaces) +> [!NOTE] +> **Context:** Organizing code in the ES Module era. +### โŒ Bad Practice +```typescript +namespace Utils { + export const log = (msg: string) => console.log(msg); +} +``` +### โš ๏ธ Problem +Namespaces are a legacy TypeScript feature. They don't play well with modern bundlers (Tree Shaking), are harder to test, and can lead to naming collisions in the global scope. +### โœ… Best Practice +```typescript +// utils.ts +export const log = (msg: string) => console.log(msg); +``` +### ๐Ÿš€ Solution +Use ES Modules (`export`/`import`). They are the industry standard, supported by all modern environments, and allow for better static analysis. + +### ๐Ÿšจ 7. `enum` vs `const object` +> [!NOTE] +> **Context:** Grouping related constants. +### โŒ Bad Practice +```typescript +enum Status { + Active, + Inactive +} +``` +### โš ๏ธ Problem +Enums generate extra runtime code and have "reverse mapping" behavior that can lead to bugs (e.g., `Status[0]` returns "Active"). They also don't align with "TypeScript as a type-only layer." +### โœ… Best Practice +```typescript +const STATUS = { + ACTIVE: 'active', + INACTIVE: 'inactive' +} as const; +type Status = typeof STATUS[keyof typeof STATUS]; +``` +### ๐Ÿš€ Solution +Use `const` objects with `as const` and a derived union type. This is more predictable, emits cleaner code, and is easier to iterate over. diff --git a/frontend/typescript/readme.md b/frontend/typescript/readme.md index 415b8c4..fabe414 100644 --- a/frontend/typescript/readme.md +++ b/frontend/typescript/readme.md @@ -12,154 +12,9 @@ last_updated: 2026-03-29 ![TypeScript Logo](https://img.icons8.com/?size=100&id=uJM6fQYqDaZK&format=png&color=000000) ## ๐Ÿš€ I. Fundamentals (1-10) -## โšก 1. `any` vs `unknown` -> [!NOTE] -> **Context:** Handling data of an uncertain type. `any` disables all type-checking, while `unknown` forces safety. -### โŒ Bad Practice -```typescript -function process(data: unknown) { - console.log(data.name); // No error, but might crash at runtime -} -``` -### โš ๏ธ Problem -`any` is a "get out of jail free" card that propagates through the codebase, effectively turning off TypeScript's benefits and hiding potential runtime exceptions. -### โœ… Best Practice -```typescript -function process(data: unknown) { - if (data && typeof data === 'object' && 'name' in data) { - console.log((data as { name: string }).name); - } -} -``` -### ๐Ÿš€ Solution -Use `unknown` for values whose type is not yet determined. It requires a type check or assertion before usage, ensuring the developer acknowledges the data's structure. ---- -## โšก 2. `null` vs `undefined` in APIs -> [!NOTE] -> **Context:** Distinguishing between "value not provided" and "value is empty." -### โŒ Bad Practice -```typescript -interface UserResponse { - bio: string | null | undefined; -} -``` -### โš ๏ธ Problem -Using both creates ambiguity. In JSON, `undefined` properties are often stripped, while `null` is preserved. Mixing them increases complexity in conditional checks. -### โœ… Best Practice -```typescript -interface UserResponse { - bio?: string | null; // Optional if missing, null if explicitly empty -} -``` -### ๐Ÿš€ Solution -Standardize: use `undefined` (optional properties) for missing keys and `null` for intentional absence of value. Avoid using both for the same field unless strictly required by a legacy API. ---- -## โšก 3. `Array` vs `T[]` -> [!NOTE] -> **Context:** Visual consistency in array declarations. -### โŒ Bad Practice -```typescript -const users: Array = []; -const complex: Array = []; -``` -### โš ๏ธ Problem -`Array` is more verbose and can be confused with other generic types. It is harder to scan in complex signatures. -### โœ… Best Practice -```typescript -const users: User[] = []; -const complex: (string | number)[] = []; -``` -### ๐Ÿš€ Solution -Prefer the shorthand `T[]`. It is idiomatic, more readable, and clearly distinguishes arrays from other generic containers like `Record` or `Promise`. ---- -## โšก 4. `interface` vs `type` -> [!NOTE] -> **Context:** Defining object structures and aliases. -### โŒ Bad Practice -```typescript -type Point = { x: number; y: number; }; // Bad: Using type for object structure -interface Status { status: "active" | "inactive"; } // Bad: Trying to use interface for a union-like structure -``` -### โš ๏ธ Problem -Using `type` for object structures prevents declaration merging and reduces performance in TS compiler caching. Using `interface` for unions is impossible or leads to awkward wrapper objects. -### โœ… Best Practice -```typescript -interface Point { x: number; y: number; } -type Status = "active" | "inactive"; -``` -### ๐Ÿš€ Solution -> [!IMPORTANT] -> Prefer `interface` for structure, `type` for unions. Interfaces provide better error messages and performance for structural types in TypeScript 5.x. -> -> **Logical Conflict Resolution:** To enforce the repo standard, NEVER use `type` for defining object structures, and NEVER use `interface` for unions. ---- -## โšก 5. Function Overloads vs Union Types -> [!NOTE] -> **Context:** Handling functions with different input/output combinations. -### โŒ Bad Practice -```typescript -function format(input: string): string; -function format(input: number): string; -function format(input: unknown): string { - return String(input); -} -``` -### โš ๏ธ Problem -Overloads are verbose and can be harder to implement correctly. They often require `any` or complex type-casting in the implementation body. -### โœ… Best Practice -```typescript -function format(input: string | number): string { - return String(input); -} -``` -### ๐Ÿš€ Solution -Prefer Union types when the implementation logic is identical for all types. Reserve overloads only for cases where the return type strictly depends on the input type and cannot be expressed via generics. ---- -## ๐ŸŽฏ 6. Global Scope Pollution (Legacy Namespaces) -> [!NOTE] -> **Context:** Organizing code in the ES Module era. -### โŒ Bad Practice -```typescript -namespace Utils { - export const log = (msg: string) => console.log(msg); -} -``` -### โš ๏ธ Problem -Namespaces are a legacy TypeScript feature. They don't play well with modern bundlers (Tree Shaking), are harder to test, and can lead to naming collisions in the global scope. -### โœ… Best Practice -```typescript -// utils.ts -export const log = (msg: string) => console.log(msg); -``` -### ๐Ÿš€ Solution -Use ES Modules (`export`/`import`). They are the industry standard, supported by all modern environments, and allow for better static analysis. ---- -## โšก 7. `enum` vs `const object` -> [!NOTE] -> **Context:** Grouping related constants. -### โŒ Bad Practice -```typescript -enum Status { - Active, - Inactive -} -``` -### โš ๏ธ Problem -Enums generate extra runtime code and have "reverse mapping" behavior that can lead to bugs (e.g., `Status[0]` returns "Active"). They also don't align with "TypeScript as a type-only layer." -### โœ… Best Practice -```typescript -const STATUS = { - ACTIVE: 'active', - INACTIVE: 'inactive' -} as const; -type Status = typeof STATUS[keyof typeof STATUS]; -``` -### ๐Ÿš€ Solution -Use `const` objects with `as const` and a derived union type. This is more predictable, emits cleaner code, and is easier to iterate over. ---- - Please refer to the specialized guides for detailed best practices: +- [๐Ÿš€ Fundamentals](./fundamentals.md) - [๐Ÿ“œ Types & Interfaces](./types-interfaces.md) - [๐Ÿ›ก๏ธ Logic Safety](./logic-safety.md)