TS-Rpc
TS-Rpc is a Typescript-library of decorators for abstraction of transport layers and data transformation
Quick Example
import { IHttpClient, IRpcMethodConfig, IRpcServiceConfig, TSRpc, TSRpcError } from 'ts-rpc';
import { deserialize, JsonName, serialize } from 'tserialize';
import { guid } from 'some-guid-generator';
/* Example transport layer */
class JsonRpcTransportLayer implements IHttpClient {
/* This is being set somewhere outside of this class */
public static $http: ng.IHttpService;
post(url: string, data: any, serviceConfig: any, methodConfig: any): any {
const { $http } = JsonRpcTransportLayer;
return new Promise((resolve, reject): void => {
$http.post(url, data, this.requestConfig)
.then(resolve)
.catch(reject);
});
}
}
/* Example model */
class BaseRequest {
@JsonName()
secret: string;
static fromServer = (obj: any): BaseRequest => deserialize(obj, BaseRequest);
toServer = (): any => serialize(this);
}
interface IJsonRpcMethodConfig extends IRpcMethodConfig {
method: string;
responseModel?: { fromServer(rawData: object): any };
}
const servicePreprocessor = (request: any, serviceConfig: IRpcServiceConfig, methodConfig: IJsonRpcMethodConfig) => ({
id: guid(),
method: methodConfig.method,
params: request
});
const servicePostprocessor = (request: any) => request.result;
export const JsonRpcService = TSRpc.makeClassDecorator({
apiUrl: '/api/v1',
httpClient: new JsonRpcTransportLayer()
});
const methodPreprocessor = (request?: any, config: IMethodConfig) => request ? request.toServer() : null;
const methodPostprocessor = (
responseObject: Promise<any>,
serviceConfig: IRpcServiceConfig,
methodConfig: IJsonRpcMethodConfig
) => responseObject
.catch(httpError => throw TSError.makeHttpError(httpError.status, httpError.statusText))
.then(({ responseModel, result }) => responseModel ? responseModel.fromServer(result) : void 0);
export const JsonRpcMethod = TSRpc.makeMethodDecorator<{ toServer(): object }, IMethodConfig>(
methodPreprocessor,
methodPostprocessor
);
API
Class decorator factory
TSRpc.makeClassDecorator(config: IRpcServiceConfig)
Method decorator factory
TSRpc.makeMethodDecorator<TRequest, TPayload>(
preprocessors: (request: TRequest) => any,
postprocessors: (response: any, payload: TPayload) => any,
transportFactory?: () => IHttpClient
)
Ideas
- Add generics to adapter if possible