From 190c7dfe33325cee82e0b6bb747766ac06ff57b1 Mon Sep 17 00:00:00 2001 From: Guillaume Date: Thu, 4 Apr 2024 11:49:28 +0200 Subject: [PATCH] Add JSONPath tool --- .../docs/latest/templating/mockoon-helpers.md | 2 +- package-lock.json | 361 ++++++++------ package.json | 2 + pages/_document.tsx | 2 +- pages/tools/index.tsx | 7 + pages/tools/json-object-path-evaluator.tsx | 452 ++++++++++++++++++ public/fonts/mockoon.woff | Bin 5712 -> 5764 bytes .../illustrations/json-path-evaluator.svg | 20 + styles/font.scss | 5 +- styles/mockoon.woff | Bin 0 -> 5764 bytes utils/tools.ts | 70 +++ 11 files changed, 775 insertions(+), 146 deletions(-) create mode 100644 pages/tools/json-object-path-evaluator.tsx create mode 100644 public/images/illustrations/json-path-evaluator.svg create mode 100644 styles/mockoon.woff create mode 100644 utils/tools.ts diff --git a/content/docs/latest/templating/mockoon-helpers.md b/content/docs/latest/templating/mockoon-helpers.md index a82cc6fc..d3c41a6b 100644 --- a/content/docs/latest/templating/mockoon-helpers.md +++ b/content/docs/latest/templating/mockoon-helpers.md @@ -1,5 +1,5 @@ --- -title: Custom helpers +title: Helpers meta: title: Create dynamic responses with templating helpers description: "Create dynamic fake data for your mock server with Mockoon's templating helpers. All formats are supported: JSON, CSV, HTML, etc." diff --git a/package-lock.json b/package-lock.json index a01b12ef..2e814704 100644 --- a/package-lock.json +++ b/package-lock.json @@ -24,7 +24,9 @@ "glob": "^10.3.10", "gray-matter": "^4.0.3", "js-yaml": "^4.1.0", + "jsonpath-plus": "^8.1.0", "next": "^14.0.2", + "object-path": "^0.11.8", "raw-loader": "^4.0.2", "react": "^18.2.0", "react-bootstrap": "^2.9.1", @@ -611,22 +613,6 @@ "node": "^12.22.0 || ^14.17.0 || >=16.0.0" } }, - "node_modules/@faker-js/faker": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/@faker-js/faker/-/faker-8.1.0.tgz", - "integrity": "sha512-38DT60rumHfBYynif3lmtxMqMqmsOQIxQgEuPZxCk2yUYN0eqWpTACgxi0VpidvsJB8CRxCpvP7B3anK85FjtQ==", - "dev": true, - "funding": [ - { - "type": "opencollective", - "url": "https://opencollective.com/fakerjs" - } - ], - "engines": { - "node": "^14.17.0 || ^16.13.0 || >=18.0.0", - "npm": ">=6.14.13" - } - }, "node_modules/@firebase/analytics": { "version": "0.10.0", "resolved": "https://registry.npmjs.org/@firebase/analytics/-/analytics-0.10.0.tgz", @@ -1599,19 +1585,23 @@ "url": "https://mockoon.com/sponsor-us/" } }, - "node_modules/@mockoon/commons": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/@mockoon/commons/-/commons-5.1.0.tgz", - "integrity": "sha512-g7g6OHy6VGS5bSRw5CQiU3E7fpCmFdnE2BiseSZaYs3OzORRLCBi0tPfUY3Fh2ZyFB/+UHABl35DchdCO3fqFA==", + "node_modules/@mockoon/cli/node_modules/@faker-js/faker": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/@faker-js/faker/-/faker-8.1.0.tgz", + "integrity": "sha512-38DT60rumHfBYynif3lmtxMqMqmsOQIxQgEuPZxCk2yUYN0eqWpTACgxi0VpidvsJB8CRxCpvP7B3anK85FjtQ==", "dev": true, - "dependencies": { - "joi": "17.10.2" - }, - "funding": { - "url": "https://mockoon.com/sponsor-us/" + "funding": [ + { + "type": "opencollective", + "url": "https://opencollective.com/fakerjs" + } + ], + "engines": { + "node": "^14.17.0 || ^16.13.0 || >=18.0.0", + "npm": ">=6.14.13" } }, - "node_modules/@mockoon/commons-server": { + "node_modules/@mockoon/cli/node_modules/@mockoon/commons-server": { "version": "5.1.0", "resolved": "https://registry.npmjs.org/@mockoon/commons-server/-/commons-server-5.1.0.tgz", "integrity": "sha512-muI8w8al3cpKYDtECe/ZV0/O0l3n+GYLYyGWE/ZubUK5K67t26VcTKCfX4GkLJrW89hLeF3QfFJcIDn8+3UwLA==", @@ -1644,6 +1634,27 @@ "url": "https://mockoon.com/sponsor-us/" } }, + "node_modules/@mockoon/cli/node_modules/jsonpath-plus": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/jsonpath-plus/-/jsonpath-plus-7.2.0.tgz", + "integrity": "sha512-zBfiUPM5nD0YZSBT/o/fbCUlCcepMIdP0CJZxM1+KgA4f2T206f6VAg9e7mX35+KlMaIc5qXW34f3BnwJ3w+RA==", + "dev": true, + "engines": { + "node": ">=12.0.0" + } + }, + "node_modules/@mockoon/commons": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/@mockoon/commons/-/commons-5.1.0.tgz", + "integrity": "sha512-g7g6OHy6VGS5bSRw5CQiU3E7fpCmFdnE2BiseSZaYs3OzORRLCBi0tPfUY3Fh2ZyFB/+UHABl35DchdCO3fqFA==", + "dev": true, + "dependencies": { + "joi": "17.10.2" + }, + "funding": { + "url": "https://mockoon.com/sponsor-us/" + } + }, "node_modules/@next/env": { "version": "14.0.2", "resolved": "https://registry.npmjs.org/@next/env/-/env-14.0.2.tgz", @@ -2148,9 +2159,9 @@ "integrity": "sha512-6i/8UoL0P5y4leBIGzvkZdS85RDMG9y1ihZzmTZQ5LdHUYmZ7pKFoj8X0236s3lusPs1Fa5HTQUpwI+UfTcmeA==" }, "node_modules/@sideway/address": { - "version": "4.1.4", - "resolved": "https://registry.npmjs.org/@sideway/address/-/address-4.1.4.tgz", - "integrity": "sha512-7vwq+rOHVWjyXxVlR76Agnvhy8I9rpzjosTESvmhNeXOXdZZB15Fl+TI9x1SiHZH5Jv2wTGduSxFDIaq0m3DUw==", + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/@sideway/address/-/address-4.1.5.tgz", + "integrity": "sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==", "dev": true, "dependencies": { "@hapi/hoek": "^9.0.0" @@ -4791,13 +4802,18 @@ } }, "node_modules/call-bind": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.5.tgz", - "integrity": "sha512-C3nQxfFZxFRVoJoGKKI8y3MOEo129NQ+FgQ08iye+Mk4zNZZGdjfs06bVTr+DBSlA66Q2VEcMki/cUCP4SercQ==", + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz", + "integrity": "sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==", "dependencies": { + "es-define-property": "^1.0.0", + "es-errors": "^1.3.0", "function-bind": "^1.1.2", - "get-intrinsic": "^1.2.1", - "set-function-length": "^1.1.1" + "get-intrinsic": "^1.2.4", + "set-function-length": "^1.2.1" + }, + "engines": { + "node": ">= 0.4" }, "funding": { "url": "https://github.com/sponsors/ljharb" @@ -5836,16 +5852,19 @@ } }, "node_modules/define-data-property": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.1.tgz", - "integrity": "sha512-E7uGkTzkk1d0ByLeSc6ZsFS79Axg+m1P/VsgYsxHgiuc3tFSj+MjMIwe90FC4lOAZzNBdY7kkO2P2wKdsQ1vgQ==", + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", + "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", "dependencies": { - "get-intrinsic": "^1.2.1", - "gopd": "^1.0.1", - "has-property-descriptors": "^1.0.0" + "es-define-property": "^1.0.0", + "es-errors": "^1.3.0", + "gopd": "^1.0.1" }, "engines": { "node": ">= 0.4" + }, + "funding": { + "url": "https://github.com/sponsors/ljharb" } }, "node_modules/define-properties": { @@ -6229,6 +6248,25 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/es-define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.0.tgz", + "integrity": "sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==", + "dependencies": { + "get-intrinsic": "^1.2.4" + }, + "engines": { + "node": ">= 0.4" + } + }, + "node_modules/es-errors": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", + "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==", + "engines": { + "node": ">= 0.4" + } + }, "node_modules/es-iterator-helpers": { "version": "1.0.15", "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.0.15.tgz", @@ -7878,15 +7916,19 @@ } }, "node_modules/get-intrinsic": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.2.tgz", - "integrity": "sha512-0gSo4ml/0j98Y3lngkFEot/zhiCeWsbYIlZ+uZOVgzLyLaUw7wxUL+nCTP0XJvJg1AXulJRI3UJi8GsbDuxdGA==", + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.4.tgz", + "integrity": "sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==", "dependencies": { + "es-errors": "^1.3.0", "function-bind": "^1.1.2", "has-proto": "^1.0.1", "has-symbols": "^1.0.3", "hasown": "^2.0.0" }, + "engines": { + "node": ">= 0.4" + }, "funding": { "url": "https://github.com/sponsors/ljharb" } @@ -8462,11 +8504,11 @@ } }, "node_modules/has-property-descriptors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.1.tgz", - "integrity": "sha512-VsX8eaIewvas0xnvinAe9bw4WfIeODpGYikiWYLH+dma0Jw6KHYqWiWfhQlgOVK8D6PvjubK5Uc4P0iIhIcNVg==", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", + "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", "dependencies": { - "get-intrinsic": "^1.2.2" + "es-define-property": "^1.0.0" }, "funding": { "url": "https://github.com/sponsors/ljharb" @@ -9936,12 +9978,15 @@ } }, "node_modules/jsonpath-plus": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/jsonpath-plus/-/jsonpath-plus-7.2.0.tgz", - "integrity": "sha512-zBfiUPM5nD0YZSBT/o/fbCUlCcepMIdP0CJZxM1+KgA4f2T206f6VAg9e7mX35+KlMaIc5qXW34f3BnwJ3w+RA==", - "dev": true, + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/jsonpath-plus/-/jsonpath-plus-8.1.0.tgz", + "integrity": "sha512-qVTiuKztFGw0dGhYi3WNqvddx3/SHtyDT0xJaeyz4uP0d1tkpG+0y5uYQ4OcIo1TLAz3PE/qDOW9F0uDt3+CTw==", + "bin": { + "jsonpath": "bin/jsonpath-cli.js", + "jsonpath-plus": "bin/jsonpath-cli.js" + }, "engines": { - "node": ">=12.0.0" + "node": ">=14.0.0" } }, "node_modules/jsonwebtoken": { @@ -12010,7 +12055,6 @@ "version": "0.11.8", "resolved": "https://registry.npmjs.org/object-path/-/object-path-0.11.8.tgz", "integrity": "sha512-YJjNZrlXJFM42wTBn6zgOJVar9KFJvzx6sTWDte8sWZF//cnjl0BxHNpfZx+ZffXX63A9q0b1zsFiBX4g4X5KA==", - "dev": true, "engines": { "node": ">= 10.12.0" } @@ -14015,14 +14059,16 @@ "optional": true }, "node_modules/set-function-length": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.1.1.tgz", - "integrity": "sha512-VoaqjbBJKiWtg4yRcKBQ7g7wnGnLV3M8oLvVWwOk2PdYY6PEFegR1vezXR0tw6fZGF9csVakIRjrJiy2veSBFQ==", + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", + "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", "dependencies": { - "define-data-property": "^1.1.1", - "get-intrinsic": "^1.2.1", + "define-data-property": "^1.1.4", + "es-errors": "^1.3.0", + "function-bind": "^1.1.2", + "get-intrinsic": "^1.2.4", "gopd": "^1.0.1", - "has-property-descriptors": "^1.0.0" + "has-property-descriptors": "^1.0.2" }, "engines": { "node": ">= 0.4" @@ -14076,13 +14122,17 @@ } }, "node_modules/side-channel": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", - "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.6.tgz", + "integrity": "sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==", "dependencies": { - "call-bind": "^1.0.0", - "get-intrinsic": "^1.0.2", - "object-inspect": "^1.9.0" + "call-bind": "^1.0.7", + "es-errors": "^1.3.0", + "get-intrinsic": "^1.2.4", + "object-inspect": "^1.13.1" + }, + "engines": { + "node": ">= 0.4" }, "funding": { "url": "https://github.com/sponsors/ljharb" @@ -15811,9 +15861,9 @@ } }, "node_modules/winston-transport": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/winston-transport/-/winston-transport-4.6.0.tgz", - "integrity": "sha512-wbBA9PbPAHxKiygo7ub7BYRiKxms0tpfU2ljtWzb3SjRjv5yl6Ozuy/TkXf00HTAt+Uylo3gSkNwzc4ME0wiIg==", + "version": "4.7.0", + "resolved": "https://registry.npmjs.org/winston-transport/-/winston-transport-4.7.0.tgz", + "integrity": "sha512-ajBj65K5I7denzer2IYW6+2bNIVqLGDHqDw3Ow8Ohh+vdW+rv4MZ6eiDvHoKhfJFZ2auyN8byXieDDJ96ViONg==", "dev": true, "dependencies": { "logform": "^2.3.2", @@ -16544,12 +16594,6 @@ "integrity": "sha512-Kn7K8dx/5U6+cT1yEhpX1w4PCSg0M+XyRILPgvwcEBjerFWCwQj5sbr3/VmxqV0JGHCBCzyd6LxypEuehypY1w==", "peer": true }, - "@faker-js/faker": { - "version": "8.1.0", - "resolved": "https://registry.npmjs.org/@faker-js/faker/-/faker-8.1.0.tgz", - "integrity": "sha512-38DT60rumHfBYynif3lmtxMqMqmsOQIxQgEuPZxCk2yUYN0eqWpTACgxi0VpidvsJB8CRxCpvP7B3anK85FjtQ==", - "dev": true - }, "@firebase/analytics": { "version": "0.10.0", "resolved": "https://registry.npmjs.org/@firebase/analytics/-/analytics-0.10.0.tgz", @@ -17331,6 +17375,47 @@ "mkdirp": "3.0.1", "mustache": "4.2.0", "tslib": "2.6.2" + }, + "dependencies": { + "@faker-js/faker": { + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/@faker-js/faker/-/faker-8.1.0.tgz", + "integrity": "sha512-38DT60rumHfBYynif3lmtxMqMqmsOQIxQgEuPZxCk2yUYN0eqWpTACgxi0VpidvsJB8CRxCpvP7B3anK85FjtQ==", + "dev": true + }, + "@mockoon/commons-server": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/@mockoon/commons-server/-/commons-server-5.1.0.tgz", + "integrity": "sha512-muI8w8al3cpKYDtECe/ZV0/O0l3n+GYLYyGWE/ZubUK5K67t26VcTKCfX4GkLJrW89hLeF3QfFJcIDn8+3UwLA==", + "dev": true, + "requires": { + "@apidevtools/swagger-parser": "10.1.0", + "@faker-js/faker": "8.1.0", + "@mockoon/commons": "5.1.0", + "append-field": "1.0.0", + "busboy": "1.6.0", + "cookie-parser": "1.4.6", + "date-fns": "2.30.0", + "express": "4.18.2", + "handlebars": "4.7.8", + "http-proxy-middleware": "2.0.6", + "jsonpath-plus": "7.2.0", + "killable": "1.0.1", + "mime-types": "2.1.35", + "object-path": "0.11.8", + "qs": "6.11.2", + "range-parser": "1.2.1", + "typed-emitter": "2.1.0", + "winston": "3.10.0", + "xml-js": "1.6.11" + } + }, + "jsonpath-plus": { + "version": "7.2.0", + "resolved": "https://registry.npmjs.org/jsonpath-plus/-/jsonpath-plus-7.2.0.tgz", + "integrity": "sha512-zBfiUPM5nD0YZSBT/o/fbCUlCcepMIdP0CJZxM1+KgA4f2T206f6VAg9e7mX35+KlMaIc5qXW34f3BnwJ3w+RA==", + "dev": true + } } }, "@mockoon/commons": { @@ -17342,33 +17427,6 @@ "joi": "17.10.2" } }, - "@mockoon/commons-server": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/@mockoon/commons-server/-/commons-server-5.1.0.tgz", - "integrity": "sha512-muI8w8al3cpKYDtECe/ZV0/O0l3n+GYLYyGWE/ZubUK5K67t26VcTKCfX4GkLJrW89hLeF3QfFJcIDn8+3UwLA==", - "dev": true, - "requires": { - "@apidevtools/swagger-parser": "10.1.0", - "@faker-js/faker": "8.1.0", - "@mockoon/commons": "5.1.0", - "append-field": "1.0.0", - "busboy": "1.6.0", - "cookie-parser": "1.4.6", - "date-fns": "2.30.0", - "express": "4.18.2", - "handlebars": "4.7.8", - "http-proxy-middleware": "2.0.6", - "jsonpath-plus": "7.2.0", - "killable": "1.0.1", - "mime-types": "2.1.35", - "object-path": "0.11.8", - "qs": "6.11.2", - "range-parser": "1.2.1", - "typed-emitter": "2.1.0", - "winston": "3.10.0", - "xml-js": "1.6.11" - } - }, "@next/env": { "version": "14.0.2", "resolved": "https://registry.npmjs.org/@next/env/-/env-14.0.2.tgz", @@ -17728,9 +17786,9 @@ "integrity": "sha512-6i/8UoL0P5y4leBIGzvkZdS85RDMG9y1ihZzmTZQ5LdHUYmZ7pKFoj8X0236s3lusPs1Fa5HTQUpwI+UfTcmeA==" }, "@sideway/address": { - "version": "4.1.4", - "resolved": "https://registry.npmjs.org/@sideway/address/-/address-4.1.4.tgz", - "integrity": "sha512-7vwq+rOHVWjyXxVlR76Agnvhy8I9rpzjosTESvmhNeXOXdZZB15Fl+TI9x1SiHZH5Jv2wTGduSxFDIaq0m3DUw==", + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/@sideway/address/-/address-4.1.5.tgz", + "integrity": "sha512-IqO/DUQHUkPeixNQ8n0JA6102hT9CmaljNTPmQ1u8MEhBo/R4Q8eKLN/vGZxuebwOroDB4cbpjheD4+/sKFK4Q==", "dev": true, "requires": { "@hapi/hoek": "^9.0.0" @@ -19985,13 +20043,15 @@ } }, "call-bind": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.5.tgz", - "integrity": "sha512-C3nQxfFZxFRVoJoGKKI8y3MOEo129NQ+FgQ08iye+Mk4zNZZGdjfs06bVTr+DBSlA66Q2VEcMki/cUCP4SercQ==", + "version": "1.0.7", + "resolved": "https://registry.npmjs.org/call-bind/-/call-bind-1.0.7.tgz", + "integrity": "sha512-GHTSNSYICQ7scH7sZ+M2rFopRoLh8t2bLSW6BbgrtLsahOIB5iyAVJf9GjWK3cYTDaMj4XdBpM1cA6pIS0Kv2w==", "requires": { + "es-define-property": "^1.0.0", + "es-errors": "^1.3.0", "function-bind": "^1.1.2", - "get-intrinsic": "^1.2.1", - "set-function-length": "^1.1.1" + "get-intrinsic": "^1.2.4", + "set-function-length": "^1.2.1" } }, "call-me-maybe": { @@ -20784,13 +20844,13 @@ } }, "define-data-property": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.1.tgz", - "integrity": "sha512-E7uGkTzkk1d0ByLeSc6ZsFS79Axg+m1P/VsgYsxHgiuc3tFSj+MjMIwe90FC4lOAZzNBdY7kkO2P2wKdsQ1vgQ==", + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/define-data-property/-/define-data-property-1.1.4.tgz", + "integrity": "sha512-rBMvIzlpA8v6E+SJZoo++HAYqsLrkg7MSfIinMPFhmkorw7X+dOXVJQs+QT69zGkzMyfDnIMN2Wid1+NbL3T+A==", "requires": { - "get-intrinsic": "^1.2.1", - "gopd": "^1.0.1", - "has-property-descriptors": "^1.0.0" + "es-define-property": "^1.0.0", + "es-errors": "^1.3.0", + "gopd": "^1.0.1" } }, "define-properties": { @@ -21095,6 +21155,19 @@ "which-typed-array": "^1.1.13" } }, + "es-define-property": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/es-define-property/-/es-define-property-1.0.0.tgz", + "integrity": "sha512-jxayLKShrEqqzJ0eumQbVhTYQM27CfT1T35+gCgDFoL82JLsXqTJ76zv6A0YLOgEnLUMvLzsDsGIrl8NFpT2gQ==", + "requires": { + "get-intrinsic": "^1.2.4" + } + }, + "es-errors": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/es-errors/-/es-errors-1.3.0.tgz", + "integrity": "sha512-Zf5H2Kxt2xjTvbJvP2ZWLEICxA6j+hAmMzIlypy4xcBg1vKVnx89Wy0GbS+kf5cwCVFFzdCFh2XSCFNULS6csw==" + }, "es-iterator-helpers": { "version": "1.0.15", "resolved": "https://registry.npmjs.org/es-iterator-helpers/-/es-iterator-helpers-1.0.15.tgz", @@ -22378,10 +22451,11 @@ "integrity": "sha512-DyFP3BM/3YHTQOCUL/w0OZHR0lpKeGrxotcHWcqNEdnltqFwXVfhEBQ94eIo34AfQpo0rGki4cyIiftY06h2Fg==" }, "get-intrinsic": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.2.tgz", - "integrity": "sha512-0gSo4ml/0j98Y3lngkFEot/zhiCeWsbYIlZ+uZOVgzLyLaUw7wxUL+nCTP0XJvJg1AXulJRI3UJi8GsbDuxdGA==", + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/get-intrinsic/-/get-intrinsic-1.2.4.tgz", + "integrity": "sha512-5uYhsJH8VJBTv7oslg4BznJYhDoRI6waYCxMmCdnTrcCrHA/fCFKoTFz2JKKE0HdDFUF7/oQuhzumXJK7paBRQ==", "requires": { + "es-errors": "^1.3.0", "function-bind": "^1.1.2", "has-proto": "^1.0.1", "has-symbols": "^1.0.3", @@ -22823,11 +22897,11 @@ "integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==" }, "has-property-descriptors": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.1.tgz", - "integrity": "sha512-VsX8eaIewvas0xnvinAe9bw4WfIeODpGYikiWYLH+dma0Jw6KHYqWiWfhQlgOVK8D6PvjubK5Uc4P0iIhIcNVg==", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/has-property-descriptors/-/has-property-descriptors-1.0.2.tgz", + "integrity": "sha512-55JNKuIW+vq4Ke1BjOTjM2YctQIvCT7GFzHwmfZPGo5wnrgkid0YQtnAleFSqumZm4az3n2BS+erby5ipJdgrg==", "requires": { - "get-intrinsic": "^1.2.2" + "es-define-property": "^1.0.0" } }, "has-proto": { @@ -23887,10 +23961,9 @@ } }, "jsonpath-plus": { - "version": "7.2.0", - "resolved": "https://registry.npmjs.org/jsonpath-plus/-/jsonpath-plus-7.2.0.tgz", - "integrity": "sha512-zBfiUPM5nD0YZSBT/o/fbCUlCcepMIdP0CJZxM1+KgA4f2T206f6VAg9e7mX35+KlMaIc5qXW34f3BnwJ3w+RA==", - "dev": true + "version": "8.1.0", + "resolved": "https://registry.npmjs.org/jsonpath-plus/-/jsonpath-plus-8.1.0.tgz", + "integrity": "sha512-qVTiuKztFGw0dGhYi3WNqvddx3/SHtyDT0xJaeyz4uP0d1tkpG+0y5uYQ4OcIo1TLAz3PE/qDOW9F0uDt3+CTw==" }, "jsonwebtoken": { "version": "9.0.2", @@ -25382,8 +25455,7 @@ "object-path": { "version": "0.11.8", "resolved": "https://registry.npmjs.org/object-path/-/object-path-0.11.8.tgz", - "integrity": "sha512-YJjNZrlXJFM42wTBn6zgOJVar9KFJvzx6sTWDte8sWZF//cnjl0BxHNpfZx+ZffXX63A9q0b1zsFiBX4g4X5KA==", - "dev": true + "integrity": "sha512-YJjNZrlXJFM42wTBn6zgOJVar9KFJvzx6sTWDte8sWZF//cnjl0BxHNpfZx+ZffXX63A9q0b1zsFiBX4g4X5KA==" }, "object-treeify": { "version": "1.1.33", @@ -26899,14 +26971,16 @@ "optional": true }, "set-function-length": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.1.1.tgz", - "integrity": "sha512-VoaqjbBJKiWtg4yRcKBQ7g7wnGnLV3M8oLvVWwOk2PdYY6PEFegR1vezXR0tw6fZGF9csVakIRjrJiy2veSBFQ==", + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/set-function-length/-/set-function-length-1.2.2.tgz", + "integrity": "sha512-pgRc4hJ4/sNjWCSS9AmnS40x3bNMDTknHgL5UaMBTMyJnU90EgWh1Rz+MC9eFu4BuN/UwZjKQuY/1v3rM7HMfg==", "requires": { - "define-data-property": "^1.1.1", - "get-intrinsic": "^1.2.1", + "define-data-property": "^1.1.4", + "es-errors": "^1.3.0", + "function-bind": "^1.1.2", + "get-intrinsic": "^1.2.4", "gopd": "^1.0.1", - "has-property-descriptors": "^1.0.0" + "has-property-descriptors": "^1.0.2" } }, "set-function-name": { @@ -26945,13 +27019,14 @@ "dev": true }, "side-channel": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.4.tgz", - "integrity": "sha512-q5XPytqFEIKHkGdiMIrY10mvLRvnQh42/+GoBlFW3b2LXLE2xxJpZFdm94we0BaoV3RwJyGqg5wS7epxTv0Zvw==", + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/side-channel/-/side-channel-1.0.6.tgz", + "integrity": "sha512-fDW/EZ6Q9RiO8eFG8Hj+7u/oW+XrPTIChwCOM2+th2A6OblDtYYIpve9m+KvI9Z4C9qSEXlaGR6bTEYHReuglA==", "requires": { - "call-bind": "^1.0.0", - "get-intrinsic": "^1.0.2", - "object-inspect": "^1.9.0" + "call-bind": "^1.0.7", + "es-errors": "^1.3.0", + "get-intrinsic": "^1.2.4", + "object-inspect": "^1.13.1" } }, "signal-exit": { @@ -28237,9 +28312,9 @@ } }, "winston-transport": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/winston-transport/-/winston-transport-4.6.0.tgz", - "integrity": "sha512-wbBA9PbPAHxKiygo7ub7BYRiKxms0tpfU2ljtWzb3SjRjv5yl6Ozuy/TkXf00HTAt+Uylo3gSkNwzc4ME0wiIg==", + "version": "4.7.0", + "resolved": "https://registry.npmjs.org/winston-transport/-/winston-transport-4.7.0.tgz", + "integrity": "sha512-ajBj65K5I7denzer2IYW6+2bNIVqLGDHqDw3Ow8Ohh+vdW+rv4MZ6eiDvHoKhfJFZ2auyN8byXieDDJ96ViONg==", "dev": true, "requires": { "logform": "^2.3.2", diff --git a/package.json b/package.json index e8216e6c..a4492afe 100644 --- a/package.json +++ b/package.json @@ -50,7 +50,9 @@ "glob": "^10.3.10", "gray-matter": "^4.0.3", "js-yaml": "^4.1.0", + "jsonpath-plus": "^8.1.0", "next": "^14.0.2", + "object-path": "^0.11.8", "raw-loader": "^4.0.2", "react": "^18.2.0", "react-bootstrap": "^2.9.1", diff --git a/pages/_document.tsx b/pages/_document.tsx index b243c4a5..8eff6fa0 100644 --- a/pages/_document.tsx +++ b/pages/_document.tsx @@ -12,7 +12,7 @@ class MyDocument extends Document { diff --git a/pages/tools/index.tsx b/pages/tools/index.tsx index 631fd24a..786b7cf3 100644 --- a/pages/tools/index.tsx +++ b/pages/tools/index.tsx @@ -43,6 +43,13 @@ const tools = [ 'Convert your data from JSON to YAML and back and verify their validity', links: [{ src: '/tools/json-to-yaml', text: 'Convert' }], imageSrc: '/images/illustrations/json-to-yaml.svg' + }, + { + title: 'JSONPath and object-path online evaluator', + description: + 'Extract values from JSON data using JSONPath or object-path syntaxes', + links: [{ src: '/tools/json-object-path-evaluator', text: 'Extract data' }], + imageSrc: '/images/illustrations/json-path-evaluator.svg' } ]; diff --git a/pages/tools/json-object-path-evaluator.tsx b/pages/tools/json-object-path-evaluator.tsx new file mode 100644 index 00000000..f9495823 --- /dev/null +++ b/pages/tools/json-object-path-evaluator.tsx @@ -0,0 +1,452 @@ +import { FunctionComponent, useState } from 'react'; +import CodeBlock from '../../components/code-block'; +import JsonEditor from '../../components/editors/json-editor'; +import Hero from '../../components/hero'; +import Meta from '../../components/meta'; +import Layout from '../../layout/layout'; +import { getValueFromPath } from '../../utils/tools'; + +const JsonPathPlayground: FunctionComponent = function () { + const [jsonContent, setJsonContent] = useState( + `{ + "property": { + "value": "example_value", + "list_of_properties": [ + { + "property_1": "value_1" + }, + { + "property_2": "value_2" + }, + { + "property_3": "value_3" + } + ], + "nested_properties": { + "nested_property": { + "nested_value": "nested_example_value" + } + }, + "multiple_values_for_property": [ + "value_1", + "value_2", + "value_3" + ] + } +}` + ); + const [extractedContent, setExtractedContent] = useState(`[ + "value_1" +]`); + + return ( + + + +
+
+ { + try { + setExtractedContent( + JSON.stringify( + getValueFromPath( + JSON.parse(jsonContent), + event.target.value, + '' + ), + null, + 2 + ) + ); + } catch (error) {} + }} + /> +

