# @appotter/nestjs-typeorm-paginate 中文文档

规范地址：https://npmcn.com/package/%40appotter/nestjs-typeorm-paginate/

版本：4\.0\.5
npm 元数据更新时间：2024-01-15T16:35:42.571Z
中文译文更新时间：2026-11-06T22:18:09.264Z
软件包许可：MIT

本文由上游 README 翻译，可能存在偏差，请结合原文核对 API、命令与配置。版权与许可归原作者所有。

原始 npm 页面：https://www.npmjs.com/package/%40appotter/nestjs-typeorm-paginate
原文对照：https://npmcn.com/package/%40appotter/nestjs-typeorm-paginate/?lang=original
源码仓库：https://github.com/appotter/nestjs-typeorm-paginate

## 关键信息（来自 npm 元数据）

- 包体积（解压后）：558 kB，30 个文件
- 模块格式：CommonJS
- TypeScript 类型：未声明
- 运行依赖：0 个
- peer 依赖：@nestjs/common ^6\.1\.1 \|\| ^5\.6\.2 \|\| ^7\.0\.0 \|\| ^8\.0\.0 \|\| ^9\.0\.0 \|\| ^10\.0\.0，typeorm ^0\.3\.0
- 首次发布：2022-11-27T14:46:39.586Z
- 最新版本发布：2024-01-15T16:35:42.392Z
- 近 30 天下载量：2269（2026-10-07 至 2026-11-05，npm 官方下载统计）
- 已发布版本数：3（近 12 个月 0 个）

## 中文简介

一个简单的 pagignation 函数来构建带有类型 的 pagignation 对象

## 安装

```sh
npm install @appotter/nestjs-typeorm-paginate
```

也可以使用：`pnpm add @appotter/nestjs-typeorm-paginate`、`yarn add @appotter/nestjs-typeorm-paginate`、`bun add @appotter/nestjs-typeorm-paginate`

## README

