Skip to content

级联操作

iBest ORM 集成了强大的 CascadeManager 级联操作管理器,支持关联数据的自动创建、更新、删除,提供事务管理和回滚机制。

核心功能

🔄 级联操作类型

  • CascadeType.Create - 级联创建
  • CascadeType.Delete - 级联删除
  • CascadeType.Update - 级联更新

🎯 集成入口

级联操作已集成到以下方法中:

  • Create() - 支持级联创建
  • DeleteByEntity() - 支持级联删除
  • Save() - 支持级联保存/更新

基础用法

级联创建

typescript
// 创建用户及其关联数据
const userWithData = new User();
userWithData.name = "张三";
userWithData.email = "zhangsan@example.com";

// 创建关联的用户资料
userWithData.profile = new UserProfile();
userWithData.profile.bio = "软件开发工程师";
userWithData.profile.avatar = "avatar.jpg";

// 创建关联的订单
userWithData.orders = [
  {
    product_name: "笔记本电脑",
    amount: 8999.00,
    items: [
      { product_name: "笔记本电脑", quantity: 1, price: 8999.00 }
    ]
  },
  {
    product_name: "无线鼠标", 
    amount: 199.00,
    items: [
      { product_name: "无线鼠标", quantity: 1, price: 199.00 }
    ]
  }
];

// 级联创建 - 自动创建所有关联数据
const result = await orm.Create(userWithData, { cascade: true });
console.log(`创建成功,影响 ${result} 条记录`);

级联删除

typescript
// 查询用户
const user = await orm.Session(User)
  .Where('id', 1)
  .First();

// 级联删除 - 自动删除用户及其所有关联数据
const deletedCount = await orm.DeleteByEntity(user, { cascade: true });
console.log(`删除成功,影响 ${deletedCount} 条记录`);

级联更新

typescript
// 查询用户及其关联数据
const user = await orm.FindWithRelations(User, {
  where: { id: 1 },
  relations: ['profile', 'orders']
});

// 修改用户信息
user.name = "李四";
user.profile.bio = "高级软件开发工程师";

// 添加新订单
user.orders.push({
  product_name: "机械键盘",
  amount: 599.00
});

// 修改现有订单
user.orders[0].amount = 9999.00;

// 级联更新 - 自动更新所有关联数据
const updatedCount = await orm.Save(user, { cascade: true });
console.log(`更新成功,影响 ${updatedCount} 条记录`);

关联注解配置

配置级联类型

在关联注解中配置级联操作:

typescript
@Table({ name: 'users' })
export class User {
  @Field({ type: FieldType.INTEGER, tag: ['primaryKey', 'autoIncrement'] })
  id: number;

  @Field({ type: FieldType.TEXT, tag: ['notNull'] })
  name: string;

  // 一对一关联 - 支持所有级联操作
  @HasOne({
    target: () => UserProfile,
    foreignKey: 'user_id',
    cascade: [CascadeType.All]
  })
  profile: UserProfile;

  // 一对多关联 - 只支持创建和更新级联
  @HasMany({
    target: () => Order,
    foreignKey: 'user_id',
    cascade: [CascadeType.Create, CascadeType.Update]
  })
  orders: Order[];

  // 多对多关联 - 支持创建和删除级联
  @ManyToMany({
    target: () => Role,
    through: 'user_roles',
    throughForeignKey: 'user_id',
    throughOtherKey: 'role_id',
    cascade: [CascadeType.Create, CascadeType.Remove]
  })
  roles: Role[];
}

@Table({ name: 'orders' })
export class Order {
  @Field({ type: FieldType.INTEGER, tag: ['primaryKey', 'autoIncrement'] })
  id: number;

  @Field({ type: FieldType.INTEGER, tag: ['notNull'] })
  user_id: number;

  @Field({ type: FieldType.TEXT, tag: ['notNull'] })
  product_name: string;

  @Field({ type: FieldType.REAL })
  amount: number;

  // 多对一关联 - 不配置级联(避免意外删除父实体)
  @BelongsTo({
    target: () => User,
    foreignKey: 'user_id'
  })
  user: User;

