In this article, we will build a professional-grade example using:
- ✅ Angular 19
- ✅ Signals
- ✅ Dependency Injection (Services)
- ✅ Standalone Components
Goal
We will create:
- A service that manages a list of heroes using
signal()
. - A component that displays and adds heroes via the service.
- Clean, reactive, and fully Angular 19-compliant code.
Setting up the Service: HeroService
import { Injectable, signal } from '@angular/core';
export interface Hero {
id: number;
name: string;
}
@Injectable({ providedIn: 'root' })
export class HeroService {
private heroes = signal<Hero[]>([
{ id: 1, name: 'Goku' },
{ id: 2, name: 'Vegeta' }
]);
getHeroes() {
return this.heroes;
}
addHero(hero: Hero) {
this.heroes.update(prev => [...prev, hero]);
}
removeHero(id: number) {
this.heroes.update(prev => prev.filter(h => h.id !== id));
}
}
Building the Component: HeroListComponent
import { Component } from '@angular/core';
import { HeroService } from './hero.service';
import { CommonModule } from '@angular/common';
import { FormsModule } from '@angular/forms';
@Component({
selector: 'app-hero-list',
standalone: true,
template: `
Hero List
{{ hero.name }}
Remove
Add Hero
`,
imports: [CommonModule, FormsModule]
})
export class HeroListComponent {
heroes = signal<Hero[]>([]);
newHeroName = '';
constructor(private heroService: HeroService) {
this.heroes = this.heroService.getHeroes();
}
add() {
if (this.newHeroName.trim()) {
const newHero = { id: Date.now(), name: this.newHeroName.trim() };
this.heroService.addHero(newHero);
this.newHeroName = '';
}
}
remove(id: number) {
this.heroService.removeHero(id);
}
}
How It Works
Layer | Purpose |
---|---|
Service (HeroService) | Owns the signal , responsible for all state |
Component (HeroListComponent) | Subscribes to the signal and reacts automatically |
Template | Renders reactive values via heroes() call |
When you call addHero()
or removeHero()
, the signal updates and the component auto-renders without manual refresh.
Key Best Practices
- Services manage signals, components consume them.
- No manual subscriptions needed.
- Keep services pure and encapsulated.
- Use standalone components for cleaner architecture.
Final Thoughts
Angular 19 is leading towards a lightweight, reactive, modular future. Using Signals and Services properly will make your apps:
- Faster
- More maintainable
- Highly scalable
Use Signals for state, Services for management, and Standalone Components for architecture.
Happy coding with Angular 19! ⚡