typeorm中如何清空表数据?TypeORM版本:V0.3.20 (2024-01-26)
在最新版的 TypeORM 中,可以通过以下几种方式清空表数据。具体方法取决于你想要的操作和使用的数据库。
// ./data-source.ts
import "reflect-metadata";
import { DataSource } from "typeorm";
export const AppDataSource = new DataSource({
type: "mysql",
host: "127.0.0.1",
port: 3306,
username: "root",
password: "12345678",
database: "test",
// 自动建表 注意:每次运行时实体与数据库是否同步?生产环境慎用。
synchronize: true,
logging: true,
entities: [
__dirname + "/entity/*/*.ts",
],
subscribers: [],
migrations: [],
})
1. 使用 QueryBuilder
执行 SQL 语句
你可以直接使用 QueryBuilder
执行 DELETE
或 TRUNCATE
SQL 语句。
使用 DELETE
import { AppDataSource } from "./data-source";
import { User } from "./entities/User"; // 示例实体
async function clearTable() {
const userRepository = AppDataSource.getRepository(User);
await userRepository.createQueryBuilder().delete().where("1 = 1").execute();
}
clearTable();
DELETE
语句会删除表中的所有数据,但不会重置自增 ID 或改变表的结构。
使用 TRUNCATE
import { AppDataSource } from "./data-source";
async function clearTable() {
await AppDataSource.query("TRUNCATE TABLE user"); // 假设 user 是要清空的表名
}
clearTable();
TRUNCATE
是一种更高效的方式,它会快速删除所有数据,并且通常会重置自增字段(例如 ID)。但它是一个 DDL 操作,不能回滚。
使用对应实体的repository清空表数据
复制代码import { AppDataSource } from "./data-source";
const clearTable = async () => {
const repository = AppDataSource.getRepository("your_table_name");
await repository.createQueryBuilder().delete().execute();
console.log("Table data cleared!");
};
clearTable();
特点:
- 只删除表中的数据,保留表结构。
- 不会重置主键自增值。
2. 使用 repository
方法(适用于删除数据)
你还可以使用 TypeORM 的 repository
API 进行删除操作。
import { AppDataSource } from "./data-source";
import { User } from "./entities/User";
async function clearTable() {
const userRepository = AppDataSource.getRepository(User);
await userRepository.clear(); // 清空表数据
}
clearTable();
clear()
方法会删除所有记录,但不会重置自增字段。
3. 删除所有表数据(批量清空)
如果你想要清空多个表的数据,可以遍历所有的实体并调用 clear()
方法:
import { AppDataSource } from "./data-source";
import { User } from "./entities/User";
import { Post } from "./entities/Post";
async function clearAllTables() {
const repositories = [User, Post]; // 将所有实体添加到数组中
for (const entity of repositories) {
const repository = AppDataSource.getRepository(entity);
await repository.clear(); // 清空每个表的数据
}
}
clearAllTables();
注意事项
TRUNCATE
会比DELETE
更高效,尤其是在清空大量数据时。它不会生成大量的DELETE
日志,也不会触发DELETE
触发器。DELETE
会触发所有的删除触发器(如果有),并且可以被回滚,而TRUNCATE
是不可回滚的。- 如果你使用的是数据库表之间有外键关系,
TRUNCATE
可能会因为外键约束而失败。在这种情况下,可以使用DELETE
或调整外键约束。
选择合适的方法依据你的具体需求,例如是否需要重置自增 ID,是否有外键约束等。
4. 使用原生 SQL 脚本
如果需要更复杂的操作,可以通过 query
方法执行自定义 SQL。
示例:清空多张表
import { AppDataSource } from "./data-source";
const clearTables = async () => {
const queryRunner = AppDataSource.createQueryRunner();
try {
await queryRunner.connect();
await queryRunner.query("SET FOREIGN_KEY_CHECKS = 0;"); // 如果有外键约束,临时禁用
await queryRunner.query("TRUNCATE TABLE table1;");
await queryRunner.query("TRUNCATE TABLE table2;");
await queryRunner.query("SET FOREIGN_KEY_CHECKS = 1;"); // 恢复外键约束
console.log("Tables cleared!");
} finally {
await queryRunner.release();
}
};
clearTables();
特点:
- 适合清空多张表的数据。
- 如果存在外键约束,需要临时禁用。
注意事项
- 权限问题:
TRUNCATE
通常需要更高权限。- 如果遇到权限不足的问题,可以使用
DELETE
作为替代。
- 外键约束:
- 如果表间存在外键约束,清空数据可能会失败。
- 可以临时禁用外键约束(如 MySQL 的
SET FOREIGN_KEY_CHECKS = 0
)。
- 生产环境慎用:
- 操作前备份数据,避免误操作导致数据丢失。
5. 使用 QueryRunner
通过 QueryRunner
执行原生 SQL,可以实现更高的灵活性。
示例:使用 TRUNCATE
清空表数据
import { AppDataSource } from "./data-source";
const truncateTable = async () => {
const queryRunner = AppDataSource.createQueryRunner();
try {
await queryRunner.connect();
await queryRunner.query("TRUNCATE TABLE your_table_name");
console.log("Table truncated!");
} finally {
await queryRunner.release();
}
};
truncateTable();
特点:
TRUNCATE
会清空表数据,同时重置主键递增值。- 注意:
TRUNCATE
需要更高的权限(DELETE
权限不足时可能会失败)。
推荐使用场景
- 需要重置主键:使用
TRUNCATE
。 - 只删除数据,保留主键状态:使用
Repository.clear
或QueryBuilder.delete
。