  // 一对多关联 - 支持所有级联操作
  @HasMany({
    target: () => OrderItem,
    foreignKey: 'order_id',
    cascade: [CascadeType.All]
  })
  items: OrderItem[];
}

级联类型说明

typescript
export enum CascadeType {
  Create = 'create',    // 级联创建 - 创建主实体时自动创建关联实体
  Update = 'update',    // 级联更新 - 更新主实体时自动更新关联实体
  Remove = 'remove',    // 级联删除 - 删除主实体时自动删除关联实体
  All = 'all'          // 所有级联操作
}

高级特性

事务管理

级联操作自动使用事务确保数据一致性:

typescript
// 级联操作会自动开启事务
try {
  const result = await orm.Create(complexEntity, { cascade: true });
  // 所有操作成功,自动提交事务
  console.log('级联创建成功');
} catch (error) {
  // 任何操作失败,自动回滚事务
  console.error('级联创建失败,已回滚:', error);
}

深度控制

控制级联操作的最大深度为 5 层,避免无限递归。

批量处理

支持批量级联操作,提高性能:

typescript
// 批量创建用户及其关联数据
const users = [
  { name: "用户1", profile: { bio: "简介1" }, orders: [...] },
  { name: "用户2", profile: { bio: "简介2" }, orders: [...] },
  // ... 更多用户
];

// 批量级联创建
const totalCreated = await orm.Create(users, { cascade: true });
console.log(`批量创建成功,共创建 ${totalCreated} 个用户`);

实际应用场景

电商订单系统

typescript
@Table({ name: 'customers' })
export class Customer {
  @Field({ type: FieldType.INTEGER, tag: ['primaryKey', 'autoIncrement'] })
  id: number;

  @Field({ type: FieldType.TEXT, tag: ['notNull'] })
  name: string;

  @HasMany({
    target: () => Order,
    foreignKey: 'customer_id',
    cascade: [CascadeType.Create, CascadeType.Update]
  })
  orders: Order[];
}

@Table({ name: 'orders' })
export class Order {
  @Field({ type: FieldType.INTEGER, tag: ['primaryKey', 'autoIncrement'] })
  id: number;

  @Field({ type: FieldType.INTEGER, tag: ['notNull'] })
  customer_id: number;

  @Field({ type: FieldType.REAL })
  total_amount: number;

  @HasMany({
    target: () => OrderItem,
    foreignKey: 'order_id',
    cascade: [CascadeType.All]
  })
  items: OrderItem[];

  @BelongsTo({
    target: () => Customer,
    foreignKey: 'customer_id'
  })
  customer: Customer;
}

@Table({ name: 'order_items' })
export class OrderItem {
  @Field({ type: FieldType.INTEGER, tag: ['primaryKey', 'autoIncrement'] })
  id: number;

  @Field({ type: FieldType.INTEGER, tag: ['notNull'] })
  order_id: number;

  @Field({ type: FieldType.INTEGER, tag: ['notNull'] })
  product_id: number;

  @Field({ type: FieldType.INTEGER })
  quantity: number;

  @Field({ type: FieldType.REAL })
  price: number;

  @BelongsTo({
    target: () => Order,
    foreignKey: 'order_id'
  })
  order: Order;
}

// 创建完整订单
async function createOrder(customerData: any) {
  const customer = new Customer();
  customer.name = customerData.name;
  
  customer.orders = customerData.orders.map(orderData => {
    const order = new Order();
    order.total_amount = orderData.total_amount;
    
    order.items = orderData.items.map(itemData => {
      const item = new OrderItem();
      item.product_id = itemData.product_id;
      item.quantity = itemData.quantity;
      item.price = itemData.price;
      return item;
    });
    
    return order;
  });

  // 级联创建整个订单结构
  return await orm.Create(customer, { cascade: true });
}

博客系统

typescript
@Table({ name: 'authors' })
export class Author {
  @Field({ type: FieldType.INTEGER, tag: ['primaryKey', 'autoIncrement'] })
  id: number;

