Skip to content

Commit 59dd226

Browse files
pwizlaMarc-Roig
andauthored
Migration guide for removing relationship duplicates (#1272)
* Add migration guide placeholder for MySQL 8 fix * add migration script * fix typos * specify duplicated relationships in description * add 4.5.0 to 4.5.1 migration guide * fix typo * check if table exists in db * change migration name to 4.4.5 to 4.5.1 * remove commas * add suggestions * change db get schema to trx schema * update migration guide 4.5.0 to 4.4.5 * fix typo * fix typo * fix typo Co-authored-by: Marc-Roig <[email protected]>
1 parent 26b22a7 commit 59dd226

File tree

2 files changed

+138
-2
lines changed

2 files changed

+138
-2
lines changed

docs/developer-docs/latest/update-migration-guides/migration-guides.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ sidebarDepth: 0
1010
Migrations are necessary when upgrades to Strapi include breaking changes. The migration guides are sequential, meaning if there is more than 1 migration guide between your current version and the latest release, follow each guide in order. If there is no specific migration guide between your current version and the latest release follow the [Update Strapi guide](update-version.md).
1111

1212
:::caution
13-
[Plugins extension](/developer-docs/latest/plugins/users-permissions.md) that create custom code or modify existing code will need to be updated and compared to the changes in the repository. Not updating the plugin extensions could break the application.
13+
[Plugins extension](/developer-docs/latest/plugins/users-permissions.md) that create custom code or modify existing code will need to be updated and compared to the changes in the repository. Not updating the plugin extensions could break the application.
1414
:::
1515

1616
## v4 migration guides
@@ -21,10 +21,11 @@ Migrations are necessary when upgrades to Strapi include breaking changes. The m
2121
- [Migration guide from 4.2.x to 4.3.x](migration-guides/v4/migration-guide-4.2.x-to-4.3.x.md)
2222
- [Migration guide from 4.3.6 to 4.3.8](migration-guides/v4/migration-guide-4.3.6-to-4.3.8.md)
2323
- [Migration guide from 4.4.3 to 4.4.5](migration-guides/v4/migration-guide-4.4.3-to-4.4.5.md)
24+
- [Migration guide from 4.4.5 to 4.5.1](migration-guides/v4/migration-guide-4.4.5-to-4.5.1.md)
2425

2526
## v3 to v4 migration guides
2627

27-
::: callout 🚧 Migration guides
28+
::: callout 🚧 Migration guides
2829
This section is still a work in progress and will continue to be updated and improved. In the meantime, feel free to ask for help on the [forum](https://forum.strapi.io/) or on the community [Discord](https://discord.strapi.io).
2930
:::
3031

Lines changed: 135 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,135 @@
1+
---
2+
title: Migrate from 4.4.5 to 4.5.1 - Strapi Developer Docs
3+
description: Learn how you can migrate your Strapi application from 4.4.5 to 4.5.1.
4+
canonicalUrl: https://docs.strapi.io/developer-docs/latest/update-migration-guides/migration-guides/v4/migration-guide-4.4.5-to-4.5.1.html
5+
---
6+
7+
# v4.4.5 to v4.5.1 migration guide
8+
9+
The Strapi v4.4.5 to v4.5.1 migration guide upgrades v4.4.5 to v4.5.1. We introduced unique indexes on relationship tables and the application will not start if there are duplicated relationships. The migration guide consists of:
10+
11+
- Upgrading the application dependencies
12+
- Installing database migration script (optional)
13+
- Reinitializing the application
14+
15+
<!-- TODO: explain what the migration focuses on (i.e. what breaking changes it fixes). -->
16+
17+
## Upgrading the application dependencies to 4.5.1
18+
19+
:::prerequisites
20+
Stop the server before starting the upgrade.
21+
:::
22+
23+
<!-- TODO: update version numbers below 👇 -->
24+
25+
1. Upgrade all of the Strapi packages in `package.json` to `4.5.1`:
26+
27+
```json
28+
// path: package.json
29+
30+
{
31+
// ...
32+
"dependencies": {
33+
"@strapi/strapi": "4.5.1",
34+
"@strapi/plugin-users-permissions": "4.5.1",
35+
"@strapi/plugin-i18n": "4.5.1"
36+
// ...
37+
}
38+
}
39+
```
40+
41+
2. Save the edited `package.json` file.
42+
43+
3. Run either `yarn` or `npm install` to install the new version.
44+
45+
::: tip
46+
If the operation doesn't work, try removing your `yarn.lock` or `package-lock.json`. If that doesn't help, remove the `node_modules` folder as well and try again.
47+
:::
48+
49+
## Installing database migration script (optional)
50+
51+
This step is only required if you have relationship duplicates in your application. If you have them, the application will not start and you will see an error message in the terminal similar to:
52+
53+
```
54+
error: alter table <SOME_TABLE> add constraint <SOME_TABLE_INDEX>
55+
unique (<COLUMN_NAME>, <COLUMN_NAME>) - could not create unique index <SOME_TABLE>
56+
```
57+
58+
To remove the duplicated relationships easily, the following migration script file was created. It will automatically remove duplicates of any relationship in the database and will be executed only once at the next launch of Strapi.
59+
60+
To prepare the migration:
61+
62+
1. Make a backup of the database in case something unexpected happens.
63+
2. In the `./database/migrations` folder, create a file named `2022.11.16T00.00.00.remove_duplicated_relationships.js`.
64+
3. Copy and paste the following code into the previously created file:
65+
66+
```jsx
67+
'use strict';
68+
69+
/**
70+
* Get the link tables names that need to be updated
71+
*/
72+
const getLinkTables = ({ strapi }) => {
73+
const contentTypes = strapi.db.metadata;
74+
const tablesToUpdate = {};
75+
76+
contentTypes.forEach(contentType => {
77+
// Get attributes
78+
const attributes = contentType.attributes;
79+
80+
// For each relation type, add the joinTable name to tablesToUpdate
81+
Object.values(attributes).forEach(attribute => {
82+
if (attribute.type === 'relation' && attribute.joinTable) {
83+
tablesToUpdate[attribute.joinTable.name] = attribute.joinTable;
84+
}
85+
});
86+
});
87+
88+
return Object.values(tablesToUpdate);
89+
};
90+
91+
async function up(trx) {
92+
const linkTablesToUpdate = getLinkTables({ strapi });
93+
94+
// Remove duplicates from link tables
95+
for (const table of linkTablesToUpdate) {
96+
const tableExists = await trx.schema.hasTable(table.name);
97+
if (!tableExists) continue;
98+
99+
strapi.log.info(`Deleting duplicates of table ${table.name}...`);
100+
101+
try {
102+
// Query to delete duplicates from a link table
103+
let query = `
104+
CREATE TEMPORARY TABLE tmp as SELECT DISTINCT t2.id as id
105+
FROM ?? as t1 JOIN ?? as t2
106+
ON t1.id < t2.id
107+
`;
108+
const pivotWhereParams = [];
109+
110+
// For each pivot column, add a on condition to the query
111+
table.pivotColumns.forEach(column => {
112+
query += ` AND t1.?? = t2.??`;
113+
pivotWhereParams.push(column, column);
114+
});
115+
116+
// Create temporary table with the ids of the repeated rows
117+
await trx.raw(query, [table.name, table.name, ...pivotWhereParams]);
118+
119+
// Delete repeated rows from the original table
120+
await trx.raw(`DELETE FROM ?? WHERE id in (SELECT * FROM tmp)`, [table.name]);
121+
} finally {
122+
// Drop temporary table
123+
await trx.raw(`DROP TABLE IF EXISTS tmp `);
124+
}
125+
}
126+
}
127+
128+
async function down() {}
129+
130+
module.exports = { up, down };
131+
```
132+
133+
<!-- TODO: complete this part -->
134+
135+
!!!include(developer-docs/latest/update-migration-guides/migration-guides/v4/snippets/Rebuild-and-start-snippet.md)!!!

0 commit comments

Comments
 (0)