From 036cb8b250b842999d47327420b26450deb1cd28 Mon Sep 17 00:00:00 2001 From: Marc-Roig Date: Mon, 2 Jan 2023 16:48:02 +0100 Subject: [PATCH 1/5] filter by entity id when reordering components --- .../core/database/lib/entity-manager/regular-relations.js | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/packages/core/database/lib/entity-manager/regular-relations.js b/packages/core/database/lib/entity-manager/regular-relations.js index bba3e9b72f..1aaece2217 100644 --- a/packages/core/database/lib/entity-manager/regular-relations.js +++ b/packages/core/database/lib/entity-manager/regular-relations.js @@ -338,7 +338,9 @@ const cleanOrderColumnsForInnoDB = async ({ .map(() => '?') .join(', ')}) ) AS inv_order - FROM ?? a`, + FROM ?? a + WHERE a.:joinColumnName: = :id + `, [ tempInvOrderTableName, joinTable.name, From 8ec567ef9f3c7c58810b391f9b27f11a89d2ab15 Mon Sep 17 00:00:00 2001 From: Marc-Roig Date: Tue, 3 Jan 2023 14:49:00 +0100 Subject: [PATCH 2/5] move mysql where clause to the correct query --- .../core/database/lib/entity-manager/regular-relations.js | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/packages/core/database/lib/entity-manager/regular-relations.js b/packages/core/database/lib/entity-manager/regular-relations.js index 1aaece2217..d1711a32e4 100644 --- a/packages/core/database/lib/entity-manager/regular-relations.js +++ b/packages/core/database/lib/entity-manager/regular-relations.js @@ -296,7 +296,9 @@ const cleanOrderColumnsForInnoDB = async ({ FROM :joinTableName: b WHERE a.:orderColumnName: >= b.:orderColumnName: AND a.:joinColumnName: = b.:joinColumnName: AND a.:joinColumnName: = :id ) AS src_order - FROM :joinTableName: a`, + FROM :joinTableName: a + WHERE a.:joinColumnName: = :id + `, { tempOrderTableName, joinTableName: joinTable.name, @@ -338,9 +340,7 @@ const cleanOrderColumnsForInnoDB = async ({ .map(() => '?') .join(', ')}) ) AS inv_order - FROM ?? a - WHERE a.:joinColumnName: = :id - `, + FROM ?? a`, [ tempInvOrderTableName, joinTable.name, From dd98293a55102a50722f592a842eb50ca960b5dd Mon Sep 17 00:00:00 2001 From: Marc-Roig Date: Fri, 13 Jan 2023 10:53:30 +0100 Subject: [PATCH 3/5] better filtering in inverse order column --- .../core/database/lib/entity-manager/regular-relations.js | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/packages/core/database/lib/entity-manager/regular-relations.js b/packages/core/database/lib/entity-manager/regular-relations.js index d1711a32e4..0443ce9330 100644 --- a/packages/core/database/lib/entity-manager/regular-relations.js +++ b/packages/core/database/lib/entity-manager/regular-relations.js @@ -340,7 +340,9 @@ const cleanOrderColumnsForInnoDB = async ({ .map(() => '?') .join(', ')}) ) AS inv_order - FROM ?? a`, + FROM ?? a + WHERE a.?? IN (${inverseRelIds.map(() => '?').join(', ')}) + `, [ tempInvOrderTableName, joinTable.name, @@ -351,6 +353,8 @@ const cleanOrderColumnsForInnoDB = async ({ inverseJoinColumn.name, ...inverseRelIds, joinTable.name, + inverseJoinColumn.name, + ...inverseRelIds, ] ) .transacting(trx); From 319c7473f35e97e47d1994331f423134e2c9ca32 Mon Sep 17 00:00:00 2001 From: Marc-Roig Date: Fri, 13 Jan 2023 15:20:46 +0100 Subject: [PATCH 4/5] test components order is preserved --- .../components/repeatable-order.test.api.js | 97 +++++++++++++++++++ 1 file changed, 97 insertions(+) create mode 100644 packages/core/strapi/tests/components/repeatable-order.test.api.js diff --git a/packages/core/strapi/tests/components/repeatable-order.test.api.js b/packages/core/strapi/tests/components/repeatable-order.test.api.js new file mode 100644 index 0000000000..d5c9390a73 --- /dev/null +++ b/packages/core/strapi/tests/components/repeatable-order.test.api.js @@ -0,0 +1,97 @@ +'use strict'; + +const { createTestBuilder } = require('../../../../../test/helpers/builder'); +const { createStrapiInstance } = require('../../../../../test/helpers/strapi'); +const { createContentAPIRequest } = require('../../../../../test/helpers/request'); + +let strapi; +let rq; + +const component = { + displayName: 'somecomponent', + attributes: { + name: { + type: 'string', + }, + }, +}; + +const ct = { + displayName: 'withcomponent', + singularName: 'withcomponent', + pluralName: 'withcomponents', + attributes: { + field: { + type: 'component', + component: 'default.somecomponent', + repeatable: true, + required: false, + }, + }, +}; + +const createEntity = async (data) => { + return rq.post('/', { + body: { data }, + qs: { populate: ['field'] }, + }); +}; + +const updateEntity = async (id, data) => { + return rq.put(`/${id}`, { + body: { data }, + qs: { populate: ['field'] }, + }); +}; + +const getEntity = async (id) => { + return rq.get(`/${id}`, { + qs: { populate: ['field'] }, + }); +}; + +describe('Given a content type with a repeatable component and two entities created', () => { + const builder = createTestBuilder(); + let entity1; + let entity2; + + beforeAll(async () => { + await builder.addComponent(component).addContentType(ct).build(); + + strapi = await createStrapiInstance(); + rq = await createContentAPIRequest({ strapi }); + rq.setURLPrefix('/api/withcomponents'); + + // Create two entities + const res1 = await createEntity({ field: [{ name: 'field1' }, { name: 'field2' }] }); + entity1 = res1.body.data; + + const res2 = await createEntity({ field: [{ name: 'field1' }, { name: 'field2' }] }); + entity2 = res2.body.data; + }); + + afterAll(async () => { + await strapi.destroy(); + await builder.cleanup(); + }); + + describe('When I update the order of one of the entities components', () => { + test('Then the order of both entity components is preserved', async () => { + const updatedEntity1 = await updateEntity(entity1.id, { + field: [{ name: 'field2' }, { name: 'field1' }], + }); + + const res = await getEntity(entity2.id); + + expect(updatedEntity1.body.data.attributes.field).toEqual([ + { id: expect.anything(), name: 'field2' }, + { id: expect.anything(), name: 'field1' }, + ]); + expect(res.statusCode).toBe(200); + expect(res.body.data.attributes.field).toEqual([ + { id: expect.anything(), name: 'field1' }, + { id: expect.anything(), name: 'field2' }, + ]); + }); + }); +}); From 49843ed7226b72b618976d0cef8533c0d8cfbb15 Mon Sep 17 00:00:00 2001 From: Marc-Roig Date: Mon, 16 Jan 2023 13:05:13 +0100 Subject: [PATCH 5/5] update entity 1 component order properly --- .../core/strapi/tests/components/repeatable-order.test.api.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/core/strapi/tests/components/repeatable-order.test.api.js b/packages/core/strapi/tests/components/repeatable-order.test.api.js index d5c9390a73..4dca110c6e 100644 --- a/packages/core/strapi/tests/components/repeatable-order.test.api.js +++ b/packages/core/strapi/tests/components/repeatable-order.test.api.js @@ -78,7 +78,7 @@ describe('Given a content type with a repeatable component and two entities crea describe('When I update the order of one of the entities components', () => { test('Then the order of both entity components is preserved', async () => { const updatedEntity1 = await updateEntity(entity1.id, { - field: [{ name: 'field2' }, { name: 'field1' }], + field: [entity1.attributes.field[1], entity1.attributes.field[0]], }); const res = await getEntity(entity2.id);