TypeORM:更新项目和 return 它

TypeORM: update item and return it

据我所知,最佳做法是 return 项目更新后。 TypeORM 的 updateById returns void,但不是更新的项目。

我的问题:是否可以在一行中更新和return修改的项目?

到目前为止我尝试了什么:

await this.taskRepository.updateById(id, { state, dueDate });
return this.taskRepository.findOne({ id });

我在找什么:

return this.taskRepository.updateById(id, { state, dueDate }); // returns updated task

我刚刚发现我可以使用 .save 方法来做到这一点:

return this.taskRepository.save({
    id: task.id,
    state,
    dueDate
});

根据the docs(部分save),部分更新也被支持:

Also supports partial updating since all undefined properties are skipped.

为了扩展 sandrooco 的回答,我是这样做的:

const property = await this.propertyRepository.findOne({
  where: { id }
});

return this.propertyRepository.save({
  ...property, // existing fields
  ...updatePropertyDto // updated fields
});

一种方法是执行更新,然后根据您指定的条件进行查找

关键是 returning response.raw[0] 以取回类型。


虽然我想要 await Table.update({}, {}) 到 return Table 但事实并非如此。我发现使用 QueryBuilder 更容易,因为它总体上给了我更多的控制权, 但是 如果你不喜欢 QueryBuilder 或者不需要,你可以这样做:

const post = await Post.update({id}, {...input}).then(response => response.raw[0]);
return post; // returns post of type Post

如果您确实想使用 QueryBuilder,我建议您采用如下方法。 上面的其他人提到了 RepositoryTable.save() 的用法,这在任何地方都不是 return 原始的 type,所以这种方法对我来说不合适。

Table.update({}, {})的例子:

@Mutation(() => PostResponse, { nullable: true })
@UseMiddleware(isAuthorized)
async updatePost(
  @Arg("id", () => Int) id: number,
  @Arg("input") input: PostInput,
  @Ctx() { req }: Context
): Promise<PostResponse | null> {
  // ...
  const post = await Post.update({id}, {...input}).then(response => response.raw[0]);
  return { post };
}

QueryBuilder的例子:

@Mutation(() => PostResponse, { nullable: true })
@UseMiddleware(isAuthorized)
async updatePost(
  @Arg("id", () => Int) id: number,
  @Arg("input") input: PostInput,
  @Ctx() { req }: Context
): Promise<PostResponse | null> {
  // ...
  const post = await getConnection()
    .createQueryBuilder()
    .update(Post)
    .set({ ...input })
    .where('id = :id and "creatorId" = :creatorId', {
      id,
      creatorId: userId,
    })
    .returning("*")
    .execute()
    .then((response) => {
      return response.raw[0];
    });

  return { post };
}

辅助函数(如果你不想一直写response.raw[0]

const typeReturn = async <T>(mutation: Promise<UpdateResult | DeleteResult | InsertResult>): Promise<T> => {
  return await mutation.then((res) => res.raw[0]);
};

用法:

const update = await typeReturn<Post>(Post.update(...));
const insert = await typeReturn<Attachment>(Attachment.insert(...));
const del    = await typeReturn<User>(User.delete(...));

注意:我在这里使用 TypeORM 和 Type-GraphQL。

.returning("*") 不适用于 MySQL,请参阅下面的评论。