181 lines
		
	
	
		
			4.4 KiB
		
	
	
	
		
			Markdown
		
	
	
	
	
	
			
		
		
	
	
			181 lines
		
	
	
		
			4.4 KiB
		
	
	
	
		
			Markdown
		
	
	
	
	
	
| # Nest.js Paginate
 | |
| 
 | |
| [](https://www.npmjs.com/package/nestjs-paginate)
 | |
| 
 | |
| [](https://codecov.io/gh/ppetzold/nestjs-paginate)
 | |
| [](https://github.com/prettier/prettier)
 | |
| [](https://github.com/semantic-release/semantic-release)
 | |
| 
 | |
| 
 | |
| Pagination and filtering helper method for TypeORM repositories or query builders using [Nest.js](https://nestjs.com/) framework.
 | |
| 
 | |
| - Pagination conforms to [JSON:API](https://jsonapi.org/)
 | |
| - Sort by multiple columns
 | |
| - Filter using operators
 | |
| - Search across columns
 | |
| 
 | |
| ## Installation
 | |
| 
 | |
| ```
 | |
| npm install nestjs-paginate
 | |
| ```
 | |
| 
 | |
| ## Usage
 | |
| 
 | |
| ### Example
 | |
| 
 | |
| The following code exposes a route that can be utilized like so:
 | |
| 
 | |
| #### Endpoint
 | |
| 
 | |
| ```url
 | |
| http://localhost:3000/cats?limit=5&page=2&sortBy=color:DESC&search=i
 | |
| ```
 | |
| 
 | |
| #### Result
 | |
| 
 | |
| ```json
 | |
| {
 | |
|   "data": [
 | |
|     {
 | |
|       "id": 4,
 | |
|       "name": "George",
 | |
|       "color": "white"
 | |
|     },
 | |
|     {
 | |
|       "id": 5,
 | |
|       "name": "Leche",
 | |
|       "color": "white"
 | |
|     },
 | |
|     {
 | |
|       "id": 2,
 | |
|       "name": "Garfield",
 | |
|       "color": "ginger"
 | |
|     },
 | |
|     {
 | |
|       "id": 1,
 | |
|       "name": "Milo",
 | |
|       "color": "brown"
 | |
|     },
 | |
|     {
 | |
|       "id": 3,
 | |
|       "name": "Kitty",
 | |
|       "color": "black"
 | |
|     }
 | |
|   ],
 | |
|   "meta": {
 | |
|     "itemsPerPage": 5,
 | |
|     "totalItems": 12,
 | |
|     "currentPage": 2,
 | |
|     "totalPages": 3,
 | |
|     "sortBy": [["color", "DESC"]],
 | |
|     "search": "i"
 | |
|   },
 | |
|   "links": {
 | |
|     "first": "http://localhost:3000/cats?limit=5&page=1&sortBy=color:DESC&search=i",
 | |
|     "previous": "http://localhost:3000/cats?limit=5&page=1&sortBy=color:DESC&search=i",
 | |
|     "current": "http://localhost:3000/cats?limit=5&page=2&sortBy=color:DESC&search=i",
 | |
|     "next": "http://localhost:3000/cats?limit=5&page=3&sortBy=color:DESC&search=i",
 | |
|     "last": "http://localhost:3000/cats?limit=5&page=3&sortBy=color:DESC&search=i"
 | |
|   }
 | |
| }
 | |
| ```
 | |
| 
 | |
| #### Code
 | |
| 
 | |
| ```ts
 | |
| import { Controller, Injectable, Get } from '@nestjs/common'
 | |
| import { InjectRepository } from '@nestjs/typeorm'
 | |
| import { Repository, Entity, PrimaryGeneratedColumn, Column } from 'typeorm'
 | |
| import { Paginate, PaginateQuery, paginate, Paginated } from 'nestjs-paginate'
 | |
| 
 | |
| @Entity()
 | |
| export class CatEntity {
 | |
|   @PrimaryGeneratedColumn()
 | |
|   id: number
 | |
| 
 | |
|   @Column('text')
 | |
|   name: string
 | |
| 
 | |
|   @Column('text')
 | |
|   color: string
 | |
| }
 | |
| 
 | |
| @Injectable()
 | |
| export class CatsService {
 | |
|   constructor(
 | |
|     @InjectRepository(CatEntity)
 | |
|     private readonly catsRepository: Repository<CatEntity>
 | |
|   ) {}
 | |
| 
 | |
|   public findAll(query: PaginateQuery): Promise<Paginated<CatEntity>> {
 | |
|     return paginate(query, this.catsRepository, {
 | |
|       sortableColumns: ['id', 'name', 'color'],
 | |
|       searchableColumns: ['name', 'color'],
 | |
|       defaultOrderby: [['color', 'DESC']],
 | |
|     })
 | |
|   }
 | |
| }
 | |
| 
 | |
| @Controller('cats')
 | |
| export class CatsController {
 | |
|   constructor(private readonly catsService: CatsService) {}
 | |
| 
 | |
|   @Get()
 | |
|   public findAll(@Paginate() query: PaginateQuery): Promise<Paginated<CatEntity>> {
 | |
|     return this.catsService.findAll(query)
 | |
|   }
 | |
| }
 | |
| ```
 | |
| 
 | |
| ### Config
 | |
| 
 | |
| ```ts
 | |
| const paginateConfig: PaginateConfig<CatEntity> {
 | |
|   /**
 | |
|    * Required: true (must have a minimum of one column)
 | |
|    * Type: (keyof CatEntity)[]
 | |
|    * Description: These are the columns that are valid to be sorted by.
 | |
|    */
 | |
|   sortableColumns: ['id', 'name', 'color'],
 | |
| 
 | |
|   /**
 | |
|    * Required: false
 | |
|    * Type: (keyof CatEntity)[]
 | |
|    * Description: These columns will be searched through when using the search query param.
 | |
|    */
 | |
|   searchableColumns: ['name', 'color'],
 | |
| 
 | |
|   /**
 | |
|    * Required: false
 | |
|    * Type: number
 | |
|    * Default: 100
 | |
|    * Description: The maximum amount of entities to return per page.
 | |
|    */
 | |
|   maxLimit: 20,
 | |
| 
 | |
|   /**
 | |
|    * Required: false
 | |
|    * Type: [keyof CatEntity, 'ASC' | 'DESC'][]
 | |
|    * Default: [[sortableColumns[0], 'ASC]]
 | |
|    * Description: The order to display the sorted entities.
 | |
|    */
 | |
|   defaultSortBy: [['name', 'DESC']],
 | |
| 
 | |
|   /**
 | |
|    * Required: false
 | |
|    * Type: number
 | |
|    * Default: 20
 | |
|    */
 | |
|   defaultLimit: 50,
 | |
| 
 | |
|   /**
 | |
|    * Required: false
 | |
|    * Type: TypeORM find options
 | |
|    * Default: None
 | |
|    * https://typeorm.io/#/find-optionsfind-options.md
 | |
|    */
 | |
|   where: { color: 'ginger' }
 | |
| }
 | |
| ```
 |