@sonibble-creators/nest-microservice-pack
Version:
Microservice pack dependencies for NestJS
143 lines (123 loc) • 3.62 kB
text/typescript
import { Type } from '@nestjs/common';
import { ObjectType, Field } from '@nestjs/graphql';
import Relay from 'graphql-relay';
// type tobe used in pagination
// return the actual data
const typeMap = {};
/**
* ## Paginated
*
* The pagination of the object graphql
* allow to paginated and sort the data
* using the cursor, or the offset and limit
*
*
* @param type
* @returns
*/
export function Paginated<T>(type: Type<T>): any {
const { name } = type;
if (typeMap[`${name}`]) return typeMap[`${name}`];
/**
* ### Edge
*
* The edge object for pagination
* will come with cursor, and the node field
* will generate and Edge based on the type extends into the params
*
* This class will never registered into the scheme
*
*/
(`${name}Edge`, { isAbstract: true })
class Edge<T> implements Relay.Edge<T> {
public name = `${name}Edge`;
({ nullable: true, description: `The cursor for ${name} pagination` })
public cursor!: Relay.ConnectionCursor;
(() => type, {
nullable: true,
description: `Node of the ${name} data`,
})
public node!: T;
}
/**
* ### PageInfo
*
* Page information of the edge
* will generate some of info depends on the parameters class extends
*
*
*/
(`${name}PageInfo`, { isAbstract: true })
class PageInfo implements Relay.PageInfo {
({ nullable: true, description: `The start cursor for ${name}` })
public startCursor!: Relay.ConnectionCursor;
({ nullable: true, description: `The end cursor for ${name}` })
public endCursor!: Relay.ConnectionCursor;
(() => Boolean, {
description: `Whether there are more items to fetch before for ${name}`,
})
public hasPreviousPage!: boolean;
(() => Boolean, {
description: `Whether there is a next page for ${name}`,
})
public hasNextPage!: boolean;
}
/**
* ### Connection
*
* Will generated connection for the type extends
* cover some data inside like edges, pageInfo,
*
*
*/
(`${name}Connection`, { isAbstract: true })
class Connection implements Relay.Connection<T> {
public name = `${name}Connection`;
(() => [Edge], {
nullable: true,
description: `Edges of the ${name} data`,
})
public edges!: Edge<T>[];
(() => PageInfo, {
nullable: true,
description: `Page info of the edges, like the cursor and posibillity to next or prev for ${name} data`,
})
public pageInfo!: PageInfo;
}
/**
* ### Page
*
* The final result will be become when data
* become paginated, the actual data will show is page, and pageData
*/
(`${name}Page`, { isAbstract: true })
abstract class Page {
public name = `${name}Page`;
(() => Connection, { description: `The ${name} data of the page` })
public page!: Connection;
(() => PageData, {
nullable: true,
description: `The ${name} data information will be showed like count, limit, and the offset`,
})
public pageData!: PageData;
}
typeMap[`${name}`] = Page;
return typeMap[`${name}`];
}
/**
* ### PageData
*
* Show some info of the pagination
* like count of the data, limit and the offset
*
*
*/
()
export class PageData {
({ description: `Data count in the page` })
public count: number;
({ description: `Limit data for the page` })
public limit: number;
({ description: `The offset data will be showed next and before` })
public offset: number;
}