![](https://avatars1.githubusercontent.com/u/43827489?s=400&u=45ac0ac47d40b6d8f277c96bdf00244c10508aef&v=4)

![](https://github.com/nestjsx/nestjs-typeorm-paginate/workflows/Tests/badge.svg) [![](https://img.shields.io/npm/v/nestjs-typeorm-paginate.svg)](https://www.npmjs.com/package/nestjs-typeorm-paginate) [![Coverage Status](https://coveralls.io/repos/github/nestjsx/nestjs-typeorm-paginate/badge.svg?branch=master)](https://coveralls.io/github/nestjsx/nestjs-typeorm-paginate?branch=master) ![](https://camo.githubusercontent.com/a34cfbf37ba6848362bf2bee0f3915c2e38b1cc1/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f5052732d77656c636f6d652d627269676874677265656e2e7376673f7374796c653d666c61742d737175617265) [![Awesome Nest](https://raw.githubusercontent.com/nestjsx/crud/master/img/awesome-nest.svg?sanitize=true)](https://github.com/juliandavidmr/awesome-nestjs#components--libraries) [![Nest Powered](https://raw.githubusercontent.com/nestjsx/crud/master/img/nest-powered.svg?sanitize=true)](https://github.com/nestjs/nest) [![](https://packagequality.com/shield/nestjs-typeorm-paginate.svg)](https://packagequality.com/#?package=nestjs-typeorm-paginate) [![npm downloads](https://img.shields.io/npm/dt/nestjs-typeorm-paginate.svg)](https://www.npmjs.com/org/nestjsx)

# NestJS 类型标注

严格打字的 TypeORM 寄存器或查询构建器的配置辅助器方法

## 安装

```bash
$ yarn add @appotter/nestjs-typeorm-paginate
```

或者说

```bash
$ npm i --save @appotter/nestjs-typeorm-paginate
```

> 请使用@appotter/nestjs-typeorm-pagnation^3 关于打字机,请使用@appotter/nestjs-打字机-pagnation^4.0.0

## 使用量

##### 服务

###### 仓库

```ts
import { Injectable } from '@nestjs/common';
import { Repository } from 'typeorm';
import { InjectRepository } from '@nestjs/typeorm';
import { CatEntity } from './entities';
import {
  paginate,
  Pagination,
  IPaginationOptions,
} from '@appotter/nestjs-typeorm-paginate';

@Injectable()
export class CatService {
  constructor(
    @InjectRepository(CatEntity)
    private readonly repository: Repository<CatEntity>,
  ) {}

  async paginate(options: IPaginationOptions): Promise<Pagination<CatEntity>> {
    return paginate<CatEntity>(this.repository, options);
  }
}
```

###### 查询构建器

```ts
import { Injectable } from '@nestjs/common';
import { Repository } from 'typeorm';
import { InjectRepository } from '@nestjs/typeorm';
import { CatEntity } from './entities';
import {
  paginate,
  Pagination,
  IPaginationOptions,
} from '@appotter/nestjs-typeorm-paginate';

@Injectable()
export class CatService {
  constructor(
    @InjectRepository(CatEntity)
    private readonly repository: Repository<CatEntity>,
  ) {}

  async paginate(options: IPaginationOptions): Promise<Pagination<CatEntity>> {
    const queryBuilder = this.repository.createQueryBuilder('c');
    queryBuilder.orderBy('c.name', 'DESC'); // Or whatever you need to do

    return paginate<CatEntity>(queryBuilder, options);
  }
}
```

##### 主计长

```ts
import { Controller, DefaultValuePipe, Get, ParseIntPipe, Query } from '@nestjs/common';
import { CatService } from './cat.service';
import { CatEntity } from './cat.entity';
import { Pagination } from '@appotter/nestjs-typeorm-paginate';

@Controller('cats')
export class CatsController {
  constructor(private readonly catService: CatService) {}
  @Get('')
  async index(
    @Query('page', new DefaultValuePipe(1), ParseIntPipe) page: number = 1,
    @Query('limit', new DefaultValuePipe(10), ParseIntPipe) limit: number = 10,
  ): Promise<Pagination<CatEntity>> {
    limit = limit > 100 ? 100 : limit;
    return this.catService.paginate({
      page,
      limit,
      route: 'http://cats.com/cats',
    });
  }
}
```

> 如果您使用 `ParseIntPipe` 在查询参数(如示例)上,不要忘记添加 `DefaultValuePipe`。见 [问题517](https://github.com/nestjsx/nestjs-typeorm-paginate/issues/517) 需要更多信息.

> 页:1 `route` pagnation 选项的属性也可以是绝对路径的短版本 `/cats` 改为 `http://cats.com/cats`

### 示例答复

```json
{
  "items": [
    {
      "lives": 9,
      "type": "tabby",
      "name": "Bobby"
    },
    {
      "lives": 2,
      "type": "Ginger",
      "name": "Garfield"
    },
    {
      "lives": 6,
      "type": "Black",
      "name": "Witch's mate"
    },
    {
      "lives": 7,
      "type": "Purssian Grey",
      "name": "Alisdaya"
    },
    {
      "lives": 1,
      "type": "Alistair",
      "name": "ali"
    },
    ...
  ],
  "meta": {
    "itemCount": 10,
    "totalItems": 20,
    "itemsPerPage": 10,
    "totalPages": 5,
    "currentPage": 2
  },
  "links" : {
    "first": "http://cats.com/cats?limit=10",
    "previous": "http://cats.com/cats?page=1&limit=10",
    "next": "http://cats.com/cats?page=3&limit=10",
    "last": "http://cats.com/cats?page=5&limit=10"
  }
}
```

`items`: 某个实体的数组

`meta.itemCount`: 项数组的长度(即本页上项的数量) `meta.totalItems`: 匹配过滤条件的某个实体的总量 `meta.itemsPerPage`: 每页要求的项目(即 `limit` 参数)

`meta.totalPages`页: 1 `limit`(中文(简体) ) `meta.currentPage`: 当前页此piginator"点"到

`links.first`: 第一个调用 QQ 的 URL `""` (blank) 如果没有 `route` 定义 `links.previous`: 上页调用QQ的 URL `""` (blank) 如果没有先前呼叫 `links.next`: 下一页调用QQ的URL `""` (空白) 如果没有页面调用 `links.last`: 最后一个调用QQ的 URL `""` (blank) 如果没有 `route` 定义

> 请注意 `links.first` 可能没有定义“ page” 查询参数

## 查找参数

```ts
@Injectable()
export class CatService {
  constructor(
    @InjectRepository(CatEntity)
    private readonly repository: Repository<CatEntity>,
  ) {}

  async paginate(options: IPaginationOptions): Promise<Pagination<CatEntity>> {
    return paginate<CatEntity>(this.repository, options, {
      lives: 9,
    });
  }
}
```

## Eager 装入

Eager加载应该和打字机的急切财产一起工作 像这样

```typescript
import { Entity, OneToMany } from 'typeorm';

@Entity()
export class CatEntity {
  @OneToMany(t => TigerKingEntity, tigerKing.cats, {
    eager: true,
  })
  tigerKings: TigerKingEntity[];
}

// service
class CatService {
  constructor(private readonly repository: Repository<CatEntity>) {}

  async paginate(page: number, limit: number): Promise<Pagination<CatEntity>> {
    return paginate(this.repository, { page, limit });
  }
}
```

#### 查询构建器

然而,在使用查询构建器时,您必须亲自给实体水分. 这是过去我用过的一个粗略的例子。 这不妙,但这是部分 类型ORM会做的.

```typescript
const results = paginate(queryBuilder, { page, limit });

return new Pagination(
  await Promise.all(
    results.items.map(async (item: SomeEntity) => {
      const hydrate = await this.someRepository.findByEntity(item);
      item.hydrated = hydrate;

      return item;
    }),
  ),
  results.meta,
  results.links,
);
```

## 原始查询

```typescript
const queryBuilder = this.repository
  .createQueryBuilder<{ type: string; totalLives: string }>('c')
  .select('c.type', 'type')
  .addSelect('SUM(c.lives)', 'totalLives')
  .groupBy('c.type')
  .orderBy('c.type', 'DESC'); // Or whatever you need to do

return paginateRaw(queryBuilder, options);
```

### 原始和实体

TypeORM 使用类似的方法 `getRawAndEntities`

让我们假设有一个结合的桌子,使每只猫与它的猫玩具相匹配. 我们要给每只猫带来多少玩具.

```typescript

const queryBuilder = this.repository
  .createQueryBuilder<{ type: string; totalLives: string }>('cat')
    .leftJoinAndSelect('cat.toys', 'toys')
    .addSelect('COUNT(toys)::INTEGER', 'toyCount')
    .groupBy('cat.name');
```

这样我们就能得到 被捕捉的猫的信息 加上额外的原始查询 来构建我们的实际反应值. 返回的 pagination 对象会是相同的,但现在可以处理或映射结果和所需的原始对象.

```typescript
const [pagination, rawResults] = await paginateRawAndEntities(query, options);
pagination.items.map((item, index) => {
  // we can do what we need with the items and raw results here
  // change your items using rawResults.find(raw => raw.id === item.id)
});
return pagination;
```

#### 关于合并表格和原始值的说明

由于原始结果的值将包含所有被询问的合并表格项目,所以您必须确保按您使用时的需要处理这些项目。 参考 TypeORM 软件 [获取Raw和实体](https://github.com/typeorm/typeorm/blob/920e7812cd9d405df921f9ae9ce52ba0a9743bea/src/query-builder/SelectQueryBuilder.ts#L1047) 视需要执行.

原始的Results阵列会看起来像这样:

```typescript
[
    { // Bobby appears 3 times due to the joined query
      "cat_lives": 9,
      "cat_type": "tabby",
      "cat_name": "Bobby",
      "toyCount": 3
    },
    {
      "cat_lives": 9,
      "cat_type": "tabby",
      "cat_name": "Bobby",
      "toyCount": 3
    },
    {
      "cat_lives": 9,
      "cat_type": "tabby",
      "cat_name": "Bobby",
      "toyCount": 3
    },
    {
      "cat_lives": 2,
      "cat_type": "Ginger",
      "cat_name": "Garfield",
      "toyCount": 1
    },
    ...
]
```

## 自定义元数据变压器

如果您想要更改从页形对象返回的元数据 。 那就用那个 `metaTransformer` 在这样的选项中

```ts

class CustomPaginationMeta {
  constructor(
    public readonly count: number,
    public readonly total: number,
  ) {}
}

return paginate<MyEntity, CustomPaginationMeta>(this.repository, { 
  page,
  limit,
  metaTransformer: (meta: IPaginationMeta): CustomPaginationMeta => new CustomPaginationMeta(
    meta.itemCount,
    meta.totalItems,
  ),
 });
```

这将导致上述返回 `CustomPaginationMeta` 输入 `meta` 属性而不是默认 `IPaginationMeta`。 。 。 .

## 自定义链接查询参数标签

如果你想改变 `limit` 和(或) `page` 元链接中的标签,然后使用 `routingLabels` 在这样的选项中

```ts

return paginate<MyEntity>(this.repository, { 
  page,
  limit,
  routingLabels: {
    limitLabel: 'page-size', // default: limit
    pageLabel: 'current-page', //default: page
  }
 });
```

这将导致链接像 `http://example.com/something?current-page=1&page-size=3`。 。 。 .

## 常见问题

### @appotter/nestjs-typeorm-paginate 是什么？

一个简单的 pagignation 函数来构建带有类型 的 pagignation 对象

### 如何安装 @appotter/nestjs-typeorm-paginate？

在项目目录运行 npm install @appotter/nestjs-typeorm-paginate，或使用 pnpm add / yarn add / bun add。它还需要宿主项目提供 peer 依赖：@nestjs/common（^6\.1\.1 \|\| ^5\.6\.2 \|\| ^7\.0\.0 \|\| ^8\.0\.0 \|\| ^9\.0\.0 \|\| ^10\.0\.0）、typeorm（^0\.3\.0）。npm 7 及以上与 pnpm 8 及以上默认会自动安装必需的 peer 依赖，Yarn 需要手动安装。

### @appotter/nestjs-typeorm-paginate 支持 TypeScript 吗？

该包的 package\.json 没有声明类型入口。需要类型提示时，可以在 npm 上查找社区维护的 @types/appotter\_\_nestjs-typeorm-paginate 是否存在。

### @appotter/nestjs-typeorm-paginate 支持 ESM 还是 CommonJS？

以 CommonJS 形式发布，可以直接 require\(\)；在 ES Module 项目中也可以用 import 引入（Node\.js 会把 module\.exports 作为默认导出）。

### @appotter/nestjs-typeorm-paginate 可以商用吗？

@appotter/nestjs-typeorm-paginate 使用 MIT 许可。宽松许可：允许商业使用、修改和再分发，通常只需在分发时保留原版权与许可声明。以上为概括，不构成法律意见，请以许可原文为准。

### @appotter/nestjs-typeorm-paginate 的下载量有多少？

根据 npm 官方下载统计，@appotter/nestjs-typeorm-paginate 在 2026/10/07 – 2026/11/05 这 30 天内被下载 2,269 次，日均约 76 次。下载量会把 CI 构建、镜像同步和作为其他包依赖的安装一并计入，适合横向比较热度，不能直接等同于使用人数。

### @appotter/nestjs-typeorm-paginate 还在维护吗？

最新版本 4\.0\.5 发布于 2024/01/16（2 年前）；至今共发布 3 个版本，其中过去 12 个月发布了 0 个；首次发布于 2022/11/27。发布频率只是参考信号：功能稳定的工具可能很少需要更新，建议结合源码仓库的 issue 和提交记录判断。