  @Field({ type: FieldType.TEXT, tag: ['notNull'] })
  name: string;

  @HasMany({
    target: () => Post,
    foreignKey: 'author_id',
    cascade: [CascadeType.Create, CascadeType.Update]
  })
  posts: Post[];
}

@Table({ name: 'posts' })
export class Post {
  @Field({ type: FieldType.INTEGER, tag: ['primaryKey', 'autoIncrement'] })
  id: number;

  @Field({ type: FieldType.TEXT, tag: ['notNull'] })
  title: string;

  @Field({ type: FieldType.TEXT })
  content: string;

  @Field({ type: FieldType.INTEGER, tag: ['notNull'] })
  author_id: number;

  @BelongsTo({
    target: () => Author,
    foreignKey: 'author_id'
  })
  author: Author;

  @HasMany({
    target: () => Comment,
    foreignKey: 'post_id',
    cascade: [CascadeType.All]
  })
  comments: Comment[];

  @ManyToMany({
    target: () => Tag,
    through: 'post_tags',
    throughForeignKey: 'post_id',
    throughOtherKey: 'tag_id',
    cascade: [CascadeType.Create]
  })
  tags: Tag[];
}

// 发布文章
async function publishPost(postData: any) {
  const post = new Post();
  post.title = postData.title;
  post.content = postData.content;
  post.author_id = postData.author_id;

  // 添加标签
  post.tags = postData.tags.map(tagName => {
    const tag = new Tag();
    tag.name = tagName;
    return tag;
  });

  // 级联创建文章和标签
  return await orm.Create(post, { cascade: true });
}

用户权限系统

typescript
@Table({ name: 'users' })
export class User {
  @Field({ type: FieldType.INTEGER, tag: ['primaryKey', 'autoIncrement'] })
  id: number;

  @Field({ type: FieldType.TEXT, tag: ['notNull'] })
  username: string;

  @ManyToMany({
    target: () => Role,
    through: 'user_roles',
    throughForeignKey: 'user_id',
    throughOtherKey: 'role_id',
    cascade: [CascadeType.Create, CascadeType.Update]
  })
  roles: Role[];
}

@Table({ name: 'roles' })
export class Role {
  @Field({ type: FieldType.INTEGER, tag: ['primaryKey', 'autoIncrement'] })
  id: number;

  @Field({ type: FieldType.TEXT, tag: ['notNull'] })
  name: string;

  @ManyToMany({
    target: () => Permission,
    through: 'role_permissions',
    throughForeignKey: 'role_id',
    throughOtherKey: 'permission_id',
    cascade: [CascadeType.Create]
  })
  permissions: Permission[];
}

// 创建用户并分配角色
async function createUserWithRoles(userData: any) {
  const user = new User();
  user.username = userData.username;

  user.roles = userData.roles.map(roleData => {
    const role = new Role();
    role.name = roleData.name;
    
    role.permissions = roleData.permissions.map(permData => {
      const permission = new Permission();
      permission.name = permData.name;
      permission.action = permData.action;
      return permission;
    });
    
    return role;
  });

  // 级联创建用户、角色和权限
  return await orm.Create(user, { cascade: true });
}

性能优化

1. 合理配置级联类型

typescript
// ✅ 推荐:根据业务需求配置特定的级联类型
@HasMany({
    target: () => Order,
    foreignKey: 'user_id',
    cascade: [CascadeType.Create, CascadeType.Update] // 不包含删除
  })
orders: Order[];

// ❌ 避免:盲目使用 All 级联
@HasMany({
    target: () => Order,
    foreignKey: 'user_id',
    cascade: [CascadeType.All] // 可能导致意外删除
})
orders: Order[];

2. 使用批量操作

typescript
// ✅ 推荐:批量级联创建
const users = [...]; // 大量用户数据
const result = await orm.Create(users, { cascade: true });

// ❌ 避免:循环单个创建
for (const user of users) {
  await orm.Create(user, { cascade: true }); // 效率低
}