fix: Reduce size of teamPermanentDeleter transactions for reliability

This commit is contained in:
Tom Moor
2024-04-18 09:32:13 -04:00
parent 18129a4bbb
commit 6b6156b032

View File

@@ -1,4 +1,3 @@
import { Transaction } from "sequelize";
import Logger from "@server/logging/Logger";
import { traceFunction } from "@server/logging/tracing";
import {
@@ -20,6 +19,13 @@ import {
} from "@server/models";
import { sequelize } from "@server/storage/database";
/**
* Permanently deletes a team and all related data from the database. Note that this does not happen
* in a single transaction due to the potential size of such a transaction, so it is possible for
* the operation to be interrupted and leave partial data. In which case it can be safely re-run.
*
* @param team - The team to delete.
*/
async function teamPermanentDeleter(team: Team) {
if (!team.deletedAt) {
throw new Error(
@@ -32,19 +38,17 @@ async function teamPermanentDeleter(team: Team) {
`Permanently destroying team ${team.name} (${team.id})`
);
const teamId = team.id;
let transaction!: Transaction;
try {
transaction = await sequelize.transaction();
await Attachment.findAllInBatches<Attachment>(
{
where: {
teamId,
},
limit: 100,
offset: 0,
await Attachment.findAllInBatches<Attachment>(
{
where: {
teamId,
},
async (attachments, options) => {
limit: 100,
offset: 0,
},
async (attachments, options) => {
await sequelize.transaction(async (transaction) => {
Logger.info(
"commands",
`Deleting attachments ${options.offset} ${
@@ -58,19 +62,22 @@ async function teamPermanentDeleter(team: Team) {
})
)
);
}
);
// Destroy user-relation models
await User.findAllInBatches<User>(
{
attributes: ["id"],
where: {
teamId,
},
limit: 100,
offset: 0,
});
}
);
// Destroy user-relation models
await User.findAllInBatches<User>(
{
attributes: ["id"],
where: {
teamId,
},
async (users) => {
limit: 100,
offset: 0,
},
async (users) => {
await sequelize.transaction(async (transaction) => {
const userIds = users.map((user) => user.id);
await UserAuthentication.destroy({
where: {
@@ -79,6 +86,13 @@ async function teamPermanentDeleter(team: Team) {
force: true,
transaction,
});
await Attachment.destroy({
where: {
userId: userIds,
},
force: true,
transaction,
});
await ApiKey.destroy({
where: {
userId: userIds,
@@ -93,9 +107,12 @@ async function teamPermanentDeleter(team: Team) {
force: true,
transaction,
});
}
);
// Destory team-relation models
});
}
);
// Destory team-relation models
await sequelize.transaction(async (transaction) => {
await AuthenticationProvider.destroy({
where: {
teamId,
@@ -180,14 +197,7 @@ async function teamPermanentDeleter(team: Team) {
transaction,
}
);
await transaction.commit();
} catch (err) {
if (transaction) {
await transaction.rollback();
}
throw err;
}
});
}
export default traceFunction({