From 5f3a7b2cf9220d95b57218333fb8a2b194b84006 Mon Sep 17 00:00:00 2001 From: James Peacock Date: Fri, 9 Feb 2024 10:49:09 +0000 Subject: [PATCH] PP-12167 Update joi Context: Need to update joi version to one which does not use hoek versions before 8.5.1 because previous versions of hoek have a vulnerability as described here: https://github.com/alphagov/pay-selfservice/security/dependabot/71 - update to current joi version 17.12.1 - update uses of joi as Joi.validate() function is no longer supported --- .../clients/stripe/StripeAccount.class.js | 6 +- .../clients/stripe/StripeBankAccount.class.js | 6 +- .../clients/stripe/StripeCompany.class.js | 6 +- .../clients/stripe/StripeDirector.class.js | 6 +- .../stripe/StripeDirector.class.test.js | 6 +- .../stripe/StripeOrganisationDetails.class.js | 6 +- .../clients/stripe/StripePerson.class.js | 6 +- .../clients/stripe/StripePerson.class.test.js | 6 +- package-lock.json | 140 ++++++++++-------- package.json | 2 +- 10 files changed, 104 insertions(+), 86 deletions(-) diff --git a/app/services/clients/stripe/StripeAccount.class.js b/app/services/clients/stripe/StripeAccount.class.js index 44628fac0a..de7ab1c981 100644 --- a/app/services/clients/stripe/StripeAccount.class.js +++ b/app/services/clients/stripe/StripeAccount.class.js @@ -2,16 +2,16 @@ const Joi = require('joi') -const schema = { +const schema = Joi.object({ url: Joi.string().optional(), entity_verification_document_id: Joi.string().optional() -} +}) class StripeAccount { constructor (body) { const params = Object.assign({}, body) - const { error, value: model } = Joi.validate(params, schema, { allowUnknown: true, stripUnknown: true }) + const { error, value: model } = schema.validate(params, { allowUnknown: true, stripUnknown: true }) if (error) { throw new Error(`StripeAccount ${error.details[0].message}`) diff --git a/app/services/clients/stripe/StripeBankAccount.class.js b/app/services/clients/stripe/StripeBankAccount.class.js index de119a503f..f7063adb25 100644 --- a/app/services/clients/stripe/StripeBankAccount.class.js +++ b/app/services/clients/stripe/StripeBankAccount.class.js @@ -2,15 +2,15 @@ const Joi = require('joi') -const schema = { +const schema = Joi.object({ bank_account_sort_code: Joi.string().required(), bank_account_number: Joi.string().required() -} +}) class StripeBankAccount { constructor (body) { const params = Object.assign({}, body) - const { error, value: model } = Joi.validate(params, schema, { allowUnknown: true, stripUnknown: true }) + const { error, value: model } = schema.validate(params, { allowUnknown: true, stripUnknown: true }) if (error) { throw new Error(`StripeBankAccount ${error.details[0].message}`) diff --git a/app/services/clients/stripe/StripeCompany.class.js b/app/services/clients/stripe/StripeCompany.class.js index 3922cbb3d4..bc485e2d84 100644 --- a/app/services/clients/stripe/StripeCompany.class.js +++ b/app/services/clients/stripe/StripeCompany.class.js @@ -2,17 +2,17 @@ const Joi = require('joi') -const schema = { +const schema = Joi.object({ vat_id: Joi.string().optional(), tax_id: Joi.string().optional(), directors_provided: Joi.boolean().optional(), executives_provided: Joi.boolean().optional() -} +}) class StripeCompany { constructor (body) { const params = Object.assign({}, body) - const { error, value: model } = Joi.validate(params, schema) + const { error, value: model } = schema.validate(params) if (error) { throw new Error(`StripeCompany ${error.details[0].message}`) diff --git a/app/services/clients/stripe/StripeDirector.class.js b/app/services/clients/stripe/StripeDirector.class.js index 99ae46acd9..865ea8b018 100644 --- a/app/services/clients/stripe/StripeDirector.class.js +++ b/app/services/clients/stripe/StripeDirector.class.js @@ -2,7 +2,7 @@ const Joi = require('joi') -const schema = { +const schema = Joi.object({ first_name: Joi.string().required(), last_name: Joi.string().required(), email: Joi.string().required(), @@ -10,13 +10,13 @@ const schema = { dob_month: Joi.number().integer().strict().min(1).max(12), dob_year: Joi.number().integer().strict().min(1900).max(2100), relationship: Joi.string().optional() -} +}) class StripeDirector { constructor (body) { const params = Object.assign({}, body) - const { error, value: model } = Joi.validate(params, schema, { allowUnknown: true, stripUnknown: true }) + const { error, value: model } = schema.validate(params, { allowUnknown: true, stripUnknown: true }) if (error) { throw new Error(`StripeDirector ${error.details[0].message}`) diff --git a/app/services/clients/stripe/StripeDirector.class.test.js b/app/services/clients/stripe/StripeDirector.class.test.js index 799e1ccb62..c6a16dc9fd 100644 --- a/app/services/clients/stripe/StripeDirector.class.test.js +++ b/app/services/clients/stripe/StripeDirector.class.test.js @@ -104,7 +104,7 @@ describe('StripeDirector', () => { dob_day: 0, dob_month: dobMonth, dob_year: dobYear - })).to.throw('StripeDirector "dob_day" must be larger than or equal to 1') + })).to.throw('StripeDirector "dob_day" must be greater than or equal to 1') }) it('Should throw error when day is more than 31', () => { @@ -128,7 +128,7 @@ describe('StripeDirector', () => { dob_day: dobDay, dob_month: 0, dob_year: dobYear - })).to.throw('StripeDirector "dob_month" must be larger than or equal to 1') + })).to.throw('StripeDirector "dob_month" must be greater than or equal to 1') }) it('Should throw error when month is larger than 12', () => { @@ -151,7 +151,7 @@ describe('StripeDirector', () => { dob_day: dobDay, dob_month: dobMonth, dob_year: 999 - })).to.throw('StripeDirector "dob_year" must be larger than or equal to 1900') + })).to.throw('StripeDirector "dob_year" must be greater than or equal to 1900') }) it('Should throw error when year is more than 9999', () => { diff --git a/app/services/clients/stripe/StripeOrganisationDetails.class.js b/app/services/clients/stripe/StripeOrganisationDetails.class.js index 482c1363ec..ebf1d89bb5 100644 --- a/app/services/clients/stripe/StripeOrganisationDetails.class.js +++ b/app/services/clients/stripe/StripeOrganisationDetails.class.js @@ -2,7 +2,7 @@ const Joi = require('joi') -const schema = { +const schema = Joi.object({ name: Joi.string().required(), address_line1: Joi.string().required(), address_line2: Joi.string().optional(), @@ -11,13 +11,13 @@ const schema = { address_country: Joi.string().required(), telephone_number: Joi.string().optional(), url: Joi.string().optional() -} +}) class StripeOrganisationDetails { constructor (body) { const params = Object.assign({}, body) - const { error, value: model } = Joi.validate(params, schema, { allowUnknown: true, stripUnknown: true }) + const { error, value: model } = schema.validate(params, { allowUnknown: true, stripUnknown: true }) if (error) { throw new Error(`StripeOrganisationDetails ${error.details[0].message}`) diff --git a/app/services/clients/stripe/StripePerson.class.js b/app/services/clients/stripe/StripePerson.class.js index c5a944e5a1..1e19ecc901 100644 --- a/app/services/clients/stripe/StripePerson.class.js +++ b/app/services/clients/stripe/StripePerson.class.js @@ -2,7 +2,7 @@ const Joi = require('joi') -const schema = { +const schema = Joi.object({ first_name: Joi.string().required(), last_name: Joi.string().required(), address_line1: Joi.string().required(), @@ -14,12 +14,12 @@ const schema = { dob_year: Joi.number().integer().strict().min(1000).max(9999), phone: Joi.string().optional(), email: Joi.string().optional() -} +}) class StripePerson { constructor (body) { const params = Object.assign({}, body) - const { error, value: model } = Joi.validate(params, schema, { allowUnknown: true, stripUnknown: true }) + const { error, value: model } = schema.validate(params, { allowUnknown: true, stripUnknown: true }) if (error) { throw new Error(`StripePerson ${error.details[0].message}`) diff --git a/app/services/clients/stripe/StripePerson.class.test.js b/app/services/clients/stripe/StripePerson.class.test.js index 18d82d299f..ffbc10db68 100644 --- a/app/services/clients/stripe/StripePerson.class.test.js +++ b/app/services/clients/stripe/StripePerson.class.test.js @@ -212,7 +212,7 @@ describe('StripePerson', () => { dob_day: 0, dob_month: dobMonth, dob_year: dobYear - })).to.throw('StripePerson "dob_day" must be larger than or equal to 1') + })).to.throw('StripePerson "dob_day" must be greater than or equal to 1') }) it('should fail when day is more than 31', () => { @@ -238,7 +238,7 @@ describe('StripePerson', () => { dob_day: dobDay, dob_month: 0, dob_year: dobYear - })).to.throw('StripePerson "dob_month" must be larger than or equal to 1') + })).to.throw('StripePerson "dob_month" must be greater than or equal to 1') }) it('should fail when month is larger than 12', () => { @@ -264,7 +264,7 @@ describe('StripePerson', () => { dob_day: dobDay, dob_month: dobMonth, dob_year: 999 - })).to.throw('StripePerson "dob_year" must be larger than or equal to 1000') + })).to.throw('StripePerson "dob_year" must be greater than or equal to 1000') }) it('should fail when year is more than 9999', () => { diff --git a/package-lock.json b/package-lock.json index 5c03b6b51a..f2035f840b 100644 --- a/package-lock.json +++ b/package-lock.json @@ -29,7 +29,7 @@ "govuk-frontend": "^4.7.0", "http-proxy": "1.18.x", "https-proxy-agent": "5.0.1", - "joi": "14.3.1", + "joi": "17.12.1", "lodash": "4.17.21", "luhn-js": "^1.1.2", "minimist": "1.2.6", @@ -2056,6 +2056,19 @@ "node": ">=10" } }, + "node_modules/@hapi/hoek": { + "version": "9.3.0", + "resolved": "https://registry.npmjs.org/@hapi/hoek/-/hoek-9.3.0.tgz", + "integrity": "sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==" + }, + "node_modules/@hapi/topo": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/@hapi/topo/-/topo-5.1.0.tgz", + "integrity": "sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==", + "dependencies": { + "@hapi/hoek": "^9.0.0" + } + }, "node_modules/@jridgewell/gen-mapping": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.1.1.tgz", @@ -2602,6 +2615,24 @@ "node": ">=6" } }, + "node_modules/@sideway/address": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/@sideway/address/-/address-4.1.5.tgz", + "integrity": "sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==", + "dependencies": { + "@hapi/hoek": "^9.0.0" + } + }, + "node_modules/@sideway/formula": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@sideway/formula/-/formula-3.0.1.tgz", + "integrity": "sha512-/poHZJJVjx3L+zVD6g9KgHfYnb443oi7wLu/XKojDviHy6HOEOA6z1Trk5aR1dGcmPenJEgb2sK2I80LeS3MIg==" + }, + "node_modules/@sideway/pinpoint": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@sideway/pinpoint/-/pinpoint-2.0.0.tgz", + "integrity": "sha512-RNiOoTPkptFtSVzQevY/yWtZwf/RxyVnPy/OcA9HBM3MlGDnBEYL5B41H0MTn0Uec8Hi+2qUtTfG2WWZBmMejQ==" + }, "node_modules/@sinonjs/commons": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/@sinonjs/commons/-/commons-2.0.0.tgz", @@ -8578,12 +8609,6 @@ "minimalistic-crypto-utils": "^1.0.1" } }, - "node_modules/hoek": { - "version": "6.1.3", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-6.1.3.tgz", - "integrity": "sha512-YXXAAhmF9zpQbC7LEcREFtXfGq5K1fmd+4PHkBq8NUqmzW3G+Dq10bI/i0KucLRwss3YYFQ0fSfoxBZYiGUqtQ==", - "deprecated": "This module has moved and is now available at @hapi/hoek. Please update your dependencies as this version is no longer maintained an may contain bugs and security issues." - }, "node_modules/homedir-polyfill": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.3.tgz", @@ -9612,17 +9637,6 @@ "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==" }, - "node_modules/isemail": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/isemail/-/isemail-3.2.0.tgz", - "integrity": "sha512-zKqkK+O+dGqevc93KNsbZ/TqTUFd46MwWjYOoMrjIMZ51eU7DtQG3Wmd9SQQT7i7RVnuTPEiYEWHU3MSbxC1Tg==", - "dependencies": { - "punycode": "2.x.x" - }, - "engines": { - "node": ">=4.0.0" - } - }, "node_modules/isexe": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", @@ -9746,14 +9760,15 @@ } }, "node_modules/joi": { - "version": "14.3.1", - "resolved": "https://registry.npmjs.org/joi/-/joi-14.3.1.tgz", - "integrity": "sha512-LQDdM+pkOrpAn4Lp+neNIFV3axv1Vna3j38bisbQhETPMANYRbFJFUyOZcOClYvM/hppMhGWuKSFEK9vjrB+bQ==", - "deprecated": "This module has moved and is now available at @hapi/joi. Please update your dependencies as this version is no longer maintained an may contain bugs and security issues.", + "version": "17.12.1", + "resolved": "https://registry.npmjs.org/joi/-/joi-17.12.1.tgz", + "integrity": "sha512-vtxmq+Lsc5SlfqotnfVjlViWfOL9nt/avKNbKYizwf6gsCfq9NYY/ceYRMFD8XDdrjJ9abJyScWmhmIiy+XRtQ==", "dependencies": { - "hoek": "6.x.x", - "isemail": "3.x.x", - "topo": "3.x.x" + "@hapi/hoek": "^9.3.0", + "@hapi/topo": "^5.1.0", + "@sideway/address": "^4.1.5", + "@sideway/formula": "^3.0.1", + "@sideway/pinpoint": "^2.0.0" } }, "node_modules/js-base64": { @@ -16494,15 +16509,6 @@ "node": ">=0.6" } }, - "node_modules/topo": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/topo/-/topo-3.0.3.tgz", - "integrity": "sha512-IgpPtvD4kjrJ7CRA3ov2FhWQADwv+Tdqbsf1ZnPUSAtCJ9e1Z44MmoSGDXGk4IppoZA7jd/QRkNddlLJWlUZsQ==", - "deprecated": "This module has moved and is now available at @hapi/topo. Please update your dependencies as this version is no longer maintained an may contain bugs and security issues.", - "dependencies": { - "hoek": "6.x.x" - } - }, "node_modules/touch": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", @@ -19057,6 +19063,19 @@ } } }, + "@hapi/hoek": { + "version": "9.3.0", + "resolved": "https://registry.npmjs.org/@hapi/hoek/-/hoek-9.3.0.tgz", + "integrity": "sha512-/c6rf4UJlmHlC9b5BaNvzAcFv7HZ2QHaV0D4/HNlBdvFnvQq8RI4kYdhyPCl7Xj+oWvTWQ8ujhqS53LIgAe6KQ==" + }, + "@hapi/topo": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/@hapi/topo/-/topo-5.1.0.tgz", + "integrity": "sha512-foQZKJig7Ob0BMAYBfcJk8d77QtOe7Wo4ox7ff1lQYoNNAb6jwcY1ncdoy2e9wQZzvNy7ODZCYJkK8kzmcAnAg==", + "requires": { + "@hapi/hoek": "^9.0.0" + } + }, "@jridgewell/gen-mapping": { "version": "0.1.1", "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.1.1.tgz", @@ -19454,6 +19473,24 @@ "tslib": "^1.9.3" } }, + "@sideway/address": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/@sideway/address/-/address-4.1.5.tgz", + "integrity": "sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==", + "requires": { + "@hapi/hoek": "^9.0.0" + } + }, + "@sideway/formula": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@sideway/formula/-/formula-3.0.1.tgz", + "integrity": "sha512-/poHZJJVjx3L+zVD6g9KgHfYnb443oi7wLu/XKojDviHy6HOEOA6z1Trk5aR1dGcmPenJEgb2sK2I80LeS3MIg==" + }, + "@sideway/pinpoint": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/@sideway/pinpoint/-/pinpoint-2.0.0.tgz", + "integrity": "sha512-RNiOoTPkptFtSVzQevY/yWtZwf/RxyVnPy/OcA9HBM3MlGDnBEYL5B41H0MTn0Uec8Hi+2qUtTfG2WWZBmMejQ==" + }, "@sinonjs/commons": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/@sinonjs/commons/-/commons-2.0.0.tgz", @@ -24143,11 +24180,6 @@ "minimalistic-crypto-utils": "^1.0.1" } }, - "hoek": { - "version": "6.1.3", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-6.1.3.tgz", - "integrity": "sha512-YXXAAhmF9zpQbC7LEcREFtXfGq5K1fmd+4PHkBq8NUqmzW3G+Dq10bI/i0KucLRwss3YYFQ0fSfoxBZYiGUqtQ==" - }, "homedir-polyfill": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/homedir-polyfill/-/homedir-polyfill-1.0.3.tgz", @@ -24898,14 +24930,6 @@ "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", "integrity": "sha512-VLghIWNM6ELQzo7zwmcg0NmTVyWKYjvIeM83yjp0wRDTmUnrM678fQbcKBo6n2CJEF0szoG//ytg+TKla89ALQ==" }, - "isemail": { - "version": "3.2.0", - "resolved": "https://registry.npmjs.org/isemail/-/isemail-3.2.0.tgz", - "integrity": "sha512-zKqkK+O+dGqevc93KNsbZ/TqTUFd46MwWjYOoMrjIMZ51eU7DtQG3Wmd9SQQT7i7RVnuTPEiYEWHU3MSbxC1Tg==", - "requires": { - "punycode": "2.x.x" - } - }, "isexe": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", @@ -24998,13 +25022,15 @@ "integrity": "sha512-9FzQjJ7MATs1tSpnco1K6ayiYE3figslrXA72G2HQ/n76RzvYlofyi5QM+iX4YRs/pu3yzxlVQSST23+dMDknw==" }, "joi": { - "version": "14.3.1", - "resolved": "https://registry.npmjs.org/joi/-/joi-14.3.1.tgz", - "integrity": "sha512-LQDdM+pkOrpAn4Lp+neNIFV3axv1Vna3j38bisbQhETPMANYRbFJFUyOZcOClYvM/hppMhGWuKSFEK9vjrB+bQ==", + "version": "17.12.1", + "resolved": "https://registry.npmjs.org/joi/-/joi-17.12.1.tgz", + "integrity": "sha512-vtxmq+Lsc5SlfqotnfVjlViWfOL9nt/avKNbKYizwf6gsCfq9NYY/ceYRMFD8XDdrjJ9abJyScWmhmIiy+XRtQ==", "requires": { - "hoek": "6.x.x", - "isemail": "3.x.x", - "topo": "3.x.x" + "@hapi/hoek": "^9.3.0", + "@hapi/topo": "^5.1.0", + "@sideway/address": "^4.1.5", + "@sideway/formula": "^3.0.1", + "@sideway/pinpoint": "^2.0.0" } }, "js-base64": { @@ -30171,14 +30197,6 @@ "resolved": "https://registry.npmjs.org/toidentifier/-/toidentifier-1.0.1.tgz", "integrity": "sha512-o5sSPKEkg/DIQNmH43V0/uerLrpzVedkUh8tGNvaeXpfpuwjKenlSox/2O/BTlZUtEe+JG7s5YhEz608PlAHRA==" }, - "topo": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/topo/-/topo-3.0.3.tgz", - "integrity": "sha512-IgpPtvD4kjrJ7CRA3ov2FhWQADwv+Tdqbsf1ZnPUSAtCJ9e1Z44MmoSGDXGk4IppoZA7jd/QRkNddlLJWlUZsQ==", - "requires": { - "hoek": "6.x.x" - } - }, "touch": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/touch/-/touch-3.1.0.tgz", diff --git a/package.json b/package.json index f3d2307810..b42bd16147 100644 --- a/package.json +++ b/package.json @@ -102,7 +102,7 @@ "govuk-frontend": "^4.7.0", "http-proxy": "1.18.x", "https-proxy-agent": "5.0.1", - "joi": "14.3.1", + "joi": "17.12.1", "lodash": "4.17.21", "luhn-js": "^1.1.2", "minimist": "1.2.6",