From a938671ef44e8fa0c8ac59e2cbfa0f0ad7feac7c Mon Sep 17 00:00:00 2001 From: James Date: Sun, 19 Apr 2020 14:33:44 -0400 Subject: [PATCH] ensures backend validation works recursively and formats pathnames according to nested fields --- demo/collections/Page/index.js | 1 + src/collections/graphql/register.js | 8 ++++---- src/collections/operations/create.js | 2 +- src/fields/validate.js | 17 ++++++++++++----- src/globals/graphql/register.js | 5 +++-- src/graphql/schema/buildMutationInputType.js | 4 ++-- src/uploads/graphql/register.js | 4 ++-- src/users/graphql/register.js | 4 ++-- 8 files changed, 27 insertions(+), 18 deletions(-) diff --git a/demo/collections/Page/index.js b/demo/collections/Page/index.js index 52b44c0c8d..f8820063a3 100644 --- a/demo/collections/Page/index.js +++ b/demo/collections/Page/index.js @@ -137,6 +137,7 @@ module.exports = { maxLength: 100, label: 'Title', width: 50, + required: true, hooks: { afterRead: value => `hooked value - ${value}`, }, diff --git a/src/collections/graphql/register.js b/src/collections/graphql/register.js index 56100274a3..5af9ecf077 100644 --- a/src/collections/graphql/register.js +++ b/src/collections/graphql/register.js @@ -43,13 +43,13 @@ function registerCollections() { singularLabel, ); - collection.graphQL.mutationInputType = this.buildMutationInputType( + collection.graphQL.mutationInputType = new GraphQLNonNull(this.buildMutationInputType( singularLabel, fields, singularLabel, - ); + )); - collection.graphQL.updateMutationInputType = this.buildMutationInputType( + collection.graphQL.updateMutationInputType = new GraphQLNonNull(this.buildMutationInputType( `${singularLabel}Update`, fields.map((field) => { return { @@ -58,7 +58,7 @@ function registerCollections() { }; }), `${singularLabel}Update`, - ); + )); this.Query.fields[singularLabel] = { type: collection.graphQL.type, diff --git a/src/collections/operations/create.js b/src/collections/operations/create.js index 04891e2f9b..07e179d8a0 100644 --- a/src/collections/operations/create.js +++ b/src/collections/operations/create.js @@ -68,7 +68,7 @@ const create = async (args) => { // 6. Execute after collection hook // ///////////////////////////////////// - const { afterCreate } = args.config.hooks.afterCreate; + const { afterCreate } = args.config.hooks; if (typeof afterCreate === 'function') { result = await afterCreate(options, result); diff --git a/src/fields/validate.js b/src/fields/validate.js index 97c856e53b..159d5af533 100644 --- a/src/fields/validate.js +++ b/src/fields/validate.js @@ -11,18 +11,25 @@ const iterateFields = async (fields, data, errors, path = '') => { } else { for (const field of fields) { if (field.required) { - const validationResult = await field.validate(data[field.name], field); + if (data && data[field.name]) { + const validationResult = await field.validate(data[field.name], field); - if (validationResult !== true) { + if (validationResult !== true) { + errors.push({ + field: `${path}${field.name}`, + message: validationResult, + }); + } + } else { errors.push({ - field: field.name, - message: validationResult, + field: `${path}${field.name}`, + message: `${path}${field.name} is required.`, }); } } if (field.fields) { - await iterateFields(field.fields, data[field.name], errors, `${path}${field.name}.`); + await iterateFields(field.fields, (data && data[field.name]), errors, `${path}${field.name}.`); } } } diff --git a/src/globals/graphql/register.js b/src/globals/graphql/register.js index ced8908032..f3ecfae011 100644 --- a/src/globals/graphql/register.js +++ b/src/globals/graphql/register.js @@ -1,3 +1,4 @@ +const { GraphQLNonNull } = require('graphql'); const formatName = require('../../graphql/utilities/formatName'); const { @@ -22,11 +23,11 @@ function registerGlobals() { formattedLabel, ); - global.graphQL.mutationInputType = this.buildMutationInputType( + global.graphQL.mutationInputType = new GraphQLNonNull(this.buildMutationInputType( formattedLabel, fields, formattedLabel, - ); + )); this.Query.fields[formattedLabel] = { type: global.graphQL.type, diff --git a/src/graphql/schema/buildMutationInputType.js b/src/graphql/schema/buildMutationInputType.js index 68fddf2c62..95fd4c3acc 100644 --- a/src/graphql/schema/buildMutationInputType.js +++ b/src/graphql/schema/buildMutationInputType.js @@ -116,12 +116,12 @@ function buildMutationInputType(name, fields, parentName) { const fieldName = formatName(name); - return new GraphQLNonNull(new GraphQLInputObjectType({ + return new GraphQLInputObjectType({ name: `mutation${fieldName}Input`, fields: { ...fieldTypes, }, - })); + }); } module.exports = buildMutationInputType; diff --git a/src/uploads/graphql/register.js b/src/uploads/graphql/register.js index 9b9f8a7db6..58db08dff4 100644 --- a/src/uploads/graphql/register.js +++ b/src/uploads/graphql/register.js @@ -42,11 +42,11 @@ function registerUpload() { singularLabel, ); - this.Upload.graphQL.mutationInputType = this.buildMutationInputType( + this.Upload.graphQL.mutationInputType = new GraphQLNonNull(this.buildMutationInputType( singularLabel, fields, singularLabel, - ); + )); this.Query.fields[singularLabel] = { type: this.Upload.graphQL.type, diff --git a/src/users/graphql/register.js b/src/users/graphql/register.js index e7730cdab0..29da8e76d0 100644 --- a/src/users/graphql/register.js +++ b/src/users/graphql/register.js @@ -59,11 +59,11 @@ function registerUser() { }, ]; - this.User.graphQL.mutationInputType = this.buildMutationInputType( + this.User.graphQL.mutationInputType = new GraphQLNonNull(this.buildMutationInputType( singularLabel, mutationFields, singularLabel, - ); + )); this.User.graphQL.updateMutationInputType = this.buildMutationInputType( `${singularLabel}Update`,