Angular patterns — standalone components, signals, inject(), reactive forms, HTTP interceptors, and new control flow
95
94%
Does it follow best practices?
Impact
99%
2.75xAverage score across 4 eval scenarios
Passed
No known issues
{
"context": "Tests whether the agent proactively applies Angular best practices when building an employee directory. The task describes only business requirements -- it says nothing about standalone components, signals, OnPush, inject(), or new control flow syntax. The agent should apply these patterns on its own.",
"type": "weighted_checklist",
"checklist": [
{
"name": "Standalone components",
"description": "All components use standalone: true in their @Component decorator. No NgModule classes are created.",
"max_score": 12
},
{
"name": "Signal inputs on card component",
"description": "The employee card component uses input() or input.required() from @angular/core for its employee data, NOT the @Input() decorator.",
"max_score": 12
},
{
"name": "inject() for dependency injection",
"description": "Services and dependencies are injected using the inject() function, NOT constructor parameter injection.",
"max_score": 12
},
{
"name": "toSignal() for observable conversion",
"description": "The component converts the service observable to a signal using toSignal() rather than manually subscribing in ngOnInit.",
"max_score": 12
},
{
"name": "OnPush change detection",
"description": "Components use changeDetection: ChangeDetectionStrategy.OnPush.",
"max_score": 10
},
{
"name": "New control flow syntax",
"description": "Templates use @for (with track expression) and @if instead of *ngFor and *ngIf structural directives.",
"max_score": 12
},
{
"name": "Service uses catchError with fallback",
"description": "The HTTP service method pipes through catchError and returns a fallback value (e.g. empty array) rather than letting errors propagate unhandled.",
"max_score": 10
},
{
"name": "Service uses map() to unwrap response",
"description": "The service uses map() in the RxJS pipe to extract the data array from the API response wrapper object, not passing through the raw response.",
"max_score": 8
},
{
"name": "providedIn root on service",
"description": "The employee service uses @Injectable({ providedIn: 'root' }).",
"max_score": 6
},
{
"name": "Track expression in @for",
"description": "The @for loop uses a track expression (e.g. track employee.id), not trackBy or no tracking.",
"max_score": 6
}
]
}