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 执行 DELETETRUNCATE 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();

特点

  • 适合清空多张表的数据。
  • 如果存在外键约束,需要临时禁用。

注意事项

  1. 权限问题
    • TRUNCATE 通常需要更高权限。
    • 如果遇到权限不足的问题,可以使用 DELETE 作为替代。
  2. 外键约束
    • 如果表间存在外键约束,清空数据可能会失败。
    • 可以临时禁用外键约束(如 MySQL 的 SET FOREIGN_KEY_CHECKS = 0)。
  3. 生产环境慎用
    • 操作前备份数据,避免误操作导致数据丢失。

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.clearQueryBuilder.delete
posted @ 2024-11-21 18:23  未来的羁绊  阅读(26)  评论(0编辑  收藏  举报