UNPKG

@granito/ngx-hal-client

Version:

A HAL client to be used in Angular projects

368 lines (359 loc) 12.9 kB
import { Type, InjectionToken, EnvironmentProviders } from '@angular/core'; import { Observable, OperatorFunction } from 'rxjs'; import { HttpClient, HttpErrorResponse } from '@angular/common/http'; /** * This class represents errors thrown by _Angular HAL Client_. It * unifies errors produced by _Angular HTTP Client_ and errors originating * in the API. */ declare class HalError extends Error { /** * The URI path where the error originated. */ path?: string; /** * The HTTP status code of the error. */ status?: number; /** * The description of the HTTP status. */ error?: string; /** * Free form error properties. */ [key: string]: any; /** * @param err the object used to set properties */ constructor(err: any); } interface Link { readonly href: string; readonly templated?: boolean; readonly methods?: string[]; } /** * The common base for resource and accessor. */ declare abstract class HalBase { protected readonly _client: HttpClient; protected readonly _links: Readonly<Record<string, Link>>; protected readonly _embedded: Readonly<Record<string, Object>>; /** * The URI of `self` link. */ get self(): string; /** * This property is `true` when the `self` link exists and either * `methods` array does not exist in the `self` link or the array * exists and contains `POST` string. It is `false` otherwise. */ get canCreate(): boolean; /** * This property is `true` when the `self` link exists and either * `methods` array does not exist in the `self` link or the array * exists and contains `GET` string. It is `false` otherwise. */ get canRead(): boolean; /** * This property is `true` when the `self` link exists and either * `methods` array does not exist in the `self` link or the array * exists and contains `DELETE` string. It is `false` otherwise. */ get canDelete(): boolean; /** * @param obj the object used to assign the properties */ constructor(obj: Object); /** * Create a new resource in the collection identified by `self` link. * It makes a `POST` call to the URI in `self` link and returns an * observable for the call. The observable emits an accessor for * the newly created resource. The `self` link in the accessor * may be set to `undefined` if `Location` header is not returned by * the call. * * @param obj the payload for the `POST` method call * @returns an observable of the resource's accessor */ create(obj: any): Observable<Accessor>; /** * Delete the resource identified by `self` link. * * @returns an observable that emits next signal on successful delete */ delete(): Observable<void>; protected withUriFor<T>(method: string, func: (x: string) => Observable<T>): Observable<T>; protected accessor(href?: string, methods?: string[]): Accessor; protected instanceOf<T>(type: Type<T>, obj: Object): T; protected roInstanceOf<T>(type: Type<T>, obj: Object): T; protected handleError(err: HttpErrorResponse): Observable<never>; protected uriFor(method: string): string | undefined; } /** * This type represent parameters for templated links. */ type Params = Record<string, string | number | boolean>; /** * This class represents an in-memory instance of a HAL resource. */ declare class Resource extends HalBase { /** * This property is `true` when the `self` link exists and either * `methods` array does not exist in the `self` link or the array * exists and contains `PUT` string. It is `false` otherwise. */ get canUpdate(): boolean; /** * Follow the relation link. Returns an accessor for the resource. * The `self` link in the accessor is set to `undefined` if no such * relation exists. * * @param rel the name of the relation link * @param params parameters for a templated link * @returns an accessor for the linked resource */ follow(rel: string, params?: Params): Accessor; /** * Refresh the resource. In other words, read the resource * identified by `self` link. * * @returns an observable of the refreshed resource instance */ read(): Observable<this>; /** * Persist the resource. Uses `PUT` request to send the new resource * state. * * @returns an observable of the resource instance */ update(): Observable<this>; /** * Returns a single embedded resource or `undefined` if no such * embedded exists. If the named resource is an array it returns * the first element. * * @param type the resource type * @param rel the name of the embedded resource * @returns the resource or `undefined` */ get<T extends Resource>(type: Type<T>, rel: string): T | undefined; /** * Returns an embedded array of resources or `undefined` if the named * embedded does not exist. If the named resource is not an array it * wraps the resource in an array. * * @param type the element resource type * @param rel the name of the embedded resource array * @returns the resource array or `undefined` */ getArray<T extends Resource>(type: Type<T>, rel: string): T[] | undefined; /** * Clones the resource instance and allows to modify the clone's * properties using the provided function. * * @param update the update function to apply to the clone * @returns the updated clone of the resource */ mutate(update: (x: this) => void): this; protected roArrayOf<T extends Resource>(type: Type<T>, values: Object[]): T[]; } /** * This class represents an in-memory collection of resources. */ declare class Collection<T extends Resource> extends Resource { private readonly type; /** * Zero-based offset of the first element of the `values` array in * the collection. */ readonly start: number; /** * A page of values of the collection starting with `start` offset. */ readonly values: T[]; /** * @param type the element resource type * @param obj the object used to assign the properties */ constructor(type: Type<T>, obj: any); /** * Follow the `next` link. If the link does not exist, the accessor * will have the `self` link set to `undefined`. * * @returns the accessor for the link */ next(): Accessor; /** * Follow the `prev` link. If the link does not exist, the accessor * will have the `self` link set to `undefined`. * * @returns the accessor for the link */ prev(): Accessor; /** * Refresh the resource collection. In other words, read * the resource collection identified by `self` link. * * @returns an observable of the refreshed resource collection * instance */ read(): Observable<this>; } /** * Convert any item to {@link Object} or {@link Array}. On conversion * HAL-related properties (`_client`, `_links`, `_embedded`) * are not included in the resulting object. Primitive types * as well as `null` or `undefined` are returned unchanged. * If the argument is an array, every item of the returned array * is converted recursively. For {@link Collection} it returns * the array of values where each item is converted recursively. * * @param item the item to convert * @returns an object, array, primitive value, `undefined` or `null` */ declare function objectFrom(item: any): any; /** * @param arg argument to test * @returns `false` if the argument is `null` or `undefined` and `true` * otherwise */ declare function isDefined<T>(arg: T | null | undefined): arg is T extends null | undefined ? never : T; /** * Returns an RxJS operator that makes the source {@link Observable} * complete at the same time as the lifetime {@link Observable}. * * @param lifetime the lifetime observable * @returns a function that transforms the source {@link Observable} */ declare function completeWith<T>(lifetime: Observable<any>): OperatorFunction<T, T>; /** * Returns an RxJS operator to follow a link on a {@link Resource}. It is * equivalent to * ```ts * map(resource => resource.follow(rel, params)) * ``` * * @param rel the relation to follow * @param params the parameters to expand the link * @returns a function that transforms the source {@link Observable} */ declare function follow(rel: string, params?: Params): OperatorFunction<Resource, Accessor>; /** * Returns an RxJS operator to create a new resource identified by * an {@link Accessor} or a {@link Resource}. It is equivalent to * ```ts * switchMap(x => x.create(obj)) * ``` * * @param obj the value for the resource * @returns a function that transforms the source {@link Observable} */ declare function create(obj: any): OperatorFunction<Accessor | Resource, Accessor>; /** * Returns an RxJS operator to read a {@link Resource} using an * {@link Accessor}. It is equivalent to * ```ts * switchMap(accessor => accessor.read(type)) * ``` * * @param type the resource type * @returns a function that transforms the source {@link Observable} */ declare function read<T extends Resource>(type: Type<T>): OperatorFunction<Accessor, T>; /** * Returns an RxJS operator to read a {@link Collection} of resources * using an {@link Accessor}. It is equivalent to * ```ts * switchMap(accessor => accessor.readCollection(type)) * ``` * * @param type the collection element type * @returns a function that transforms the source {@link Observable} */ declare function readCollection<T extends Resource>(type: Type<T>): OperatorFunction<Accessor, Collection<T>>; /** * Returns an RxJS operator to refresh a {@link Resource} or * {@link Collection} of resources. It is equivalent to * ```ts * switchMap(resource => resource.read()) * ``` * * @returns a function that transforms the source {@link Observable} */ declare function refresh<T extends Resource>(): OperatorFunction<T, T>; /** * Returns an RxJS operator to clone a {@link Resource} and modify * the cloned instance using the provided update function. It is * equivalent to * ```ts * map(resource => resource.mutate(update)) * ``` * * @param update the update function to apply * @returns a function that transforms the source {@link Observable} */ declare function mutate<T extends Resource>(update: (x: T) => void): OperatorFunction<T, T>; /** * Returns an RxJS operator to update a {@link Resource}. * It is equivalent to * ```ts * switchMap(resource => resource.update()) * ``` * * @returns a function that transforms the source {@link Observable} */ declare function update<T extends Resource>(): OperatorFunction<T, T>; /** * Returns an RxJS operator to delete a resource identified by * an {@link Accessor} or a {@link Resource}. It is equivalent to * ```ts * switchMap(x => x.delete()) * ``` * * @returns a function that transforms the source {@link Observable} */ declare function del(): OperatorFunction<Accessor | Resource, void>; /** * Returns an RxJS operator to filter out `null` and `undefined` items * from the source {@link Observable}. * * @returns a function that transforms the source {@link Observable} */ declare function defined<T>(): OperatorFunction<T | null | undefined, T extends null | undefined ? never : T>; /** * This class provides a way to execute operations on HAL resources * without reading them first. Accessors are obtained either by following * resource links or by getting the root entry point for the API. */ declare class Accessor extends HalBase { /** * Read the resource identified by `self` link. * * @param type the resource type * @returns an observable of the resource instance */ read<T extends Resource>(type: Type<T>): Observable<T>; /** * Read the resource collection identified by `self` link. * * @param type the collection element type * @returns an observable of the collection instance */ readCollection<T extends Resource>(type: Type<T>): Observable<Collection<T>>; } /** * The injection token for HAL root URL. */ declare const HAL_ROOT: InjectionToken<Accessor>; /** * Configure HAL client using the provided the root URL for the API. * * @param url the root URL * @return an array of environment providers with a single factory * provider for the {@link Accessor} for the API root */ declare function provideHalRoot(url: string): EnvironmentProviders; export { Accessor, Collection, HAL_ROOT, HalError, Resource, completeWith, create, defined, del, follow, isDefined, mutate, objectFrom, provideHalRoot, read, readCollection, refresh, update }; export type { Params };