From 510572d029ede37476e25308d70214323e14ab75 Mon Sep 17 00:00:00 2001 From: Thomas Sunde Nielsen Date: Thu, 14 Nov 2024 12:05:01 +0100 Subject: [PATCH 1/6] Remove unnecessary id from create test --- packages/server/tests/api/rest.test.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/packages/server/tests/api/rest.test.ts b/packages/server/tests/api/rest.test.ts index 1b546365..1c52060a 100644 --- a/packages/server/tests/api/rest.test.ts +++ b/packages/server/tests/api/rest.test.ts @@ -1742,7 +1742,6 @@ describe('REST server tests', () => { requestBody: { data: { type: 'postLike', - id: `1${idDivider}user1`, attributes: { userId: 'user1', postId: 1, superLike: false }, }, }, From 057c73ba977899e53b543b6b3fac434b5788dcce Mon Sep 17 00:00:00 2001 From: Thomas Sunde Nielsen Date: Thu, 14 Nov 2024 12:09:15 +0100 Subject: [PATCH 2/6] Change openapi create openapi to match server --- packages/plugins/openapi/src/rest-generator.ts | 4 ++-- .../plugins/openapi/tests/baseline/rest-3.0.0.baseline.yaml | 3 --- .../plugins/openapi/tests/baseline/rest-3.1.0.baseline.yaml | 1 - 3 files changed, 2 insertions(+), 6 deletions(-) diff --git a/packages/plugins/openapi/src/rest-generator.ts b/packages/plugins/openapi/src/rest-generator.ts index 4e7c8bcb..c0447763 100644 --- a/packages/plugins/openapi/src/rest-generator.ts +++ b/packages/plugins/openapi/src/rest-generator.ts @@ -860,7 +860,7 @@ export class RESTfulOpenAPIGenerator extends OpenAPIGeneratorBase { // For compound ids each component is also exposed as a separate fields for read operations, // but not required for write operations const fields = - idFields.length > 1 && mode === 'read' ? model.fields : model.fields.filter((f) => !isIdField(f)); + idFields.length > 1 && mode !== 'update' ? model.fields : model.fields.filter((f) => !isIdField(f)); const attributes: Record = {}; const relationships: Record = {}; @@ -907,7 +907,7 @@ export class RESTfulOpenAPIGenerator extends OpenAPIGeneratorBase { if (mode === 'create') { // 'id' is required if there's no default value const idFields = model.fields.filter((f) => isIdField(f)); - if (idFields.length && idFields.every((f) => !hasAttribute(f, '@default'))) { + if (idFields.length === 1 && idFields.every((f) => !hasAttribute(f, '@default'))) { properties = { id: { type: 'string' }, ...properties }; toplevelRequired.unshift('id'); } diff --git a/packages/plugins/openapi/tests/baseline/rest-3.0.0.baseline.yaml b/packages/plugins/openapi/tests/baseline/rest-3.0.0.baseline.yaml index adb9ded1..f0b46fc9 100644 --- a/packages/plugins/openapi/tests/baseline/rest-3.0.0.baseline.yaml +++ b/packages/plugins/openapi/tests/baseline/rest-3.0.0.baseline.yaml @@ -3135,14 +3135,11 @@ components: type: object description: The "PostLike" model required: - - id - type - attributes properties: type: type: string - attributes: - type: object relationships: type: object properties: diff --git a/packages/plugins/openapi/tests/baseline/rest-3.1.0.baseline.yaml b/packages/plugins/openapi/tests/baseline/rest-3.1.0.baseline.yaml index f69536b3..79e0c020 100644 --- a/packages/plugins/openapi/tests/baseline/rest-3.1.0.baseline.yaml +++ b/packages/plugins/openapi/tests/baseline/rest-3.1.0.baseline.yaml @@ -3149,7 +3149,6 @@ components: type: object description: The "PostLike" model required: - - id - type - attributes properties: From 00990d8df5d788dd58008c3f43aae2f84cb84530 Mon Sep 17 00:00:00 2001 From: Thomas Sunde Nielsen Date: Fri, 15 Nov 2024 10:39:27 +0100 Subject: [PATCH 3/6] Add test for updating compound id --- packages/server/tests/api/rest.test.ts | 25 +++++++++++++++++++++++++ 1 file changed, 25 insertions(+) diff --git a/packages/server/tests/api/rest.test.ts b/packages/server/tests/api/rest.test.ts index 1c52060a..449cf563 100644 --- a/packages/server/tests/api/rest.test.ts +++ b/packages/server/tests/api/rest.test.ts @@ -2006,6 +2006,31 @@ describe('REST server tests', () => { expect(r.status).toBe(200); }); + it('update the id of an item with compound id', async () => { + await prisma.user.create({ data: { myId: 'user1', email: 'user1@abc.com' } }); + await prisma.post.create({ data: { id: 1, title: 'Post1' } }); + await prisma.post.create({ data: { id: 2, title: 'Post2' } }); + await prisma.postLike.create({ data: { userId: 'user1', postId: 1, superLike: false } }); + + const r = await handler({ + method: 'put', + path: `/postLike/1${idDivider}user1`, + query: {}, + requestBody: { + data: { + type: 'postLike', + relationships: { + post: { data: { type: 'post', id: 2 } }, + }, + }, + }, + prisma, + }); + + expect(r.status).toBe(200); + expect(r.body.data.id).toBe(`2${idDivider}user1`); + }); + it('update a single relation', async () => { await prisma.user.create({ data: { myId: 'user1', email: 'user1@abc.com' } }); await prisma.post.create({ From 040d1bd336a05ddb9b4890c5abcdad066b853df8 Mon Sep 17 00:00:00 2001 From: Thomas Sunde Nielsen Date: Fri, 15 Nov 2024 10:39:35 +0100 Subject: [PATCH 4/6] Fix update of single relationship --- packages/server/src/api/rest/index.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/server/src/api/rest/index.ts b/packages/server/src/api/rest/index.ts index 1c9c56f4..8fa403f2 100644 --- a/packages/server/src/api/rest/index.ts +++ b/packages/server/src/api/rest/index.ts @@ -959,7 +959,7 @@ class RequestHandler extends APIHandlerBase { return this.makeError('invalidRelationData'); } updatePayload.data[key] = { - set: { + connect: { [this.makePrismaIdKey(relationInfo.idFields)]: data.data.id, }, }; From 4d9530650bd264bf36f8c14485d6b05f3e2d6288 Mon Sep 17 00:00:00 2001 From: Thomas Sunde Nielsen Date: Fri, 15 Nov 2024 10:40:55 +0100 Subject: [PATCH 5/6] Expose compound id as separate fields always --- packages/plugins/openapi/src/rest-generator.ts | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/packages/plugins/openapi/src/rest-generator.ts b/packages/plugins/openapi/src/rest-generator.ts index c0447763..d6fb4859 100644 --- a/packages/plugins/openapi/src/rest-generator.ts +++ b/packages/plugins/openapi/src/rest-generator.ts @@ -857,10 +857,8 @@ export class RESTfulOpenAPIGenerator extends OpenAPIGeneratorBase { private generateModelEntity(model: DataModel, mode: 'read' | 'create' | 'update'): OAPI.SchemaObject { const idFields = model.fields.filter((f) => isIdField(f)); - // For compound ids each component is also exposed as a separate fields for read operations, - // but not required for write operations - const fields = - idFields.length > 1 && mode !== 'update' ? model.fields : model.fields.filter((f) => !isIdField(f)); + // For compound ids each component is also exposed as a separate fields. + const fields = idFields.length > 1 ? model.fields : model.fields.filter((f) => !isIdField(f)); const attributes: Record = {}; const relationships: Record = {}; From de8aefab125e375e80de7745201ab062aee4e52e Mon Sep 17 00:00:00 2001 From: Thomas Sunde Nielsen Date: Sat, 16 Nov 2024 21:08:25 +0100 Subject: [PATCH 6/6] Simplify id fields @default check --- packages/plugins/openapi/src/rest-generator.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/plugins/openapi/src/rest-generator.ts b/packages/plugins/openapi/src/rest-generator.ts index d6fb4859..1434edc2 100644 --- a/packages/plugins/openapi/src/rest-generator.ts +++ b/packages/plugins/openapi/src/rest-generator.ts @@ -905,7 +905,7 @@ export class RESTfulOpenAPIGenerator extends OpenAPIGeneratorBase { if (mode === 'create') { // 'id' is required if there's no default value const idFields = model.fields.filter((f) => isIdField(f)); - if (idFields.length === 1 && idFields.every((f) => !hasAttribute(f, '@default'))) { + if (idFields.length === 1 && !hasAttribute(idFields[0], '@default')) { properties = { id: { type: 'string' }, ...properties }; toplevelRequired.unshift('id'); }