1
0
Fork 0
mirror of https://github.com/plankanban/planka.git synced 2025-07-19 05:09:43 +02:00

fix: Use batch inserts to avoid query size limits

This commit is contained in:
Maksim Eltyshev 2025-05-19 17:27:18 +02:00
parent 3aedbff5d0
commit 652c5e9475

View file

@ -97,7 +97,9 @@ const upgradeDatabase = async () => {
const whereInUserIds = ['0', ...userIds]; const whereInUserIds = ['0', ...userIds];
if (users.length > 0) { if (users.length > 0) {
await trx('user_account').insert( await knex
.batchInsert(
'user_account',
users.map((user) => ({ users.map((user) => ({
..._.pick(user, [ ..._.pick(user, [
'id', 'id',
@ -127,20 +129,21 @@ const upgradeDatabase = async () => {
is_sso_user: user.is_sso, is_sso_user: user.is_sso,
is_deactivated: false, is_deactivated: false,
})), })),
); )
.transacting(trx);
const identityProviderUsers = await trx('identity_provider_user') const identityProviderUsers = await trx('identity_provider_user')
.withSchema('v1') .withSchema('v1')
.whereIn('user_id', whereInUserIds); .whereIn('user_id', whereInUserIds);
if (identityProviderUsers.length > 0) { if (identityProviderUsers.length > 0) {
await trx('identity_provider_user').insert(identityProviderUsers); await knex.batchInsert('identity_provider_user', identityProviderUsers).transacting(trx);
} }
const sessions = await trx('session').withSchema('v1').whereIn('user_id', whereInUserIds); const sessions = await trx('session').withSchema('v1').whereIn('user_id', whereInUserIds);
if (sessions.length > 0) { if (sessions.length > 0) {
await trx('session').insert(sessions); await knex.batchInsert('session', sessions).transacting(trx);
} }
} }
@ -154,22 +157,27 @@ const upgradeDatabase = async () => {
if (projectsWithBackgroundImage.length > 0) { if (projectsWithBackgroundImage.length > 0) {
const createdAt = new Date().toISOString(); const createdAt = new Date().toISOString();
const backgroundImages = await trx('background_image').insert( const backgroundImages = await knex
.batchInsert(
'background_image',
projectsWithBackgroundImage.map((project) => ({ projectsWithBackgroundImage.map((project) => ({
...project.background_image, ...project.background_image,
project_id: project.id, project_id: project.id,
size_in_bytes: 0, size_in_bytes: 0,
created_at: createdAt, created_at: createdAt,
})), })),
['id', 'project_id'], )
); .returning(['id', 'project_id'])
.transacting(trx);
backgroundImages.forEach((backgroundImage) => { backgroundImages.forEach((backgroundImage) => {
backgroundImageIdByProjectId[backgroundImage.project_id] = backgroundImage.id; backgroundImageIdByProjectId[backgroundImage.project_id] = backgroundImage.id;
}); });
} }
await trx('project').insert( await knex
.batchInsert(
'project',
projects.map((project) => { projects.map((project) => {
const data = { const data = {
..._.pick(project, ['id', 'name', 'created_at', 'updated_at']), ..._.pick(project, ['id', 'name', 'created_at', 'updated_at']),
@ -194,7 +202,8 @@ const upgradeDatabase = async () => {
return data; return data;
}), }),
); )
.transacting(trx);
} }
const projectManagers = await trx('project_manager') const projectManagers = await trx('project_manager')
@ -202,7 +211,7 @@ const upgradeDatabase = async () => {
.whereIn('project_id', whereInProjectIds); .whereIn('project_id', whereInProjectIds);
if (projectManagers.length > 0) { if (projectManagers.length > 0) {
await trx('project_manager').insert(projectManagers); await knex.batchInsert('project_manager', projectManagers).transacting(trx);
} }
const boards = await trx('board').withSchema('v1').whereIn('project_id', whereInProjectIds); const boards = await trx('board').withSchema('v1').whereIn('project_id', whereInProjectIds);
@ -218,7 +227,9 @@ const upgradeDatabase = async () => {
const whereInBoardIds = ['0', ...Object.keys(projectIdByBoardId)]; const whereInBoardIds = ['0', ...Object.keys(projectIdByBoardId)];
if (boards.length > 0) { if (boards.length > 0) {
await trx('board').insert( await knex
.batchInsert(
'board',
boards.map((board) => ({ boards.map((board) => ({
..._.pick(board, ['id', 'project_id', 'position', 'name', 'created_at', 'updated_at']), ..._.pick(board, ['id', 'project_id', 'position', 'name', 'created_at', 'updated_at']),
default_view: Board.Views.KANBAN, default_view: Board.Views.KANBAN,
@ -226,11 +237,14 @@ const upgradeDatabase = async () => {
limit_card_types_to_default_one: false, limit_card_types_to_default_one: false,
always_display_card_creator: false, always_display_card_creator: false,
})), })),
); )
.transacting(trx);
const createdAt = new Date().toISOString(); const createdAt = new Date().toISOString();
await trx('list').insert( await knex
.batchInsert(
'list',
boards.flatMap((board) => boards.flatMap((board) =>
[List.Types.ARCHIVE, List.Types.TRASH].map((type) => ({ [List.Types.ARCHIVE, List.Types.TRASH].map((type) => ({
type, type,
@ -238,7 +252,8 @@ const upgradeDatabase = async () => {
created_at: createdAt, created_at: createdAt,
})), })),
), ),
); )
.transacting(trx);
} }
const boardMemberships = await trx('board_membership') const boardMemberships = await trx('board_membership')
@ -246,7 +261,9 @@ const upgradeDatabase = async () => {
.whereIn('board_id', whereInBoardIds); .whereIn('board_id', whereInBoardIds);
if (boardMemberships.length > 0) { if (boardMemberships.length > 0) {
await trx('board_membership').insert( await knex
.batchInsert(
'board_membership',
boardMemberships.map((boardMembership) => ({ boardMemberships.map((boardMembership) => ({
..._.pick(boardMembership, [ ..._.pick(boardMembership, [
'id', 'id',
@ -259,20 +276,23 @@ const upgradeDatabase = async () => {
]), ]),
project_id: projectIdByBoardId[boardMembership.board_id], project_id: projectIdByBoardId[boardMembership.board_id],
})), })),
); )
.transacting(trx);
} }
const labels = await trx('label').withSchema('v1').whereIn('board_id', whereInBoardIds); const labels = await trx('label').withSchema('v1').whereIn('board_id', whereInBoardIds);
if (labels.length > 0) { if (labels.length > 0) {
await trx('label').insert(labels); await knex.batchInsert('label', labels).transacting(trx);
} }
const lists = await trx('list').withSchema('v1').whereIn('board_id', whereInBoardIds); const lists = await trx('list').withSchema('v1').whereIn('board_id', whereInBoardIds);
const whereInListIds = ['0', ...lists.map(({ id }) => id)]; const whereInListIds = ['0', ...lists.map(({ id }) => id)];
if (lists.length > 0) { if (lists.length > 0) {
await trx('list').insert( await knex
.batchInsert(
'list',
lists.map((list) => ({ lists.map((list) => ({
..._.pick(list, [ ..._.pick(list, [
'id', 'id',
@ -285,7 +305,8 @@ const upgradeDatabase = async () => {
]), ]),
type: List.Types.ACTIVE, type: List.Types.ACTIVE,
})), })),
); )
.transacting(trx);
} }
const cards = await trx('card') const cards = await trx('card')
@ -297,7 +318,9 @@ const upgradeDatabase = async () => {
const whereInCardIds = ['0', ...Object.keys(cardById)]; const whereInCardIds = ['0', ...Object.keys(cardById)];
if (cards.length > 0) { if (cards.length > 0) {
await trx('card').insert( await knex
.batchInsert(
'card',
cards.map((card) => ({ cards.map((card) => ({
..._.pick(card, [ ..._.pick(card, [
'id', 'id',
@ -316,7 +339,8 @@ const upgradeDatabase = async () => {
type: Card.Types.PROJECT, type: Card.Types.PROJECT,
list_changed_at: card.created_at, list_changed_at: card.created_at,
})), })),
); )
.transacting(trx);
} }
const cardSubscriptions = await trx('card_subscription') const cardSubscriptions = await trx('card_subscription')
@ -324,7 +348,7 @@ const upgradeDatabase = async () => {
.whereIn('card_id', whereInCardIds); .whereIn('card_id', whereInCardIds);
if (cardSubscriptions.length > 0) { if (cardSubscriptions.length > 0) {
await trx('card_subscription').insert(cardSubscriptions); await knex.batchInsert('card_subscription', cardSubscriptions).transacting(trx);
} }
const cardMemberships = await trx('card_membership') const cardMemberships = await trx('card_membership')
@ -332,13 +356,13 @@ const upgradeDatabase = async () => {
.whereIn('card_id', whereInCardIds); .whereIn('card_id', whereInCardIds);
if (cardMemberships.length > 0) { if (cardMemberships.length > 0) {
await trx('card_membership').insert(cardMemberships); await knex.batchInsert('card_membership', cardMemberships).transacting(trx);
} }
const cardLabels = await trx('card_label').withSchema('v1').whereIn('card_id', whereInCardIds); const cardLabels = await trx('card_label').withSchema('v1').whereIn('card_id', whereInCardIds);
if (cardLabels.length > 0) { if (cardLabels.length > 0) {
await trx('card_label').insert(cardLabels); await knex.batchInsert('card_label', cardLabels).transacting(trx);
} }
const tasks = await trx('task').withSchema('v1').whereIn('card_id', whereInCardIds); const tasks = await trx('task').withSchema('v1').whereIn('card_id', whereInCardIds);
@ -349,7 +373,9 @@ const upgradeDatabase = async () => {
if (taskCardIds.length > 0) { if (taskCardIds.length > 0) {
const createdAt = new Date().toISOString(); const createdAt = new Date().toISOString();
const taskLists = await trx('task_list').insert( const taskLists = await knex
.batchInsert(
'task_list',
taskCardIds.map((cardId) => ({ taskCardIds.map((cardId) => ({
card_id: cardId, card_id: cardId,
position: POSITION_GAP, position: POSITION_GAP,
@ -357,23 +383,36 @@ const upgradeDatabase = async () => {
show_on_front_of_card: true, show_on_front_of_card: true,
created_at: createdAt, created_at: createdAt,
})), })),
['id', 'card_id'], )
); .returning(['id', 'card_id'])
.transacting(trx);
await trx('task').insert( await knex
.batchInsert(
'task',
taskLists.flatMap((taskList) => taskLists.flatMap((taskList) =>
tasksByCardId[taskList.card_id].map((task) => ({ tasksByCardId[taskList.card_id].map((task) => ({
..._.pick(task, ['id', 'position', 'name', 'is_completed', 'created_at', 'updated_at']), ..._.pick(task, [
'id',
'position',
'name',
'is_completed',
'created_at',
'updated_at',
]),
task_list_id: taskList.id, task_list_id: taskList.id,
})), })),
), ),
); )
.transacting(trx);
} }
const attachments = await trx('attachment').withSchema('v1').whereIn('card_id', whereInCardIds); const attachments = await trx('attachment').withSchema('v1').whereIn('card_id', whereInCardIds);
if (attachments.length > 0) { if (attachments.length > 0) {
await trx('attachment').insert( await knex
.batchInsert(
'attachment',
attachments.map((attachment) => ({ attachments.map((attachment) => ({
..._.pick(attachment, ['id', 'card_id', 'name', 'created_at', 'updated_at']), ..._.pick(attachment, ['id', 'card_id', 'name', 'created_at', 'updated_at']),
creator_user_id: userIdsSet.has(attachment.creator_user_id) creator_user_id: userIdsSet.has(attachment.creator_user_id)
@ -389,7 +428,8 @@ const upgradeDatabase = async () => {
image: attachment.image, image: attachment.image,
}, },
})), })),
); )
.transacting(trx);
} }
const actions = await trx('action').withSchema('v1').whereIn('card_id', whereInCardIds); const actions = await trx('action').withSchema('v1').whereIn('card_id', whereInCardIds);
@ -409,17 +449,22 @@ const upgradeDatabase = async () => {
}); });
if (commentActions.length > 0) { if (commentActions.length > 0) {
await trx('comment').insert( await knex
.batchInsert(
'comment',
commentActions.map((action) => ({ commentActions.map((action) => ({
..._.pick(action, ['id', 'card_id', 'created_at', 'updated_at']), ..._.pick(action, ['id', 'card_id', 'created_at', 'updated_at']),
user_id: userIdsSet.has(action.user_id) ? action.user_id : null, user_id: userIdsSet.has(action.user_id) ? action.user_id : null,
text: action.data.text, text: action.data.text,
})), })),
); )
.transacting(trx);
} }
if (otherActions.length > 0) { if (otherActions.length > 0) {
await trx('action').insert( await knex
.batchInsert(
'action',
otherActions.map((action) => { otherActions.map((action) => {
const data = { const data = {
..._.pick(action, ['id', 'card_id', 'type', 'created_at', 'updated_at']), ..._.pick(action, ['id', 'card_id', 'type', 'created_at', 'updated_at']),
@ -454,7 +499,8 @@ const upgradeDatabase = async () => {
return data; return data;
}), }),
); )
.transacting(trx);
} }
const notifications = await trx('notification') const notifications = await trx('notification')
@ -464,7 +510,9 @@ const upgradeDatabase = async () => {
.whereIn('card_id', whereInCardIds); .whereIn('card_id', whereInCardIds);
if (notifications.length > 0) { if (notifications.length > 0) {
await trx('notification').insert( await knex
.batchInsert(
'notification',
notifications.map((notification) => { notifications.map((notification) => {
const card = cardById[notification.card_id]; const card = cardById[notification.card_id];
const action = actionById[notification.action_id]; const action = actionById[notification.action_id];
@ -512,7 +560,8 @@ const upgradeDatabase = async () => {
return data; return data;
}), }),
); )
.transacting(trx);
} }
await trx.schema.dropSchema('v1', true); await trx.schema.dropSchema('v1', true);