Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save alfonmga/8569a2710294e1f9f3f719cbe911443f to your computer and use it in GitHub Desktop.
Save alfonmga/8569a2710294e1f9f3f719cbe911443f to your computer and use it in GitHub Desktop.
Promisify @grpc-js service client with typescript
import { Client, ServiceError, Metadata, CallOptions, ClientUnaryCall } from '@grpc/grpc-js';
import { Message } from 'google-protobuf';
type OriginalCall<T, U> = (request: T, metadata: Metadata, options: Partial<CallOptions>, callback: (error: ServiceError, res: U) => void) => ClientUnaryCall;
type PromisifiedCall<T, U> = ((request: T, metadata?: Metadata, options?: Partial<CallOptions>) => Promise<U>);
export type Promisified<C> = { $: C; } & {
[prop in Exclude<keyof C, keyof Client>]: (C[prop] extends OriginalCall<infer T, infer U> ? PromisifiedCall<T, U> : never);
}
export function promisify<C extends Client>(client: C): Promisified<C> {
return new Proxy(client, {
get: (target, descriptor) => {
if (descriptor === '$') {
return target;
}
return (...args: any[]) => new Promise((resolve, reject) => target[descriptor](...[...args, (err: ServiceError, res: Message) => err ? reject(err) : resolve(res)]));
},
}) as unknown as Promisified<C>;
}
export class SearchService {
private searchServiceClient: Promisified<SearchServiceClient>;
constructor(private config: Config) {
const { host, grpcPort } = this.config.services.shopCore;
this.searchServiceClient = promisify(new SearchServiceClient(`${host}:${grpcPort}`, ChannelCredentials.createInsecure()));
}
async search(query: string, limit: number): Promise<SearchResult> {
const request = new SearchRequest().setQuery(query);
const response = await this.searchServiceClient.search(request);
return {
items: response.getResultsList().map(item => ({
name: item.getName(),
url: item.getUrl(),
})),
};
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment