HTTP Resource Plugin โ
Generate Angular services using the httpResource API for automatic caching, state management, and reactive data loading.
Overview โ
The HTTP Resource plugin extends ng-openapi to generate services that leverage Angular's new httpResource API instead of traditional HttpClient. This provides built-in caching, loading states, error handling, and reactive updates through Angular Signals.
Installation โ
Install the plugin alongside ng-openapi:
npm install ng-openapi @ng-openapi/http-resource --save-devConfiguration โ
Add the plugin to your OpenAPI configuration:
// openapi.config.ts
import { GeneratorConfig } from "ng-openapi";
import { HttpResourcePlugin } from "@ng-openapi/http-resource";
export default {
input: "./swagger.json",
output: "./src/api",
clientName: "MyApi",
plugins: [HttpResourcePlugin],
options: {
dateType: "Date",
enumStyle: "enum",
},
} as GeneratorConfig;Generation โ
Generate your API resources:
ng-openapi -c openapi.config.tsThis creates both traditional services and HTTP resource services:
src/api/
โโโ models/ # TypeScript interfaces
โโโ services/ # Traditional HttpClient services
โโโ resources/ # HTTP Resource services
โ โโโ index.ts # Resource exports
โ โโโ *.resource.ts # Generated resources
โโโ providers.ts # Provider functions
โโโ index.ts # Main exportsProvider Setup โ
Configure the provider in your application:
// app.config.ts
import { ApplicationConfig } from "@angular/core";
import { provideMyApiClient } from "./api/providers";
export const appConfig: ApplicationConfig = {
providers: [
provideMyApiClient({
basePath: "https://api.example.com",
}),
],
};Basic Usage โ
Inject and use the generated resources in your components:
import { Component, inject } from "@angular/core";
import { UsersResource } from "./api/resources";
@Component({
selector: "app-users",
template: `
<div>
@if (users.isLoading()) {
<p>Loading users...</p>
} @else if (users.error()) {
<p>Error: {{ users.error()?.message }}</p>
} @else {
@for (user of users.value(); track user.id) {
<div>{{ user.name }}</div>
}
}
</div>
`,
})
export class UsersComponent {
private readonly usersResource = inject(UsersResource);
readonly users = this.usersResource.getUsers();
}Dynamic Parameters โ
Use Signals for reactive parameter binding:
export class UserDetailComponent {
private readonly usersResource = inject(UsersResource);
private readonly userId = signal(1);
// Automatically refetches when userId changes
readonly user = this.usersResource.getUserById(this.userId);
updateUser(newId: number) {
this.userId.set(newId); // Triggers automatic refetch
}
}Default Values โ
Provide fallback values while data is loading:
export class UsersComponent {
private readonly usersResource = inject(UsersResource);
readonly users = this.usersResource.getUsers({ defaultValue: [] });
}Query Parameters โ
Pass both static and reactive query parameters:
export class SearchComponent {
private readonly usersResource = inject(UsersResource);
private readonly searchTerm = signal("");
private readonly pageSize = signal(10);
readonly searchResults = this.usersResource.searchUsers(
this.searchTerm, // reactive search term
this.pageSize, // reactive page size
"active", // static status filter
);
updateSearch(term: string) {
this.searchTerm.set(term);
}
}Resource vs Service Comparison โ
| Feature | HTTP Resource | Traditional Service |
|---|---|---|
| Loading State | โ
Built-in isLoading() | โ Manual state management |
| Error Handling | โ
Built-in error() | โ Manual error handling |
| Reactivity | โ Signal-based | โ Observable-based |
| Parameter Binding | โ Signal or static | โ Manual subscription |
| Request Deduplication | โ Automatic | โ Manual implementation |
| Maturity | โ Stable | โ Stable |
Limitations โ
- GET Requests Only: Currently optimized for "GET" requests (see Angular Docs โ๏ธ)