SKILL: Angular Moderno (SkullRender Standard)
[!IMPORTANT] Filosofía: Componentes Standalone, Signals para estado y Rendimiento. Basado en la documentación oficial de Angular y el estándar Gentleman.
Documentation: angular.dev
Related Workflows
/create-angular19-app-global— Create new Angular 19 app with SSR and GitHub integration
When to Use
- Siempre que se escriba código Angular (Componentes, Servicios, Pipes).
- En refactorizaciones de módulos legacy a Standalone.
Critical Patterns (The "Must Haves")
1. Arquitectura de Componentes
- Standalone: Todo componente debe ser
standalone: true. - Separación de Archivos: Obligatorio usar
templateUrlystyleUrl. Prohibido template/styles inline (salvo componentes triviales < 3 líneas). - ChangeDetection: Siempre
ChangeDetectionStrategy.OnPush. - Inject: Usar
inject()en lugar de inyección por constructor.
2. Gestión de Estado (Signals)
- Inputs: Usar
input()yinput.required(). - Outputs: Usar
output(). - State: Preferir
signal()ycomputed()sobreBehaviorSubjectpara estado síncrono local. - Effects: Usar
effect()con precaución, solo para efectos secundarios (logging, sync manual).
3. Control Flow & Defer
- Sintaxis: Usar
@if,@for,@switch(Nuevo Control Flow). - Defer: Usar
@deferpara cargar componentes pesados no visibles en el viewport inicial.
4. Zoneless Architecture (Angular 19+)
- Zoneless: Usar
provideZonelessChangeDetection(). - No NgZone: Evitar inyectar
NgZone. Usar Signals para disparar actualizaciones de vista. - Async: Evitar
asyncpipe si es posible, preferirtoSignal()orxResource(Angular 19).
5. Shell Compatibility (Windows/PowerShell)
- Command Chaining: ❌ DO NOT use
&&for chaining commands.- Reason: It fails in standard Windows PowerShell (v5.1).
- Solution: Run commands sequentially or use
;if you are sure about the shell, but sequentialrun_commandcalls are safer and preferred by the Agent.
Anti-Patterns (The "Never Do's")
- ❌ Usar
NgModules(salvo excepciones muy justificadas). - ❌ Suscribirse manualmente en componentes (
.subscribe()) sin manejar la desuscripción (preferirasyncpipe o Signals). - ❌ Usar decoradores viejos
@Input(),@Output()(preferir Signals API). - ❌ Lógica de negocio compleja dentro del componente (mover a Servicios/Facades).
Code Examples
Good: Modern Component
@Component({
standalone: true,
selector: 'app-user-profile',
imports: [CommonModule, UserAvatarComponent],
template: `
@if (user(); as u) {
<app-user-avatar [url]="u.avatarUrl" />
<h1>{{ u.name }}</h1>
} @else {
<p>Loading...</p>
}
`,
changeDetection: ChangeDetectionStrategy.OnPush
})
export class UserProfileComponent {
private userService = inject(UserService);
// Signal Input
userId = input.required<string>();
// Computed State
user = toSignal(this.userService.getUser(this.userId()));
}