NestJS-TypeORM QueryBuilder 常用 SQL 写法

在 NestJS 项目中,this.xxxRepository.createQueryBuilder() 是最常用、最规范的 QueryBuilder 使用方式。

本文以 UserEntity 为例,系统整理 QueryBuilder 对应的常见 SQL 写法 ,所有示例可直接复制使用。

一、基础准备

复制代码
@Injectable()
export class UserService {
  constructor(
    @InjectRepository(UserEntity)
    private readonly userRepository: Repository<UserEntity>,
  ) {}
}

以下示例默认写在 UserService 中。

一、新增 & 更新 & 删除

1. INSERT

复制代码
return this.userRepository
  .createQueryBuilder()
  .insert()
  .into(UserEntity)
  .values({
    name: '张三',
    age: 18,
    status: 1,
  })
  .execute();

批量新增

复制代码
return this.userRepository
  .createQueryBuilder()
  .insert()
  .into(UserEntity)
  .values([
    { name: '张三', age: 18 },
    { name: '李四', age: 20 },
  ])
  .execute();

2. UPDATE

复制代码
return this.userRepository
  .createQueryBuilder()
  .update(UserEntity)
  .set({ status: 0 })
  .where('id = :id', { id })
  .execute();

3. DELETE

复制代码
return this.userRepository
  .createQueryBuilder()
  .delete()
  .from(UserEntity)
  .where('id = :id', { id })
  .execute();

二、基础查询(SELECT)

1. 查询单表数据

SQL

复制代码
SELECT * FROM user WHERE status = 1;

QueryBuilder

复制代码
return this.userRepository
  .createQueryBuilder('u')
  .where('u.status = :status', { status: 1 })
  .getMany();

2. 查询指定字段

SQL

复制代码
SELECT id, name FROM user;

return this.userRepository
  .createQueryBuilder('u')
  .select(['u.id', 'u.name'])
  .getMany();

3. 查询单条数据

复制代码
return this.userRepository
  .createQueryBuilder('u')
  .where('u.id = :id', { id })
  .getOne();

三、WHERE 条件用法

1. 多条件 AND / OR

SQL

复制代码
SELECT * FROM user WHERE age > 18 AND status = 1;

return this.userRepository
  .createQueryBuilder('u')
  .where('u.age > :age', { age: 18 })
  .andWhere('u.status = :status', { status: 1 })
  .getMany();

OR

复制代码
.orWhere('u.role = :role', { role: 'admin' })

2. IN 查询

SQL

复制代码
SELECT * FROM user WHERE id IN (1,2,3);

return this.userRepository
  .createQueryBuilder('u')
  .where('u.id IN (:...ids)', { ids: [1, 2, 3] })
  .getMany();

3. LIKE 模糊查询

SQL

复制代码
SELECT * FROM user WHERE name LIKE '%张%';

return this.userRepository
  .createQueryBuilder('u')
  .where('u.name LIKE :name', { name: `%张%` })
  .getMany();

四、排序 & 分页

1. ORDER BY

复制代码
return this.userRepository
  .createQueryBuilder('u')
  .orderBy('u.createTime', 'DESC')
  .getMany();

2. 分页查询

复制代码
return this.userRepository
  .createQueryBuilder('u')
  .skip((page - 1) * pageSize)
  .take(pageSize)
  .getMany();

3. 分页 + 总数

复制代码
return this.userRepository
  .createQueryBuilder('u')
  .skip((page - 1) * pageSize)
  .take(pageSize)
  .getManyAndCount();

五、JOIN 多表查询

1. LEFT JOIN

SQL

复制代码
SELECT * FROM user u
LEFT JOIN order o ON u.id = o.user_id;

return this.userRepository
  .createQueryBuilder('u')
  .leftJoin(OrderEntity, 'o', 'o.userId = u.id')
  .getMany();

2. LEFT JOIN 并返回关联数据

复制代码
return this.userRepository
  .createQueryBuilder('u')
  .leftJoinAndSelect('u.orders', 'o')
  .getMany();

⚠️ 前提:UserEntity 中定义了 @OneToMany(() => OrderEntity, ...)

六、聚合函数(COUNT / SUM)

1. COUNT 查询

复制代码
return this.userRepository
  .createQueryBuilder('u')
  .where('u.status = :status', { status: 1 })
  .getCount();

2. GROUP BY 统计

SQL

复制代码
SELECT status, COUNT(*) total FROM user GROUP BY status;

return this.userRepository
  .createQueryBuilder('u')
  .select('u.status', 'status')
  .addSelect('COUNT(*)', 'total')
  .groupBy('u.status')
  .getRawMany();

3. HAVING

复制代码
return this.userRepository
  .createQueryBuilder('u')
  .select('u.status', 'status')
  .addSelect('COUNT(*)', 'total')
  .groupBy('u.status')
  .having('COUNT(*) > :count', { count: 10 })
  .getRawMany();

七、子查询

1. 子查询 IN

SQL

复制代码
SELECT * FROM user
WHERE id IN (SELECT user_id FROM order WHERE amount > 100);

return this.userRepository
  .createQueryBuilder('u')
  .where(qb => {
    const subQuery = qb
      .subQuery()
      .select('o.userId')
      .from(OrderEntity, 'o')
      .where('o.amount > :amount')
      .getQuery();
    return 'u.id IN ' + subQuery;
  })
  .setParameter('amount', 100)
  .getMany();
相关推荐
Wang's Blog10 分钟前
Java 项目实战: 交友项目 - Dubbo 的内部结构与一次调用的完整链路
java·dubbo
geovindu13 分钟前
sql:Search-Optimized SQL Queries using mysql 9.0
android·数据库·sql·mysql·数据库开发·数据库架构
Wang's Blog14 分钟前
Java 项目实战: 交友项目 - Dubbo 入门引导
java·dubbo·交友
for_ever_love__21 分钟前
MySQL SELECT 与 WHERE 优化实战:可搜索条件、联合索引与执行计划
数据库·mysql·oracle·select·where·条件优化·查询优化技巧
2501_9318037533 分钟前
MySQL 锁机制详解
数据库·mysql
蜗牛互联网1 小时前
Python Agent工具调用的白名单、参数校验与审批门禁
java·服务器·前端·人工智能·后端·python
Nturmoils1 小时前
SQL 编辑器不只是写查询:我用 KStudio 排查一次订单异常
数据库
SL_staff1 小时前
当规则引擎开始‘懂业务’:JVS-Rules金融风控四大原生能力拆解
java·python·全栈
IvorySQL1 小时前
PostgreSQL 日报|逻辑解码 DDL 子事务缺陷修复(10 月 12 日)
数据库·postgresql
Shaoshing1 小时前
前缀和与差分
java·数据结构·算法·前缀和·差分