Security News
Highlights from the 2024 Rails Community Survey
A record 2,709 developers participated in the 2024 Ruby on Rails Community Survey, revealing key tools, practices, and trends shaping the Rails ecosystem.
@innova2/ngx-http-helper
Advanced tools
A lightweight library to easily call your APIs and add JWT token or API key on each header request
A lightweight library to easily call your APIs and add JWT token or API key on each header request
The signature of the following methods changes:
This library allows :
To import the library you just need to run this command :
ng add @innova2/ngx-http-helper
You need to install UrlBuilder to use this library
npm install @innova2/url-builder
Import the module and configure it according to your choices.
@NgModule({
...
imports: [
...
NgxHttpHelperModule.forRoot({<options here>})
],
})
export class AppModule {}
You can specify multiple interceptors by domain(s) and token. For example, if you need to add an API key to the domain 'foo.sample.com' and a JWT to 'bar.sample.com':
NgxHttpHelperModule.forRoot({
authenticators: [{
tokenSelector: () => of('My API Key'),
domains: ['https://foo.sample.com'],
// This add the 'My API Key' to 'Authorization' header of each request to 'https://foo.sample.com'
}, {
tokenSelector: () => of('My JWT Token'),
scheme: 'Bearer',
domains: ['https://bar.sample.com'],
// This add the 'Bearer My JWT Token' to 'Authorization' header of each request to 'https://bar.sample.com'
}],
})
As you can see, to transmit your token or API key, you must create the 'tokenSelector' function and return an observable of your token. Also, you can target specific domains for each token. Note: You can target all domains by removing the 'domains' property.
For JWT token, you can add scheme 'Bearer' (or another) to prefix the token (e.g. Bearer My JWT Token).
You can also change the header name by setting the property 'header'.
NgxHttpHelperModule.forRoot({
authenticators: [{
tokenSelector: () => of('My API Key'),
domains: ['https://foo.sample.com'],
header: 'X-Api-Key'
}],
})
The ApiClient provide methods to call HttpClient easily:
The 'Content-Type' is automatically set to 'application/json' and the 'observe' is set to 'response'. You can override all options with the 'opts' params of methods:
import { ApiClient } from '@innova2/ngx-http-helper';
import { UrlBuilder } from '@innova2/url-builder';
@Component(...)
class ListUsersComponent {
url = UrlBuilder.createFromUrl('https://foo.sample.com/users');
constructor(private apiClient: ApiClient) {}
getUsers() {
const cache = {
ttl: 10, // in seconds (ngx-http-helper use ionic-cache)
group: 'users'
};
const options = {
'Content-Type': 'application/xml' // if you want to override json ContentType
// All options are those provided by Angular's HttpClient
};
this.apiClient.get(this.url, cache, options).subscribe(users => ...);
}
addUser(user: User) {
this.apiClient.post(this.url, user).subscribe(() => ...);
}
}
If you must catch all http errors, you can set the 'catch' property to the module configuration:
NgxHttpHelperModule.forRoot({
client: [{
catch: (err) => {
console.log('Oh snap, an error occured', err);
throwError(() => ({
...err,
foo: 'bar'
}));
}
}],
})
To use this service, you need to create your own child of RestService. Don't call directly the RestService.
Configure it from the module configuration:
NgxHttpHelperModule.forRoot({
client: [{
baseUrl: 'https://foo.sample.com',
defaultCacheTTL: 100
}],
})
See this example:
import { RestService } from '@innova2/ngx-http-helper';
interface User {
id: string;
name: string;
avatar: string;
createdAt: string;
}
@Injectable(...)
export class UserService extends RestService<User> {
protected override readonly resourceUri = 'users';
}
Then, call your service:
@Component(...)
class ListUsersComponent {
constructor(private userService: UserService) {}
getUsers() {
this.userService.findAll().subscribe(users => ...);
// This automatically call in GET method the 'https://foo.sample.com/users'
// If your web service is paginated
const numPage = 1;
this.userService.findAll(numPage).subscribe(page => ...);
}
getUser(id: string) {
this.userService.findById(id).subscribe(user => ...);
}
addUser(user: User) {
this.userService.create(user).subscribe(() => ...);
// In RESTful, your web service does not return the user but add the 'location' header to the response
// If you want automatically can this location to retrieve the created user,
// you can do it by passing the parameter 'callIdentifier' to true
this.userService.create(user, {}, {}, true).subscribe((user) => ...);
}
}
You can override the resourceUri for specific call if needed:
import { RestService } from '@innova2/ngx-http-helper';
interface User {
id: string;
name: string;
avatar: string;
createdAt: string;
}
@Injectable(...)
export class UserService extends RestService<User> {
protected override readonly resourceUri = 'users';
findAllByRoleId(roleId: number) {
return this.findAll({
resourceUri: 'roles/:roleId/users',
params: { roleId }
});
}
}
We are not using the 'resourceUri' class property here, but instead we are using that provided as a function argument 'opts' (options).
export interface IAuthConfig {
tokenSelector: () => Observable<string>;
header?: string;
scheme?: string;
domains?: string[];
}
export interface IClientConfig {
baseUrl?: string;
defaultCacheTTL?: number;
catch?: (err: any, caught: Observable<any>) => ObservableInput<any>;
}
export class Config {
authenticators: IAuthConfig[] = [];
client: IClientConfig = {};
}
get<T>(url: UrlBuilder, cache?: CacheOptions, opts?: any): Observable<HttpResponse<T>>
post<T>(url: UrlBuilder, data: any, opts?: any): Observable<HttpResponse<T>>
put<T>(url: UrlBuilder, data: any, opts?: any): Observable<HttpResponse<T>>
patch<T>(url: UrlBuilder, data: any, opts?: any): Observable<HttpResponse<T>>
delete<T>(url: UrlBuilder, data?: any, opts?: any): Observable<HttpResponse<T>>
protected readonly baseUrl = this.config.client.baseUrl;
protected readonly resourceUri!: string;
findAll(opts?: FindAllOptions): Observable<O[]>;
findAll(page: number, opts?: FindAllOptions): Observable<PaginatedData<O>>;
findAll(pageOrOpts?: number | FindAllOptions, opts?: FindAllOptions): any;
findById(id: string | number, opts: FindOptions = {}): Observable<O>;
create(data: Partial<I>, opts: BaseApiOptions = {}, callIdentifier = false): Observable<O>;
update(id: string, data: Partial<I>, opts: BaseApiOptions = {}): Observable<O>;
delete(id: string, opts: BaseApiOptions = {}, data?: Partial<I>): Observable<HttpResponse<void>>;
protected initializeCacheOptions = (url: UrlBuilder, ttl?: number): CacheOptions;
The initializeCacheOptions return by default:
{
group: url.getRelativePath(),
ttl: ttl ?? this.config.client.defaultCacheTTL ?? 0,
}
Note: You can override this function.
Do not hesitate to participate in the project! Contributors list will be displayed below.
FAQs
A lightweight library to easily call your APIs and add JWT token or API key on each header request
The npm package @innova2/ngx-http-helper receives a total of 2 weekly downloads. As such, @innova2/ngx-http-helper popularity was classified as not popular.
We found that @innova2/ngx-http-helper demonstrated a healthy version release cadence and project activity because the last version was released less than a year ago. It has 2 open source maintainers collaborating on the project.
Did you know?
Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.
Security News
A record 2,709 developers participated in the 2024 Ruby on Rails Community Survey, revealing key tools, practices, and trends shaping the Rails ecosystem.
Security News
In 2023, data breaches surged 78% from zero-day and supply chain attacks, but developers are still buried under alerts that are unable to prevent these threats.
Security News
Solo open source maintainers face burnout and security challenges, with 60% unpaid and 60% considering quitting.