+ + Supports both{' '} + + JSONPath-plus + {' '} + and{' '} + + object-path + {' '} + syntaxes. Examples: $.property.value or{' '} + property.value + +

+
+
+
+
+ { + try { + setJsonContent(value); + setExtractedContent( + JSON.stringify( + getValueFromPath( + JSON.parse(value), + (document.querySelector('#path') as HTMLInputElement) + .value, + '' + ), + null, + 2 + ) + ); + } catch (error) {} + }} + /> +
+ +
+ +
+ + +
+
+
+ +
+
+
+
+

About this tool

+

+ This online tool allows you to extract values from JSON data + using{' '} + + JSONPath + {' '} + or{' '} + + object-path + {' '} + syntaxes. The extracted content is updated in real time as you + type your path. +

+

+ This playground uses the same logic as the Mockoon features that + support JSONPath and object-path syntaxes: +

+ + +

About JSONPath

+

+ JSONPath is a query language for JSON data. It allows you to + analyze, transform, and extract data from JSON documents. +
+ JSONPath is used in many programming languages and data + processing tools. It is similar to XPath for XML documents. +

+ +

Syntax cheat sheet

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
SymbolDescription
$the root object/element
@the current object/element
. or []child operator
..nested descendants
* + wildcard, all objects/elements regardless of their names +
[]subscript operator
[,] + JSONPath allows alternate names or array indices as a set. +
[start:end:step]array slice operator
?()applies a filter (script) expression
+ +

JSONPath examples

+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
JSONPathResult
+ $.store.book[*].author + the authors of all books in the store
+ $..author + all authors
+ $.store.* + + all things in store, which are some books and a red + bicycle +
+ $.store..price + the price of everything in the store
+ $..book[2] + the third book
+ $..book[(@.length-1)] +
+ $..book[-1:] +
the last book in order
+ $..book[0,1] +
+ $..book[:2] +
the first two books
+ $..book[?(@.isbn)] + filter all books with isbn number
+ {`$..book[?(@.price<10)]`} + filter all books cheapier than 10
+ $..* + All members of JSON data item
+ +

About object-path

+

+ object-path is a simpler library to access and manipulate + properties on objects using paths. It is similar to JSONPath but + less powerful and more straightforward to use. +
+ object-path is mainly using the dot and bracket notations to + access nested properties. However, it doesn't support all the + features of JSONPath. +

+ +

object-path examples

+ + + + + + + + + + + + + + + + + + + + + + + + + + + +
object-pathResult
+ store.book + + the books in the store, which are an array of objects +
+ store.bicycle.color + the color of the bicycle
+ store.book[0].author + the author of the first book
+ store.book[1].title + the title of the second book
+
+
+
+
+
+ ); +}; + +export default JsonPathPlayground; diff --git a/public/fonts/mockoon.woff b/public/fonts/mockoon.woff index 3657391b1e00c161ad3854811311e924363bdf1f..01ff46668b706e6a210120b6899baad4fc92b817 100644 GIT binary patch delta 374 zcmcbh)1oU61xKA zb3m~`dQN2;Q0xu^gWw4eR%DS^&qz&7VPFtm0#suL!s;He%QAq1Krx^?1{DxyKg9eX zBe$f2fk6bwWvBt+0$HF%`N=?aej*?N2N2fO(yPc#tN>apvIodl0Ao$YwRwrTsX#HH zfsAb+JlBu+e?fk63D74%%c1I+fh=a`JCk`ByBWnM&tOz$W#U`Rw`lVL#!fCBMh1re z2bjZ{4}g5b$)s+sXsW2r#K0K#ZGztmB*Z2#;?o1IiBC< zD+4zR&|n6JM!$86f;)R_5%C)Wj492H_H*8Z!`9`_6nQ11Ja-TLa{) zfH3YQ;sF$}17YniY7DuF6+nwcI)HoyFxFsP zo0piI3KUxbw7d<3=lb#fFUT(jS}JA$SH}!wF*Dzu%){8tC^~rtqcSTa-y*(+n-4H{ za&4~UF=m%pR8a6ap5Nvx12+p$Ed#^D*Y}sh=*cI9%^Bq;iDXR95pkDX#iqj+!f^&D Y2?{ki#?=g*AcYJ}pfKBfUt}pG0DoFfjsO4v diff --git a/public/images/illustrations/json-path-evaluator.svg b/public/images/illustrations/json-path-evaluator.svg new file mode 100644 index 00000000..22ea1ae1 --- /dev/null +++ b/public/images/illustrations/json-path-evaluator.svg @@ -0,0 +1,20 @@ + + + + + + + + + + + + + + + + $. + + + + diff --git a/styles/font.scss b/styles/font.scss index 00cf72f5..9f071e42 100644 --- a/styles/font.scss +++ b/styles/font.scss @@ -1,6 +1,6 @@ @font-face { font-family: 'mockoon'; - src: url('/fonts/mockoon.woff?dqmqhc') format('woff'); + src: url('/fonts/mockoon.woff?exgtff') format('woff'); font-weight: normal; font-style: normal; font-display: block; @@ -79,6 +79,9 @@ .icon-arrow_drop_down:before { content: '\e905'; } +.icon-arrow_forward:before { + content: '\e916'; +} .icon-check:before { content: '\e902'; } diff --git a/styles/mockoon.woff b/styles/mockoon.woff new file mode 100644 index 0000000000000000000000000000000000000000..01ff46668b706e6a210120b6899baad4fc92b817 GIT binary patch literal 5764 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 Q&OWrd`v`dOSUwH^4@<_-XaE2J literal 0 HcmV?d00001 diff --git a/utils/tools.ts b/utils/tools.ts new file mode 100644 index 00000000..a8ecde94 --- /dev/null +++ b/utils/tools.ts @@ -0,0 +1,70 @@ +import { JSONPath } from 'jsonpath-plus'; +import { get as objectGet } from 'object-path'; + +// code taken from @mockoon/commons-server package as it contains node-specific code + +/** + * Convert an object path (for the object-path lib) containing escaped dots '\.' + * to an array of strings to allow fetching properties containing dots. + * + * Example: + * 'get.a.property\.with\.dots => ['get', 'a', 'property.with.dots'] + * + * To query an object like this: + * + * ``` + * { + * get: { + * a: { + * 'propery.with.dots': "value" + * } + * } + * } + * ``` + * @param str + */ +export const convertPathToArray = (str: string): string | string[] => { + if (str.includes('\\.')) { + return str + .replace(/\\\./g, '%#%') + .split('.') + .map((s) => s.replace(/%#%/g, '.')); + } + + return str; +}; + +/** + * Look for a value in an object or array using a path (dot notation or JSONPath). + * If no path is provided, return the full data. + * If the value is not found, return the default value. + * + * @param data + * @param path + * @param defaultValue + * @returns + */ +export const getValueFromPath = ( + data: any, + path: string, + defaultValue: any +) => { + if ( + (Array.isArray(data) || typeof data === 'object') && + typeof path === 'string' && + path !== '' + ) { + let foundValue: any; + + // Added wrap = false (Check https://github.com/mockoon/mockoon/issues/1297) + if (path.startsWith('$')) { + foundValue = JSONPath({ json: data, path: path, wrap: false }); + } else { + foundValue = objectGet(data, convertPathToArray(path)); + } + + return foundValue !== undefined ? foundValue : defaultValue; + } + + return data; +};