From 6a8372513c3d8bdf09e65ee7baeb268797cce41a Mon Sep 17 00:00:00 2001 From: Trevor Scheer Date: Thu, 15 Sep 2022 13:49:21 -0700 Subject: [PATCH 1/6] Add lint config for mdx files --- .eslintrc.cjs | 11 +- .prettierignore | 2 - .vscode/settings.json | 9 +- package-lock.json | 3426 +++++++++++++++++++++++++++++++++++++++-- 4 files changed, 3307 insertions(+), 141 deletions(-) diff --git a/.eslintrc.cjs b/.eslintrc.cjs index c05e1c2f0fd..1fb9e48b5d5 100644 --- a/.eslintrc.cjs +++ b/.eslintrc.cjs @@ -1,10 +1,11 @@ module.exports = { root: true, - parser: '@typescript-eslint/parser', - plugins: ['@typescript-eslint', 'import'], - extends: ['plugin:import/typescript'], + ignorePatterns: ['**/*.js'], overrides: [ { + extends: ['plugin:import/typescript'], + parser: '@typescript-eslint/parser', + plugins: ['@typescript-eslint', 'import'], // Enable import/extensions on all TS files because our ESM builds require // you to specify local imports as full paths with extensions. We don't // need this on tests because Jest doesn't require it. @@ -12,5 +13,9 @@ module.exports = { excludedFiles: '**/__tests__/**/*.ts', rules: { 'import/extensions': ['error', 'ignorePackages'] }, }, + { + extends: ['plugin:mdx/recommended', 'plugin:prettier/recommended'], + files: ['**/*.md?(x)'], + }, ], }; diff --git a/.prettierignore b/.prettierignore index 5aee528f388..88e1849c7df 100644 --- a/.prettierignore +++ b/.prettierignore @@ -1,8 +1,6 @@ *.json *.json5 *.yml -*.md -*.mdx *.snap dist/ diff --git a/.vscode/settings.json b/.vscode/settings.json index 5e5d8c13428..cedd00e7a5b 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -6,5 +6,12 @@ "files.trimTrailingWhitespace": true, "files.insertFinalNewline": true, "typescript.tsdk": "./node_modules/typescript/lib", - "typescript.enablePromptUseWorkspaceTsdk": true + "typescript.enablePromptUseWorkspaceTsdk": true, + "eslint.validate": [ + "md", + "mdx" + ], + "eslint.options": { + "extensions": [".md", ".mdx"] + } } diff --git a/package-lock.json b/package-lock.json index c7b89742a70..2f1189b4f51 100644 --- a/package-lock.json +++ b/package-lock.json @@ -60,7 +60,10 @@ "cors": "2.8.5", "cspell": "6.9.0", "eslint": "8.23.1", + "eslint-config-prettier": "^8.5.0", "eslint-plugin-import": "2.26.0", + "eslint-plugin-mdx": "2.0.4", + "eslint-plugin-prettier": "^4.2.1", "express": "4.18.1", "graphql": "16.5.0", "graphql-tag": "2.12.6", @@ -3954,6 +3957,26 @@ "node": ">=10.12.0" } }, + "node_modules/@pkgr/utils": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/@pkgr/utils/-/utils-2.3.1.tgz", + "integrity": "sha512-wfzX8kc1PMyUILA+1Z/EqoE4UCXGy0iRGMhPwdfae1+f0OXlLqCk+By+aMzgJBzR9AzS4CDizioG6Ss1gvAFJw==", + "dev": true, + "dependencies": { + "cross-spawn": "^7.0.3", + "is-glob": "^4.0.3", + "open": "^8.4.0", + "picocolors": "^1.0.0", + "tiny-glob": "^0.2.9", + "tslib": "^2.4.0" + }, + "engines": { + "node": "^12.20.0 || ^14.18.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/unts" + } + }, "node_modules/@protobufjs/aspromise": { "version": "1.1.2", "license": "BSD-3-Clause" @@ -4103,6 +4126,15 @@ "integrity": "sha512-yOlFc+7UtL/89t2ZhjPvvB/DeAr3r+Dq58IgzsFkOAvVC6NMJXmCGjbptdXdR9qsX7pKcTL+s87FtYREi2dEEQ==", "devOptional": true }, + "node_modules/@types/acorn": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/@types/acorn/-/acorn-4.0.6.tgz", + "integrity": "sha512-veQTnWP+1D/xbxVrPC3zHnCZRjSrKfhbMUlEA43iMZLu7EsnTtkJklIuwrCPbOi8YkvDQAiW05VQQFvvz9oieQ==", + "dev": true, + "dependencies": { + "@types/estree": "*" + } + }, "node_modules/@types/async-retry": { "version": "1.4.5", "resolved": "https://registry.npmjs.org/@types/async-retry/-/async-retry-1.4.5.tgz", @@ -4183,11 +4215,29 @@ "dev": true, "license": "MIT" }, + "node_modules/@types/debug": { + "version": "4.1.7", + "resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.7.tgz", + "integrity": "sha512-9AonUzyTjXXhEOa0DnqpzZi6VHlqKMswga9EXjpXnnqxwLtdvPPtlO8evrI5D9S6asFRCQ6v+wpiUKbw+vKqyg==", + "dev": true, + "dependencies": { + "@types/ms": "*" + } + }, "node_modules/@types/estree": { "version": "0.0.39", "dev": true, "license": "MIT" }, + "node_modules/@types/estree-jsx": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@types/estree-jsx/-/estree-jsx-1.0.0.tgz", + "integrity": "sha512-3qvGd0z8F2ENTGr/GG1yViqfiKmRfrXVx5sJyHGFu3z7m5g5utCQtGp/g29JnjflhtQJBv1WDQukHiT58xPcYQ==", + "dev": true, + "dependencies": { + "@types/estree": "*" + } + }, "node_modules/@types/express": { "version": "4.17.14", "resolved": "https://registry.npmjs.org/@types/express/-/express-4.17.14.tgz", @@ -4217,6 +4267,15 @@ "@types/node": "*" } }, + "node_modules/@types/hast": { + "version": "2.3.4", + "resolved": "https://registry.npmjs.org/@types/hast/-/hast-2.3.4.tgz", + "integrity": "sha512-wLEm0QvaoawEDoTRwzTXp4b4jpwiJDvR5KMnFnVodm3scufTlBOWRD6N1OBf9TZMhjlNsSfcO5V+7AF4+Vy+9g==", + "dev": true, + "dependencies": { + "@types/unist": "*" + } + }, "node_modules/@types/is-ci": { "version": "3.0.0", "dev": true, @@ -4355,6 +4414,15 @@ "version": "4.0.1", "license": "MIT" }, + "node_modules/@types/mdast": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-3.0.10.tgz", + "integrity": "sha512-W864tg/Osz1+9f4lrGTZpCSO5/z4608eUp19tbozkq2HJK6i3z1kT0H9tlADXuYIb1YYOBByU4Jsqkk75q48qA==", + "dev": true, + "dependencies": { + "@types/unist": "*" + } + }, "node_modules/@types/mime": { "version": "1.3.2", "license": "MIT" @@ -4364,6 +4432,12 @@ "dev": true, "license": "MIT" }, + "node_modules/@types/ms": { + "version": "0.7.31", + "resolved": "https://registry.npmjs.org/@types/ms/-/ms-0.7.31.tgz", + "integrity": "sha512-iiUgKzV9AuaEkZqkOLDIvlQiL6ltuZd9tGcW3gwpnX8JbuiuhFlEGmmFXEXkN50Cvq7Os88IY2v0dkDqXYWVgA==", + "dev": true + }, "node_modules/@types/negotiator": { "version": "0.6.1", "dev": true, @@ -4508,6 +4582,12 @@ "@types/node": "*" } }, + "node_modules/@types/unist": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.6.tgz", + "integrity": "sha512-PBjIUxZHOuj0R15/xuwJYjFi+KZdNFrehocChv4g5hu6aFroHue8m0lBP0POdK2nKzbw0cgV1mws8+V/JAcEkQ==", + "dev": true + }, "node_modules/@types/uuid": { "version": "8.3.4", "dev": true, @@ -6441,6 +6521,16 @@ "@babel/core": "^7.0.0" } }, + "node_modules/bail": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/bail/-/bail-2.0.2.tgz", + "integrity": "sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/balanced-match": { "version": "1.0.2", "license": "MIT" @@ -6838,6 +6928,16 @@ "license": "Apache-2.0", "peer": true }, + "node_modules/ccount": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/ccount/-/ccount-2.0.1.tgz", + "integrity": "sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/chalk": { "version": "4.1.2", "license": "MIT", @@ -6896,6 +6996,46 @@ "node": ">=10" } }, + "node_modules/character-entities": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-1.2.4.tgz", + "integrity": "sha512-iBMyeEHxfVnIakwOuDXpVkc54HijNgCyQB2w0VfGQThle6NXn50zU6V/u+LDhxHcDUPojn6Kpga3PTAD8W1bQw==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-entities-html4": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/character-entities-html4/-/character-entities-html4-2.1.0.tgz", + "integrity": "sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-entities-legacy": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-1.1.4.tgz", + "integrity": "sha512-3Xnr+7ZFS1uxeiUDvV02wQ+QDbc55o97tIV5zHScSPJpcLm/r0DFPcoY3tYRp+VZukxuMeKgXYmsXQHO05zQeA==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/character-reference-invalid": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-1.1.4.tgz", + "integrity": "sha512-mKKUkUbhPpQlCOfIuZkvSEgktjPFIsZKRRbC6KWVEMvlzblj3i3asQv5ODsrwt0N3pHAEvjP8KTQPHkp0+6jOg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/chardet": { "version": "0.7.0", "dev": true, @@ -7779,6 +7919,29 @@ "node": ">=0.10.0" } }, + "node_modules/decode-named-character-reference": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.0.2.tgz", + "integrity": "sha512-O8x12RzrUF8xyVcY0KJowWsmaJxQbmy0/EtnNtHRpsOcT7dFk5W598coHqBVpmWo1oQQfsCqfCmkZN5DJrZVdg==", + "dev": true, + "dependencies": { + "character-entities": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/decode-named-character-reference/node_modules/character-entities": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz", + "integrity": "sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/dedent": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/dedent/-/dedent-0.7.0.tgz", @@ -7831,6 +7994,15 @@ "clone": "^1.0.2" } }, + "node_modules/define-lazy-prop": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-2.0.0.tgz", + "integrity": "sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==", + "dev": true, + "engines": { + "node": ">=8" + } + }, "node_modules/define-properties": { "version": "1.1.4", "dev": true, @@ -7869,6 +8041,15 @@ "node": ">= 0.6.0" } }, + "node_modules/dequal": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", + "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", + "dev": true, + "engines": { + "node": ">=6" + } + }, "node_modules/destroy": { "version": "1.2.0", "license": "MIT", @@ -8297,6 +8478,18 @@ "url": "https://opencollective.com/eslint" } }, + "node_modules/eslint-config-prettier": { + "version": "8.5.0", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-8.5.0.tgz", + "integrity": "sha512-obmWKLUNCnhtQRKc+tmnYuQl0pFU1ibYJQ5BGhTVB08bHe9wC8qUeG7c08dj9XX+AuPj1YSGSQIHl1pnDHZR0Q==", + "dev": true, + "bin": { + "eslint-config-prettier": "bin/cli.js" + }, + "peerDependencies": { + "eslint": ">=7.0.0" + } + }, "node_modules/eslint-import-resolver-node": { "version": "0.3.6", "dev": true, @@ -8314,6 +8507,38 @@ "ms": "^2.1.1" } }, + "node_modules/eslint-mdx": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/eslint-mdx/-/eslint-mdx-2.0.4.tgz", + "integrity": "sha512-SEgeWByCKYNRSqV+FtxHIcBadW7xCDtfZVACEZgFN1woGuPbr1XQicUMHO5pE0LSSQfWNHXTXP9MCMBkRRVS4A==", + "dev": true, + "dependencies": { + "acorn": "^8.8.0", + "acorn-jsx": "^5.3.2", + "cosmiconfig": "^7.0.1", + "espree": "^9.4.0", + "estree-util-visit": "^1.2.0", + "remark-mdx": "^2.1.3", + "remark-parse": "^10.0.1", + "remark-stringify": "^10.0.2", + "synckit": "^0.8.4", + "tslib": "^2.4.0", + "unified": "^10.1.2", + "unist-util-visit": "^4.1.1", + "uvu": "^0.5.6", + "vfile": "^5.3.4" + }, + "engines": { + "node": "^12.20.0 || ^14.18.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + }, + "peerDependencies": { + "eslint": ">=8.0.0" + } + }, "node_modules/eslint-module-utils": { "version": "2.7.3", "dev": true, @@ -8461,6 +8686,68 @@ "integrity": "sha512-Tpp60P6IUJDTuOq/5Z8cdskzJujfwqfOTkrwIwj7IRISpnkJnT6SyJ4PCPnGMoFjC9ddhal5KVIYtAt97ix05A==", "dev": true }, + "node_modules/eslint-plugin-markdown": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-markdown/-/eslint-plugin-markdown-3.0.0.tgz", + "integrity": "sha512-hRs5RUJGbeHDLfS7ELanT0e29Ocyssf/7kBM+p7KluY5AwngGkDf8Oyu4658/NZSGTTq05FZeWbkxXtbVyHPwg==", + "dev": true, + "dependencies": { + "mdast-util-from-markdown": "^0.8.5" + }, + "engines": { + "node": "^12.22.0 || ^14.17.0 || >=16.0.0" + }, + "peerDependencies": { + "eslint": "^6.0.0 || ^7.0.0 || ^8.0.0" + } + }, + "node_modules/eslint-plugin-mdx": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/eslint-plugin-mdx/-/eslint-plugin-mdx-2.0.4.tgz", + "integrity": "sha512-dDxtpaQl4EFAj8pZKa3Wk5s6QH2wz22Ba25j4OtW40zkB2Bb/Su/8xWoikF61bZoL99Y3aUV24eUTS39n0PJLQ==", + "dev": true, + "dependencies": { + "eslint-mdx": "^2.0.4", + "eslint-plugin-markdown": "^3.0.0", + "remark-mdx": "^2.1.3", + "remark-parse": "^10.0.1", + "remark-stringify": "^10.0.2", + "tslib": "^2.4.0", + "unified": "^10.1.2", + "vfile": "^5.3.4" + }, + "engines": { + "node": "^12.20.0 || ^14.18.0 || >=16.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + }, + "peerDependencies": { + "eslint": ">=8.0.0" + } + }, + "node_modules/eslint-plugin-prettier": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-4.2.1.tgz", + "integrity": "sha512-f/0rXLXUt0oFYs8ra4w49wYZBG5GKZpAYsJSm6rnYL5uVDjd+zowwMwVZHnAjf4edNrKpCDYfXDgmRE/Ak7QyQ==", + "dev": true, + "dependencies": { + "prettier-linter-helpers": "^1.0.0" + }, + "engines": { + "node": ">=12.0.0" + }, + "peerDependencies": { + "eslint": ">=7.28.0", + "prettier": ">=2.0.0" + }, + "peerDependenciesMeta": { + "eslint-config-prettier": { + "optional": true + } + } + }, "node_modules/eslint-scope": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", @@ -8715,6 +9002,30 @@ "node": ">=4.0" } }, + "node_modules/estree-util-is-identifier-name": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/estree-util-is-identifier-name/-/estree-util-is-identifier-name-2.0.1.tgz", + "integrity": "sha512-rxZj1GkQhY4x1j/CSnybK9cGuMFQYFPLq0iNyopqf14aOVLFtMv7Esika+ObJWPWiOHuMOAHz3YkWoLYYRnzWQ==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/estree-util-visit": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/estree-util-visit/-/estree-util-visit-1.2.0.tgz", + "integrity": "sha512-wdsoqhWueuJKsh5hqLw3j8lwFqNStm92VcwtAOAny8g/KS/l5Y8RISjR4k5W6skCj3Nirag/WUCMS0Nfy3sgsg==", + "dev": true, + "dependencies": { + "@types/estree-jsx": "^1.0.0", + "@types/unist": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, "node_modules/estree-walker": { "version": "2.0.2", "dev": true, @@ -8856,8 +9167,7 @@ "node_modules/extend": { "version": "3.0.2", "dev": true, - "license": "MIT", - "peer": true + "license": "MIT" }, "node_modules/extendable-error": { "version": "0.1.7", @@ -8903,6 +9213,12 @@ "dev": true, "license": "MIT" }, + "node_modules/fast-diff": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/fast-diff/-/fast-diff-1.2.0.tgz", + "integrity": "sha512-xJuoT5+L99XlZ8twedaRf6Ax2TgQVxvgZOYoPKqZufmJib0tL2tegPBOZb1pVNgIhlqDlA0eO0c3wBvQcmzx4w==", + "dev": true + }, "node_modules/fast-equals": { "version": "4.0.3", "resolved": "https://registry.npmjs.org/fast-equals/-/fast-equals-4.0.3.tgz", @@ -9421,6 +9737,12 @@ "node": ">=4" } }, + "node_modules/globalyzer": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/globalyzer/-/globalyzer-0.1.0.tgz", + "integrity": "sha512-40oNTM9UfG6aBmuKxk/giHn5nQ8RVz/SS4Ir6zgzOv9/qC3kKZ9v4etGTcJbEl/NyVQH7FGU7d+X1egr57Md2Q==", + "dev": true + }, "node_modules/globby": { "version": "11.1.0", "dev": true, @@ -9440,6 +9762,12 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/globrex": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/globrex/-/globrex-0.1.2.tgz", + "integrity": "sha512-uHJgbwAMwNFf5mLst7IWLNg14x1CkeqglJb/K3doi4dw6q2IvAAmM/Y81kevy83wP+Sst+nutFTYOGg3d1lsxg==", + "dev": true + }, "node_modules/graceful-fs": { "version": "4.2.10", "license": "ISC" @@ -10000,6 +10328,30 @@ "node": ">=0.10.0" } }, + "node_modules/is-alphabetical": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-1.0.4.tgz", + "integrity": "sha512-DwzsA04LQ10FHTZuL0/grVDk4rFoVH1pjAToYwBrHSxcrBIGQuXrQMtD5U1b0U2XVgKZCTLLP8u2Qxqhy3l2Vg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/is-alphanumerical": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-1.0.4.tgz", + "integrity": "sha512-UzoZUr+XfVz3t3v4KyGEniVL9BDRoQtY7tOyrRybkVNjDFWyo1yhXNGrrBTQxp3ib9BLAWs7k2YKBQsFRkZG9A==", + "dev": true, + "dependencies": { + "is-alphabetical": "^1.0.0", + "is-decimal": "^1.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/is-arguments": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/is-arguments/-/is-arguments-1.1.1.tgz", @@ -10057,6 +10409,29 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/is-buffer": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-2.0.5.tgz", + "integrity": "sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "engines": { + "node": ">=4" + } + }, "node_modules/is-callable": { "version": "1.2.4", "dev": true, @@ -10103,6 +10478,31 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/is-decimal": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-1.0.4.tgz", + "integrity": "sha512-RGdriMmQQvZ2aqaQq3awNA6dCGtKpiDFcOzrTWrDAT2MiWrKQVPmxLGHl7Y2nNu6led0kEyoX0enY0qXYsv9zw==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/is-docker": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/is-docker/-/is-docker-2.2.1.tgz", + "integrity": "sha512-F+i2BKsFrH66iaUFc0woD8sLy8getkwTwtOBjvs56Cx4CgJDeKQeqfz8wAYiSb8JOprWhHH5p77PbmYCvvUuXQ==", + "dev": true, + "bin": { + "is-docker": "cli.js" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/is-extglob": { "version": "2.1.1", "dev": true, @@ -10137,6 +10537,16 @@ "node": ">=0.10.0" } }, + "node_modules/is-hexadecimal": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-1.0.4.tgz", + "integrity": "sha512-gyPJuv83bHMpocVYoqof5VDiZveEoGoFL8m3BXNb2VW8Xs+rz9kqO8LOQ5DH6EsuvilT1ApazU0pyl+ytbPtlw==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/is-interactive": { "version": "1.0.0", "dev": true, @@ -10420,6 +10830,18 @@ "node": ">=0.10.0" } }, + "node_modules/is-wsl": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-2.2.0.tgz", + "integrity": "sha512-fKzAra0rGJUUBwGBgNkHZuToZcn+TtXHpeCgmkMJMMYx1sQDYaCSyjJBSCa2nH1DGm7s3n1oBnohoVTBaN7Lww==", + "dev": true, + "dependencies": { + "is-docker": "^2.0.0" + }, + "engines": { + "node": ">=8" + } + }, "node_modules/isarray": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", @@ -11945,6 +12367,16 @@ "version": "4.0.0", "license": "Apache-2.0" }, + "node_modules/longest-streak": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-3.0.1.tgz", + "integrity": "sha512-cHlYSUpL2s7Fb3394mYxwTYj8niTaNHUCLr0qdiCXQfSjfuA7CKofpX2uSwEfFDQ0EB7JcnMnm+GjbqqoinYYg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/loose-envify": { "version": "1.4.0", "license": "MIT", @@ -12080,104 +12512,1086 @@ "url": "https://github.com/sponsors/sindresorhus" } }, - "node_modules/media-typer": { - "version": "0.3.0", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } + "node_modules/mdast-util-from-markdown": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-0.8.5.tgz", + "integrity": "sha512-2hkTXtYYnr+NubD/g6KGBS/0mFmBcifAsI0yIWRiRo0PjVs6SSOSOdtzbp6kSGnShDN6G5aWZpKQ2lWRy27mWQ==", + "dev": true, + "dependencies": { + "@types/mdast": "^3.0.0", + "mdast-util-to-string": "^2.0.0", + "micromark": "~2.11.0", + "parse-entities": "^2.0.0", + "unist-util-stringify-position": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdx": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-mdx/-/mdast-util-mdx-2.0.0.tgz", + "integrity": "sha512-M09lW0CcBT1VrJUaF/PYxemxxHa7SLDHdSn94Q9FhxjCQfuW7nMAWKWimTmA3OyDMSTH981NN1csW1X+HPSluw==", + "dev": true, + "dependencies": { + "mdast-util-mdx-expression": "^1.0.0", + "mdast-util-mdx-jsx": "^2.0.0", + "mdast-util-mdxjs-esm": "^1.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdx-expression": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/mdast-util-mdx-expression/-/mdast-util-mdx-expression-1.3.0.tgz", + "integrity": "sha512-9kTO13HaL/ChfzVCIEfDRdp1m5hsvsm6+R8yr67mH+KS2ikzZ0ISGLPTbTswOFpLLlgVHO9id3cul4ajutCvCA==", + "dev": true, + "dependencies": { + "@types/estree-jsx": "^1.0.0", + "@types/hast": "^2.0.0", + "@types/mdast": "^3.0.0", + "mdast-util-from-markdown": "^1.0.0", + "mdast-util-to-markdown": "^1.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdx-expression/node_modules/mdast-util-from-markdown": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-1.2.0.tgz", + "integrity": "sha512-iZJyyvKD1+K7QX1b5jXdE7Sc5dtoTry1vzV28UZZe8Z1xVnB/czKntJ7ZAkG0tANqRnBF6p3p7GpU1y19DTf2Q==", + "dev": true, + "dependencies": { + "@types/mdast": "^3.0.0", + "@types/unist": "^2.0.0", + "decode-named-character-reference": "^1.0.0", + "mdast-util-to-string": "^3.1.0", + "micromark": "^3.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-decode-string": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-stringify-position": "^3.0.0", + "uvu": "^0.5.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdx-expression/node_modules/mdast-util-to-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.1.0.tgz", + "integrity": "sha512-n4Vypz/DZgwo0iMHLQL49dJzlp7YtAJP+N07MZHpjPf/5XJuHUWstviF4Mn2jEiR/GNmtnRRqnwsXExk3igfFA==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdx-expression/node_modules/micromark": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-3.0.10.tgz", + "integrity": "sha512-ryTDy6UUunOXy2HPjelppgJ2sNfcPz1pLlMdA6Rz9jPzhLikWXv/irpWV/I2jd68Uhmny7hHxAlAhk4+vWggpg==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "@types/debug": "^4.0.0", + "debug": "^4.0.0", + "decode-named-character-reference": "^1.0.0", + "micromark-core-commonmark": "^1.0.1", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-chunked": "^1.0.0", + "micromark-util-combine-extensions": "^1.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-encode": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-resolve-all": "^1.0.0", + "micromark-util-sanitize-uri": "^1.0.0", + "micromark-util-subtokenize": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.1", + "uvu": "^0.5.0" + } + }, + "node_modules/mdast-util-mdx-expression/node_modules/unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdx-jsx": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-mdx-jsx/-/mdast-util-mdx-jsx-2.1.0.tgz", + "integrity": "sha512-KzgzfWMhdteDkrY4mQtyvTU5bc/W4ppxhe9SzelO6QUUiwLAM+Et2Dnjjprik74a336kHdo0zKm7Tp+n6FFeRg==", + "dev": true, + "dependencies": { + "@types/estree-jsx": "^1.0.0", + "@types/hast": "^2.0.0", + "@types/mdast": "^3.0.0", + "ccount": "^2.0.0", + "mdast-util-to-markdown": "^1.3.0", + "parse-entities": "^4.0.0", + "stringify-entities": "^4.0.0", + "unist-util-remove-position": "^4.0.0", + "unist-util-stringify-position": "^3.0.0", + "vfile-message": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdx-jsx/node_modules/character-entities": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz", + "integrity": "sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/mdast-util-mdx-jsx/node_modules/character-entities-legacy": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", + "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/mdast-util-mdx-jsx/node_modules/character-reference-invalid": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-2.0.1.tgz", + "integrity": "sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/mdast-util-mdx-jsx/node_modules/is-alphabetical": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-2.0.1.tgz", + "integrity": "sha512-FWyyY60MeTNyeSRpkM2Iry0G9hpr7/9kD40mD/cGQEuilcZYS4okz8SN2Q6rLCJ8gbCt6fN+rC+6tMGS99LaxQ==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/mdast-util-mdx-jsx/node_modules/is-alphanumerical": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-2.0.1.tgz", + "integrity": "sha512-hmbYhX/9MUMF5uh7tOXyK/n0ZvWpad5caBA17GsC6vyuCqaWliRG5K1qS9inmUhEMaOBIW7/whAnSwveW/LtZw==", + "dev": true, + "dependencies": { + "is-alphabetical": "^2.0.0", + "is-decimal": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/mdast-util-mdx-jsx/node_modules/is-decimal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-2.0.1.tgz", + "integrity": "sha512-AAB9hiomQs5DXWcRB1rqsxGUstbRroFOPPVAomNk/3XHR5JyEZChOyTWe2oayKnsSsr/kcGqF+z6yuH6HHpN0A==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/mdast-util-mdx-jsx/node_modules/is-hexadecimal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-2.0.1.tgz", + "integrity": "sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/mdast-util-mdx-jsx/node_modules/parse-entities": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-4.0.0.tgz", + "integrity": "sha512-5nk9Fn03x3rEhGaX1FU6IDwG/k+GxLXlFAkgrbM1asuAFl3BhdQWvASaIsmwWypRNcZKHPYnIuOSfIWEyEQnPQ==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0", + "character-entities": "^2.0.0", + "character-entities-legacy": "^3.0.0", + "character-reference-invalid": "^2.0.0", + "decode-named-character-reference": "^1.0.0", + "is-alphanumerical": "^2.0.0", + "is-decimal": "^2.0.0", + "is-hexadecimal": "^2.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/mdast-util-mdx-jsx/node_modules/unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdxjs-esm": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/mdast-util-mdxjs-esm/-/mdast-util-mdxjs-esm-1.3.0.tgz", + "integrity": "sha512-7N5ihsOkAEGjFotIX9p/YPdl4TqUoMxL4ajNz7PbT89BqsdWJuBC9rvgt6wpbwTZqWWR0jKWqQbwsOWDBUZv4g==", + "dev": true, + "dependencies": { + "@types/estree-jsx": "^1.0.0", + "@types/hast": "^2.0.0", + "@types/mdast": "^3.0.0", + "mdast-util-from-markdown": "^1.0.0", + "mdast-util-to-markdown": "^1.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdxjs-esm/node_modules/mdast-util-from-markdown": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-1.2.0.tgz", + "integrity": "sha512-iZJyyvKD1+K7QX1b5jXdE7Sc5dtoTry1vzV28UZZe8Z1xVnB/czKntJ7ZAkG0tANqRnBF6p3p7GpU1y19DTf2Q==", + "dev": true, + "dependencies": { + "@types/mdast": "^3.0.0", + "@types/unist": "^2.0.0", + "decode-named-character-reference": "^1.0.0", + "mdast-util-to-string": "^3.1.0", + "micromark": "^3.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-decode-string": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-stringify-position": "^3.0.0", + "uvu": "^0.5.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdxjs-esm/node_modules/mdast-util-to-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.1.0.tgz", + "integrity": "sha512-n4Vypz/DZgwo0iMHLQL49dJzlp7YtAJP+N07MZHpjPf/5XJuHUWstviF4Mn2jEiR/GNmtnRRqnwsXExk3igfFA==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-mdxjs-esm/node_modules/micromark": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-3.0.10.tgz", + "integrity": "sha512-ryTDy6UUunOXy2HPjelppgJ2sNfcPz1pLlMdA6Rz9jPzhLikWXv/irpWV/I2jd68Uhmny7hHxAlAhk4+vWggpg==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "@types/debug": "^4.0.0", + "debug": "^4.0.0", + "decode-named-character-reference": "^1.0.0", + "micromark-core-commonmark": "^1.0.1", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-chunked": "^1.0.0", + "micromark-util-combine-extensions": "^1.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-encode": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-resolve-all": "^1.0.0", + "micromark-util-sanitize-uri": "^1.0.0", + "micromark-util-subtokenize": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.1", + "uvu": "^0.5.0" + } + }, + "node_modules/mdast-util-mdxjs-esm/node_modules/unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-to-markdown": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-1.3.0.tgz", + "integrity": "sha512-6tUSs4r+KK4JGTTiQ7FfHmVOaDrLQJPmpjD6wPMlHGUVXoG9Vjc3jIeP+uyBWRf8clwB2blM+W7+KrlMYQnftA==", + "dev": true, + "dependencies": { + "@types/mdast": "^3.0.0", + "@types/unist": "^2.0.0", + "longest-streak": "^3.0.0", + "mdast-util-to-string": "^3.0.0", + "micromark-util-decode-string": "^1.0.0", + "unist-util-visit": "^4.0.0", + "zwitch": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-to-markdown/node_modules/mdast-util-to-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.1.0.tgz", + "integrity": "sha512-n4Vypz/DZgwo0iMHLQL49dJzlp7YtAJP+N07MZHpjPf/5XJuHUWstviF4Mn2jEiR/GNmtnRRqnwsXExk3igfFA==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/mdast-util-to-string": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-2.0.0.tgz", + "integrity": "sha512-AW4DRS3QbBayY/jJmD8437V1Gombjf8RSOUCMFBuo5iHi58AGEgVCKQ+ezHkZZDpAQS75hcBMpLqjpJTjtUL7w==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/media-typer": { + "version": "0.3.0", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/memorizer": { + "version": "1.0.1", + "dev": true, + "license": "MIT" + }, + "node_modules/meow": { + "version": "6.1.1", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/minimist": "^1.2.0", + "camelcase-keys": "^6.2.2", + "decamelize-keys": "^1.1.0", + "hard-rejection": "^2.1.0", + "minimist-options": "^4.0.2", + "normalize-package-data": "^2.5.0", + "read-pkg-up": "^7.0.1", + "redent": "^3.0.0", + "trim-newlines": "^3.0.0", + "type-fest": "^0.13.1", + "yargs-parser": "^18.1.3" + }, + "engines": { + "node": ">=8" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/meow/node_modules/type-fest": { + "version": "0.13.1", + "dev": true, + "license": "(MIT OR CC0-1.0)", + "engines": { + "node": ">=10" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, + "node_modules/meow/node_modules/yargs-parser": { + "version": "18.1.3", + "dev": true, + "license": "ISC", + "dependencies": { + "camelcase": "^5.0.0", + "decamelize": "^1.2.0" + }, + "engines": { + "node": ">=6" + } + }, + "node_modules/merge-descriptors": { + "version": "1.0.1", + "license": "MIT" + }, + "node_modules/merge-stream": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", + "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==" + }, + "node_modules/merge2": { + "version": "1.4.1", + "dev": true, + "license": "MIT", + "engines": { + "node": ">= 8" + } + }, + "node_modules/meros": { + "version": "1.2.0", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=12" + }, + "peerDependencies": { + "@types/node": ">=12" + }, + "peerDependenciesMeta": { + "@types/node": { + "optional": true + } + } + }, + "node_modules/methods": { + "version": "1.1.2", + "license": "MIT", + "engines": { + "node": ">= 0.6" + } + }, + "node_modules/micromark": { + "version": "2.11.4", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-2.11.4.tgz", + "integrity": "sha512-+WoovN/ppKolQOFIAajxi7Lu9kInbPxFuTBVEavFcL8eAfVstoc5MocPmqBeAdBOJV00uaVjegzH4+MA0DN/uA==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "debug": "^4.0.0", + "parse-entities": "^2.0.0" + } + }, + "node_modules/micromark-core-commonmark": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-1.0.6.tgz", + "integrity": "sha512-K+PkJTxqjFfSNkfAhp4GB+cZPfQd6dxtTXnf+RjZOV7T4EEXnvgzOcnp+eSTmpGk9d1S9sL6/lqrgSNn/s0HZA==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "decode-named-character-reference": "^1.0.0", + "micromark-factory-destination": "^1.0.0", + "micromark-factory-label": "^1.0.0", + "micromark-factory-space": "^1.0.0", + "micromark-factory-title": "^1.0.0", + "micromark-factory-whitespace": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-chunked": "^1.0.0", + "micromark-util-classify-character": "^1.0.0", + "micromark-util-html-tag-name": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-resolve-all": "^1.0.0", + "micromark-util-subtokenize": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.1", + "uvu": "^0.5.0" + } + }, + "node_modules/micromark-extension-mdx-expression": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/micromark-extension-mdx-expression/-/micromark-extension-mdx-expression-1.0.3.tgz", + "integrity": "sha512-TjYtjEMszWze51NJCZmhv7MEBcgYRgb3tJeMAJ+HQCAaZHHRBaDCccqQzGizR/H4ODefP44wRTgOn2vE5I6nZA==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-factory-mdx-expression": "^1.0.0", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-events-to-acorn": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0" + } + }, + "node_modules/micromark-extension-mdx-jsx": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/micromark-extension-mdx-jsx/-/micromark-extension-mdx-jsx-1.0.3.tgz", + "integrity": "sha512-VfA369RdqUISF0qGgv2FfV7gGjHDfn9+Qfiv5hEwpyr1xscRj/CiVRkU7rywGFCO7JwJ5L0e7CJz60lY52+qOA==", + "dev": true, + "dependencies": { + "@types/acorn": "^4.0.0", + "estree-util-is-identifier-name": "^2.0.0", + "micromark-factory-mdx-expression": "^1.0.0", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0", + "vfile-message": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-extension-mdx-md": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-extension-mdx-md/-/micromark-extension-mdx-md-1.0.0.tgz", + "integrity": "sha512-xaRAMoSkKdqZXDAoSgp20Azm0aRQKGOl0RrS81yGu8Hr/JhMsBmfs4wR7m9kgVUIO36cMUQjNyiyDKPrsv8gOw==", + "dev": true, + "dependencies": { + "micromark-util-types": "^1.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-extension-mdxjs": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-extension-mdxjs/-/micromark-extension-mdxjs-1.0.0.tgz", + "integrity": "sha512-TZZRZgeHvtgm+IhtgC2+uDMR7h8eTKF0QUX9YsgoL9+bADBpBY6SiLvWqnBlLbCEevITmTqmEuY3FoxMKVs1rQ==", + "dev": true, + "dependencies": { + "acorn": "^8.0.0", + "acorn-jsx": "^5.0.0", + "micromark-extension-mdx-expression": "^1.0.0", + "micromark-extension-mdx-jsx": "^1.0.0", + "micromark-extension-mdx-md": "^1.0.0", + "micromark-extension-mdxjs-esm": "^1.0.0", + "micromark-util-combine-extensions": "^1.0.0", + "micromark-util-types": "^1.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-extension-mdxjs-esm": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/micromark-extension-mdxjs-esm/-/micromark-extension-mdxjs-esm-1.0.3.tgz", + "integrity": "sha512-2N13ol4KMoxb85rdDwTAC6uzs8lMX0zeqpcyx7FhS7PxXomOnLactu8WI8iBNXW8AVyea3KIJd/1CKnUmwrK9A==", + "dev": true, + "dependencies": { + "micromark-core-commonmark": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-events-to-acorn": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-position-from-estree": "^1.1.0", + "uvu": "^0.5.0", + "vfile-message": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/micromark-factory-destination": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-1.0.0.tgz", + "integrity": "sha512-eUBA7Rs1/xtTVun9TmV3gjfPz2wEwgK5R5xcbIM5ZYAtvGF6JkyaDsj0agx8urXnO31tEO6Ug83iVH3tdedLnw==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "node_modules/micromark-factory-label": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-1.0.2.tgz", + "integrity": "sha512-CTIwxlOnU7dEshXDQ+dsr2n+yxpP0+fn271pu0bwDIS8uqfFcumXpj5mLn3hSC8iw2MUr6Gx8EcKng1dD7i6hg==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0" + } + }, + "node_modules/micromark-factory-mdx-expression": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/micromark-factory-mdx-expression/-/micromark-factory-mdx-expression-1.0.6.tgz", + "integrity": "sha512-WRQIc78FV7KrCfjsEf/sETopbYjElh3xAmNpLkd1ODPqxEngP42eVRGbiPEQWpRV27LzqW+XVTvQAMIIRLPnNA==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-events-to-acorn": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-position-from-estree": "^1.0.0", + "uvu": "^0.5.0", + "vfile-message": "^3.0.0" + } + }, + "node_modules/micromark-factory-space": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-1.0.0.tgz", + "integrity": "sha512-qUmqs4kj9a5yBnk3JMLyjtWYN6Mzfcx8uJfi5XAveBniDevmZasdGBba5b4QsvRcAkmvGo5ACmSUmyGiKTLZew==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-character": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "node_modules/micromark-factory-title": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-1.0.2.tgz", + "integrity": "sha512-zily+Nr4yFqgMGRKLpTVsNl5L4PMu485fGFDOQJQBl2NFpjGte1e86zC0da93wf97jrc4+2G2GQudFMHn3IX+A==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0" + } + }, + "node_modules/micromark-factory-whitespace": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-1.0.0.tgz", + "integrity": "sha512-Qx7uEyahU1lt1RnsECBiuEbfr9INjQTGa6Err+gF3g0Tx4YEviPbqqGKNv/NrBaE7dVHdn1bVZKM/n5I/Bak7A==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "node_modules/micromark-util-character": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-1.1.0.tgz", + "integrity": "sha512-agJ5B3unGNJ9rJvADMJ5ZiYjBRyDpzKAOk01Kpi1TKhlT1APx3XZk6eN7RtSz1erbWHC2L8T3xLZ81wdtGRZzg==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "node_modules/micromark-util-chunked": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-1.0.0.tgz", + "integrity": "sha512-5e8xTis5tEZKgesfbQMKRCyzvffRRUX+lK/y+DvsMFdabAicPkkZV6gO+FEWi9RfuKKoxxPwNL+dFF0SMImc1g==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-symbol": "^1.0.0" + } + }, + "node_modules/micromark-util-classify-character": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-1.0.0.tgz", + "integrity": "sha512-F8oW2KKrQRb3vS5ud5HIqBVkCqQi224Nm55o5wYLzY/9PwHGXC01tr3d7+TqHHz6zrKQ72Okwtvm/xQm6OVNZA==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "node_modules/micromark-util-combine-extensions": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-1.0.0.tgz", + "integrity": "sha512-J8H058vFBdo/6+AsjHp2NF7AJ02SZtWaVUjsayNFeAiydTxUwViQPxN0Hf8dp4FmCQi0UUFovFsEyRSUmFH3MA==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-chunked": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "node_modules/micromark-util-decode-numeric-character-reference": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-1.0.0.tgz", + "integrity": "sha512-OzO9AI5VUtrTD7KSdagf4MWgHMtET17Ua1fIpXTpuhclCqD8egFWo85GxSGvxgkGS74bEahvtM0WP0HjvV0e4w==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-symbol": "^1.0.0" + } + }, + "node_modules/micromark-util-decode-string": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-1.0.2.tgz", + "integrity": "sha512-DLT5Ho02qr6QWVNYbRZ3RYOSSWWFuH3tJexd3dgN1odEuPNxCngTCXJum7+ViRAd9BbdxCvMToPOD/IvVhzG6Q==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "decode-named-character-reference": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-symbol": "^1.0.0" + } + }, + "node_modules/micromark-util-encode": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-1.0.1.tgz", + "integrity": "sha512-U2s5YdnAYexjKDel31SVMPbfi+eF8y1U4pfiRW/Y8EFVCy/vgxk/2wWTxzcqE71LHtCuCzlBDRU2a5CQ5j+mQA==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ] + }, + "node_modules/micromark-util-events-to-acorn": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/micromark-util-events-to-acorn/-/micromark-util-events-to-acorn-1.2.0.tgz", + "integrity": "sha512-WWp3bf7xT9MppNuw3yPjpnOxa8cj5ACivEzXJKu0WwnjBYfzaBvIAT9KfeyI0Qkll+bfQtfftSwdgTH6QhTOKw==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "@types/acorn": "^4.0.0", + "@types/estree": "^1.0.0", + "estree-util-visit": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0", + "vfile-location": "^4.0.0", + "vfile-message": "^3.0.0" + } + }, + "node_modules/micromark-util-events-to-acorn/node_modules/@types/estree": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.0.tgz", + "integrity": "sha512-WulqXMDUTYAXCjZnk6JtIHPigp55cVtDgDrO2gHRwhyJto21+1zbVCtOYB2L1F9w4qCQ0rOGWBnBe0FNTiEJIQ==", + "dev": true }, - "node_modules/memorizer": { - "version": "1.0.1", + "node_modules/micromark-util-html-tag-name": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-1.1.0.tgz", + "integrity": "sha512-BKlClMmYROy9UiV03SwNmckkjn8QHVaWkqoAqzivabvdGcwNGMMMH/5szAnywmsTBUzDsU57/mFi0sp4BQO6dA==", "dev": true, - "license": "MIT" + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ] }, - "node_modules/meow": { - "version": "6.1.1", + "node_modules/micromark-util-normalize-identifier": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-1.0.0.tgz", + "integrity": "sha512-yg+zrL14bBTFrQ7n35CmByWUTFsgst5JhA4gJYoty4Dqzj4Z4Fr/DHekSS5aLfH9bdlfnSvKAWsAgJhIbogyBg==", "dev": true, - "license": "MIT", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], "dependencies": { - "@types/minimist": "^1.2.0", - "camelcase-keys": "^6.2.2", - "decamelize-keys": "^1.1.0", - "hard-rejection": "^2.1.0", - "minimist-options": "^4.0.2", - "normalize-package-data": "^2.5.0", - "read-pkg-up": "^7.0.1", - "redent": "^3.0.0", - "trim-newlines": "^3.0.0", - "type-fest": "^0.13.1", - "yargs-parser": "^18.1.3" - }, - "engines": { - "node": ">=8" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "micromark-util-symbol": "^1.0.0" } }, - "node_modules/meow/node_modules/type-fest": { - "version": "0.13.1", + "node_modules/micromark-util-resolve-all": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-1.0.0.tgz", + "integrity": "sha512-CB/AGk98u50k42kvgaMM94wzBqozSzDDaonKU7P7jwQIuH2RU0TeBqGYJz2WY1UdihhjweivStrJ2JdkdEmcfw==", "dev": true, - "license": "(MIT OR CC0-1.0)", - "engines": { - "node": ">=10" - }, - "funding": { - "url": "https://github.com/sponsors/sindresorhus" + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-types": "^1.0.0" } }, - "node_modules/meow/node_modules/yargs-parser": { - "version": "18.1.3", + "node_modules/micromark-util-sanitize-uri": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-1.0.0.tgz", + "integrity": "sha512-cCxvBKlmac4rxCGx6ejlIviRaMKZc0fWm5HdCHEeDWRSkn44l6NdYVRyU+0nT1XC72EQJMZV8IPHF+jTr56lAg==", "dev": true, - "license": "ISC", + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], "dependencies": { - "camelcase": "^5.0.0", - "decamelize": "^1.2.0" - }, - "engines": { - "node": ">=6" + "micromark-util-character": "^1.0.0", + "micromark-util-encode": "^1.0.0", + "micromark-util-symbol": "^1.0.0" } }, - "node_modules/merge-descriptors": { - "version": "1.0.1", - "license": "MIT" - }, - "node_modules/merge-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", - "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==" - }, - "node_modules/merge2": { - "version": "1.4.1", + "node_modules/micromark-util-subtokenize": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-1.0.2.tgz", + "integrity": "sha512-d90uqCnXp/cy4G881Ub4psE57Sf8YD0pim9QdjCRNjfas2M1u6Lbt+XZK9gnHL2XFhnozZiEdCa9CNfXSfQ6xA==", "dev": true, - "license": "MIT", - "engines": { - "node": ">= 8" + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "micromark-util-chunked": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0" } }, - "node_modules/meros": { - "version": "1.2.0", + "node_modules/micromark-util-symbol": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-1.0.1.tgz", + "integrity": "sha512-oKDEMK2u5qqAptasDAwWDXq0tG9AssVwAx3E9bBF3t/shRIGsWIRG+cGafs2p/SnDSOecnt6hZPCE2o6lHfFmQ==", "dev": true, - "license": "MIT", - "engines": { - "node": ">=12" - }, - "peerDependencies": { - "@types/node": ">=12" - }, - "peerDependenciesMeta": { - "@types/node": { - "optional": true + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" } - } + ] }, - "node_modules/methods": { - "version": "1.1.2", - "license": "MIT", - "engines": { - "node": ">= 0.6" - } + "node_modules/micromark-util-types": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-1.0.2.tgz", + "integrity": "sha512-DCfg/T8fcrhrRKTPjRrw/5LLvdGV7BHySf/1LOZx7TzWZdYRjogNtyNq885z3nNallwr3QUKARjqvHqX1/7t+w==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ] }, "node_modules/micromatch": { "version": "4.0.5", @@ -12390,6 +13804,15 @@ "mkdirp": "bin/cmd.js" } }, + "node_modules/mri": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mri/-/mri-1.2.0.tgz", + "integrity": "sha512-tzzskb3bG8LvYGFF/mDTpq3jpI6Q9wc3LEmBaghu+DdCssd1FakN7Bc0hVNmEyGq1bq3RgfkCb3cmQLpNPOroA==", + "dev": true, + "engines": { + "node": ">=4" + } + }, "node_modules/ms": { "version": "2.1.2", "license": "MIT" @@ -12664,6 +14087,23 @@ "url": "https://github.com/sponsors/sindresorhus" } }, + "node_modules/open": { + "version": "8.4.0", + "resolved": "https://registry.npmjs.org/open/-/open-8.4.0.tgz", + "integrity": "sha512-XgFPPM+B28FtCCgSb9I+s9szOC1vZRSwgWsRUA5ylIxRTgKozqjOCrVOqGsYABPYK5qnfqClxZTFBa8PKt2v6Q==", + "dev": true, + "dependencies": { + "define-lazy-prop": "^2.0.0", + "is-docker": "^2.1.1", + "is-wsl": "^2.2.0" + }, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/optimism": { "version": "0.16.1", "license": "MIT", @@ -12809,6 +14249,24 @@ "node": ">=8" } }, + "node_modules/parse-entities": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-2.0.0.tgz", + "integrity": "sha512-kkywGpCcRYhqQIchaWqZ875wzpS/bMKhz5HnN3p7wveJTkTtyAB/AlnS0f8DFSqYW1T82t6yEAkEcB+A1I3MbQ==", + "dev": true, + "dependencies": { + "character-entities": "^1.0.0", + "character-entities-legacy": "^1.0.0", + "character-reference-invalid": "^1.0.0", + "is-alphanumerical": "^1.0.0", + "is-decimal": "^1.0.0", + "is-hexadecimal": "^1.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/parse-filepath": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/parse-filepath/-/parse-filepath-1.0.2.tgz", @@ -13054,6 +14512,18 @@ "url": "https://github.com/prettier/prettier?sponsor=1" } }, + "node_modules/prettier-linter-helpers": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/prettier-linter-helpers/-/prettier-linter-helpers-1.0.0.tgz", + "integrity": "sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w==", + "dev": true, + "dependencies": { + "fast-diff": "^1.1.2" + }, + "engines": { + "node": ">=6.0.0" + } + }, "node_modules/pretty-format": { "version": "28.1.3", "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-28.1.3.tgz", @@ -13472,6 +14942,132 @@ "invariant": "^2.2.4" } }, + "node_modules/remark-mdx": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/remark-mdx/-/remark-mdx-2.1.3.tgz", + "integrity": "sha512-3SmtXOy9+jIaVctL8Cs3VAQInjRLGOwNXfrBB9KCT+EpJpKD3PQiy0x8hUNGyjQmdyOs40BqgPU7kYtH9uoR6w==", + "dev": true, + "dependencies": { + "mdast-util-mdx": "^2.0.0", + "micromark-extension-mdxjs": "^1.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-parse": { + "version": "10.0.1", + "resolved": "https://registry.npmjs.org/remark-parse/-/remark-parse-10.0.1.tgz", + "integrity": "sha512-1fUyHr2jLsVOkhbvPRBJ5zTKZZyD6yZzYaWCS6BPBdQ8vEMBCH+9zNCDA6tET/zHCi/jLqjCWtlJZUPk+DbnFw==", + "dev": true, + "dependencies": { + "@types/mdast": "^3.0.0", + "mdast-util-from-markdown": "^1.0.0", + "unified": "^10.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-parse/node_modules/mdast-util-from-markdown": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-1.2.0.tgz", + "integrity": "sha512-iZJyyvKD1+K7QX1b5jXdE7Sc5dtoTry1vzV28UZZe8Z1xVnB/czKntJ7ZAkG0tANqRnBF6p3p7GpU1y19DTf2Q==", + "dev": true, + "dependencies": { + "@types/mdast": "^3.0.0", + "@types/unist": "^2.0.0", + "decode-named-character-reference": "^1.0.0", + "mdast-util-to-string": "^3.1.0", + "micromark": "^3.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-decode-string": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-stringify-position": "^3.0.0", + "uvu": "^0.5.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-parse/node_modules/mdast-util-to-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.1.0.tgz", + "integrity": "sha512-n4Vypz/DZgwo0iMHLQL49dJzlp7YtAJP+N07MZHpjPf/5XJuHUWstviF4Mn2jEiR/GNmtnRRqnwsXExk3igfFA==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-parse/node_modules/micromark": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-3.0.10.tgz", + "integrity": "sha512-ryTDy6UUunOXy2HPjelppgJ2sNfcPz1pLlMdA6Rz9jPzhLikWXv/irpWV/I2jd68Uhmny7hHxAlAhk4+vWggpg==", + "dev": true, + "funding": [ + { + "type": "GitHub Sponsors", + "url": "https://github.com/sponsors/unifiedjs" + }, + { + "type": "OpenCollective", + "url": "https://opencollective.com/unified" + } + ], + "dependencies": { + "@types/debug": "^4.0.0", + "debug": "^4.0.0", + "decode-named-character-reference": "^1.0.0", + "micromark-core-commonmark": "^1.0.1", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-chunked": "^1.0.0", + "micromark-util-combine-extensions": "^1.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-encode": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-resolve-all": "^1.0.0", + "micromark-util-sanitize-uri": "^1.0.0", + "micromark-util-subtokenize": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.1", + "uvu": "^0.5.0" + } + }, + "node_modules/remark-parse/node_modules/unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/remark-stringify": { + "version": "10.0.2", + "resolved": "https://registry.npmjs.org/remark-stringify/-/remark-stringify-10.0.2.tgz", + "integrity": "sha512-6wV3pvbPvHkbNnWB0wdDvVFHOe1hBRAx1Q/5g/EpH4RppAII6J8Gnwe7VbHuXaoKIF6LAg6ExTel/+kNqSQ7lw==", + "dev": true, + "dependencies": { + "@types/mdast": "^3.0.0", + "mdast-util-to-markdown": "^1.0.0", + "unified": "^10.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, "node_modules/remedial": { "version": "1.0.8", "dev": true, @@ -13812,6 +15408,18 @@ "tslib": "^2.1.0" } }, + "node_modules/sade": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/sade/-/sade-1.8.1.tgz", + "integrity": "sha512-xal3CZX1Xlo/k4ApwCFrHVACi9fBqJ7V+mwhBsuf/1IOKbBy098Fex+Wa/5QMubw09pSZ/u8EY8PWgevJsXp1A==", + "dev": true, + "dependencies": { + "mri": "^1.1.0" + }, + "engines": { + "node": ">=6" + } + }, "node_modules/safe-buffer": { "version": "5.2.1", "funding": [ @@ -14423,6 +16031,30 @@ "url": "https://github.com/sponsors/ljharb" } }, + "node_modules/stringify-entities": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/stringify-entities/-/stringify-entities-4.0.3.tgz", + "integrity": "sha512-BP9nNHMhhfcMbiuQKCqMjhDP5yBCAxsPu4pHFFzJ6Alo9dZgY4VLDPutXqIjpRiMoKdp7Av85Gr73Q5uH9k7+g==", + "dev": true, + "dependencies": { + "character-entities-html4": "^2.0.0", + "character-entities-legacy": "^3.0.0" + }, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, + "node_modules/stringify-entities/node_modules/character-entities-legacy": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", + "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/strip-ansi": { "version": "6.0.1", "license": "MIT", @@ -14579,6 +16211,22 @@ "node": ">=0.10" } }, + "node_modules/synckit": { + "version": "0.8.4", + "resolved": "https://registry.npmjs.org/synckit/-/synckit-0.8.4.tgz", + "integrity": "sha512-Dn2ZkzMdSX827QbowGbU/4yjWuvNaCoScLLoMo/yKbu+P4GBR6cRGKZH27k6a9bRzdqcyd1DE96pQtQ6uNkmyw==", + "dev": true, + "dependencies": { + "@pkgr/utils": "^2.3.1", + "tslib": "^2.4.0" + }, + "engines": { + "node": "^14.18.0 || >=16.0.0" + }, + "funding": { + "url": "https://opencollective.com/unts" + } + }, "node_modules/tar": { "version": "6.1.11", "resolved": "https://registry.npmjs.org/tar/-/tar-6.1.11.tgz", @@ -14719,6 +16367,16 @@ "dev": true, "license": "MIT" }, + "node_modules/tiny-glob": { + "version": "0.2.9", + "resolved": "https://registry.npmjs.org/tiny-glob/-/tiny-glob-0.2.9.tgz", + "integrity": "sha512-g/55ssRPUjShh+xkfx9UPDXqhckHEsHr4Vd9zX55oSdGZc/MD0m3sferOkwWtp98bv+kcVfEHtRJgBVJzelrzg==", + "dev": true, + "dependencies": { + "globalyzer": "0.1.0", + "globrex": "^0.1.2" + } + }, "node_modules/title-case": { "version": "3.0.3", "dev": true, @@ -14787,6 +16445,16 @@ "node": ">=8" } }, + "node_modules/trough": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/trough/-/trough-2.1.0.tgz", + "integrity": "sha512-AqTiAOLcj85xS7vQ8QkAV41hPDIJ71XJB4RCUrzo/1GM2CQwhkJGaf9Hgr7BOugMRpgGUrqRg/DrBDl4H40+8g==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "node_modules/ts-graphviz": { "version": "0.16.0", "resolved": "https://registry.npmjs.org/ts-graphviz/-/ts-graphviz-0.16.0.tgz", @@ -15110,6 +16778,37 @@ "node": ">=12.18" } }, + "node_modules/unified": { + "version": "10.1.2", + "resolved": "https://registry.npmjs.org/unified/-/unified-10.1.2.tgz", + "integrity": "sha512-pUSWAi/RAnVy1Pif2kAoeWNBa3JVrx0MId2LASj8G+7AiHWoKZNTomq6LG326T68U7/e263X6fTdcXIy7XnF7Q==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0", + "bail": "^2.0.0", + "extend": "^3.0.0", + "is-buffer": "^2.0.0", + "is-plain-obj": "^4.0.0", + "trough": "^2.0.0", + "vfile": "^5.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unified/node_modules/is-plain-obj": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz", + "integrity": "sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==", + "dev": true, + "engines": { + "node": ">=12" + }, + "funding": { + "url": "https://github.com/sponsors/sindresorhus" + } + }, "node_modules/unique-filename": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/unique-filename/-/unique-filename-1.1.1.tgz", @@ -15140,6 +16839,85 @@ "node": ">=8" } }, + "node_modules/unist-util-is": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-5.1.1.tgz", + "integrity": "sha512-F5CZ68eYzuSvJjGhCLPL3cYx45IxkqXSetCcRgUXtbcm50X2L9oOWQlfUfDdAf+6Pd27YDblBfdtmsThXmwpbQ==", + "dev": true, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-position-from-estree": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/unist-util-position-from-estree/-/unist-util-position-from-estree-1.1.1.tgz", + "integrity": "sha512-xtoY50b5+7IH8tFbkw64gisG9tMSpxDjhX9TmaJJae/XuxQ9R/Kc8Nv1eOsf43Gt4KV/LkriMy9mptDr7XLcaw==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-remove-position": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/unist-util-remove-position/-/unist-util-remove-position-4.0.1.tgz", + "integrity": "sha512-0yDkppiIhDlPrfHELgB+NLQD5mfjup3a8UYclHruTJWmY74je8g+CIFr79x5f6AkmzSwlvKLbs63hC0meOMowQ==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0", + "unist-util-visit": "^4.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-stringify-position": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-2.0.3.tgz", + "integrity": "sha512-3faScn5I+hy9VleOq/qNbAd6pAx7iH5jYBMS9I1HgQVijz/4mv5Bvw5iw1sC/90CODiKo81G/ps8AJrISn687g==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.2" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-visit": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-4.1.1.tgz", + "integrity": "sha512-n9KN3WV9k4h1DxYR1LoajgN93wpEi/7ZplVe02IoB4gH5ctI1AaF2670BLHQYbwj+pY83gFtyeySFiyMHJklrg==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0", + "unist-util-is": "^5.0.0", + "unist-util-visit-parents": "^5.1.1" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/unist-util-visit-parents": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-5.1.1.tgz", + "integrity": "sha512-gks4baapT/kNRaWxuGkl5BIhoanZo7sC/cUT/JToSRNL1dYoXRFl75d++NkjYk4TAu2uv2Px+l8guMajogeuiw==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0", + "unist-util-is": "^5.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, "node_modules/universalify": { "version": "0.1.2", "dev": true, @@ -15229,6 +17007,42 @@ "uuid": "dist/bin/uuid" } }, + "node_modules/uvu": { + "version": "0.5.6", + "resolved": "https://registry.npmjs.org/uvu/-/uvu-0.5.6.tgz", + "integrity": "sha512-+g8ENReyr8YsOc6fv/NVJs2vFdHBnBNdfE49rshrTzDWOlUx4Gq7KOS2GD8eqhy2j+Ejq29+SbKH8yjkAqXqoA==", + "dev": true, + "dependencies": { + "dequal": "^2.0.0", + "diff": "^5.0.0", + "kleur": "^4.0.3", + "sade": "^1.7.3" + }, + "bin": { + "uvu": "bin.js" + }, + "engines": { + "node": ">=8" + } + }, + "node_modules/uvu/node_modules/diff": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/diff/-/diff-5.1.0.tgz", + "integrity": "sha512-D+mk+qE8VC/PAUrlAU34N+VfXev0ghe5ywmpqrawphmVZc1bEfn56uo9qpyGp1p4xpzOHkSW4ztBd6L7Xx4ACw==", + "dev": true, + "engines": { + "node": ">=0.3.1" + } + }, + "node_modules/uvu/node_modules/kleur": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/kleur/-/kleur-4.1.5.tgz", + "integrity": "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==", + "dev": true, + "engines": { + "node": ">=6" + } + }, "node_modules/v8-compile-cache-lib": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", @@ -15291,6 +17105,76 @@ "license": "MIT", "peer": true }, + "node_modules/vfile": { + "version": "5.3.5", + "resolved": "https://registry.npmjs.org/vfile/-/vfile-5.3.5.tgz", + "integrity": "sha512-U1ho2ga33eZ8y8pkbQLH54uKqGhFJ6GYIHnnG5AhRpAh3OWjkrRHKa/KogbmQn8We+c0KVV3rTOgR9V/WowbXQ==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0", + "is-buffer": "^2.0.0", + "unist-util-stringify-position": "^3.0.0", + "vfile-message": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vfile-location": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/vfile-location/-/vfile-location-4.0.1.tgz", + "integrity": "sha512-JDxPlTbZrZCQXogGheBHjbRWjESSPEak770XwWPfw5mTc1v1nWGLB/apzZxsx8a0SJVfF8HK8ql8RD308vXRUw==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0", + "vfile": "^5.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vfile-message": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-3.1.2.tgz", + "integrity": "sha512-QjSNP6Yxzyycd4SVOtmKKyTsSvClqBPJcd00Z0zuPj3hOIjg0rUPG6DbFGPvUKRgYyaIWLPKpuEclcuvb3H8qA==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0", + "unist-util-stringify-position": "^3.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vfile-message/node_modules/unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, + "node_modules/vfile/node_modules/unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "dependencies": { + "@types/unist": "^2.0.0" + }, + "funding": { + "type": "opencollective", + "url": "https://opencollective.com/unified" + } + }, "node_modules/vscode-languageserver-textdocument": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/vscode-languageserver-textdocument/-/vscode-languageserver-textdocument-1.0.7.tgz", @@ -15611,6 +17495,16 @@ "zen-observable": "0.8.15" } }, + "node_modules/zwitch": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/zwitch/-/zwitch-2.0.2.tgz", + "integrity": "sha512-JZxotl7SxAJH0j7dN4pxsTV6ZLXoLdGME+PsjkL/DaBrVryK9kTGq06GfKrwcSOqypP+fdXGoCHE36b99fWVoA==", + "dev": true, + "funding": { + "type": "github", + "url": "https://github.com/sponsors/wooorm" + } + }, "packages/integration-testsuite": { "name": "@apollo/server-integration-testsuite", "version": "4.0.0-alpha.11", @@ -18826,6 +20720,20 @@ "webcrypto-core": "^1.7.4" } }, + "@pkgr/utils": { + "version": "2.3.1", + "resolved": "https://registry.npmjs.org/@pkgr/utils/-/utils-2.3.1.tgz", + "integrity": "sha512-wfzX8kc1PMyUILA+1Z/EqoE4UCXGy0iRGMhPwdfae1+f0OXlLqCk+By+aMzgJBzR9AzS4CDizioG6Ss1gvAFJw==", + "dev": true, + "requires": { + "cross-spawn": "^7.0.3", + "is-glob": "^4.0.3", + "open": "^8.4.0", + "picocolors": "^1.0.0", + "tiny-glob": "^0.2.9", + "tslib": "^2.4.0" + } + }, "@protobufjs/aspromise": { "version": "1.1.2" }, @@ -18947,6 +20855,15 @@ "integrity": "sha512-yOlFc+7UtL/89t2ZhjPvvB/DeAr3r+Dq58IgzsFkOAvVC6NMJXmCGjbptdXdR9qsX7pKcTL+s87FtYREi2dEEQ==", "devOptional": true }, + "@types/acorn": { + "version": "4.0.6", + "resolved": "https://registry.npmjs.org/@types/acorn/-/acorn-4.0.6.tgz", + "integrity": "sha512-veQTnWP+1D/xbxVrPC3zHnCZRjSrKfhbMUlEA43iMZLu7EsnTtkJklIuwrCPbOi8YkvDQAiW05VQQFvvz9oieQ==", + "dev": true, + "requires": { + "@types/estree": "*" + } + }, "@types/async-retry": { "version": "1.4.5", "resolved": "https://registry.npmjs.org/@types/async-retry/-/async-retry-1.4.5.tgz", @@ -19020,10 +20937,28 @@ "version": "2.8.12", "dev": true }, + "@types/debug": { + "version": "4.1.7", + "resolved": "https://registry.npmjs.org/@types/debug/-/debug-4.1.7.tgz", + "integrity": "sha512-9AonUzyTjXXhEOa0DnqpzZi6VHlqKMswga9EXjpXnnqxwLtdvPPtlO8evrI5D9S6asFRCQ6v+wpiUKbw+vKqyg==", + "dev": true, + "requires": { + "@types/ms": "*" + } + }, "@types/estree": { "version": "0.0.39", "dev": true }, + "@types/estree-jsx": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@types/estree-jsx/-/estree-jsx-1.0.0.tgz", + "integrity": "sha512-3qvGd0z8F2ENTGr/GG1yViqfiKmRfrXVx5sJyHGFu3z7m5g5utCQtGp/g29JnjflhtQJBv1WDQukHiT58xPcYQ==", + "dev": true, + "requires": { + "@types/estree": "*" + } + }, "@types/express": { "version": "4.17.14", "resolved": "https://registry.npmjs.org/@types/express/-/express-4.17.14.tgz", @@ -19053,6 +20988,15 @@ "@types/node": "*" } }, + "@types/hast": { + "version": "2.3.4", + "resolved": "https://registry.npmjs.org/@types/hast/-/hast-2.3.4.tgz", + "integrity": "sha512-wLEm0QvaoawEDoTRwzTXp4b4jpwiJDvR5KMnFnVodm3scufTlBOWRD6N1OBf9TZMhjlNsSfcO5V+7AF4+Vy+9g==", + "dev": true, + "requires": { + "@types/unist": "*" + } + }, "@types/is-ci": { "version": "3.0.0", "dev": true, @@ -19173,6 +21117,15 @@ "@types/long": { "version": "4.0.1" }, + "@types/mdast": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/@types/mdast/-/mdast-3.0.10.tgz", + "integrity": "sha512-W864tg/Osz1+9f4lrGTZpCSO5/z4608eUp19tbozkq2HJK6i3z1kT0H9tlADXuYIb1YYOBByU4Jsqkk75q48qA==", + "dev": true, + "requires": { + "@types/unist": "*" + } + }, "@types/mime": { "version": "1.3.2" }, @@ -19180,6 +21133,12 @@ "version": "1.2.2", "dev": true }, + "@types/ms": { + "version": "0.7.31", + "resolved": "https://registry.npmjs.org/@types/ms/-/ms-0.7.31.tgz", + "integrity": "sha512-iiUgKzV9AuaEkZqkOLDIvlQiL6ltuZd9tGcW3gwpnX8JbuiuhFlEGmmFXEXkN50Cvq7Os88IY2v0dkDqXYWVgA==", + "dev": true + }, "@types/negotiator": { "version": "0.6.1", "dev": true @@ -19305,6 +21264,12 @@ "@types/node": "*" } }, + "@types/unist": { + "version": "2.0.6", + "resolved": "https://registry.npmjs.org/@types/unist/-/unist-2.0.6.tgz", + "integrity": "sha512-PBjIUxZHOuj0R15/xuwJYjFi+KZdNFrehocChv4g5hu6aFroHue8m0lBP0POdK2nKzbw0cgV1mws8+V/JAcEkQ==", + "dev": true + }, "@types/uuid": { "version": "8.3.4", "dev": true @@ -20701,6 +22666,12 @@ "babel-preset-current-node-syntax": "^1.0.0" } }, + "bail": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/bail/-/bail-2.0.2.tgz", + "integrity": "sha512-0xO6mYd7JB2YesxDKplafRpsiOzPt9V02ddPCLbY1xYGPOX24NTyN50qnUxgCPcSoYMhKpAuBTjQoRZCAkUDRw==", + "dev": true + }, "balanced-match": { "version": "1.0.2" }, @@ -20965,6 +22936,12 @@ "dev": true, "peer": true }, + "ccount": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/ccount/-/ccount-2.0.1.tgz", + "integrity": "sha512-eyrF0jiFpY+3drT6383f1qhkbGsLSifNAjA61IUjZjmLCWjItY6LB9ft9YhoDgwfmclB2zhu51Lc7+95b8NRAg==", + "dev": true + }, "chalk": { "version": "4.1.2", "requires": { @@ -21011,6 +22988,30 @@ "resolved": "https://registry.npmjs.org/char-regex/-/char-regex-1.0.2.tgz", "integrity": "sha512-kWWXztvZ5SBQV+eRgKFeh8q5sLuZY2+8WUIzlxWVTg+oGwY14qylx1KbKzHd8P6ZYkAg0xyIDU9JMHhyJMZ1jw==" }, + "character-entities": { + "version": "1.2.4", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-1.2.4.tgz", + "integrity": "sha512-iBMyeEHxfVnIakwOuDXpVkc54HijNgCyQB2w0VfGQThle6NXn50zU6V/u+LDhxHcDUPojn6Kpga3PTAD8W1bQw==", + "dev": true + }, + "character-entities-html4": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/character-entities-html4/-/character-entities-html4-2.1.0.tgz", + "integrity": "sha512-1v7fgQRj6hnSwFpq1Eu0ynr/CDEw0rXo2B61qXrLNdHZmPKgb7fqS1a2JwF0rISo9q77jDI8VMEHoApn8qDoZA==", + "dev": true + }, + "character-entities-legacy": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-1.1.4.tgz", + "integrity": "sha512-3Xnr+7ZFS1uxeiUDvV02wQ+QDbc55o97tIV5zHScSPJpcLm/r0DFPcoY3tYRp+VZukxuMeKgXYmsXQHO05zQeA==", + "dev": true + }, + "character-reference-invalid": { + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-1.1.4.tgz", + "integrity": "sha512-mKKUkUbhPpQlCOfIuZkvSEgktjPFIsZKRRbC6KWVEMvlzblj3i3asQv5ODsrwt0N3pHAEvjP8KTQPHkp0+6jOg==", + "dev": true + }, "chardet": { "version": "0.7.0", "dev": true @@ -21644,6 +23645,23 @@ } } }, + "decode-named-character-reference": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/decode-named-character-reference/-/decode-named-character-reference-1.0.2.tgz", + "integrity": "sha512-O8x12RzrUF8xyVcY0KJowWsmaJxQbmy0/EtnNtHRpsOcT7dFk5W598coHqBVpmWo1oQQfsCqfCmkZN5DJrZVdg==", + "dev": true, + "requires": { + "character-entities": "^2.0.0" + }, + "dependencies": { + "character-entities": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz", + "integrity": "sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==", + "dev": true + } + } + }, "dedent": { "version": "0.7.0", "resolved": "https://registry.npmjs.org/dedent/-/dedent-0.7.0.tgz", @@ -21688,6 +23706,12 @@ "clone": "^1.0.2" } }, + "define-lazy-prop": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/define-lazy-prop/-/define-lazy-prop-2.0.0.tgz", + "integrity": "sha512-Ds09qNh8yw3khSjiJjiUInaGX9xlqZDY7JVryGxdxV7NPeuqQfplOpQ66yJFZut3jLa5zOwkXw1g9EI2uKh4Og==", + "dev": true + }, "define-properties": { "version": "1.1.4", "dev": true, @@ -21708,6 +23732,12 @@ "integrity": "sha512-JeMq7fEshyepOWDfcfHK06N3MhyPhz++vtqWhMT5O9A3K42rdsEDpfdVqjaqaAhsw6a+ZqeDvQVtD0hFHQWrzg==", "dev": true }, + "dequal": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/dequal/-/dequal-2.0.3.tgz", + "integrity": "sha512-0je+qPKHEMohvfRTCEo3CrPG6cAzAYgmzKyxRiYSSDkS6eGJdyVJm7WaYA5ECaAD9wLB2T4EEeymA5aFVcYXCA==", + "dev": true + }, "destroy": { "version": "1.2.0" }, @@ -22121,6 +24151,13 @@ } } }, + "eslint-config-prettier": { + "version": "8.5.0", + "resolved": "https://registry.npmjs.org/eslint-config-prettier/-/eslint-config-prettier-8.5.0.tgz", + "integrity": "sha512-obmWKLUNCnhtQRKc+tmnYuQl0pFU1ibYJQ5BGhTVB08bHe9wC8qUeG7c08dj9XX+AuPj1YSGSQIHl1pnDHZR0Q==", + "dev": true, + "requires": {} + }, "eslint-import-resolver-node": { "version": "0.3.6", "dev": true, @@ -22138,6 +24175,28 @@ } } }, + "eslint-mdx": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/eslint-mdx/-/eslint-mdx-2.0.4.tgz", + "integrity": "sha512-SEgeWByCKYNRSqV+FtxHIcBadW7xCDtfZVACEZgFN1woGuPbr1XQicUMHO5pE0LSSQfWNHXTXP9MCMBkRRVS4A==", + "dev": true, + "requires": { + "acorn": "^8.8.0", + "acorn-jsx": "^5.3.2", + "cosmiconfig": "^7.0.1", + "espree": "^9.4.0", + "estree-util-visit": "^1.2.0", + "remark-mdx": "^2.1.3", + "remark-parse": "^10.0.1", + "remark-stringify": "^10.0.2", + "synckit": "^0.8.4", + "tslib": "^2.4.0", + "unified": "^10.1.2", + "unist-util-visit": "^4.1.1", + "uvu": "^0.5.6", + "vfile": "^5.3.4" + } + }, "eslint-module-utils": { "version": "2.7.3", "dev": true, @@ -22248,6 +24307,40 @@ } } }, + "eslint-plugin-markdown": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/eslint-plugin-markdown/-/eslint-plugin-markdown-3.0.0.tgz", + "integrity": "sha512-hRs5RUJGbeHDLfS7ELanT0e29Ocyssf/7kBM+p7KluY5AwngGkDf8Oyu4658/NZSGTTq05FZeWbkxXtbVyHPwg==", + "dev": true, + "requires": { + "mdast-util-from-markdown": "^0.8.5" + } + }, + "eslint-plugin-mdx": { + "version": "2.0.4", + "resolved": "https://registry.npmjs.org/eslint-plugin-mdx/-/eslint-plugin-mdx-2.0.4.tgz", + "integrity": "sha512-dDxtpaQl4EFAj8pZKa3Wk5s6QH2wz22Ba25j4OtW40zkB2Bb/Su/8xWoikF61bZoL99Y3aUV24eUTS39n0PJLQ==", + "dev": true, + "requires": { + "eslint-mdx": "^2.0.4", + "eslint-plugin-markdown": "^3.0.0", + "remark-mdx": "^2.1.3", + "remark-parse": "^10.0.1", + "remark-stringify": "^10.0.2", + "tslib": "^2.4.0", + "unified": "^10.1.2", + "vfile": "^5.3.4" + } + }, + "eslint-plugin-prettier": { + "version": "4.2.1", + "resolved": "https://registry.npmjs.org/eslint-plugin-prettier/-/eslint-plugin-prettier-4.2.1.tgz", + "integrity": "sha512-f/0rXLXUt0oFYs8ra4w49wYZBG5GKZpAYsJSm6rnYL5uVDjd+zowwMwVZHnAjf4edNrKpCDYfXDgmRE/Ak7QyQ==", + "dev": true, + "requires": { + "prettier-linter-helpers": "^1.0.0" + } + }, "eslint-scope": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-5.1.1.tgz", @@ -22325,6 +24418,22 @@ "integrity": "sha512-39nnKffWz8xN1BU/2c79n9nB9HDzo0niYUqx6xyqUnyoAnQyyWpOTdZEeiCch8BBu515t4wp9ZmgVfVhn9EBpw==", "dev": true }, + "estree-util-is-identifier-name": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/estree-util-is-identifier-name/-/estree-util-is-identifier-name-2.0.1.tgz", + "integrity": "sha512-rxZj1GkQhY4x1j/CSnybK9cGuMFQYFPLq0iNyopqf14aOVLFtMv7Esika+ObJWPWiOHuMOAHz3YkWoLYYRnzWQ==", + "dev": true + }, + "estree-util-visit": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/estree-util-visit/-/estree-util-visit-1.2.0.tgz", + "integrity": "sha512-wdsoqhWueuJKsh5hqLw3j8lwFqNStm92VcwtAOAny8g/KS/l5Y8RISjR4k5W6skCj3Nirag/WUCMS0Nfy3sgsg==", + "dev": true, + "requires": { + "@types/estree-jsx": "^1.0.0", + "@types/unist": "^2.0.0" + } + }, "estree-walker": { "version": "2.0.2", "dev": true @@ -22433,8 +24542,7 @@ }, "extend": { "version": "3.0.2", - "dev": true, - "peer": true + "dev": true }, "extendable-error": { "version": "0.1.7", @@ -22464,6 +24572,12 @@ "version": "3.1.3", "dev": true }, + "fast-diff": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/fast-diff/-/fast-diff-1.2.0.tgz", + "integrity": "sha512-xJuoT5+L99XlZ8twedaRf6Ax2TgQVxvgZOYoPKqZufmJib0tL2tegPBOZb1pVNgIhlqDlA0eO0c3wBvQcmzx4w==", + "dev": true + }, "fast-equals": { "version": "4.0.3", "resolved": "https://registry.npmjs.org/fast-equals/-/fast-equals-4.0.3.tgz", @@ -22825,6 +24939,12 @@ "globals": { "version": "11.12.0" }, + "globalyzer": { + "version": "0.1.0", + "resolved": "https://registry.npmjs.org/globalyzer/-/globalyzer-0.1.0.tgz", + "integrity": "sha512-40oNTM9UfG6aBmuKxk/giHn5nQ8RVz/SS4Ir6zgzOv9/qC3kKZ9v4etGTcJbEl/NyVQH7FGU7d+X1egr57Md2Q==", + "dev": true + }, "globby": { "version": "11.1.0", "dev": true, @@ -22837,6 +24957,12 @@ "slash": "^3.0.0" } }, + "globrex": { + "version": "0.1.2", + "resolved": "https://registry.npmjs.org/globrex/-/globrex-0.1.2.tgz", + "integrity": "sha512-uHJgbwAMwNFf5mLst7IWLNg14x1CkeqglJb/K3doi4dw6q2IvAAmM/Y81kevy83wP+Sst+nutFTYOGg3d1lsxg==", + "dev": true + }, "graceful-fs": { "version": "4.2.10" }, @@ -23212,6 +25338,22 @@ "is-windows": "^1.0.1" } }, + "is-alphabetical": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-1.0.4.tgz", + "integrity": "sha512-DwzsA04LQ10FHTZuL0/grVDk4rFoVH1pjAToYwBrHSxcrBIGQuXrQMtD5U1b0U2XVgKZCTLLP8u2Qxqhy3l2Vg==", + "dev": true + }, + "is-alphanumerical": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-1.0.4.tgz", + "integrity": "sha512-UzoZUr+XfVz3t3v4KyGEniVL9BDRoQtY7tOyrRybkVNjDFWyo1yhXNGrrBTQxp3ib9BLAWs7k2YKBQsFRkZG9A==", + "dev": true, + "requires": { + "is-alphabetical": "^1.0.0", + "is-decimal": "^1.0.0" + } + }, "is-arguments": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/is-arguments/-/is-arguments-1.1.1.tgz", @@ -23247,6 +25389,12 @@ "has-tostringtag": "^1.0.0" } }, + "is-buffer": { + "version": "2.0.5", + "resolved": "https://registry.npmjs.org/is-buffer/-/is-buffer-2.0.5.tgz", + "integrity": "sha512-i2R6zNFDwgEHJyQUtJEk0XFi1i0dPFn/oqjK3/vPCcDeJvW5NQ83V8QbicfF1SupOaB0h8ntgBC2YiE7dfyctQ==", + "dev": true + }, "is-callable": { "version": "1.2.4", "dev": true @@ -23271,6 +25419,18 @@ "has-tostringtag": "^1.0.0" } }, + "is-decimal": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-1.0.4.tgz", + "integrity": "sha512-RGdriMmQQvZ2aqaQq3awNA6dCGtKpiDFcOzrTWrDAT2MiWrKQVPmxLGHl7Y2nNu6led0kEyoX0enY0qXYsv9zw==", + "dev": true + }, + "is-docker": { + "version": "2.2.1", + "resolved": "https://registry.npmjs.org/is-docker/-/is-docker-2.2.1.tgz", + "integrity": "sha512-F+i2BKsFrH66iaUFc0woD8sLy8getkwTwtOBjvs56Cx4CgJDeKQeqfz8wAYiSb8JOprWhHH5p77PbmYCvvUuXQ==", + "dev": true + }, "is-extglob": { "version": "2.1.1", "dev": true @@ -23290,6 +25450,12 @@ "is-extglob": "^2.1.1" } }, + "is-hexadecimal": { + "version": "1.0.4", + "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-1.0.4.tgz", + "integrity": "sha512-gyPJuv83bHMpocVYoqof5VDiZveEoGoFL8m3BXNb2VW8Xs+rz9kqO8LOQ5DH6EsuvilT1ApazU0pyl+ytbPtlw==", + "dev": true + }, "is-interactive": { "version": "1.0.0", "dev": true @@ -23468,6 +25634,15 @@ "integrity": "sha512-eXK1UInq2bPmjyX6e3VHIzMLobc4J94i4AWn+Hpq3OU5KkrRC96OAcR3PRJ/pGu6m8TRnBHP9dkXQVsT/COVIA==", "dev": true }, + "is-wsl": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/is-wsl/-/is-wsl-2.2.0.tgz", + "integrity": "sha512-fKzAra0rGJUUBwGBgNkHZuToZcn+TtXHpeCgmkMJMMYx1sQDYaCSyjJBSCa2nH1DGm7s3n1oBnohoVTBaN7Lww==", + "dev": true, + "requires": { + "is-docker": "^2.0.0" + } + }, "isarray": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/isarray/-/isarray-2.0.5.tgz", @@ -24612,6 +26787,12 @@ "long": { "version": "4.0.0" }, + "longest-streak": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/longest-streak/-/longest-streak-3.0.1.tgz", + "integrity": "sha512-cHlYSUpL2s7Fb3394mYxwTYj8niTaNHUCLr0qdiCXQfSjfuA7CKofpX2uSwEfFDQ0EB7JcnMnm+GjbqqoinYYg==", + "dev": true + }, "loose-envify": { "version": "1.4.0", "requires": { @@ -24696,81 +26877,705 @@ } } }, - "makeerror": { - "version": "1.0.12", - "resolved": "https://registry.npmjs.org/makeerror/-/makeerror-1.0.12.tgz", - "integrity": "sha512-JmqCvUhmt43madlpFzG4BQzG2Z3m6tvQDNKdClZnO3VbIudJYmxsT0FNJMeiB2+JTSlTQTSbU8QdesVmwJcmLg==", + "makeerror": { + "version": "1.0.12", + "resolved": "https://registry.npmjs.org/makeerror/-/makeerror-1.0.12.tgz", + "integrity": "sha512-JmqCvUhmt43madlpFzG4BQzG2Z3m6tvQDNKdClZnO3VbIudJYmxsT0FNJMeiB2+JTSlTQTSbU8QdesVmwJcmLg==", + "requires": { + "tmpl": "1.0.5" + } + }, + "map-cache": { + "version": "0.2.2", + "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", + "integrity": "sha512-8y/eV9QQZCiyn1SprXSrCmqJN0yNRATe+PO8ztwqrvrbdRLA3eYJF0yaR0YayLWkMbsQSKWS9N2gPcGEc4UsZg==", + "dev": true + }, + "map-obj": { + "version": "4.3.0", + "dev": true + }, + "mdast-util-from-markdown": { + "version": "0.8.5", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-0.8.5.tgz", + "integrity": "sha512-2hkTXtYYnr+NubD/g6KGBS/0mFmBcifAsI0yIWRiRo0PjVs6SSOSOdtzbp6kSGnShDN6G5aWZpKQ2lWRy27mWQ==", + "dev": true, + "requires": { + "@types/mdast": "^3.0.0", + "mdast-util-to-string": "^2.0.0", + "micromark": "~2.11.0", + "parse-entities": "^2.0.0", + "unist-util-stringify-position": "^2.0.0" + } + }, + "mdast-util-mdx": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-mdx/-/mdast-util-mdx-2.0.0.tgz", + "integrity": "sha512-M09lW0CcBT1VrJUaF/PYxemxxHa7SLDHdSn94Q9FhxjCQfuW7nMAWKWimTmA3OyDMSTH981NN1csW1X+HPSluw==", + "dev": true, + "requires": { + "mdast-util-mdx-expression": "^1.0.0", + "mdast-util-mdx-jsx": "^2.0.0", + "mdast-util-mdxjs-esm": "^1.0.0" + } + }, + "mdast-util-mdx-expression": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/mdast-util-mdx-expression/-/mdast-util-mdx-expression-1.3.0.tgz", + "integrity": "sha512-9kTO13HaL/ChfzVCIEfDRdp1m5hsvsm6+R8yr67mH+KS2ikzZ0ISGLPTbTswOFpLLlgVHO9id3cul4ajutCvCA==", + "dev": true, + "requires": { + "@types/estree-jsx": "^1.0.0", + "@types/hast": "^2.0.0", + "@types/mdast": "^3.0.0", + "mdast-util-from-markdown": "^1.0.0", + "mdast-util-to-markdown": "^1.0.0" + }, + "dependencies": { + "mdast-util-from-markdown": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-1.2.0.tgz", + "integrity": "sha512-iZJyyvKD1+K7QX1b5jXdE7Sc5dtoTry1vzV28UZZe8Z1xVnB/czKntJ7ZAkG0tANqRnBF6p3p7GpU1y19DTf2Q==", + "dev": true, + "requires": { + "@types/mdast": "^3.0.0", + "@types/unist": "^2.0.0", + "decode-named-character-reference": "^1.0.0", + "mdast-util-to-string": "^3.1.0", + "micromark": "^3.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-decode-string": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-stringify-position": "^3.0.0", + "uvu": "^0.5.0" + } + }, + "mdast-util-to-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.1.0.tgz", + "integrity": "sha512-n4Vypz/DZgwo0iMHLQL49dJzlp7YtAJP+N07MZHpjPf/5XJuHUWstviF4Mn2jEiR/GNmtnRRqnwsXExk3igfFA==", + "dev": true + }, + "micromark": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-3.0.10.tgz", + "integrity": "sha512-ryTDy6UUunOXy2HPjelppgJ2sNfcPz1pLlMdA6Rz9jPzhLikWXv/irpWV/I2jd68Uhmny7hHxAlAhk4+vWggpg==", + "dev": true, + "requires": { + "@types/debug": "^4.0.0", + "debug": "^4.0.0", + "decode-named-character-reference": "^1.0.0", + "micromark-core-commonmark": "^1.0.1", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-chunked": "^1.0.0", + "micromark-util-combine-extensions": "^1.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-encode": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-resolve-all": "^1.0.0", + "micromark-util-sanitize-uri": "^1.0.0", + "micromark-util-subtokenize": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.1", + "uvu": "^0.5.0" + } + }, + "unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0" + } + } + } + }, + "mdast-util-mdx-jsx": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-mdx-jsx/-/mdast-util-mdx-jsx-2.1.0.tgz", + "integrity": "sha512-KzgzfWMhdteDkrY4mQtyvTU5bc/W4ppxhe9SzelO6QUUiwLAM+Et2Dnjjprik74a336kHdo0zKm7Tp+n6FFeRg==", + "dev": true, + "requires": { + "@types/estree-jsx": "^1.0.0", + "@types/hast": "^2.0.0", + "@types/mdast": "^3.0.0", + "ccount": "^2.0.0", + "mdast-util-to-markdown": "^1.3.0", + "parse-entities": "^4.0.0", + "stringify-entities": "^4.0.0", + "unist-util-remove-position": "^4.0.0", + "unist-util-stringify-position": "^3.0.0", + "vfile-message": "^3.0.0" + }, + "dependencies": { + "character-entities": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/character-entities/-/character-entities-2.0.2.tgz", + "integrity": "sha512-shx7oQ0Awen/BRIdkjkvz54PnEEI/EjwXDSIZp86/KKdbafHh1Df/RYGBhn4hbe2+uKC9FnT5UCEdyPz3ai9hQ==", + "dev": true + }, + "character-entities-legacy": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", + "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", + "dev": true + }, + "character-reference-invalid": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/character-reference-invalid/-/character-reference-invalid-2.0.1.tgz", + "integrity": "sha512-iBZ4F4wRbyORVsu0jPV7gXkOsGYjGHPmAyv+HiHG8gi5PtC9KI2j1+v8/tlibRvjoWX027ypmG/n0HtO5t7unw==", + "dev": true + }, + "is-alphabetical": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-2.0.1.tgz", + "integrity": "sha512-FWyyY60MeTNyeSRpkM2Iry0G9hpr7/9kD40mD/cGQEuilcZYS4okz8SN2Q6rLCJ8gbCt6fN+rC+6tMGS99LaxQ==", + "dev": true + }, + "is-alphanumerical": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-alphanumerical/-/is-alphanumerical-2.0.1.tgz", + "integrity": "sha512-hmbYhX/9MUMF5uh7tOXyK/n0ZvWpad5caBA17GsC6vyuCqaWliRG5K1qS9inmUhEMaOBIW7/whAnSwveW/LtZw==", + "dev": true, + "requires": { + "is-alphabetical": "^2.0.0", + "is-decimal": "^2.0.0" + } + }, + "is-decimal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-decimal/-/is-decimal-2.0.1.tgz", + "integrity": "sha512-AAB9hiomQs5DXWcRB1rqsxGUstbRroFOPPVAomNk/3XHR5JyEZChOyTWe2oayKnsSsr/kcGqF+z6yuH6HHpN0A==", + "dev": true + }, + "is-hexadecimal": { + "version": "2.0.1", + "resolved": "https://registry.npmjs.org/is-hexadecimal/-/is-hexadecimal-2.0.1.tgz", + "integrity": "sha512-DgZQp241c8oO6cA1SbTEWiXeoxV42vlcJxgH+B3hi1AiqqKruZR3ZGF8In3fj4+/y/7rHvlOZLZtgJ/4ttYGZg==", + "dev": true + }, + "parse-entities": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-4.0.0.tgz", + "integrity": "sha512-5nk9Fn03x3rEhGaX1FU6IDwG/k+GxLXlFAkgrbM1asuAFl3BhdQWvASaIsmwWypRNcZKHPYnIuOSfIWEyEQnPQ==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "character-entities": "^2.0.0", + "character-entities-legacy": "^3.0.0", + "character-reference-invalid": "^2.0.0", + "decode-named-character-reference": "^1.0.0", + "is-alphanumerical": "^2.0.0", + "is-decimal": "^2.0.0", + "is-hexadecimal": "^2.0.0" + } + }, + "unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0" + } + } + } + }, + "mdast-util-mdxjs-esm": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/mdast-util-mdxjs-esm/-/mdast-util-mdxjs-esm-1.3.0.tgz", + "integrity": "sha512-7N5ihsOkAEGjFotIX9p/YPdl4TqUoMxL4ajNz7PbT89BqsdWJuBC9rvgt6wpbwTZqWWR0jKWqQbwsOWDBUZv4g==", + "dev": true, + "requires": { + "@types/estree-jsx": "^1.0.0", + "@types/hast": "^2.0.0", + "@types/mdast": "^3.0.0", + "mdast-util-from-markdown": "^1.0.0", + "mdast-util-to-markdown": "^1.0.0" + }, + "dependencies": { + "mdast-util-from-markdown": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-1.2.0.tgz", + "integrity": "sha512-iZJyyvKD1+K7QX1b5jXdE7Sc5dtoTry1vzV28UZZe8Z1xVnB/czKntJ7ZAkG0tANqRnBF6p3p7GpU1y19DTf2Q==", + "dev": true, + "requires": { + "@types/mdast": "^3.0.0", + "@types/unist": "^2.0.0", + "decode-named-character-reference": "^1.0.0", + "mdast-util-to-string": "^3.1.0", + "micromark": "^3.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-decode-string": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-stringify-position": "^3.0.0", + "uvu": "^0.5.0" + } + }, + "mdast-util-to-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.1.0.tgz", + "integrity": "sha512-n4Vypz/DZgwo0iMHLQL49dJzlp7YtAJP+N07MZHpjPf/5XJuHUWstviF4Mn2jEiR/GNmtnRRqnwsXExk3igfFA==", + "dev": true + }, + "micromark": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-3.0.10.tgz", + "integrity": "sha512-ryTDy6UUunOXy2HPjelppgJ2sNfcPz1pLlMdA6Rz9jPzhLikWXv/irpWV/I2jd68Uhmny7hHxAlAhk4+vWggpg==", + "dev": true, + "requires": { + "@types/debug": "^4.0.0", + "debug": "^4.0.0", + "decode-named-character-reference": "^1.0.0", + "micromark-core-commonmark": "^1.0.1", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-chunked": "^1.0.0", + "micromark-util-combine-extensions": "^1.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-encode": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-resolve-all": "^1.0.0", + "micromark-util-sanitize-uri": "^1.0.0", + "micromark-util-subtokenize": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.1", + "uvu": "^0.5.0" + } + }, + "unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0" + } + } + } + }, + "mdast-util-to-markdown": { + "version": "1.3.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-markdown/-/mdast-util-to-markdown-1.3.0.tgz", + "integrity": "sha512-6tUSs4r+KK4JGTTiQ7FfHmVOaDrLQJPmpjD6wPMlHGUVXoG9Vjc3jIeP+uyBWRf8clwB2blM+W7+KrlMYQnftA==", + "dev": true, + "requires": { + "@types/mdast": "^3.0.0", + "@types/unist": "^2.0.0", + "longest-streak": "^3.0.0", + "mdast-util-to-string": "^3.0.0", + "micromark-util-decode-string": "^1.0.0", + "unist-util-visit": "^4.0.0", + "zwitch": "^2.0.0" + }, + "dependencies": { + "mdast-util-to-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.1.0.tgz", + "integrity": "sha512-n4Vypz/DZgwo0iMHLQL49dJzlp7YtAJP+N07MZHpjPf/5XJuHUWstviF4Mn2jEiR/GNmtnRRqnwsXExk3igfFA==", + "dev": true + } + } + }, + "mdast-util-to-string": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-2.0.0.tgz", + "integrity": "sha512-AW4DRS3QbBayY/jJmD8437V1Gombjf8RSOUCMFBuo5iHi58AGEgVCKQ+ezHkZZDpAQS75hcBMpLqjpJTjtUL7w==", + "dev": true + }, + "media-typer": { + "version": "0.3.0" + }, + "memorizer": { + "version": "1.0.1", + "dev": true + }, + "meow": { + "version": "6.1.1", + "dev": true, + "requires": { + "@types/minimist": "^1.2.0", + "camelcase-keys": "^6.2.2", + "decamelize-keys": "^1.1.0", + "hard-rejection": "^2.1.0", + "minimist-options": "^4.0.2", + "normalize-package-data": "^2.5.0", + "read-pkg-up": "^7.0.1", + "redent": "^3.0.0", + "trim-newlines": "^3.0.0", + "type-fest": "^0.13.1", + "yargs-parser": "^18.1.3" + }, + "dependencies": { + "type-fest": { + "version": "0.13.1", + "dev": true + }, + "yargs-parser": { + "version": "18.1.3", + "dev": true, + "requires": { + "camelcase": "^5.0.0", + "decamelize": "^1.2.0" + } + } + } + }, + "merge-descriptors": { + "version": "1.0.1" + }, + "merge-stream": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", + "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==" + }, + "merge2": { + "version": "1.4.1", + "dev": true + }, + "meros": { + "version": "1.2.0", + "dev": true, + "requires": {} + }, + "methods": { + "version": "1.1.2" + }, + "micromark": { + "version": "2.11.4", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-2.11.4.tgz", + "integrity": "sha512-+WoovN/ppKolQOFIAajxi7Lu9kInbPxFuTBVEavFcL8eAfVstoc5MocPmqBeAdBOJV00uaVjegzH4+MA0DN/uA==", + "dev": true, + "requires": { + "debug": "^4.0.0", + "parse-entities": "^2.0.0" + } + }, + "micromark-core-commonmark": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/micromark-core-commonmark/-/micromark-core-commonmark-1.0.6.tgz", + "integrity": "sha512-K+PkJTxqjFfSNkfAhp4GB+cZPfQd6dxtTXnf+RjZOV7T4EEXnvgzOcnp+eSTmpGk9d1S9sL6/lqrgSNn/s0HZA==", + "dev": true, + "requires": { + "decode-named-character-reference": "^1.0.0", + "micromark-factory-destination": "^1.0.0", + "micromark-factory-label": "^1.0.0", + "micromark-factory-space": "^1.0.0", + "micromark-factory-title": "^1.0.0", + "micromark-factory-whitespace": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-chunked": "^1.0.0", + "micromark-util-classify-character": "^1.0.0", + "micromark-util-html-tag-name": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-resolve-all": "^1.0.0", + "micromark-util-subtokenize": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.1", + "uvu": "^0.5.0" + } + }, + "micromark-extension-mdx-expression": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/micromark-extension-mdx-expression/-/micromark-extension-mdx-expression-1.0.3.tgz", + "integrity": "sha512-TjYtjEMszWze51NJCZmhv7MEBcgYRgb3tJeMAJ+HQCAaZHHRBaDCccqQzGizR/H4ODefP44wRTgOn2vE5I6nZA==", + "dev": true, + "requires": { + "micromark-factory-mdx-expression": "^1.0.0", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-events-to-acorn": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0" + } + }, + "micromark-extension-mdx-jsx": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/micromark-extension-mdx-jsx/-/micromark-extension-mdx-jsx-1.0.3.tgz", + "integrity": "sha512-VfA369RdqUISF0qGgv2FfV7gGjHDfn9+Qfiv5hEwpyr1xscRj/CiVRkU7rywGFCO7JwJ5L0e7CJz60lY52+qOA==", + "dev": true, + "requires": { + "@types/acorn": "^4.0.0", + "estree-util-is-identifier-name": "^2.0.0", + "micromark-factory-mdx-expression": "^1.0.0", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0", + "vfile-message": "^3.0.0" + } + }, + "micromark-extension-mdx-md": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-extension-mdx-md/-/micromark-extension-mdx-md-1.0.0.tgz", + "integrity": "sha512-xaRAMoSkKdqZXDAoSgp20Azm0aRQKGOl0RrS81yGu8Hr/JhMsBmfs4wR7m9kgVUIO36cMUQjNyiyDKPrsv8gOw==", + "dev": true, + "requires": { + "micromark-util-types": "^1.0.0" + } + }, + "micromark-extension-mdxjs": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-extension-mdxjs/-/micromark-extension-mdxjs-1.0.0.tgz", + "integrity": "sha512-TZZRZgeHvtgm+IhtgC2+uDMR7h8eTKF0QUX9YsgoL9+bADBpBY6SiLvWqnBlLbCEevITmTqmEuY3FoxMKVs1rQ==", + "dev": true, + "requires": { + "acorn": "^8.0.0", + "acorn-jsx": "^5.0.0", + "micromark-extension-mdx-expression": "^1.0.0", + "micromark-extension-mdx-jsx": "^1.0.0", + "micromark-extension-mdx-md": "^1.0.0", + "micromark-extension-mdxjs-esm": "^1.0.0", + "micromark-util-combine-extensions": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "micromark-extension-mdxjs-esm": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/micromark-extension-mdxjs-esm/-/micromark-extension-mdxjs-esm-1.0.3.tgz", + "integrity": "sha512-2N13ol4KMoxb85rdDwTAC6uzs8lMX0zeqpcyx7FhS7PxXomOnLactu8WI8iBNXW8AVyea3KIJd/1CKnUmwrK9A==", + "dev": true, + "requires": { + "micromark-core-commonmark": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-events-to-acorn": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-position-from-estree": "^1.1.0", + "uvu": "^0.5.0", + "vfile-message": "^3.0.0" + } + }, + "micromark-factory-destination": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-factory-destination/-/micromark-factory-destination-1.0.0.tgz", + "integrity": "sha512-eUBA7Rs1/xtTVun9TmV3gjfPz2wEwgK5R5xcbIM5ZYAtvGF6JkyaDsj0agx8urXnO31tEO6Ug83iVH3tdedLnw==", + "dev": true, + "requires": { + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "micromark-factory-label": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-factory-label/-/micromark-factory-label-1.0.2.tgz", + "integrity": "sha512-CTIwxlOnU7dEshXDQ+dsr2n+yxpP0+fn271pu0bwDIS8uqfFcumXpj5mLn3hSC8iw2MUr6Gx8EcKng1dD7i6hg==", + "dev": true, + "requires": { + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0" + } + }, + "micromark-factory-mdx-expression": { + "version": "1.0.6", + "resolved": "https://registry.npmjs.org/micromark-factory-mdx-expression/-/micromark-factory-mdx-expression-1.0.6.tgz", + "integrity": "sha512-WRQIc78FV7KrCfjsEf/sETopbYjElh3xAmNpLkd1ODPqxEngP42eVRGbiPEQWpRV27LzqW+XVTvQAMIIRLPnNA==", + "dev": true, + "requires": { + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-events-to-acorn": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-position-from-estree": "^1.0.0", + "uvu": "^0.5.0", + "vfile-message": "^3.0.0" + } + }, + "micromark-factory-space": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-factory-space/-/micromark-factory-space-1.0.0.tgz", + "integrity": "sha512-qUmqs4kj9a5yBnk3JMLyjtWYN6Mzfcx8uJfi5XAveBniDevmZasdGBba5b4QsvRcAkmvGo5ACmSUmyGiKTLZew==", + "dev": true, + "requires": { + "micromark-util-character": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "micromark-factory-title": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-factory-title/-/micromark-factory-title-1.0.2.tgz", + "integrity": "sha512-zily+Nr4yFqgMGRKLpTVsNl5L4PMu485fGFDOQJQBl2NFpjGte1e86zC0da93wf97jrc4+2G2GQudFMHn3IX+A==", + "dev": true, + "requires": { + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0" + } + }, + "micromark-factory-whitespace": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-factory-whitespace/-/micromark-factory-whitespace-1.0.0.tgz", + "integrity": "sha512-Qx7uEyahU1lt1RnsECBiuEbfr9INjQTGa6Err+gF3g0Tx4YEviPbqqGKNv/NrBaE7dVHdn1bVZKM/n5I/Bak7A==", + "dev": true, + "requires": { + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0" + } + }, + "micromark-util-character": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/micromark-util-character/-/micromark-util-character-1.1.0.tgz", + "integrity": "sha512-agJ5B3unGNJ9rJvADMJ5ZiYjBRyDpzKAOk01Kpi1TKhlT1APx3XZk6eN7RtSz1erbWHC2L8T3xLZ81wdtGRZzg==", + "dev": true, "requires": { - "tmpl": "1.0.5" + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0" } }, - "map-cache": { - "version": "0.2.2", - "resolved": "https://registry.npmjs.org/map-cache/-/map-cache-0.2.2.tgz", - "integrity": "sha512-8y/eV9QQZCiyn1SprXSrCmqJN0yNRATe+PO8ztwqrvrbdRLA3eYJF0yaR0YayLWkMbsQSKWS9N2gPcGEc4UsZg==", - "dev": true + "micromark-util-chunked": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-chunked/-/micromark-util-chunked-1.0.0.tgz", + "integrity": "sha512-5e8xTis5tEZKgesfbQMKRCyzvffRRUX+lK/y+DvsMFdabAicPkkZV6gO+FEWi9RfuKKoxxPwNL+dFF0SMImc1g==", + "dev": true, + "requires": { + "micromark-util-symbol": "^1.0.0" + } }, - "map-obj": { - "version": "4.3.0", - "dev": true + "micromark-util-classify-character": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-classify-character/-/micromark-util-classify-character-1.0.0.tgz", + "integrity": "sha512-F8oW2KKrQRb3vS5ud5HIqBVkCqQi224Nm55o5wYLzY/9PwHGXC01tr3d7+TqHHz6zrKQ72Okwtvm/xQm6OVNZA==", + "dev": true, + "requires": { + "micromark-util-character": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0" + } }, - "media-typer": { - "version": "0.3.0" + "micromark-util-combine-extensions": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-combine-extensions/-/micromark-util-combine-extensions-1.0.0.tgz", + "integrity": "sha512-J8H058vFBdo/6+AsjHp2NF7AJ02SZtWaVUjsayNFeAiydTxUwViQPxN0Hf8dp4FmCQi0UUFovFsEyRSUmFH3MA==", + "dev": true, + "requires": { + "micromark-util-chunked": "^1.0.0", + "micromark-util-types": "^1.0.0" + } }, - "memorizer": { + "micromark-util-decode-numeric-character-reference": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-decode-numeric-character-reference/-/micromark-util-decode-numeric-character-reference-1.0.0.tgz", + "integrity": "sha512-OzO9AI5VUtrTD7KSdagf4MWgHMtET17Ua1fIpXTpuhclCqD8egFWo85GxSGvxgkGS74bEahvtM0WP0HjvV0e4w==", + "dev": true, + "requires": { + "micromark-util-symbol": "^1.0.0" + } + }, + "micromark-util-decode-string": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-decode-string/-/micromark-util-decode-string-1.0.2.tgz", + "integrity": "sha512-DLT5Ho02qr6QWVNYbRZ3RYOSSWWFuH3tJexd3dgN1odEuPNxCngTCXJum7+ViRAd9BbdxCvMToPOD/IvVhzG6Q==", + "dev": true, + "requires": { + "decode-named-character-reference": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-symbol": "^1.0.0" + } + }, + "micromark-util-encode": { "version": "1.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-encode/-/micromark-util-encode-1.0.1.tgz", + "integrity": "sha512-U2s5YdnAYexjKDel31SVMPbfi+eF8y1U4pfiRW/Y8EFVCy/vgxk/2wWTxzcqE71LHtCuCzlBDRU2a5CQ5j+mQA==", "dev": true }, - "meow": { - "version": "6.1.1", + "micromark-util-events-to-acorn": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/micromark-util-events-to-acorn/-/micromark-util-events-to-acorn-1.2.0.tgz", + "integrity": "sha512-WWp3bf7xT9MppNuw3yPjpnOxa8cj5ACivEzXJKu0WwnjBYfzaBvIAT9KfeyI0Qkll+bfQtfftSwdgTH6QhTOKw==", "dev": true, "requires": { - "@types/minimist": "^1.2.0", - "camelcase-keys": "^6.2.2", - "decamelize-keys": "^1.1.0", - "hard-rejection": "^2.1.0", - "minimist-options": "^4.0.2", - "normalize-package-data": "^2.5.0", - "read-pkg-up": "^7.0.1", - "redent": "^3.0.0", - "trim-newlines": "^3.0.0", - "type-fest": "^0.13.1", - "yargs-parser": "^18.1.3" + "@types/acorn": "^4.0.0", + "@types/estree": "^1.0.0", + "estree-util-visit": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0", + "vfile-location": "^4.0.0", + "vfile-message": "^3.0.0" }, "dependencies": { - "type-fest": { - "version": "0.13.1", + "@types/estree": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.0.tgz", + "integrity": "sha512-WulqXMDUTYAXCjZnk6JtIHPigp55cVtDgDrO2gHRwhyJto21+1zbVCtOYB2L1F9w4qCQ0rOGWBnBe0FNTiEJIQ==", "dev": true - }, - "yargs-parser": { - "version": "18.1.3", - "dev": true, - "requires": { - "camelcase": "^5.0.0", - "decamelize": "^1.2.0" - } } } }, - "merge-descriptors": { - "version": "1.0.1" + "micromark-util-html-tag-name": { + "version": "1.1.0", + "resolved": "https://registry.npmjs.org/micromark-util-html-tag-name/-/micromark-util-html-tag-name-1.1.0.tgz", + "integrity": "sha512-BKlClMmYROy9UiV03SwNmckkjn8QHVaWkqoAqzivabvdGcwNGMMMH/5szAnywmsTBUzDsU57/mFi0sp4BQO6dA==", + "dev": true }, - "merge-stream": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/merge-stream/-/merge-stream-2.0.0.tgz", - "integrity": "sha512-abv/qOcuPfk3URPfDzmZU1LKmuw8kT+0nIHvKrKgFrwifol/doWcdA4ZqsWQ8ENrFKkd67Mfpo/LovbIUsbt3w==" + "micromark-util-normalize-identifier": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-normalize-identifier/-/micromark-util-normalize-identifier-1.0.0.tgz", + "integrity": "sha512-yg+zrL14bBTFrQ7n35CmByWUTFsgst5JhA4gJYoty4Dqzj4Z4Fr/DHekSS5aLfH9bdlfnSvKAWsAgJhIbogyBg==", + "dev": true, + "requires": { + "micromark-util-symbol": "^1.0.0" + } }, - "merge2": { - "version": "1.4.1", - "dev": true + "micromark-util-resolve-all": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-resolve-all/-/micromark-util-resolve-all-1.0.0.tgz", + "integrity": "sha512-CB/AGk98u50k42kvgaMM94wzBqozSzDDaonKU7P7jwQIuH2RU0TeBqGYJz2WY1UdihhjweivStrJ2JdkdEmcfw==", + "dev": true, + "requires": { + "micromark-util-types": "^1.0.0" + } }, - "meros": { - "version": "1.2.0", + "micromark-util-sanitize-uri": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/micromark-util-sanitize-uri/-/micromark-util-sanitize-uri-1.0.0.tgz", + "integrity": "sha512-cCxvBKlmac4rxCGx6ejlIviRaMKZc0fWm5HdCHEeDWRSkn44l6NdYVRyU+0nT1XC72EQJMZV8IPHF+jTr56lAg==", "dev": true, - "requires": {} + "requires": { + "micromark-util-character": "^1.0.0", + "micromark-util-encode": "^1.0.0", + "micromark-util-symbol": "^1.0.0" + } }, - "methods": { - "version": "1.1.2" + "micromark-util-subtokenize": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-subtokenize/-/micromark-util-subtokenize-1.0.2.tgz", + "integrity": "sha512-d90uqCnXp/cy4G881Ub4psE57Sf8YD0pim9QdjCRNjfas2M1u6Lbt+XZK9gnHL2XFhnozZiEdCa9CNfXSfQ6xA==", + "dev": true, + "requires": { + "micromark-util-chunked": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "uvu": "^0.5.0" + } + }, + "micromark-util-symbol": { + "version": "1.0.1", + "resolved": "https://registry.npmjs.org/micromark-util-symbol/-/micromark-util-symbol-1.0.1.tgz", + "integrity": "sha512-oKDEMK2u5qqAptasDAwWDXq0tG9AssVwAx3E9bBF3t/shRIGsWIRG+cGafs2p/SnDSOecnt6hZPCE2o6lHfFmQ==", + "dev": true + }, + "micromark-util-types": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/micromark-util-types/-/micromark-util-types-1.0.2.tgz", + "integrity": "sha512-DCfg/T8fcrhrRKTPjRrw/5LLvdGV7BHySf/1LOZx7TzWZdYRjogNtyNq885z3nNallwr3QUKARjqvHqX1/7t+w==", + "dev": true }, "micromatch": { "version": "4.0.5", @@ -24910,6 +27715,12 @@ } } }, + "mri": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mri/-/mri-1.2.0.tgz", + "integrity": "sha512-tzzskb3bG8LvYGFF/mDTpq3jpI6Q9wc3LEmBaghu+DdCssd1FakN7Bc0hVNmEyGq1bq3RgfkCb3cmQLpNPOroA==", + "dev": true + }, "ms": { "version": "2.1.2" }, @@ -25086,6 +27897,17 @@ "mimic-fn": "^2.1.0" } }, + "open": { + "version": "8.4.0", + "resolved": "https://registry.npmjs.org/open/-/open-8.4.0.tgz", + "integrity": "sha512-XgFPPM+B28FtCCgSb9I+s9szOC1vZRSwgWsRUA5ylIxRTgKozqjOCrVOqGsYABPYK5qnfqClxZTFBa8PKt2v6Q==", + "dev": true, + "requires": { + "define-lazy-prop": "^2.0.0", + "is-docker": "^2.1.1", + "is-wsl": "^2.2.0" + } + }, "optimism": { "version": "0.16.1", "requires": { @@ -25185,6 +28007,20 @@ "callsites": "^3.1.0" } }, + "parse-entities": { + "version": "2.0.0", + "resolved": "https://registry.npmjs.org/parse-entities/-/parse-entities-2.0.0.tgz", + "integrity": "sha512-kkywGpCcRYhqQIchaWqZ875wzpS/bMKhz5HnN3p7wveJTkTtyAB/AlnS0f8DFSqYW1T82t6yEAkEcB+A1I3MbQ==", + "dev": true, + "requires": { + "character-entities": "^1.0.0", + "character-entities-legacy": "^1.0.0", + "character-reference-invalid": "^1.0.0", + "is-alphanumerical": "^1.0.0", + "is-decimal": "^1.0.0", + "is-hexadecimal": "^1.0.0" + } + }, "parse-filepath": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/parse-filepath/-/parse-filepath-1.0.2.tgz", @@ -25331,6 +28167,15 @@ "version": "2.7.1", "dev": true }, + "prettier-linter-helpers": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/prettier-linter-helpers/-/prettier-linter-helpers-1.0.0.tgz", + "integrity": "sha512-GbK2cP9nraSSUF9N2XwUwqfzlAFlMNYYl+ShE/V+H8a9uNl/oUqB1w2EL54Jh0OlyRSd8RfWYJ3coVS4TROP2w==", + "dev": true, + "requires": { + "fast-diff": "^1.1.2" + } + }, "pretty-format": { "version": "28.1.3", "resolved": "https://registry.npmjs.org/pretty-format/-/pretty-format-28.1.3.tgz", @@ -25620,6 +28465,100 @@ "invariant": "^2.2.4" } }, + "remark-mdx": { + "version": "2.1.3", + "resolved": "https://registry.npmjs.org/remark-mdx/-/remark-mdx-2.1.3.tgz", + "integrity": "sha512-3SmtXOy9+jIaVctL8Cs3VAQInjRLGOwNXfrBB9KCT+EpJpKD3PQiy0x8hUNGyjQmdyOs40BqgPU7kYtH9uoR6w==", + "dev": true, + "requires": { + "mdast-util-mdx": "^2.0.0", + "micromark-extension-mdxjs": "^1.0.0" + } + }, + "remark-parse": { + "version": "10.0.1", + "resolved": "https://registry.npmjs.org/remark-parse/-/remark-parse-10.0.1.tgz", + "integrity": "sha512-1fUyHr2jLsVOkhbvPRBJ5zTKZZyD6yZzYaWCS6BPBdQ8vEMBCH+9zNCDA6tET/zHCi/jLqjCWtlJZUPk+DbnFw==", + "dev": true, + "requires": { + "@types/mdast": "^3.0.0", + "mdast-util-from-markdown": "^1.0.0", + "unified": "^10.0.0" + }, + "dependencies": { + "mdast-util-from-markdown": { + "version": "1.2.0", + "resolved": "https://registry.npmjs.org/mdast-util-from-markdown/-/mdast-util-from-markdown-1.2.0.tgz", + "integrity": "sha512-iZJyyvKD1+K7QX1b5jXdE7Sc5dtoTry1vzV28UZZe8Z1xVnB/czKntJ7ZAkG0tANqRnBF6p3p7GpU1y19DTf2Q==", + "dev": true, + "requires": { + "@types/mdast": "^3.0.0", + "@types/unist": "^2.0.0", + "decode-named-character-reference": "^1.0.0", + "mdast-util-to-string": "^3.1.0", + "micromark": "^3.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-decode-string": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.0", + "unist-util-stringify-position": "^3.0.0", + "uvu": "^0.5.0" + } + }, + "mdast-util-to-string": { + "version": "3.1.0", + "resolved": "https://registry.npmjs.org/mdast-util-to-string/-/mdast-util-to-string-3.1.0.tgz", + "integrity": "sha512-n4Vypz/DZgwo0iMHLQL49dJzlp7YtAJP+N07MZHpjPf/5XJuHUWstviF4Mn2jEiR/GNmtnRRqnwsXExk3igfFA==", + "dev": true + }, + "micromark": { + "version": "3.0.10", + "resolved": "https://registry.npmjs.org/micromark/-/micromark-3.0.10.tgz", + "integrity": "sha512-ryTDy6UUunOXy2HPjelppgJ2sNfcPz1pLlMdA6Rz9jPzhLikWXv/irpWV/I2jd68Uhmny7hHxAlAhk4+vWggpg==", + "dev": true, + "requires": { + "@types/debug": "^4.0.0", + "debug": "^4.0.0", + "decode-named-character-reference": "^1.0.0", + "micromark-core-commonmark": "^1.0.1", + "micromark-factory-space": "^1.0.0", + "micromark-util-character": "^1.0.0", + "micromark-util-chunked": "^1.0.0", + "micromark-util-combine-extensions": "^1.0.0", + "micromark-util-decode-numeric-character-reference": "^1.0.0", + "micromark-util-encode": "^1.0.0", + "micromark-util-normalize-identifier": "^1.0.0", + "micromark-util-resolve-all": "^1.0.0", + "micromark-util-sanitize-uri": "^1.0.0", + "micromark-util-subtokenize": "^1.0.0", + "micromark-util-symbol": "^1.0.0", + "micromark-util-types": "^1.0.1", + "uvu": "^0.5.0" + } + }, + "unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0" + } + } + } + }, + "remark-stringify": { + "version": "10.0.2", + "resolved": "https://registry.npmjs.org/remark-stringify/-/remark-stringify-10.0.2.tgz", + "integrity": "sha512-6wV3pvbPvHkbNnWB0wdDvVFHOe1hBRAx1Q/5g/EpH4RppAII6J8Gnwe7VbHuXaoKIF6LAg6ExTel/+kNqSQ7lw==", + "dev": true, + "requires": { + "@types/mdast": "^3.0.0", + "mdast-util-to-markdown": "^1.0.0", + "unified": "^10.0.0" + } + }, "remedial": { "version": "1.0.8", "dev": true @@ -25841,6 +28780,15 @@ "tslib": "^2.1.0" } }, + "sade": { + "version": "1.8.1", + "resolved": "https://registry.npmjs.org/sade/-/sade-1.8.1.tgz", + "integrity": "sha512-xal3CZX1Xlo/k4ApwCFrHVACi9fBqJ7V+mwhBsuf/1IOKbBy098Fex+Wa/5QMubw09pSZ/u8EY8PWgevJsXp1A==", + "dev": true, + "requires": { + "mri": "^1.1.0" + } + }, "safe-buffer": { "version": "5.2.1" }, @@ -26299,6 +29247,24 @@ "es-abstract": "^1.19.5" } }, + "stringify-entities": { + "version": "4.0.3", + "resolved": "https://registry.npmjs.org/stringify-entities/-/stringify-entities-4.0.3.tgz", + "integrity": "sha512-BP9nNHMhhfcMbiuQKCqMjhDP5yBCAxsPu4pHFFzJ6Alo9dZgY4VLDPutXqIjpRiMoKdp7Av85Gr73Q5uH9k7+g==", + "dev": true, + "requires": { + "character-entities-html4": "^2.0.0", + "character-entities-legacy": "^3.0.0" + }, + "dependencies": { + "character-entities-legacy": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/character-entities-legacy/-/character-entities-legacy-3.0.0.tgz", + "integrity": "sha512-RpPp0asT/6ufRm//AJVwpViZbGM/MkjQFxJccQRHmISF/22NBtsHqAWmL+/pmkPWoIUJdWyeVleTl1wydHATVQ==", + "dev": true + } + } + }, "strip-ansi": { "version": "6.0.1", "requires": { @@ -26401,6 +29367,16 @@ "symbol-observable": { "version": "4.0.0" }, + "synckit": { + "version": "0.8.4", + "resolved": "https://registry.npmjs.org/synckit/-/synckit-0.8.4.tgz", + "integrity": "sha512-Dn2ZkzMdSX827QbowGbU/4yjWuvNaCoScLLoMo/yKbu+P4GBR6cRGKZH27k6a9bRzdqcyd1DE96pQtQ6uNkmyw==", + "dev": true, + "requires": { + "@pkgr/utils": "^2.3.1", + "tslib": "^2.4.0" + } + }, "tar": { "version": "6.1.11", "resolved": "https://registry.npmjs.org/tar/-/tar-6.1.11.tgz", @@ -26500,6 +29476,16 @@ "version": "2.3.8", "dev": true }, + "tiny-glob": { + "version": "0.2.9", + "resolved": "https://registry.npmjs.org/tiny-glob/-/tiny-glob-0.2.9.tgz", + "integrity": "sha512-g/55ssRPUjShh+xkfx9UPDXqhckHEsHr4Vd9zX55oSdGZc/MD0m3sferOkwWtp98bv+kcVfEHtRJgBVJzelrzg==", + "dev": true, + "requires": { + "globalyzer": "0.1.0", + "globrex": "^0.1.2" + } + }, "title-case": { "version": "3.0.3", "dev": true, @@ -26543,6 +29529,12 @@ "version": "3.0.1", "dev": true }, + "trough": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/trough/-/trough-2.1.0.tgz", + "integrity": "sha512-AqTiAOLcj85xS7vQ8QkAV41hPDIJ71XJB4RCUrzo/1GM2CQwhkJGaf9Hgr7BOugMRpgGUrqRg/DrBDl4H40+8g==", + "dev": true + }, "ts-graphviz": { "version": "0.16.0", "resolved": "https://registry.npmjs.org/ts-graphviz/-/ts-graphviz-0.16.0.tgz", @@ -26732,6 +29724,29 @@ "integrity": "sha512-1F7Vtcez5w/LwH2G2tGnFIihuWUlc58YidwLiCv+jR2Z50x0tNXpRRw7eOIJ+GvqCqIkg9SB7NWAJ/T9TLfv8Q==", "dev": true }, + "unified": { + "version": "10.1.2", + "resolved": "https://registry.npmjs.org/unified/-/unified-10.1.2.tgz", + "integrity": "sha512-pUSWAi/RAnVy1Pif2kAoeWNBa3JVrx0MId2LASj8G+7AiHWoKZNTomq6LG326T68U7/e263X6fTdcXIy7XnF7Q==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "bail": "^2.0.0", + "extend": "^3.0.0", + "is-buffer": "^2.0.0", + "is-plain-obj": "^4.0.0", + "trough": "^2.0.0", + "vfile": "^5.0.0" + }, + "dependencies": { + "is-plain-obj": { + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/is-plain-obj/-/is-plain-obj-4.1.0.tgz", + "integrity": "sha512-+Pgi+vMuUNkJyExiMBt5IlFoMyKnr5zhJ4Uspz58WOhBF5QoIZkFyNHIbBAtHwzVAgk5RtndVNsDRN61/mmDqg==", + "dev": true + } + } + }, "unique-filename": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/unique-filename/-/unique-filename-1.1.1.tgz", @@ -26759,6 +29774,61 @@ "crypto-random-string": "^2.0.0" } }, + "unist-util-is": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/unist-util-is/-/unist-util-is-5.1.1.tgz", + "integrity": "sha512-F5CZ68eYzuSvJjGhCLPL3cYx45IxkqXSetCcRgUXtbcm50X2L9oOWQlfUfDdAf+6Pd27YDblBfdtmsThXmwpbQ==", + "dev": true + }, + "unist-util-position-from-estree": { + "version": "1.1.1", + "resolved": "https://registry.npmjs.org/unist-util-position-from-estree/-/unist-util-position-from-estree-1.1.1.tgz", + "integrity": "sha512-xtoY50b5+7IH8tFbkw64gisG9tMSpxDjhX9TmaJJae/XuxQ9R/Kc8Nv1eOsf43Gt4KV/LkriMy9mptDr7XLcaw==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0" + } + }, + "unist-util-remove-position": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/unist-util-remove-position/-/unist-util-remove-position-4.0.1.tgz", + "integrity": "sha512-0yDkppiIhDlPrfHELgB+NLQD5mfjup3a8UYclHruTJWmY74je8g+CIFr79x5f6AkmzSwlvKLbs63hC0meOMowQ==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "unist-util-visit": "^4.0.0" + } + }, + "unist-util-stringify-position": { + "version": "2.0.3", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-2.0.3.tgz", + "integrity": "sha512-3faScn5I+hy9VleOq/qNbAd6pAx7iH5jYBMS9I1HgQVijz/4mv5Bvw5iw1sC/90CODiKo81G/ps8AJrISn687g==", + "dev": true, + "requires": { + "@types/unist": "^2.0.2" + } + }, + "unist-util-visit": { + "version": "4.1.1", + "resolved": "https://registry.npmjs.org/unist-util-visit/-/unist-util-visit-4.1.1.tgz", + "integrity": "sha512-n9KN3WV9k4h1DxYR1LoajgN93wpEi/7ZplVe02IoB4gH5ctI1AaF2670BLHQYbwj+pY83gFtyeySFiyMHJklrg==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "unist-util-is": "^5.0.0", + "unist-util-visit-parents": "^5.1.1" + } + }, + "unist-util-visit-parents": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/unist-util-visit-parents/-/unist-util-visit-parents-5.1.1.tgz", + "integrity": "sha512-gks4baapT/kNRaWxuGkl5BIhoanZo7sC/cUT/JToSRNL1dYoXRFl75d++NkjYk4TAu2uv2Px+l8guMajogeuiw==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "unist-util-is": "^5.0.0" + } + }, "universalify": { "version": "0.1.2", "dev": true @@ -26822,6 +29892,32 @@ "integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==", "dev": true }, + "uvu": { + "version": "0.5.6", + "resolved": "https://registry.npmjs.org/uvu/-/uvu-0.5.6.tgz", + "integrity": "sha512-+g8ENReyr8YsOc6fv/NVJs2vFdHBnBNdfE49rshrTzDWOlUx4Gq7KOS2GD8eqhy2j+Ejq29+SbKH8yjkAqXqoA==", + "dev": true, + "requires": { + "dequal": "^2.0.0", + "diff": "^5.0.0", + "kleur": "^4.0.3", + "sade": "^1.7.3" + }, + "dependencies": { + "diff": { + "version": "5.1.0", + "resolved": "https://registry.npmjs.org/diff/-/diff-5.1.0.tgz", + "integrity": "sha512-D+mk+qE8VC/PAUrlAU34N+VfXev0ghe5ywmpqrawphmVZc1bEfn56uo9qpyGp1p4xpzOHkSW4ztBd6L7Xx4ACw==", + "dev": true + }, + "kleur": { + "version": "4.1.5", + "resolved": "https://registry.npmjs.org/kleur/-/kleur-4.1.5.tgz", + "integrity": "sha512-o+NO+8WrRiQEE4/7nwRJhN1HWpVmJm511pBHUxPLtp0BUISzlBplORYSmTclCnJvQq2tKu/sgl3xVpkc7ZWuQQ==", + "dev": true + } + } + }, "v8-compile-cache-lib": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/v8-compile-cache-lib/-/v8-compile-cache-lib-3.0.1.tgz", @@ -26869,6 +29965,60 @@ } } }, + "vfile": { + "version": "5.3.5", + "resolved": "https://registry.npmjs.org/vfile/-/vfile-5.3.5.tgz", + "integrity": "sha512-U1ho2ga33eZ8y8pkbQLH54uKqGhFJ6GYIHnnG5AhRpAh3OWjkrRHKa/KogbmQn8We+c0KVV3rTOgR9V/WowbXQ==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "is-buffer": "^2.0.0", + "unist-util-stringify-position": "^3.0.0", + "vfile-message": "^3.0.0" + }, + "dependencies": { + "unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0" + } + } + } + }, + "vfile-location": { + "version": "4.0.1", + "resolved": "https://registry.npmjs.org/vfile-location/-/vfile-location-4.0.1.tgz", + "integrity": "sha512-JDxPlTbZrZCQXogGheBHjbRWjESSPEak770XwWPfw5mTc1v1nWGLB/apzZxsx8a0SJVfF8HK8ql8RD308vXRUw==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "vfile": "^5.0.0" + } + }, + "vfile-message": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/vfile-message/-/vfile-message-3.1.2.tgz", + "integrity": "sha512-QjSNP6Yxzyycd4SVOtmKKyTsSvClqBPJcd00Z0zuPj3hOIjg0rUPG6DbFGPvUKRgYyaIWLPKpuEclcuvb3H8qA==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0", + "unist-util-stringify-position": "^3.0.0" + }, + "dependencies": { + "unist-util-stringify-position": { + "version": "3.0.2", + "resolved": "https://registry.npmjs.org/unist-util-stringify-position/-/unist-util-stringify-position-3.0.2.tgz", + "integrity": "sha512-7A6eiDCs9UtjcwZOcCpM4aPII3bAAGv13E96IkawkOAW0OhH+yRxtY0lzo8KiHpzEMfH7Q+FizUmwp8Iqy5EWg==", + "dev": true, + "requires": { + "@types/unist": "^2.0.0" + } + } + } + }, "vscode-languageserver-textdocument": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/vscode-languageserver-textdocument/-/vscode-languageserver-textdocument-1.0.7.tgz", @@ -27085,6 +30235,12 @@ "requires": { "zen-observable": "0.8.15" } + }, + "zwitch": { + "version": "2.0.2", + "resolved": "https://registry.npmjs.org/zwitch/-/zwitch-2.0.2.tgz", + "integrity": "sha512-JZxotl7SxAJH0j7dN4pxsTV6ZLXoLdGME+PsjkL/DaBrVryK9kTGq06GfKrwcSOqypP+fdXGoCHE36b99fWVoA==", + "dev": true } } } From ae40046aa986ae494a61ea44f5e11d267185f70f Mon Sep 17 00:00:00 2001 From: Trevor Scheer Date: Thu, 15 Sep 2022 14:17:07 -0700 Subject: [PATCH 2/6] deps --- package-lock.json | 4 ++-- package.json | 7 +++++-- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/package-lock.json b/package-lock.json index 2f1189b4f51..45a346db11b 100644 --- a/package-lock.json +++ b/package-lock.json @@ -60,10 +60,10 @@ "cors": "2.8.5", "cspell": "6.9.0", "eslint": "8.23.1", - "eslint-config-prettier": "^8.5.0", + "eslint-config-prettier": "8.5.0", "eslint-plugin-import": "2.26.0", "eslint-plugin-mdx": "2.0.4", - "eslint-plugin-prettier": "^4.2.1", + "eslint-plugin-prettier": "4.2.1", "express": "4.18.1", "graphql": "16.5.0", "graphql-tag": "2.12.6", diff --git a/package.json b/package.json index afd3a262139..fe0dbe27ef0 100644 --- a/package.json +++ b/package.json @@ -77,19 +77,22 @@ "@typescript-eslint/eslint-plugin": "5.37.0", "@typescript-eslint/parser": "5.37.0", "@vendia/serverless-express": "4.10.1", - "apollo-gateway-0-oldest-supported": "npm:@apollo/gateway@0.50.1", "apollo-gateway-0-before-asgi": "npm:@apollo/gateway@0.51.0", "apollo-gateway-0-latest": "npm:@apollo/gateway@0.52.1", - "apollo-gateway-2-oldest-supported": "npm:@apollo/gateway@2.0.0", + "apollo-gateway-0-oldest-supported": "npm:@apollo/gateway@0.50.1", "apollo-gateway-2-before-asgi": "npm:@apollo/gateway@2.0.5", "apollo-gateway-2-latest": "npm:@apollo/gateway@2.1.0-alpha.3", + "apollo-gateway-2-oldest-supported": "npm:@apollo/gateway@2.0.0", "awaiting": "3.0.0", "body-parser": "1.20.0", "codecov": "3.8.3", "cors": "2.8.5", "cspell": "6.9.0", "eslint": "8.23.1", + "eslint-config-prettier": "8.5.0", "eslint-plugin-import": "2.26.0", + "eslint-plugin-mdx": "2.0.4", + "eslint-plugin-prettier": "4.2.1", "express": "4.18.1", "graphql": "16.5.0", "graphql-tag": "2.12.6", From f79e03d483755d57cbd6eafadb803f6d6787a85c Mon Sep 17 00:00:00 2001 From: Trevor Scheer Date: Thu, 15 Sep 2022 14:17:45 -0700 Subject: [PATCH 3/6] Run lint --fix --- CHANGELOG.md | 170 ++++---- CONTRIBUTING.md | 16 +- DEVELOPMENT.md | 8 +- ROADMAP.md | 28 +- docs/README.md | 2 +- docs/source/api/apollo-server.mdx | 124 ++++-- docs/source/api/express-middleware.mdx | 27 +- docs/source/api/plugin/cache-control.mdx | 11 +- docs/source/api/plugin/drain-http-server.mdx | 17 +- docs/source/api/plugin/inline-trace.mdx | 18 +- docs/source/api/plugin/landing-pages.mdx | 63 ++- docs/source/api/plugin/schema-reporting.mdx | 24 +- docs/source/api/plugin/usage-reporting.mdx | 94 +++-- docs/source/api/standalone.mdx | 30 +- docs/source/builtin-plugins.md | 18 +- docs/source/data/errors.mdx | 19 +- docs/source/data/fetching-data.mdx | 2 +- docs/source/data/fetching-rest.mdx | 46 ++- docs/source/data/resolvers.mdx | 77 ++-- docs/source/data/subscriptions.mdx | 16 +- docs/source/deployment/azure-functions.mdx | 21 +- docs/source/deployment/gcp-functions.mdx | 16 +- docs/source/deployment/heroku.md | 12 +- docs/source/deployment/lambda.md | 18 +- docs/source/getting-started.mdx | 5 +- docs/source/index.mdx | 26 +- .../integrations/building-integrations.md | 18 +- .../integrations/plugins-event-reference.mdx | 93 +++-- docs/source/integrations/plugins.mdx | 67 ++-- docs/source/migration.mdx | 376 ++++++++++-------- docs/source/monitoring/health-checks.md | 6 +- docs/source/monitoring/metrics.mdx | 26 +- docs/source/performance/cache-backends.mdx | 55 +-- docs/source/performance/caching.md | 39 +- docs/source/schema/creating-directives.mdx | 13 +- docs/source/schema/directives.md | 10 +- docs/source/security/authentication.mdx | 7 +- docs/source/security/cors.mdx | 40 +- docs/source/security/terminating-ssl.mdx | 11 +- docs/source/testing/mocking.md | 4 +- docs/source/testing/testing.mdx | 10 +- docs/source/workflow/build-run-queries.mdx | 4 +- packages/integration-testsuite/README.md | 7 +- packages/plugin-response-cache/README.md | 1 - packages/server/README.md | 25 +- packages/usage-reporting-protobuf/README.md | 9 +- 46 files changed, 953 insertions(+), 776 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 0f293a53441..5efd72d891a 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,6 @@ # CHANGELOG -The version headers in this history reflect the versions of Apollo Server itself. Versions of other packages (e.g., those which are not actual HTTP integrations; packages not prefixed with "`apollo-server`", or just supporting packages) may use different versions. +The version headers in this history reflect the versions of Apollo Server itself. Versions of other packages (e.g., those which are not actual HTTP integrations; packages not prefixed with "`apollo-server`", or just supporting packages) may use different versions. ๐Ÿ†• **Please Note!**: ๐Ÿ†• **The `@apollo/federation` and `@apollo/gateway` packages now live in the [`apollographql/federation`](https://github.com/apollographql/federation) repository.** @@ -26,7 +26,7 @@ The version headers in this history reflect the versions of Apollo Server itself ## v3.6.6 -- โš ๏ธ **SECURITY** `apollo-server-core`: Apollo Server 3.4.0 introduced a new `documentStore` constructor option (replacing the `experimental_approximateDocumentStoreMiB` option) which allows you to customize an internal cache used by ApolloServer to memoize the results of parsing and validating GraphQL operations. When this option was combined with the `gateway` option, it was possible for Apollo Server to attempt to execute invalid GraphQL operations. Specifically, if a server processed an operation and then its schema was updated with a change that made that operation no longer valid, the server could still attempt to execute the operation again without re-validating it against the new schema. The problem only lasts until the server is restarted. This release changes the semantics of the `documentStore` option so that a different key prefix is used each time the schema is updated. (As a side effect, you no longer have to be careful to avoid sharing a `documentStore` between multiple `ApolloServer` objects.) **This update is highly recommended for any users that specify both `documentStore` and `gateway` in `new ApolloServer()`.** +- โš ๏ธ **SECURITY** `apollo-server-core`: Apollo Server 3.4.0 introduced a new `documentStore` constructor option (replacing the `experimental_approximateDocumentStoreMiB` option) which allows you to customize an internal cache used by ApolloServer to memoize the results of parsing and validating GraphQL operations. When this option was combined with the `gateway` option, it was possible for Apollo Server to attempt to execute invalid GraphQL operations. Specifically, if a server processed an operation and then its schema was updated with a change that made that operation no longer valid, the server could still attempt to execute the operation again without re-validating it against the new schema. The problem only lasts until the server is restarted. This release changes the semantics of the `documentStore` option so that a different key prefix is used each time the schema is updated. (As a side effect, you no longer have to be careful to avoid sharing a `documentStore` between multiple `ApolloServer` objects.) **This update is highly recommended for any users that specify both `documentStore` and `gateway` in `new ApolloServer()`.** ## v3.6.5 @@ -62,7 +62,7 @@ The version headers in this history reflect the versions of Apollo Server itself ## v3.5.0 - Apollo Server now supports `graphql@16`. (There is a very small backwards incompatibility: `ApolloError.originalError` can no longer be `null`, matching the type of `GraphQLError.originalError`. Use `undefined` instead. If this causes challenges, let us know and we can try to adapt.) [PR #5857](https://github.com/apollographql/apollo-server/pull/5857) --ย `apollo-server-core`: Fix build error when building with `@rollup/plugin-commonjs`. [PR #5797](https://github.com/apollographql/apollo-server/pull/5797) + -ย `apollo-server-core`: Fix build error when building with `@rollup/plugin-commonjs`. [PR #5797](https://github.com/apollographql/apollo-server/pull/5797) - `apollo-server-plugin-response-cache`: Add missing dependency on `apollo-server-types` (broken since v3.0.0). [Issue #5804](https://github.com/apollographql/apollo-server/issues/5804) [PR #5816](https://github.com/apollographql/apollo-server/pull/5816) - `apollo-server-core`: The default landing page plugins now take `document`, `variables`, and `headers` arguments which fill in default values if you click through to Explorer. [PR #5711](https://github.com/apollographql/apollo-server/pull/5711) - `apollo-server-core`: Support for HTTP request batching can now be disabled by passing `allowBatchedHttpRequests: false` to `new ApolloServer`. [PR #5778](https://github.com/apollographql/apollo-server/pull/5778) [Issue #5686](https://github.com/apollographql/apollo-server/issues/5686) @@ -83,7 +83,7 @@ The version headers in this history reflect the versions of Apollo Server itself sizeCalculator: InMemoryLRUCache.jsonBytesSizeCalculator, }), ...moreOptions, - }) + }); ``` [PR #5644](https://github.com/apollographql/apollo-server/pull/5644) [Issue #5634](https://github.com/apollographql/apollo-server/issues/5634) - `apollo-server-core`: For ease of testing, you can specify the node environment via `new ApolloServer({nodeEnv})` in addition to via the `NODE_ENV` environment variable. The environment variable is now only read during server startup (and in some error cases) rather than on every request. [PR #5657](https://github.com/apollographql/apollo-server/pull/5657) @@ -121,7 +121,7 @@ The version headers in this history reflect the versions of Apollo Server itself - `apollo-server-core`/`apollo-server-plugin-base`: Add support for `schemaDidLoadOrUpdate` event hooks, to be specified by the `serverWillStart` event hook. Plugins listening for this event will receive the API schema (and core schema for gateways) when the server's schema is initially loaded and when the server's schema is updated. For more information about this plugin event, see [the plugin event reference documentation](https://www.apollographql.com/docs/apollo-server/integrations/plugins-event-reference/). [PR #5187](https://github.com/apollographql/apollo-server/pull/5187) - `apollo-server-core`: Add support for schema reporting when using Apollo Gateway. At the time of this package's release, Apollo Studio does not yet support schema reporting from gateways, so you should not use this feature yet for gateways (unless instructed otherwise by Apollo staff or by the Studio docs). If you do enable schema reporting for a gateway, the version of `@apollo/gateway` must be at least `0.35.0` , or else `start()` will error. [PR #5187](https://github.com/apollographql/apollo-server/pull/5187) - `apollo-server-core`: Support gateways without executors, to help with mocking gateways. Note that if you have a custom `GatewayInterface` implementation, Apollo Server will now honor the `executor` returned from `load` and will ignore the `executor` method on the gateway itself. See the PR for details. [PR #5539](https://github.com/apollographql/apollo-server/pull/5539) -- `apollo-server-plugin-response-cache`, `apollo-server-plugin-operation-registry`: Change how the default export from the package is set up to fix errors with some build tools. [PR #5542](https://github.com/apollographql/apollo-server/pull/5542) +- `apollo-server-plugin-response-cache`, `apollo-server-plugin-operation-registry`: Change how the default export from the package is set up to fix errors with some build tools. [PR #5542](https://github.com/apollographql/apollo-server/pull/5542) ## v3.0.2 @@ -164,6 +164,7 @@ Certain undersupported and underused Apollo Server features have been removed in - To re-enable file uploads in Apollo Server 3 as they're supported in v2, [see the migration guide](https://www.apollographql.com/docs/apollo-server/migration/#File-uploads). - Dropped support for the `graphql-extensions` API (e.g., `GraphQLExtensions`, `extensions`) in favor of the Apollo Server [plugins API](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). - Dropped support for passing the `schemaDirectives` option to the `ApolloServer` constructor. + - This option was passed directly to the `graphql-tools` function `makeExecutableSchema`. To continue using it, you can import `makeExecutableSchema` from `@graphql-tools/schema` and call it yourself: ``` @@ -177,6 +178,7 @@ Certain undersupported and underused Apollo Server features have been removed in ``` Note that `graphql-tools` calls this feature ["legacy" schema directives](https://www.graphql-tools.com/docs/legacy-schema-directives/), and you might want to consider the newer [`schemaTransforms`](https://www.graphql-tools.com/docs/schema-directives/) option instead. + - Removed the deprecated `ApolloServer.schema` field, which never worked with federated gateways. - To extract your schema from your server, you can make a plugin with `serverWillStart` or register `onSchemaChange` on your gateway. - `apollo-datasource-rest`: We no longer officially support overriding the `baseURL` property with a getter, because TypeScript 4 does not allow you to do so. @@ -184,6 +186,7 @@ Certain undersupported and underused Apollo Server features have been removed in - This directive was added in some circumstances but not in others, which caused confusion. - If you use `@cacheControl`, you can [define it in your schema as shown in the docs](https://www.apollographql.com/docs/apollo-server/performance/caching/#in-your-schema-static). - Removed the `tracing` option passed to the `ApolloServer` constructor. The corresponding `apollo-tracing` package has been deprecated and is no longer being published. + - This package implemented an inefficient JSON format for execution traces returned via the `tracing` GraphQL response extension. This format was only consumed by the deprecated `engineproxy` and GraphQL Playground. - If you rely on this trace format, the old version of `apollo-tracing` should still work: @@ -194,6 +197,7 @@ Certain undersupported and underused Apollo Server features have been removed in ] }); ``` + - Removed a redundant mechanism for applying extensions to an `ApolloError`. - Applied extensions are now available only on `error.extensions`, and are not _also_ available on `error` itself. - For details, see [#5294](https://github.com/apollographql/apollo-server/pull/5294). @@ -204,12 +208,13 @@ Certain undersupported and underused Apollo Server features have been removed in - The `CacheHint` and `CacheScope` types are now exported from `apollo-server-types`. The `info.cacheControl.cacheHint` object now has additional methods (`replace`, `restrict`, and `policyIfCacheable`), and its fields update when those methods or `setCacheHint` are called. These methods also exist on `requestContext.overallCachePolicy`, which is always defined and which should not be overwritten (use `replace` instead). There is also a new function `info.cacheControl.cacheHintFromType` available. - `@cacheControl` directives on type extensions are no longer ignored. Fields returning union types are now treated similarly to fields returning object and interface types (`@cacheControl` directives on the type are honored, the default `maxAge` is applied to them). - New feature: `@cacheControl(inheritMaxAge: true)` when applied to a composite type or a field returning a composite type means that the default `maxAge` is not applied to that field (unless it is a root field). -- Due to conflicts with same/similar globals provided by `@types/supertest` (which we use in our testing), some global TypeScript definitions have been removed from `apollo-server-env` including that of, e.g., `fetch`, `RequestInfo`, `Headers`, `Request`, `Response`, `ResponseInit`, and more. [See the full list prior to removal here](https://github.com/apollographql/apollo-server/blob/32cfdcfdbd44f4f4e826f347f47fdcbc0475b5cc/packages/apollo-server-env/src/global.d.ts). Internally in the Apollo Server tests, for the time-being, we are relying on the same-named types from TypeScript's `lib.dom.d.ts` โ€”ย e.g., [its `RequestInfo` type definition](https://github.com/microsoft/TypeScript/blob/3c604f1c0a412ef41f58c3f9b239b25e8d725751/lib/lib.dom.d.ts#L1470). For more details, [see PR #5165](https://github.com/apollographql/apollo-server/pull/5165). +- Due to conflicts with same/similar globals provided by `@types/supertest` (which we use in our testing), some global TypeScript definitions have been removed from `apollo-server-env` including that of, e.g., `fetch`, `RequestInfo`, `Headers`, `Request`, `Response`, `ResponseInit`, and more. [See the full list prior to removal here](https://github.com/apollographql/apollo-server/blob/32cfdcfdbd44f4f4e826f347f47fdcbc0475b5cc/packages/apollo-server-env/src/global.d.ts). Internally in the Apollo Server tests, for the time-being, we are relying on the same-named types from TypeScript's `lib.dom.d.ts` โ€”ย e.g., [its `RequestInfo` type definition](https://github.com/microsoft/TypeScript/blob/3c604f1c0a412ef41f58c3f9b239b25e8d725751/lib/lib.dom.d.ts#L1470). For more details, [see PR #5165](https://github.com/apollographql/apollo-server/pull/5165). - Top-level exports have changed. For example: - We no longer re-export the entirety of `graphql-tools` (including `makeExecutableSchema`) from all Apollo Server packages. To continue using them, install [`graphql-tools`](https://www.graphql-tools.com/) or one of its sub-packages yourself. - - The `Upload` scalar is no longer exported as part of dropping built-in support for file uploads. + - The `Upload` scalar is no longer exported as part of dropping built-in support for file uploads. + - Stopped publishing the deprecated `apollo-server-testing` package. This package is just a wrapper around `server.executeOperation`, which you can use directly. - `apollo-server-caching`: The test suite helper works differently, and the `TestableKeyValueCache` interface is removed. - The `engine` constructor option, `ENGINE_API_KEY` environment variable, and `ENGINE_SCHEMA_TAG` environment variables are no longer supported. Use the `apollo` constructor option, `APOLLO_KEY` environment variable, and `APOLLO_GRAPH_VARIANT` environment variable instead, as described in [the `engine` option migration guide from v2.18)[https://www.apollographql.com/docs/apollo-server/v2/migration-engine-plugins/]. @@ -238,16 +243,18 @@ Certain undersupported and underused Apollo Server features have been removed in #### Changes to Node.js framework integrations -- When using a non-serverless framework integration (Express, Fastify, Hapi, Koa, Micro, or Cloudflare), you now *must* call `await server.start()` before attaching the server to your framework. - * This method was introduced in v2.22 but was optional prior to Apollo Server 3. - * This requirement does not apply to the `apollo-server` library or to _serverless_ framework integrations. +- When using a non-serverless framework integration (Express, Fastify, Hapi, Koa, Micro, or Cloudflare), you now _must_ call `await server.start()` before attaching the server to your framework. + - This method was introduced in v2.22 but was optional prior to Apollo Server 3. + - This requirement does not apply to the `apollo-server` library or to _serverless_ framework integrations. - `apollo-server-express` no longer officially supports using with the `connect` framework. - We have not actively removed any `connect` compatibility code, and we do still test that it works with `connect`. However, we reserve the right to break that compatibility without a major version bump of this package (we will certainly note in this changelog if we do so). - `apollo-server-lambda`: This package is now implemented as a wrapper around `apollo-server-express`. `createHandler`'s argument now has different options: + - `expressGetMiddlewareOptions`, which includes options like `cors` and is passed through to `apollo-server-express`'s `getMiddleware` - `expressAppFromMiddleware`, which lets you customize HTTP processing Also, the `context` function now receives an `express: { req, res }` option in addition to `event` and `context` + - `apollo-server-lambda`: The handler returned by `createHandler` can now only be called as an async function returning a `Promise` (it no longer optionally accepts a callback as the third argument). - All current Lambda Node runtimes support this invocation mode (so `exports.handler = server.createHandler()` will keep working without any changes). - If you've written your _own_ handler that calls the handler returned by `createHandler` with a callback, you'll need to handle its `Promise` return value instead. @@ -315,7 +322,7 @@ Certain undersupported and underused Apollo Server features have been removed in - `apollo-server-lambda`: The `onHealthCheck` option did not previously work. Additionally, health checks (with `onHealthCheck` or without) didn't work in all Lambda contexts, such as behind Custom Domains; the path check is now more flexible. [Issue #3999](https://github.com/apollographql/apollo-server/issues/3999) [PR #4969](https://github.com/apollographql/apollo-server/pull/4969) [Issue #4891](https://github.com/apollographql/apollo-server/issues/4891) [PR #4892](https://github.com/apollographql/apollo-server/pull/4892) - The `debug` option to `new ApolloServer` (which adds stack traces to errors) now affects errors that come from requests executed with `server.executeOperation` (and its wrapper `apollo-server-testing`), instead of just errors that come from requests executed over HTTP. [Issue #4107](https://github.com/apollographql/apollo-server/issues/4107) [PR #4948](https://github.com/apollographql/apollo-server/pull/4948) -- Bump version of `@apollographql/graphql-playground-html` to v1.6.27 and `@apollographql/graphql-playground-react` to v1.7.39 to resolve incorrectly rendered CDN URL when Playground `version` was `false`-y. [PR #4932](https://github.com/apollographql/apollo-server/pull/4932) [PR #4955](https://github.com/apollographql/apollo-server/pull/4955) [Issue #4937](https://github.com/apollographql/apollo-server/issues/4937) +- Bump version of `@apollographql/graphql-playground-html` to v1.6.27 and `@apollographql/graphql-playground-react` to v1.7.39 to resolve incorrectly rendered CDN URL when Playground `version` was `false`-y. [PR #4932](https://github.com/apollographql/apollo-server/pull/4932) [PR #4955](https://github.com/apollographql/apollo-server/pull/4955) [Issue #4937](https://github.com/apollographql/apollo-server/issues/4937) ## v2.21.0 @@ -344,7 +351,7 @@ Certain undersupported and underused Apollo Server features have been removed in - `apollo-server-testing`: types: Allow generic `variables` usage of `query` and `mutate` functions. [PR #4383](https://github.com/apollograpqh/apollo-server/pull/4383) - `apollo-server-express`: Export the `GetMiddlewareOptions` type. [PR #4599](https://github.com/apollograpqh/apollo-server/pull/4599) - `apollo-server-lambda`: Fix file uploads - ignore base64 decoding for multipart queries. [PR #4506](https://github.com/apollographql/apollo-server/pull/4506) -- `apollo-server-core`: Do not send operation documents that cannot be executed to Apollo Studio. Instead, information about these operations will be combined into one "operation" for parse failures, one for validation failures, and one for unknown operation names. +- `apollo-server-core`: Do not send operation documents that cannot be executed to Apollo Studio. Instead, information about these operations will be combined into one "operation" for parse failures, one for validation failures, and one for unknown operation names. ## v2.18.2 @@ -366,13 +373,13 @@ Certain undersupported and underused Apollo Server features have been removed in - Apollo Server's support for communicating with Apolloโ€™s commercial products has been refactored into three separate plugins exported from `apollo-server-core` (for usage reporting, schema reporting, and inline tracing), configured using the standard `plugins` option. The `engine` option continues to work for backwards compatibility in the 2.x series; support for `engine` will be deprecated in Apollo Server 3.x. Full details are available in [the migration guide](https://www.apollographql.com/docs/apollo-server/v2/migration-engine-plugins/). [PR #4453](https://github.com/apollographql/apollo-server/pull/4453) -- To consistently support tracing, inline tracing is enabled by default on federated implementing services, even when an Apollo API key is provided. Previously it was not enabled when an API key was provided. You can disable it with `ApolloServerPluginInlineTraceDisabled`. [PR #4453](https://github.com/apollographql/apollo-server/pull/4453) +- To consistently support tracing, inline tracing is enabled by default on federated implementing services, even when an Apollo API key is provided. Previously it was not enabled when an API key was provided. You can disable it with `ApolloServerPluginInlineTraceDisabled`. [PR #4453](https://github.com/apollographql/apollo-server/pull/4453) - The `apollo-engine-reporting` npm package has been obsoleted and will no longer receive updates. [PR #4453](https://github.com/apollographql/apollo-server/pull/4453) -- The `apollo-engine-reporting-protobuf` package has been renamed to `apollo-reporting-protobuf`. No new versions of the old package will be published. [PR #4453](https://github.com/apollographql/apollo-server/pull/4453) +- The `apollo-engine-reporting-protobuf` package has been renamed to `apollo-reporting-protobuf`. No new versions of the old package will be published. [PR #4453](https://github.com/apollographql/apollo-server/pull/4453) -- Implementations of `ApolloServer` for serverless frameworks such as Lambda now override the `serverlessFramework()` method to return true. We have changed our own integrations, but other implementations that extend `ApolloServer` which need this behavior should do the same. Support for `engine.sendReportsImmediately` will be dropped in Apollo Server 3.x. [PR #4453](https://github.com/apollographql/apollo-server/pull/4453) +- Implementations of `ApolloServer` for serverless frameworks such as Lambda now override the `serverlessFramework()` method to return true. We have changed our own integrations, but other implementations that extend `ApolloServer` which need this behavior should do the same. Support for `engine.sendReportsImmediately` will be dropped in Apollo Server 3.x. [PR #4453](https://github.com/apollographql/apollo-server/pull/4453) - The `GraphQLServiceContext` type passed to the plugin serverWillStart method now contains `apollo` and `serverlessFramework` values. [PR #4453](https://github.com/apollographql/apollo-server/pull/4453) @@ -403,12 +410,12 @@ Certain undersupported and underused Apollo Server features have been removed in ## v2.15.1 -- The default branch of the repository has been changed to `main`. As this changed a number of references in the repository's `package.json` and `README.md` files (e.g., for badges, links, etc.), this necessitates a release to publish those changes to npm. [PR #4302](https://github.com/apollographql/apollo-server/pull/4302) +- The default branch of the repository has been changed to `main`. As this changed a number of references in the repository's `package.json` and `README.md` files (e.g., for badges, links, etc.), this necessitates a release to publish those changes to npm. [PR #4302](https://github.com/apollographql/apollo-server/pull/4302) ## v2.15.0 -- `apollo-engine-reporting`: Added a `reportTiming` API to allow trace reporting to be enabled or disabled on a per request basis. The option takes either a boolean or a predicate function that takes a [`GraphQLRequestContextDidResolveOperation`](https://github.com/apollographql/apollo-server/blob/a926b7eedbb87abab2ec70fb03d71743985cb18d/packages/apollo-server-types/src/index.ts#L185-L190) or [`GraphQLRequestContextDidEncounterErrors`](https://github.com/apollographql/apollo-server/blob/a926b7eedbb87abab2ec70fb03d71743985cb18d/packages/apollo-server-types/src/index.ts#L191-L195) and returns a boolean. If the boolean is false the request will not be instrumented for tracing and no trace will be sent to Apollo Graph Manager. The default is `true` so all traces will get instrumented and sent, which is the same as the previous default behavior. [PR #3918](https://github.com/apollographql/apollo-server/pull/3918) -- `apollo-engine-reporting`: Removed `GraphQLServerOptions.reporting`. It isn't known whether a trace will be reported at the beginning of the request because of the above change. We believe this field was only used internally within Apollo Server; let us know if this is a problem and we can suggest alternatives. Additionally, the field `requestContext.metrics.captureTraces` is now initialized later in the request pipeline. [PR #3918](https://github.com/apollographql/apollo-server/pull/3918) +- `apollo-engine-reporting`: Added a `reportTiming` API to allow trace reporting to be enabled or disabled on a per request basis. The option takes either a boolean or a predicate function that takes a [`GraphQLRequestContextDidResolveOperation`](https://github.com/apollographql/apollo-server/blob/a926b7eedbb87abab2ec70fb03d71743985cb18d/packages/apollo-server-types/src/index.ts#L185-L190) or [`GraphQLRequestContextDidEncounterErrors`](https://github.com/apollographql/apollo-server/blob/a926b7eedbb87abab2ec70fb03d71743985cb18d/packages/apollo-server-types/src/index.ts#L191-L195) and returns a boolean. If the boolean is false the request will not be instrumented for tracing and no trace will be sent to Apollo Graph Manager. The default is `true` so all traces will get instrumented and sent, which is the same as the previous default behavior. [PR #3918](https://github.com/apollographql/apollo-server/pull/3918) +- `apollo-engine-reporting`: Removed `GraphQLServerOptions.reporting`. It isn't known whether a trace will be reported at the beginning of the request because of the above change. We believe this field was only used internally within Apollo Server; let us know if this is a problem and we can suggest alternatives. Additionally, the field `requestContext.metrics.captureTraces` is now initialized later in the request pipeline. [PR #3918](https://github.com/apollographql/apollo-server/pull/3918) - `apollo-engine-reporting`: Make Apollo Server throw if schema reporting is enabled for a gateway or federated service. [PR #4246](https://github.com/apollographql/apollo-server/pull/4246) - `apollo-engine-reporting`: Remove the `experimental_` prefix from schema reporting options, and specifically rename `experimental_schemaReporting` option name to `reportSchema`. (The old option names remain functional, but are deprecated.) [PR #4236](https://github.com/apollographql/apollo-server/pull/4236) @@ -420,7 +427,7 @@ Certain undersupported and underused Apollo Server features have been removed in - `apollo-engine-reporting`: Add environment variable `APOLLO_SCHEMA_REPORTING` that can enable schema reporting. If `experimental__schemaReporting` is set it will override the environment variable. [PR #4206](https://github.com/apollographql/apollo-server/pull/4206) - `apollo-engine-reporting`: The schema reporting URL has been changed to use the new dedicated sub-domain `https://edge-server-reporting.api.apollographql.com`. [PR #4232](https://github.com/apollographql/apollo-server/pull/4232) -- `apollo-server-core`: Though Apollo Server **is not affected** due to the way it is integrated, in response to [an upstream security advisory for GraphQL Playground](https://github.com/prisma-labs/graphql-playground/security/advisories/GHSA-4852-vrh7-28rf) we have published [the same patch](https://github.com/prisma-labs/graphql-playground/commit/bf1883db538c97b076801a60677733816cb3cfb7) on our `@apollographql/graphql-playground-html` fork and bumped Apollo Server to use it. Again, this was done out of an **abundance of caution** since the way that Apollo Server utilizes `renderPlaygroundPage` is _not_ vulnerable as it does not allow per-request Playground configuration that could allow interpolation of user-input. [PR #4231](https://github.com/apollographql/apollo-server/pull/4231) +- `apollo-server-core`: Though Apollo Server **is not affected** due to the way it is integrated, in response to [an upstream security advisory for GraphQL Playground](https://github.com/prisma-labs/graphql-playground/security/advisories/GHSA-4852-vrh7-28rf) we have published [the same patch](https://github.com/prisma-labs/graphql-playground/commit/bf1883db538c97b076801a60677733816cb3cfb7) on our `@apollographql/graphql-playground-html` fork and bumped Apollo Server to use it. Again, this was done out of an **abundance of caution** since the way that Apollo Server utilizes `renderPlaygroundPage` is _not_ vulnerable as it does not allow per-request Playground configuration that could allow interpolation of user-input. [PR #4231](https://github.com/apollographql/apollo-server/pull/4231) ## v2.14.3 @@ -428,7 +435,7 @@ Certain undersupported and underused Apollo Server features have been removed in ## v2.14.2 -> **Note:** This release is is related to a GitHub Security Advisory published by the Apollo Server team. Please read the attached advisory to understand the impact. +> **Note:** This release is is related to a GitHub Security Advisory published by the Apollo Server team. Please read the attached advisory to understand the impact. - โš ๏ธ **SECURITY:** Pass all schema validation rules to the subscription server, including validation rules that restrict introspection when introspection is meant to be disabled. **[Read the full GitHub Security Advisory for details](https://github.com/apollographql/apollo-server/security/advisories/GHSA-w42g-7vfc-xf37)**. @@ -436,14 +443,14 @@ Certain undersupported and underused Apollo Server features have been removed in > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/2da65ef9204027e43baedf9ce385bb3794fd0c9b) -- `apollo-server-testing`: Ensure that user-provided context is cloned when using `createTestClient`, per the instructions in the [integration testing]() section of the Apollo Server documentation. [Issue #4170](https://github.com/apollographql/apollo-server/issues/4170) [PR #4175](https://github.com/apollographql/apollo-server/pull/4175) +- `apollo-server-testing`: Ensure that user-provided context is cloned when using `createTestClient`, per the instructions in the [integration testing]() section of the Apollo Server documentation. [Issue #4170](https://github.com/apollographql/apollo-server/issues/4170) [PR #4175](https://github.com/apollographql/apollo-server/pull/4175) ## v2.14.0 > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/d159e320879f594ba2d04036e3e1aa0653ff164d) -- `apollo-server-core` / `apollo-server-plugin-base`: Add support for `willResolveField` and corresponding end-handler within `executionDidStart`. This brings the remaining bit of functionality that was previously only available from `graphql-extensions` to the new plugin API. The `graphql-extensions` API (which was never documented) will be deprecated in Apollo Server 3.x. To see the documentation for the request pipeline API, see [its documentation](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). For more details, see the attached PR. [PR #3988](https://github.com/apollographql/apollo-server/pull/3988) -- `apollo-server-core`: Deprecate `graphql-extensions`. All internal usages of the `graphql-extensions` API have been migrated to the request pipeline plugin API. For any implementor-supplied `extensions`, a deprecation warning will be printed once per-extension, per-server-startup, notifying of the intention to deprecate. Extensions should migrate to the plugin API, which is outlined in [its documentation](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). [PR #4135](https://github.com/apollographql/apollo-server/pull/4135) +- `apollo-server-core` / `apollo-server-plugin-base`: Add support for `willResolveField` and corresponding end-handler within `executionDidStart`. This brings the remaining bit of functionality that was previously only available from `graphql-extensions` to the new plugin API. The `graphql-extensions` API (which was never documented) will be deprecated in Apollo Server 3.x. To see the documentation for the request pipeline API, see [its documentation](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). For more details, see the attached PR. [PR #3988](https://github.com/apollographql/apollo-server/pull/3988) +- `apollo-server-core`: Deprecate `graphql-extensions`. All internal usages of the `graphql-extensions` API have been migrated to the request pipeline plugin API. For any implementor-supplied `extensions`, a deprecation warning will be printed once per-extension, per-server-startup, notifying of the intention to deprecate. Extensions should migrate to the plugin API, which is outlined in [its documentation](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). [PR #4135](https://github.com/apollographql/apollo-server/pull/4135) - `apollo-engine-reporting`: **Currently only for non-federated graphs.** Added an _experimental_ schema reporting option, `experimental_schemaReporting`, for Apollo Graph Manager users. **During @@ -452,13 +459,13 @@ Certain undersupported and underused Apollo Server features have been removed in Prior to the introduction of this feature, the only way to get schemas into the schema registry in Apollo Graph Manager was to use the CLI and run - `apollo schema:push`. _Apollo schema reporting protocol_ is a *new* + `apollo schema:push`. _Apollo schema reporting protocol_ is a _new_ specification for GraphQL servers to automatically report schemas to the Apollo Graph Manager schema registry. **To enable schema reporting,** provide a Graph Manager API key (available free from [Apollo Graph Manager](https://engine.apollographql.com/)) in the - `APOLLO_KEY` environment variable *and* set the `experimental_schemaReporting` + `APOLLO_KEY` environment variable _and_ set the `experimental_schemaReporting` option to `true` in the Apollo Server constructor options, like so: ```js @@ -472,19 +479,21 @@ Certain undersupported and underused Apollo Server features have been removed in }); ``` - > When enabled, a schema reporter is initiated by the `apollo-engine-reporting` agent. It will loop until the `ApolloServer` instance is stopped, periodically calling back to Apollo Graph Manager to send information. The life-cycle of this reporter is managed by the agent. + > When enabled, a schema reporter is initiated by the `apollo-engine-reporting` agent. It will loop until the `ApolloServer` instance is stopped, periodically calling back to Apollo Graph Manager to send information. The life-cycle of this reporter is managed by the agent. For more details on the implementation of this new protocol, see the PR which introduced it to Apollo Server and the [preview documentation](https://github.com/apollographql/apollo-schema-reporting-preview-docs). [PR #4084](https://github.com/apollographql/apollo-server/pull/4084) + - `apollo-engine-reporting`: The underlying integration of this plugin, which instruments and traces the graph's resolver performance and transmits these metrics to [Apollo Graph Manager](https://engine.apollographql.com/), has been changed from the (soon to be deprecated) `graphql-extensions` API to the new [request pipeline `plugins` API](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). [PR #3998](https://github.com/apollographql/apollo-server/pull/3998) - _This change should be purely an implementation detail for a majority of users_. There are, however, some special considerations which are worth noting: + _This change should be purely an implementation detail for a majority of users_. There are, however, some special considerations which are worth noting: - - The federated tracing plugin's `ftv1` response on `extensions` (which is present on the response from an implementing service to the gateway) is now placed on the `extensions` _after_ the `formatResponse` hook. Anyone leveraging the `extensions`.`ftv1` data from the `formatResponse` hook will find that it is no longer present at that phase. -- `apollo-tracing`: This package's internal integration with Apollo Server has been switched from using the soon-to-be-deprecated `graphql-extensions` API to using [the request pipeline plugin API](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). Behavior should remain otherwise the same. [PR #3991](https://github.com/apollographql/apollo-server/pull/3991) -- `apollo-cache-control`: This package's internal integration with Apollo Server has been switched from using the soon-to-be-deprecated `graphql-extensions` API to using [the request pipeline plugin API](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). Behavior should remain otherwise the same. [PR #3997](https://github.com/apollographql/apollo-server/pull/3997) + - The federated tracing plugin's `ftv1` response on `extensions` (which is present on the response from an implementing service to the gateway) is now placed on the `extensions` _after_ the `formatResponse` hook. Anyone leveraging the `extensions`.`ftv1` data from the `formatResponse` hook will find that it is no longer present at that phase. + +- `apollo-tracing`: This package's internal integration with Apollo Server has been switched from using the soon-to-be-deprecated `graphql-extensions` API to using [the request pipeline plugin API](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). Behavior should remain otherwise the same. [PR #3991](https://github.com/apollographql/apollo-server/pull/3991) +- `apollo-cache-control`: This package's internal integration with Apollo Server has been switched from using the soon-to-be-deprecated `graphql-extensions` API to using [the request pipeline plugin API](https://www.apollographql.com/docs/apollo-server/integrations/plugins/). Behavior should remain otherwise the same. [PR #3997](https://github.com/apollographql/apollo-server/pull/3997) ## v2.13.0 @@ -493,16 +502,16 @@ Certain undersupported and underused Apollo Server features have been removed in - Allow passing a `WebSocket.Server` to `ApolloServer.installSubscriptionHandlers`. [PR #2314](https://github.com/apollographql/apollo-server/pull/2314) - `apollo-server-lambda`: Support file uploads on AWS Lambda [Issue #1419](https://github.com/apollographql/apollo-server/issues/1419) [Issue #1703](https://github.com/apollographql/apollo-server/issues/1703) [PR #3926](https://github.com/apollographql/apollo-server/pull/3926) - `apollo-engine-reporting`: Fix inadvertent conditional formatting which prevented automated persisted query (APQ) hits and misses from being reported to Apollo Graph Manager. [PR #3986](https://github.com/apollographql/apollo-server/pull/3986) -- `apollo-engine-reporting`: Deprecate the `ENGINE_API_KEY` environment variable in favor of its new name, `APOLLO_KEY`. Continued use of `ENGINE_API_KEY` will result in deprecation warnings and support for it will be removed in a future major version. [#3923](https://github.com/apollographql/apollo-server/pull/3923) -- `apollo-engine-reporting`: Deprecated the `APOLLO_SCHEMA_TAG` environment variable in favor of its new name, `APOLLO_GRAPH_VARIANT`. Similarly, within the `engine` configuration object, the `schemaTag` property has been renamed `graphVariant`. The functionality remains otherwise unchanged, but their new names mirror the name used within Apollo Graph Manager. Continued use of the now-deprecated names will result in deprecation warnings and support will be dropped completely in the next "major" update. To avoid misconfiguration, a runtime error will be thrown if _both_ new and deprecated names are set. [PR #3855](https://github.com/apollographql/apollo-server/pull/3855) -- `apollo-engine-reporting-protobuf`: __(This is a breaking change only if you directly depend on `apollo-engine-reporting-protobuf`.)__ Drop legacy fields that were never used by `apollo-engine-reporting`. Added new fields `StatsContext` to allow `apollo-server` to send summary stats instead of full traces, and renamed `FullTracesReport` to `Report` and `Traces` to `TracesAndStats` since reports now can include stats as well as traces. +- `apollo-engine-reporting`: Deprecate the `ENGINE_API_KEY` environment variable in favor of its new name, `APOLLO_KEY`. Continued use of `ENGINE_API_KEY` will result in deprecation warnings and support for it will be removed in a future major version. [#3923](https://github.com/apollographql/apollo-server/pull/3923) +- `apollo-engine-reporting`: Deprecated the `APOLLO_SCHEMA_TAG` environment variable in favor of its new name, `APOLLO_GRAPH_VARIANT`. Similarly, within the `engine` configuration object, the `schemaTag` property has been renamed `graphVariant`. The functionality remains otherwise unchanged, but their new names mirror the name used within Apollo Graph Manager. Continued use of the now-deprecated names will result in deprecation warnings and support will be dropped completely in the next "major" update. To avoid misconfiguration, a runtime error will be thrown if _both_ new and deprecated names are set. [PR #3855](https://github.com/apollographql/apollo-server/pull/3855) +- `apollo-engine-reporting-protobuf`: **(This is a breaking change only if you directly depend on `apollo-engine-reporting-protobuf`.)** Drop legacy fields that were never used by `apollo-engine-reporting`. Added new fields `StatsContext` to allow `apollo-server` to send summary stats instead of full traces, and renamed `FullTracesReport` to `Report` and `Traces` to `TracesAndStats` since reports now can include stats as well as traces. ## v2.12.0 > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/71a3863f59f4ab2c9052c316479d94c6708c4309) -- `apollo-server-core`: Support providing a custom logger implementation (e.g. [`winston`](https://npm.im/winston), [`bunyan`](https://npm.im/bunyan), etc.) to capture server console messages. Though there has historically been limited output from Apollo Server, some messages are important to capture in the larger context of production logging facilities or can benefit from using more advanced structure, like JSON-based logging. This also introduces a `logger` property to the `GraphQLRequestContext` that is exposed to plugins, making it possible for plugins to leverage the same server-level logger, and allowing implementors to create request-specific log contexts, if desired. When not provided, these will still output to `console`. [PR #3894](https://github.com/apollographql/apollo-server/pull/3894) -- `apollo-server-core`: When operating in gateway mode using the `gateway` property of the Apollo Server constructor options, the failure to initialize a schema during initial start-up, e.g. connectivity problems, will no longer result in the federated executor from being assigned when the schema eventually becomes available. This precludes a state where the gateway may never become available to serve federated requests, even when failure conditions are no longer present. [PR #3811](https://github.com/apollographql/apollo-server/pull/3811) +- `apollo-server-core`: Support providing a custom logger implementation (e.g. [`winston`](https://npm.im/winston), [`bunyan`](https://npm.im/bunyan), etc.) to capture server console messages. Though there has historically been limited output from Apollo Server, some messages are important to capture in the larger context of production logging facilities or can benefit from using more advanced structure, like JSON-based logging. This also introduces a `logger` property to the `GraphQLRequestContext` that is exposed to plugins, making it possible for plugins to leverage the same server-level logger, and allowing implementors to create request-specific log contexts, if desired. When not provided, these will still output to `console`. [PR #3894](https://github.com/apollographql/apollo-server/pull/3894) +- `apollo-server-core`: When operating in gateway mode using the `gateway` property of the Apollo Server constructor options, the failure to initialize a schema during initial start-up, e.g. connectivity problems, will no longer result in the federated executor from being assigned when the schema eventually becomes available. This precludes a state where the gateway may never become available to serve federated requests, even when failure conditions are no longer present. [PR #3811](https://github.com/apollographql/apollo-server/pull/3811) - `apollo-server-core`: Prevent a condition which prefixed an error message on each request when the initial gateway initialization resulted in a Promise-rejection which was memoized and re-prepended with `Invalid options provided to ApolloServer:` on each request. [PR #3811](https://github.com/apollographql/apollo-server/pull/3811) - `apollo-server-express`: Disable the automatic inclusion of the `x-powered-by: express` header. [PR #3821](https://github.com/apollographql/apollo-server/pull/3821) - `apollo-engine-reporting`: Avoid creating new arrays when building trace trees. [PR #3479](https://github.com/apollographql/apollo-server/pull/3479) @@ -512,14 +521,14 @@ Certain undersupported and underused Apollo Server features have been removed in > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/056f083ddaf116633e6f759a2b3d69248bb18f66) -- The range of accepted `peerDependencies` versions for `graphql` has been widened to include `graphql@^15.0.0-rc.2` so as to accommodate the latest release-candidate of the `graphql@15` package, and an intention to support it when it is finally released on the `latest` npm tag. While this change will subdue peer dependency warnings for Apollo Server packages, many dependencies from outside of this repository will continue to raise similar warnings until those packages own `peerDependencies` are updated. It is unlikely that all of those packages will update their ranges prior to the final version of `graphql@15` being released, but if everything is working as expected, the warnings can be safely ignored. [PR #3825](https://github.com/apollographql/apollo-server/pull/3825) +- The range of accepted `peerDependencies` versions for `graphql` has been widened to include `graphql@^15.0.0-rc.2` so as to accommodate the latest release-candidate of the `graphql@15` package, and an intention to support it when it is finally released on the `latest` npm tag. While this change will subdue peer dependency warnings for Apollo Server packages, many dependencies from outside of this repository will continue to raise similar warnings until those packages own `peerDependencies` are updated. It is unlikely that all of those packages will update their ranges prior to the final version of `graphql@15` being released, but if everything is working as expected, the warnings can be safely ignored. [PR #3825](https://github.com/apollographql/apollo-server/pull/3825) ## v2.10.1 > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/dba97895485d6444535a684d4646f1363954f698) - `apollo-server-core`: Update GraphQL Playground to latest version to remove a rogue curly-brace appearing in the top-right corner of the interface under certain conditions. [PR #3702](https://github.com/apollographql/apollo-server/pull/3702) [Playground PR](https://github.com/apollographql/graphql-playground/pull/21) -- `apollo-server-core`: Typings: Allow the `cache` property inside `persistedQueries` to be optional. This was already optional at runtime where it defaults to the top-level global cache when unspecified, but with the introduction of the `ttl` property, it now makes sense that one may be provided without the other. [#3671](https://github.com/apollographql/apollo-server/pull/3671) +- `apollo-server-core`: Typings: Allow the `cache` property inside `persistedQueries` to be optional. This was already optional at runtime where it defaults to the top-level global cache when unspecified, but with the introduction of the `ttl` property, it now makes sense that one may be provided without the other. [#3671](https://github.com/apollographql/apollo-server/pull/3671) ## v2.10.0 @@ -539,10 +548,10 @@ Certain undersupported and underused Apollo Server features have been removed in > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/0743d6b2f1737758cf09e80d2086917772bc00c9) -- `apollo-engine-reporting`: Fix regression introduced by [#3614](https://github.com/apollographql/apollo-server/pull/3614) which caused `PersistedQueryNotFoundError`, `PersistedQueryNotSupportedError` and `InvalidGraphQLRequestError` errors to be triggered before the `requestDidStart` handler triggered `treeBuilder`'s `startTiming` method. This fix preserves the existing behavior by special-casing these specific errors. [#3638](https://github.com/apollographql/apollo-server/pull/3638) fixes [#3627](https://github.com/apollographql/apollo-server/issues/3627) +- `apollo-engine-reporting`: Fix regression introduced by [#3614](https://github.com/apollographql/apollo-server/pull/3614) which caused `PersistedQueryNotFoundError`, `PersistedQueryNotSupportedError` and `InvalidGraphQLRequestError` errors to be triggered before the `requestDidStart` handler triggered `treeBuilder`'s `startTiming` method. This fix preserves the existing behavior by special-casing these specific errors. [#3638](https://github.com/apollographql/apollo-server/pull/3638) fixes [#3627](https://github.com/apollographql/apollo-server/issues/3627) - `apollo-server-cloud-functions`: Transmit CORS headers on `OPTIONS` request. [#3557](https://github.com/apollographql/apollo-server/pull/3557) - `apollo-server-caching`: De-compose options interface for `KeyValueCache.prototype.set` to accommodate better TSDoc annotations for its properties (e.g. to specify that `ttl` is defined in _seconds_). [#3619](https://github.com/apollographql/apollo-server/pull/3619) -- `apollo-server-core`, `apollo-server-caching`: Introduce a `ttl` property, specified in seconds, on the options for automated persisted queries (APQ) which applies specific TTL settings to the cache `set`s during APQ registration. Previously, all APQ cache records were set to 300 seconds. Additionally, this adds support (to the underlying `apollo-server-caching` mechanisms) for a time-to-live (TTL) value of `null` which, when supported by the cache implementation, skips the assignment of a TTL value altogether. This allows the cache's controller to determine when eviction happens (e.g. cache forever, and purge least recently used when the cache is full), which may be desireable for network cache stores (e.g. Memcached, Redis). [#3623](https://github.com/apollographql/apollo-server/pull/3623) +- `apollo-server-core`, `apollo-server-caching`: Introduce a `ttl` property, specified in seconds, on the options for automated persisted queries (APQ) which applies specific TTL settings to the cache `set`s during APQ registration. Previously, all APQ cache records were set to 300 seconds. Additionally, this adds support (to the underlying `apollo-server-caching` mechanisms) for a time-to-live (TTL) value of `null` which, when supported by the cache implementation, skips the assignment of a TTL value altogether. This allows the cache's controller to determine when eviction happens (e.g. cache forever, and purge least recently used when the cache is full), which may be desireable for network cache stores (e.g. Memcached, Redis). [#3623](https://github.com/apollographql/apollo-server/pull/3623) - `apollo-server-core`: Upgrade TS to 3.7.3 [#3618](https://github.com/apollographql/apollo-server/pull/3618) ## v2.9.14 @@ -598,7 +607,7 @@ Certain undersupported and underused Apollo Server features have been removed in > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/fc7462ec5f8604bd6cba99aa9a377a9b8e045566) -- `@apollo/gateway`, `@apollo/federation`, `apollo-engine-reporting`: Update `apollo-graphql` dependency to bring in [`apollo-tooling`'s #1551](https://github.com/apollographql/apollo-tooling/pull/1551) which resolve runtime errors when its source is minified. While this fixes a particular minification bug when Apollo Server packages are minified, we _do not_ recommend minification of server code in most cases. [#3387](https://github.com/apollographql/apollo-server/pull/3387) fixes [#3335](https://github.com/apollographql/apollo-server/issues/3335) +- `@apollo/gateway`, `@apollo/federation`, `apollo-engine-reporting`: Update `apollo-graphql` dependency to bring in [`apollo-tooling`'s #1551](https://github.com/apollographql/apollo-tooling/pull/1551) which resolve runtime errors when its source is minified. While this fixes a particular minification bug when Apollo Server packages are minified, we _do not_ recommend minification of server code in most cases. [#3387](https://github.com/apollographql/apollo-server/pull/3387) fixes [#3335](https://github.com/apollographql/apollo-server/issues/3335) - `apollo-server-koa`: Correctly declare dependency on `koa-compose`. [#3356](https://github.com/apollographql/apollo-server/pull/3356) - `apollo-server-core`: Preserve any `extensions` that have been placed on the response when pre-execution errors occur. [#3394](https://github.com/apollographql/apollo-server/pull/3394) @@ -606,7 +615,7 @@ Certain undersupported and underused Apollo Server features have been removed in > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/a1fbf95fc01739d5cbaa59919149bb85c563fdaa) -- `apollo-server-express`: Add direct dependency on `express` to allow for usage of `express.Router` for `getMiddleware` functionality (from [#2435](https://github.com/apollographql/apollo-server/pull/2435)). Previously, unlike other server integration packages, `apollo-server-express` did not directly need `express` as a dependency since it only relied on `express` for TypeScript typings. [#3239](https://github.com/apollographql/apollo-server/pull/3239) fixes [#3238](https://github.com/apollographql/apollo-server/issues/3238) +- `apollo-server-express`: Add direct dependency on `express` to allow for usage of `express.Router` for `getMiddleware` functionality (from [#2435](https://github.com/apollographql/apollo-server/pull/2435)). Previously, unlike other server integration packages, `apollo-server-express` did not directly need `express` as a dependency since it only relied on `express` for TypeScript typings. [#3239](https://github.com/apollographql/apollo-server/pull/3239) fixes [#3238](https://github.com/apollographql/apollo-server/issues/3238) - `apollo-server-lambda`: Add `@types/aws-lambda` as a direct dependency to `apollo-server-express` to allow usage of its typings without needing to separately install it. [#3242](https://github.com/apollographql/apollo-server/pull/3242) fixes [#2351](https://github.com/apollographql/apollo-server/issue/2351) ## v2.9.2 @@ -621,7 +630,7 @@ Certain undersupported and underused Apollo Server features have been removed in > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/029c8dca3af812ee70589cdb6de749df3d2843d8) - `apollo-server-core`: Make `formatError` available to subscriptions in the same spirit as the existing `formatResponse`. [#2942](https://github.com/apollographql/apollo-server/pull/2942) -- `apollo-engine-reporting`: The behavior of the `engine.maxAttempts` parameter previously did not match its documentation. It is documented as being the max number of attempts *including* the initial attempt, but until this release it was actually the number of retries *excluding* the initial attempt. The behavior has been changed to match the documentation (and the literal reading of the option name). [#3218](https://github.com/apollographql/apollo-server/pull/3218) +- `apollo-engine-reporting`: The behavior of the `engine.maxAttempts` parameter previously did not match its documentation. It is documented as being the max number of attempts _including_ the initial attempt, but until this release it was actually the number of retries _excluding_ the initial attempt. The behavior has been changed to match the documentation (and the literal reading of the option name). [#3218](https://github.com/apollographql/apollo-server/pull/3218) - `apollo-engine-reporting`: When sending the report fails with a server-side 5xx error, include the full error from the server in the logs. [#3218](https://github.com/apollographql/apollo-server/pull/3218) - `apollo-server-core`: Fix regression which prevented the resizing of the schema panel in GraphQL Playground. [#3224](https://github.com/apollographql/apollo-server/pull/3224) and [upstream](https://github.com/apollographql/graphql-playground/pull/19) @@ -629,7 +638,7 @@ Certain undersupported and underused Apollo Server features have been removed in > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/6037f6e80fdaa53b50b99ae94d93c724c382c23c) -- `apollo-server-express`, `apollo-server-koa`: A new `getMiddleware` method has been introduced, which accepts the same parameters as `applyMiddleware` with the exception of the `app` property. This allows implementors to obtain the middleware directly and "`use`" it within an existing `app`. In the near-term, this should ease some of the pain points with the previous technique. Longer-term, we are exploring what we consider to be a much more natural approach by introducing an "HTTP transport" in Apollo Server 3.x. See [this proposal issue](https://github.com/apollographql/apollo-server/issues/3184) for more information. [#2435](https://github.com/apollographql/apollo-server/pull/2435) +- `apollo-server-express`, `apollo-server-koa`: A new `getMiddleware` method has been introduced, which accepts the same parameters as `applyMiddleware` with the exception of the `app` property. This allows implementors to obtain the middleware directly and "`use`" it within an existing `app`. In the near-term, this should ease some of the pain points with the previous technique. Longer-term, we are exploring what we consider to be a much more natural approach by introducing an "HTTP transport" in Apollo Server 3.x. See [this proposal issue](https://github.com/apollographql/apollo-server/issues/3184) for more information. [#2435](https://github.com/apollographql/apollo-server/pull/2435) - `@apollo/federation`: `buildFederatedSchema`'s `typeDefs` parameter now accepts arrays of `DocumentNode`s (i.e. type definitions wrapped in `gql`) and `resolvers` to make the migration from a single service into a federated service easier for teams previously utilizing this pattern. [#3188](https://github.com/apollographql/apollo-server/pull/3188) ## v2.8.2 @@ -646,7 +655,7 @@ Certain undersupported and underused Apollo Server features have been removed in - `apollo-engine-reporting`: Fix reporting errors which have non-array `path` fields (eg, non-GraphQLError errors). [PR #3112](https://github.com/apollographql/apollo-server/pull/3112) - `apollo-engine-reporting`: Add missing `apollo-server-caching` dependency. [PR #3054](https://github.com/apollographql/apollo-server/pull/3054) - `apollo-server-hapi`: Revert switch from `accept` and `boom` which took place in v2.8.0. [PR #3089](https://github.com/apollographql/apollo-server/pull/3089) -- `@apollo/gateway`: Change the `setInterval` timer, which is used to continuously check for updates to a federated graph from the Apollo Graph Manager, to be an `unref`'d timer. Without this change, the server wouldn't terminate properly once polling had started since the event-loop would continue to have unprocessed events on it. [PR #3105](https://github.com/apollographql/apollo-server/pull/3105) +- `@apollo/gateway`: Change the `setInterval` timer, which is used to continuously check for updates to a federated graph from the Apollo Graph Manager, to be an `unref`'d timer. Without this change, the server wouldn't terminate properly once polling had started since the event-loop would continue to have unprocessed events on it. [PR #3105](https://github.com/apollographql/apollo-server/pull/3105) - Switch to using community `@types/graphql-upload` types. - `apollo-server-fastify`: Change the typing of the HTTP `response` from `OutgoingMessage` to `ServerResponse`. [Commit](https://github.com/apollographql/apollo-server/commit/7638f643fa0445f5f8151ef884da779d85fb954c) - `apollo-server-hapi`: Pass the `raw` request and response objects to `graphql-upload`s `processRequest` method to align on the same TypeScript types. [Commit](https://github.com/apollographql/apollo-server/commit/8e49b288a6aecd0e134637e64ef4ed751aa8d304) @@ -655,7 +664,7 @@ Certain undersupported and underused Apollo Server features have been removed in > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/ddeb71f8d6a0f3c91646aa0c7c99d2003b5bf73f) -- `@apollo/federation`: Add support for "value types", which are type definitions which live on multiple services' types, inputs, unions or interfaces. These common types must be identical by name, kind and field across all services. [PR #3063](https://github.com/apollographql/apollo-server/pull/3063) +- `@apollo/federation`: Add support for "value types", which are type definitions which live on multiple services' types, inputs, unions or interfaces. These common types must be identical by name, kind and field across all services. [PR #3063](https://github.com/apollographql/apollo-server/pull/3063) - `apollo-server-express`: Use the Express `send` method, rather than calling `net.Socket.prototype.end`. [PR #2842](https://github.com/apollographql/apollo-server/pull/2842) - `apollo-server-hapi`: Update internal dependencies to use scoped packages `@hapi/accept` and `@hapi/boom`, in place of `accept` and `boom` respectively. [PR #3089](https://github.com/apollographql/apollo-server/pull/3089) @@ -671,7 +680,7 @@ Certain undersupported and underused Apollo Server features have been removed in > [See complete versioning details.](https://github.com/apollographql/apollo-server/commit/2f87e4af9a6f1e3c8f4c51b4f77860bd3150c8c6) - `apollo-engine-reporting`: If an error is thrown by a custom variable transform function passed into the reporting option `sendVariableValues: { transform: ... }`, all variable values will be replaced with the string `[PREDICATE_FUNCTION_ERROR]`. -- `apollo-server-express`: Typing fix for the `connection` property, which was missing from the `ExpressContext` interface. [PR #2959](https://github.com/apollographql/apollo-server/pull/2959) +- `apollo-server-express`: Typing fix for the `connection` property, which was missing from the `ExpressContext` interface. [PR #2959](https://github.com/apollographql/apollo-server/pull/2959) - `@apollo/gateway`: Ensure execution of correct document within multi-operation documents by including the `operationName` in the cache key used when caching query plans used in federated execution. [PR #3084](https://github.com/apollographql/apollo-server/pull/3084) ## v2.7.0 @@ -684,21 +693,28 @@ Certain undersupported and underused Apollo Server features have been removed in ```js engine: { - sendVariableValues: { all: true } + sendVariableValues: { + all: true; + } } ``` + - `apollo-engine-reporting`: **Behavior change**: By default, send no GraphQL request headers and values to Apollo's servers instead of sending all. Adding the new EngineReportingOption `sendHeaders` to send some or all header values. This replaces the `privateHeaders` option, which is now deprecated. [PR #2931](https://github.com/apollographql/apollo-server/pull/2931) - To maintain the previous behavior of transmitting **all** GraphQL request headers and values, configure `engine`.`sendHeaders` as following: - ```js - engine: { - sendHeaders: { all: true } - } - ``` + To maintain the previous behavior of transmitting **all** GraphQL request headers and values, configure `engine`.`sendHeaders` as following: + + ```js + engine: { + sendHeaders: { + all: true; + } + } + ``` + - `apollo-engine-reporting`: **Behavior change**: If the error returned from the `engine.rewriteError` hook has an `extensions` property, that property will be used instead of the original error's extensions. Document that changes to most other `GraphQLError` fields by `engine.rewriteError` are ignored. [PR #2932](https://github.com/apollographql/apollo-server/pull/2932) - `apollo-engine-reporting`: **Behavior change**: The `engine.maskErrorDetails` option, deprecated by `engine.rewriteError` in v2.5.0, now behaves a bit more like the new option: while all error messages will be redacted, they will still show up on the appropriate nodes in a trace. [PR #2932](https://github.com/apollographql/apollo-server/pull/2932) -- `apollo-server-core`, `@apollo/gateway`: **Introduced managed federation support**. For more information on managed federation, see [the blog post](https://blog.apollographql.com/announcing-managed-federation-265c9f0bc88e) or jump to the [documentation for managed federation](https://www.apollographql.com/docs/platform/federation/). -- `@apollo/gateway@0.7.1`: Don't print a warning about an unspecified "graph variant" (previously, and in many ways still, known as "schema tag") every few seconds. We do highly recommend specifying one when using the Apollo Platform features though! [PR #3043](https://github.com/apollographql/apollo-server/pull/3043) +- `apollo-server-core`, `@apollo/gateway`: **Introduced managed federation support**. For more information on managed federation, see [the blog post](https://blog.apollographql.com/announcing-managed-federation-265c9f0bc88e) or jump to the [documentation for managed federation](https://www.apollographql.com/docs/platform/federation/). +- `@apollo/gateway@0.7.1`: Don't print a warning about an unspecified "graph variant" (previously, and in many ways still, known as "schema tag") every few seconds. We do highly recommend specifying one when using the Apollo Platform features though! [PR #3043](https://github.com/apollographql/apollo-server/pull/3043) - `graphql-playground`: Update to resolve incorrect background color on tabs when using the `light` theme. [PR #2989](https://github.com/apollographql/apollo-server/pull/2989) [Issue #2979](https://github.com/apollographql/apollo-server/issues/2979) - `graphql-playground`: Fix "Query Planner" and "Tracing" panels which were off the edge of the viewport. - `apollo-server-plugin-base`: Fix `GraphQLRequestListener` type definitions to allow `return void`. [PR #2368](https://github.com/apollographql/apollo-server/pull/2368) @@ -758,28 +774,28 @@ Certain undersupported and underused Apollo Server features have been removed in ## v2.6.0 -- `apollo-server-core`: Introduce new `didEncounterErrors` life-cycle hook which has access to unformatted `errors` property on the `requestContext`, which is the first positional parameter that this new request life-cycle receives. [PR #2719](https://github.com/apollographql/apollo-server/pull/2719) -- `apollo-server-core`: Allow request pipeline life-cycle hooks (i.e. plugins) to modify the response's `http.status` code (an integer) in the event of an error. When combined with the new `didEncounterErrors` life-cycle hook (see above), this will allow modifying the HTTP status code in the event of an error. [PR #2714](https://github.com/apollographql/apollo-server/pull/2714) +- `apollo-server-core`: Introduce new `didEncounterErrors` life-cycle hook which has access to unformatted `errors` property on the `requestContext`, which is the first positional parameter that this new request life-cycle receives. [PR #2719](https://github.com/apollographql/apollo-server/pull/2719) +- `apollo-server-core`: Allow request pipeline life-cycle hooks (i.e. plugins) to modify the response's `http.status` code (an integer) in the event of an error. When combined with the new `didEncounterErrors` life-cycle hook (see above), this will allow modifying the HTTP status code in the event of an error. [PR #2714](https://github.com/apollographql/apollo-server/pull/2714) - `apollo-server-lambda`: Set `callbackWaitsForEmptyEventLoop` to `false` for `OPTIONS` requests to return as soon as the `callback` is triggered instead of waiting for the event loop to empty. [PR #2638](https://github.com/apollographql/apollo-server/pull/2638) -- `apollo-server`: Support `onHealthCheck` in the `ApolloServer` constructor in the same way as `cors` is supported. This contrasts with the `-express`, `-hapi`, etc. variations which accept this parameter via their `applyMiddleware` methods and will remain as-is. [PR #2672](https://github.com/apollographql/apollo-server/pull/2672) +- `apollo-server`: Support `onHealthCheck` in the `ApolloServer` constructor in the same way as `cors` is supported. This contrasts with the `-express`, `-hapi`, etc. variations which accept this parameter via their `applyMiddleware` methods and will remain as-is. [PR #2672](https://github.com/apollographql/apollo-server/pull/2672) - core: Expose SHA-512 hex hash digest of the Engine API key to plugins, when available, as `engine.apiKeyHash`. [PR #2685](https://github.com/apollographql/apollo-server/pull/2685) [PR #2736](https://github.com/apollographql/apollo-server/pull/2736) - `apollo-datasource-rest`: If another `Content-type` is already set on the response, don't overwrite it with `application/json`, allowing the user's initial `Content-type` to prevail. [PR #2520](https://github.com/apollographql/apollo-server/issues/2035) - Don't add `cacheControl` directive if one has already been defined. [PR #2428](https://github.com/apollographql/apollo-server/pull/2428) - `apollo-cache-control`: Do not respond with `Cache-control` headers if the HTTP response contains `errors`. [PR #2715](https://github.com/apollographql/apollo-server/pull/2715) - `apollo-server-core`: Skip loading `util.promisify`, `Array.flat`, `Array.flatMap`, and `Object.fromEntries` polyfills, none of which are needed in Node 12+. [PR #2278](https://github.com/apollographql/apollo-server/pull/2278) [PR #5244](https://github.com/apollographql/apollo-server/pull/5244) - `apollo-server-core`: Lazy load `subscriptions-transport-ws` in core [PR #2278](https://github.com/apollographql/apollo-server/pull/2278) -- `apollo-server-cache-redis`: **BREAKING FOR USERS OF `apollo-server-cache-redis`** (This is a package that must be updated separately but shares the same `CHANGELOG.md` with Apollo Server itself.) A new **major** version of this package has been published and updated to support Redis Standalone, Cluster and Sentinel modes. This is a breaking change since it is now based on [`ioredis`](https://github.com/luin/ioredis) instead of [`node_redis`](https://github.com/NodeRedis/node_redis). Although this update is compatible with the most common uses of `apollo-server-cache-redis`, please check the [options supported by `ioredis`](https://github.com/luin/ioredis/blob/master/API.md#new-redisport-host-options) while updating to this version. The constructor options are passed directly from `RedisCache` to the new Redis adapter. The pre-1.0 versions should continue to work with Apollo Server without modification. [PR #1770](https://github.com/apollographql/apollo-server/pull/1770) +- `apollo-server-cache-redis`: **BREAKING FOR USERS OF `apollo-server-cache-redis`** (This is a package that must be updated separately but shares the same `CHANGELOG.md` with Apollo Server itself.) A new **major** version of this package has been published and updated to support Redis Standalone, Cluster and Sentinel modes. This is a breaking change since it is now based on [`ioredis`](https://github.com/luin/ioredis) instead of [`node_redis`](https://github.com/NodeRedis/node_redis). Although this update is compatible with the most common uses of `apollo-server-cache-redis`, please check the [options supported by `ioredis`](https://github.com/luin/ioredis/blob/master/API.md#new-redisport-host-options) while updating to this version. The constructor options are passed directly from `RedisCache` to the new Redis adapter. The pre-1.0 versions should continue to work with Apollo Server without modification. [PR #1770](https://github.com/apollographql/apollo-server/pull/1770) ## v2.5.1 -- Upgrade GraphQL Playground to the latest upstream release. This release also includes a new "Query Plan" panel for displaying the query planning results when running the Apollo Gateway. +- Upgrade GraphQL Playground to the latest upstream release. This release also includes a new "Query Plan" panel for displaying the query planning results when running the Apollo Gateway. ## v2.5.0 ### New -- New plugin package `apollo-server-plugin-response-cache` implementing a full query response cache based on `apollo-cache-control` hints. The implementation added a few hooks and context fields; see the PR for details. There is a slight change to `cacheControl` object: previously, `cacheControl.stripFormattedExtensions` defaulted to false if you did not provide a `cacheControl` option object, but defaulted to true if you provided (eg) `cacheControl: {defaultMaxAge: 10}`. Now `stripFormattedExtensions` defaults to false unless explicitly provided as `true`, or if you use the legacy boolean `cacheControl: true`. For more information, [read the documentation](https://www.apollographql.com/docs/apollo-server/features/caching). [PR #2437](https://github.com/apollographql/apollo-server/pull/2437) -- Add `rewriteError` option to `EngineReportingOptions` (i.e. the `engine` property of the `ApolloServer` constructor). When defined as a `function`, it will receive an `err` property as its first argument which can be used to manipulate (e.g. redaction) an error prior to sending it to Apollo Engine by modifying, e.g., its `message` property. The error can also be suppressed from reporting entirely by returning an explicit `null` value. For more information, [read the documentation](https://www.apollographql.com/docs/apollo-server/features/errors#for-apollo-engine-reporting) and the [`EngineReportingOptions` API reference](https://www.apollographql.com/docs/apollo-server/api/apollo-server#enginereportingoptions). `maskErrorDetails` is now deprecated. [PR #1639](https://github.com/apollographql/apollo-server/pull/1639) +- New plugin package `apollo-server-plugin-response-cache` implementing a full query response cache based on `apollo-cache-control` hints. The implementation added a few hooks and context fields; see the PR for details. There is a slight change to `cacheControl` object: previously, `cacheControl.stripFormattedExtensions` defaulted to false if you did not provide a `cacheControl` option object, but defaulted to true if you provided (eg) `cacheControl: {defaultMaxAge: 10}`. Now `stripFormattedExtensions` defaults to false unless explicitly provided as `true`, or if you use the legacy boolean `cacheControl: true`. For more information, [read the documentation](https://www.apollographql.com/docs/apollo-server/features/caching). [PR #2437](https://github.com/apollographql/apollo-server/pull/2437) +- Add `rewriteError` option to `EngineReportingOptions` (i.e. the `engine` property of the `ApolloServer` constructor). When defined as a `function`, it will receive an `err` property as its first argument which can be used to manipulate (e.g. redaction) an error prior to sending it to Apollo Engine by modifying, e.g., its `message` property. The error can also be suppressed from reporting entirely by returning an explicit `null` value. For more information, [read the documentation](https://www.apollographql.com/docs/apollo-server/features/errors#for-apollo-engine-reporting) and the [`EngineReportingOptions` API reference](https://www.apollographql.com/docs/apollo-server/api/apollo-server#enginereportingoptions). `maskErrorDetails` is now deprecated. [PR #1639](https://github.com/apollographql/apollo-server/pull/1639) - `apollo-server-azure-functions`: Support `@azure/functions` to enable Apollo Server [Typescript development in Azure Functions](https://azure.microsoft.com/en-us/blog/improving-the-typescript-support-in-azure-functions/). [PR #2487](https://github.com/apollographql/apollo-server/pull/2487) - Allow `GraphQLRequestListener` callbacks in plugins to depend on `this`. [PR #2470](https://github.com/apollographql/apollo-server/pull/2470) - `apollo-server-testing`: Add `variables` and `operationName` to `Query` and `Mutation` types. [PR #2307](https://github.com/apollographql/apollo-server/pull/2307) [Issue #2172](https://github.com/apollographql/apollo-server/issue/2172) @@ -794,7 +810,7 @@ Certain undersupported and underused Apollo Server features have been removed in ## v2.4.8 -- No functional changes in this version. The patch version has been bumped to fix the `README.md` displayed on the [npm package for `apollo-server`](https://npm.im/apollo-server) as a result of a broken publish. Apologies for the additional noise! +- No functional changes in this version. The patch version has been bumped to fix the `README.md` displayed on the [npm package for `apollo-server`](https://npm.im/apollo-server) as a result of a broken publish. Apologies for the additional noise! ## v2.4.7 @@ -821,7 +837,7 @@ Certain undersupported and underused Apollo Server features have been removed in ## v2.4.2 -- `apollo-server-fastify` is now on Apollo Server and lives within the `apollo-server` repository. This is being introduced in a _patch_ version, however it's a _major_ version bump from the last time `apollo-server-fastify` was published under `1.0.2`. [PR #1971](https://github.com/apollostack/apollo-server/pull/1971) +- `apollo-server-fastify` is now on Apollo Server and lives within the `apollo-server` repository. This is being introduced in a _patch_ version, however it's a _major_ version bump from the last time `apollo-server-fastify` was published under `1.0.2`. [PR #1971](https://github.com/apollostack/apollo-server/pull/1971) - Move `apollo-graphql` package to the `apollo-tooling` repository [PR #2316](https://github.com/apollographql/apollo-server/pull/2316) ## v2.4.1 @@ -841,7 +857,7 @@ Certain undersupported and underused Apollo Server features have been removed in ## v2.3.3 -- `apollo-server` (only): Stop double-invocation of `serverWillStart` life-cycle event. (More specific integrations - e.g. Express, Koa, Hapi, etc. - were unaffected.) [PR #2239](https://github.com/apollographql/apollo-server/pull/2239) +- `apollo-server` (only): Stop double-invocation of `serverWillStart` life-cycle event. (More specific integrations - e.g. Express, Koa, Hapi, etc. - were unaffected.) [PR #2239](https://github.com/apollographql/apollo-server/pull/2239) - Avoid traversing `graphql-upload` module tree in run-time environments which aren't Node.js. [PR #2235](https://github.com/apollographql/apollo-server/pull/2235) ## v2.3.2 @@ -852,7 +868,7 @@ Certain undersupported and underused Apollo Server features have been removed in - Don't write to the persisted query cache until execution will begin. [PR #2227](https://github.com/apollographql/apollo-server/pull/2227) - `apollo-server-azure-functions`: Added Azure Functions documentation and deployment examples [PR #2131](https://github.com/apollographql/apollo-server/pull/2131), -[Issue #2092](https://github.com/apollographql/apollo-server/issues/2092) + [Issue #2092](https://github.com/apollographql/apollo-server/issues/2092) ## v2.3.1 @@ -860,11 +876,11 @@ Certain undersupported and underused Apollo Server features have been removed in ## v2.3.0 -- **BREAKING FOR NODE.JS <= 8.5.0 ONLY**: To continue using Apollo Server 2.x in versions of Node.js prior to v8.5.0, file uploads must be disabled by setting `uploads: false` on the `ApolloServer` constructor options. Without explicitly disabling file-uploads, the server will `throw` at launch (with instructions and a link to our documentation). +- **BREAKING FOR NODE.JS <= 8.5.0 ONLY**: To continue using Apollo Server 2.x in versions of Node.js prior to v8.5.0, file uploads must be disabled by setting `uploads: false` on the `ApolloServer` constructor options. Without explicitly disabling file-uploads, the server will `throw` at launch (with instructions and a link to our documentation). - This early deprecation is due to changes in the third-party `graphql-upload` package which Apollo Server utilizes to implement out-of-the-box file upload functionality. While, in general, Apollo Server 2.x aims to support all Node.js versions which were under an LTS policy at the time of its release, we felt this required an exception. By `throw`-ing when `uploads` is not explicitly set to `false`, we aim to make it clear immediately (rather than surprisingly) that this deprecation has taken effect. + This early deprecation is due to changes in the third-party `graphql-upload` package which Apollo Server utilizes to implement out-of-the-box file upload functionality. While, in general, Apollo Server 2.x aims to support all Node.js versions which were under an LTS policy at the time of its release, we felt this required an exception. By `throw`-ing when `uploads` is not explicitly set to `false`, we aim to make it clear immediately (rather than surprisingly) that this deprecation has taken effect. - While Node.js 6.x is covered by a [Long Term Support agreement by the Node.js Foundation](https://github.com/nodejs/Release#release-schedule) until April 2019, there are substantial performance (e.g. [V8](https://v8.dev/) improvements) and language changes (e.g. "modern" ECMAScript support) offered by newer Node.js engines (e.g. 8.x, 10.x). We encourage _all users_ of Apollo Server to update to newer LTS versions of Node.js prior to the "end-of-life" dates for their current server version. + While Node.js 6.x is covered by a [Long Term Support agreement by the Node.js Foundation](https://github.com/nodejs/Release#release-schedule) until April 2019, there are substantial performance (e.g. [V8](https://v8.dev/) improvements) and language changes (e.g. "modern" ECMAScript support) offered by newer Node.js engines (e.g. 8.x, 10.x). We encourage _all users_ of Apollo Server to update to newer LTS versions of Node.js prior to the "end-of-life" dates for their current server version. **We intend to drop support for Node.js 6.x in the next major version of Apollo Server.** @@ -889,10 +905,10 @@ Certain undersupported and underused Apollo Server features have been removed in ## v2.2.3 - When `generateClientInfo` is not used to define the client name, client version and -client reference ID, Apollo Server will now default to the values present in the HTTP headers -of the request (`apollographql-client-name`, `apollographql-client-reference-id` and -`apollographql-client-version` respectively). As a last resort, when those headers are not set, -the query extensions' `clientInfo` values will be used. [PR #1960](https://github.com/apollographql/apollo-server/pull/1960) + client reference ID, Apollo Server will now default to the values present in the HTTP headers + of the request (`apollographql-client-name`, `apollographql-client-reference-id` and + `apollographql-client-version` respectively). As a last resort, when those headers are not set, + the query extensions' `clientInfo` values will be used. [PR #1960](https://github.com/apollographql/apollo-server/pull/1960) ## v2.2.2 @@ -901,8 +917,8 @@ the query extensions' `clientInfo` values will be used. [PR #1960](https://githu ## v2.2.1 -- Added support for an array of `modules` on the `ApolloServer` constructor options. Each element of the `modules` can point to a module which exports `typeDefs` and `resolvers`. These modules can be used in lieu of, or in combination with, directly specifying `schema` or `typeDefs`/`resolvers` on the constructor options. This provides greater modularity and improved organization for logic which might be limited to a specific service. [`8f6481e6`](https://github.com/apollographql/apollo-server/commit/8f6481e60f8418738f9ebbe9d5ab5e7e2ce4d319). -- Added `resolveObject` support to query execution. [`bb67584`](https://github.com/apollographql/apollo-server/commit/bb67584a224843a5b2509c2ebdd94e616fe6227c). +- Added support for an array of `modules` on the `ApolloServer` constructor options. Each element of the `modules` can point to a module which exports `typeDefs` and `resolvers`. These modules can be used in lieu of, or in combination with, directly specifying `schema` or `typeDefs`/`resolvers` on the constructor options. This provides greater modularity and improved organization for logic which might be limited to a specific service. [`8f6481e6`](https://github.com/apollographql/apollo-server/commit/8f6481e60f8418738f9ebbe9d5ab5e7e2ce4d319). +- Added `resolveObject` support to query execution. [`bb67584`](https://github.com/apollographql/apollo-server/commit/bb67584a224843a5b2509c2ebdd94e616fe6227c). - Fix broken `apollo-server-cloud-functions` in 2.2.0 caused by missing TypeScript project references which resulted in the package not being published to npm in compiled form. [PR #1948](https://github.com/apollographql/apollo-server/pull/1948) ## v2.2.0 @@ -916,7 +932,7 @@ the query extensions' `clientInfo` values will be used. [PR #1960](https://githu - Follow-up on the work in [PR #1516](https://github.com/apollographql/apollo-server/pull/1516) to also fix missing insertion cursor/caret when a custom GraphQL configuration is specified which doesn't specify its own `cursorShape` property. [PR #1607](https://github.com/apollographql/apollo-server/pull/1607) - Azure functions support [Issue #1752](https://github.com/apollographql/apollo-server/issue/1752) [PR #1753](https://github.com/apollographql/apollo-server/pull/1753) [PR #1948](https://github.com/apollographql/apollo-server/pull/1948) - Allow JSON parsing in `RESTDataSource` of Content Type `application/hal+json`. [PR #185](https://github.com/apollographql/apollo-server/pull/1853) -- Add support for a `requestAgent` configuration parameter within the `engine` configuration. This can be utilized when a proxy is necessary to transmit tracing and metrics data to Apollo Engine. It accepts either an [`http.Agent`](https://nodejs.org/docs/latest-v8.x/api/http.html#http_class_http_agent) or [`https.Agent`](https://nodejs.org/docs/latest-v8.x/api/https.html#https_class_https_agent) and behaves the same as the `agent` parameter to Node.js' [`http.request`](https://nodejs.org/docs/latest-v8.x/api/http.html#http_http_request_options_callback). [PR #1879](https://github.com/apollographql/apollo-server/pull/1879) +- Add support for a `requestAgent` configuration parameter within the `engine` configuration. This can be utilized when a proxy is necessary to transmit tracing and metrics data to Apollo Engine. It accepts either an [`http.Agent`](https://nodejs.org/docs/latest-v8.x/api/http.html#http_class_http_agent) or [`https.Agent`](https://nodejs.org/docs/latest-v8.x/api/https.html#https_class_https_agent) and behaves the same as the `agent` parameter to Node.js' [`http.request`](https://nodejs.org/docs/latest-v8.x/api/http.html#http_http_request_options_callback). [PR #1879](https://github.com/apollographql/apollo-server/pull/1879) - Allow an optional parameter to the `RESTDataSource` constructor which takes a `node-fetch`-compatible `fetch` implementation that will be used for HTTP calls instead of the default fetch. [PR #1807](https://github.com/apollographql/apollo-server/pull/1807) ## v2.1.0 @@ -1124,7 +1140,7 @@ ListenOptions: ## v1.3.0 -- **Breaking:** `apollo-server-hapi`: now supports Hapi v17, and no longer supports Hapi v16. For information on running Apollo Server 1.x with Hapi v16, [check this documentation](https://www.apollographql.com/docs/apollo-server/v1/servers/hapi.html#Hapi-16). +- **Breaking:** `apollo-server-hapi`: now supports Hapi v17, and no longer supports Hapi v16. For information on running Apollo Server 1.x with Hapi v16, [check this documentation](https://www.apollographql.com/docs/apollo-server/v1/servers/hapi.html#Hapi-16). - **New package**: `apollo-server-adonis` supporting the Adonis framework! - The `graphqlOptions` parameter to server GraphQL integration functions now accepts context as a function and as an object with a prototype. [PR #679](https://github.com/apollographql/apollo-server/pull/679) - `apollo-server-express`: Send Content-Length header. diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 33b6e4a12a1..7095877b020 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -8,12 +8,12 @@ Oh, and if you haven't already, sign up for the [Apollo community forum](https:/ Here are some ways to contribute to the project, from easiest to most difficult: -* [Reporting bugs](#reporting-bugs) -* [Improving the documentation](#improving-the-documentation) -* [Responding to issues](#responding-to-issues) -* [Small bug fixes](#small-bug-fixes) -* [Suggesting features](#suggesting-features) -* [Big pull requests](#big-prs) +- [Reporting bugs](#reporting-bugs) +- [Improving the documentation](#improving-the-documentation) +- [Responding to issues](#responding-to-issues) +- [Small bug fixes](#small-bug-fixes) +- [Suggesting features](#suggesting-features) +- [Big pull requests](#big-prs) ## Issues @@ -57,8 +57,8 @@ Once there is a consensus on the need for a new feature, proceed as listed below This includes: -* Big bug fixes -* New features +- Big bug fixes +- New features For significant changes to a repository, itโ€™s important to settle on a design before starting on the implementation. This way, we can make sure that major improvements get the care and attention they deserve. Since big changes can be risky and might not always get merged, itโ€™s good to reduce the amount of possible wasted effort by agreeing on an implementation design/plan first. diff --git a/DEVELOPMENT.md b/DEVELOPMENT.md index 4bc0e1eafdd..c78dbdaeedf 100644 --- a/DEVELOPMENT.md +++ b/DEVELOPMENT.md @@ -44,7 +44,7 @@ When at least one changeset exists, the workflow will open and update a release Apollo Server is "dual-published", shipping with both ESM and CJS, and leverages deep imports. Combined with TypeScript, this introduces a fair amount of complexity into the build infrastructure of this repository. A few quirks to keep in mind while working in this project: -* Each dual-published package has 2 tsconfigs: one for ESM and one for CJS. These must also be referenced at the top-level in the respective esm/cjs-specific tsconfig files. -* Deep imports in the `@apollo/server` package must be listed within the `package.json` ["exports"](https://nodejs.org/api/packages.html#exports) property. It's important to note that each "exports" entry must be specifically in the order: "types", "import", "require". Both [Node](https://nodejs.org/api/packages.html#exports) and [TypeScript](https://www.typescriptlang.org/docs/handbook/esm-node.html#packagejson-exports-imports-and-self-referencing)(via [`moduleResolution: "node16"`](https://www.typescriptlang.org/tsconfig#moduleResolution)) make use of these entries. -* Additional deep imports must be represented in `server/` and must contain a `package.json` file. See [`server/express4/package.json`](server/express4/package.json) for an example. This is separate from the actual source code for this new import, which should exist in `server/src/`. This is used by TypeScript's CommonJS configuration (`moduleResolution: "node"`). -* Smoke tests to ensure proper builds and importability exist in the `smoke-test` directory. If new deep imports are added, they should be incorporated into the smoke tests. +- Each dual-published package has 2 tsconfigs: one for ESM and one for CJS. These must also be referenced at the top-level in the respective esm/cjs-specific tsconfig files. +- Deep imports in the `@apollo/server` package must be listed within the `package.json` ["exports"](https://nodejs.org/api/packages.html#exports) property. It's important to note that each "exports" entry must be specifically in the order: "types", "import", "require". Both [Node](https://nodejs.org/api/packages.html#exports) and [TypeScript](https://www.typescriptlang.org/docs/handbook/esm-node.html#packagejson-exports-imports-and-self-referencing)(via [`moduleResolution: "node16"`](https://www.typescriptlang.org/tsconfig#moduleResolution)) make use of these entries. +- Additional deep imports must be represented in `server/` and must contain a `package.json` file. See [`server/express4/package.json`](server/express4/package.json) for an example. This is separate from the actual source code for this new import, which should exist in `server/src/`. This is used by TypeScript's CommonJS configuration (`moduleResolution: "node"`). +- Smoke tests to ensure proper builds and importability exist in the `smoke-test` directory. If new deep imports are added, they should be incorporated into the smoke tests. diff --git a/ROADMAP.md b/ROADMAP.md index fd7ef9c3621..c1367a5949e 100644 --- a/ROADMAP.md +++ b/ROADMAP.md @@ -1,6 +1,6 @@ # Apollo Server Roadmap -*Last updated: January 2022* +_Last updated: January 2022_ > **Please note:** This is an approximation of **larger effort** work planned for the next 3 - 6 months. It does not cover all new functionality that will be added, and nothing here is set in stone. Also note that each of these releases, and several patch/minor releases in-between, will include bug fixes (based on issue triaging) and community submitted PRs. @@ -8,19 +8,19 @@ **Estimated release:** Q2 2022 -We are now actively working on Apollo Server 4. This project consists of a number of refactors focused on making Apollo Server simpler to use, maintain, document, and extend. Much of this builds on proposals that were originally part of the Apollo Server 3 plan which we removed from that release due to scope. Much of the below is based on a [proposal from 2019](https://github.com/apollographql/apollo-server/issues/3184) which is one of the most up-voted issues in our repository. +We are now actively working on Apollo Server 4. This project consists of a number of refactors focused on making Apollo Server simpler to use, maintain, document, and extend. Much of this builds on proposals that were originally part of the Apollo Server 3 plan which we removed from that release due to scope. Much of the below is based on a [proposal from 2019](https://github.com/apollographql/apollo-server/issues/3184) which is one of the most up-voted issues in our repository. ### Replace 9 core-maintained bindings with a stable HTTP abstraction -Currently, Apollo Server has core-maintained bindings to a large number of web frameworks and serverless environments. There is no stable, easy API to allow you to write your own binding to a new framework. These bindings are all maintained by the Apollo Server core team, but we do not have practical experience running servers that use most of these frameworks. Adding new features to Apollo Server often requires making very similar changes in every binding package, which is a big barrier to making real improvements. The different bindings are implemented as separate npm packages which subclass the core `ApolloServer` package, which means that the API for `ApolloServer` is [different for different packages](https://www.apollographql.com/docs/apollo-server/api/apollo-server/#framework-specific-middleware-function), which is challenging to document and understand. +Currently, Apollo Server has core-maintained bindings to a large number of web frameworks and serverless environments. There is no stable, easy API to allow you to write your own binding to a new framework. These bindings are all maintained by the Apollo Server core team, but we do not have practical experience running servers that use most of these frameworks. Adding new features to Apollo Server often requires making very similar changes in every binding package, which is a big barrier to making real improvements. The different bindings are implemented as separate npm packages which subclass the core `ApolloServer` package, which means that the API for `ApolloServer` is [different for different packages](https://www.apollographql.com/docs/apollo-server/api/apollo-server/#framework-specific-middleware-function), which is challenging to document and understand. In Apollo Server 4, we will follow the 2019 proposal to add a well-defined API for processing an HTTP request to `ApolloServer`. `ApolloServer` will have a single documentable API rather than being extended via subclasses. Framework integration packages can export functions or classes that take in `ApolloServer` and call its methods appropriately instead of adding their own methods to the object. As part of the main Apollo Server package, we will maintain integrations that work on Node's built-in `http` request and response types. You will be able to use these directly with `http.createServer` or with Express (whose request and response types extend Node's). -Currently, the `apollo-server` package exports a "batteries-included" version of `ApolloServer` with a very different API: it has a `listen` method instead of a framework integration method, and various aspects of it cannot be configured. The fact that the package whose name is closest to the name of the project exports a class with the same name as every other `ApolloServer` but has different behavior may in some ways be "convenient" but it makes it challenging to document; we have recently started taking the verbose approach of always referring to `apollo-server` as "the batteries-included `apollo-server` package". In Apollo Server 4, we plan to introduce an `ApolloServerStandalone` class in the main Apollo Server package which is similar in concept to remove ambiguity and make the name more easily reference-able. +Currently, the `apollo-server` package exports a "batteries-included" version of `ApolloServer` with a very different API: it has a `listen` method instead of a framework integration method, and various aspects of it cannot be configured. The fact that the package whose name is closest to the name of the project exports a class with the same name as every other `ApolloServer` but has different behavior may in some ways be "convenient" but it makes it challenging to document; we have recently started taking the verbose approach of always referring to `apollo-server` as "the batteries-included `apollo-server` package". In Apollo Server 4, we plan to introduce an `ApolloServerStandalone` class in the main Apollo Server package which is similar in concept to remove ambiguity and make the name more easily reference-able. -The Apollo Server core team will no longer try to maintain integrations for which we have no hands-on operational experience. **This is where the larger community can help!** During the development process of Apollo Server 4, we'd like to find community members who are excited to maintain the integrations for most of the web frameworks (Fastify, Hapi, Koa, Micro, Lambda, Google Cloud Functions, Azure Functions, and Cloudflare). Writing these integrations should be much easier in the new model, because the only responsibility of these packages will be translating requests and responses between the framework's native format and the types used by `ApolloServer`'s API. We will add more direct support to the `ApolloServer` API for the patterns that are repeated across the serverless integration packages today. +The Apollo Server core team will no longer try to maintain integrations for which we have no hands-on operational experience. **This is where the larger community can help!** During the development process of Apollo Server 4, we'd like to find community members who are excited to maintain the integrations for most of the web frameworks (Fastify, Hapi, Koa, Micro, Lambda, Google Cloud Functions, Azure Functions, and Cloudflare). Writing these integrations should be much easier in the new model, because the only responsibility of these packages will be translating requests and responses between the framework's native format and the types used by `ApolloServer`'s API. We will add more direct support to the `ApolloServer` API for the patterns that are repeated across the serverless integration packages today. Separating these packages from the Apollo Server release cycle will have many advantages: @@ -32,9 +32,10 @@ We are looking for volunteers to maintain these integrations! See [the issues wi ### Combine many packages into `@apollo/server` -You may have noticed the recurring phrase "the main Apollo Server package" above. Another challenge of maintaining and using Apollo Server is how many separate npm packages are in the project! Most of the core logic is in `apollo-server-core`, but this isn't the package that users interact most directly with. There isn't much value provided by the separation into many classes, but it does add a lot of complexity to maintaining and using the package. +You may have noticed the recurring phrase "the main Apollo Server package" above. Another challenge of maintaining and using Apollo Server is how many separate npm packages are in the project! Most of the core logic is in `apollo-server-core`, but this isn't the package that users interact most directly with. There isn't much value provided by the separation into many classes, but it does add a lot of complexity to maintaining and using the package. We believe we can combine the following packages into a single `@apollo/server` package: + - `apollo-server-core` - `apollo-server` (the "batteries-included" package --- we are looking forward to never having to type this phrase again) - `apollo-server-plugin-base` @@ -53,7 +54,7 @@ This package will be the only package in the `apollo-server` repository. We can ### Remove features that wrap framework-specific libraries -Some parts of Apollo Server take parameters that are passed directly to framework-specific libraries. These libraries are ones that most users of the framework already know how to use, and they vary across frameworks making our APIs challenging to document. This specifically includes body-parsing and CORS-handling packages. +Some parts of Apollo Server take parameters that are passed directly to framework-specific libraries. These libraries are ones that most users of the framework already know how to use, and they vary across frameworks making our APIs challenging to document. This specifically includes body-parsing and CORS-handling packages. In Apollo Server 4, framework integration functions won't try to wrap these basic framework-specific libraries. If you want to use our Express middleware, you'll be required to use the standard `body-parser` middleware yourself. (We'll have good error handling to help you figure out if you forgot to do this.) This means we won't have to have a special option just for passing options through to `body-parser`. @@ -63,7 +64,7 @@ In Apollo Server 4, framework integration functions won't try to wrap these basi The โ€œhealth checkโ€ feature is just "an HTTP path which always returns 200 and which allows you to pass in a handler to run arbitrary code instead". Itโ€™s notably not actually connected to the state of the ApolloServer object itself (eg, if something is broken that prevents operations from executing then health checks can still pass). Our docs (https://www.apollographql.com/docs/apollo-server/monitoring/health-checks/) no longer actively encourage the use of this feature and instead recommend running a trivial GraphQL query over GET. If for some reason running this query is not an acceptable health check, folks integrating Apollo Server into a web framework can define their own health check via their web framework directly. -This feature is the main remaining reason that ApolloServer needs to know about and parse URI paths. This leads to a bunch of confusing complexity: thereโ€™s a concept of `server.graphqlPath` which middleware uses to decide whether or not to process a request as GraphQL, but you can also use your web framework itself to specify directly what path middleware is mounted at. (This flexibility is not provided to the batteries-included server, which always has a `graphqlPath` of `/`.) Path parsing has been a challenge for many integrations; for example, when running in AWS Lambda, the full path at which your function is invoked generally contains some extra components which need to be ignored to figure out if the request is a health check. +This feature is the main remaining reason that ApolloServer needs to know about and parse URI paths. This leads to a bunch of confusing complexity: thereโ€™s a concept of `server.graphqlPath` which middleware uses to decide whether or not to process a request as GraphQL, but you can also use your web framework itself to specify directly what path middleware is mounted at. (This flexibility is not provided to the batteries-included server, which always has a `graphqlPath` of `/`.) Path parsing has been a challenge for many integrations; for example, when running in AWS Lambda, the full path at which your function is invoked generally contains some extra components which need to be ignored to figure out if the request is a health check. So if weโ€™re removing health checks from Apollo Server, we can also remove path parsing; if you want to mount your GraphQL server at `/api/graphql`, you should do that via `app.use('/api/graphql', apolloServer.getMiddleware())` rather than via `app.use(apolloServer.getMiddleware({ graphqlPath: '/api/graphql' }))` (both of which currently work with slightly and confusingly different semantics). @@ -71,7 +72,7 @@ We may consider leaving health check support in `ApolloServerStandalone` (where ### Replace `apollo-server-caching` with an existing key/value cache abstraction -The Apollo Server project includes the `apollo-server-caching` package, which defines an abstraction over key/value data stores like Redis and Memcached. This abstraction is used as a building block for several features such as the full-response cache implemented in `apollo-server-plugin-response-cache` and the caching HTTP client implemented in `apollo-datasource-rest`. The Apollo Server project maintains implementations of this interface for Redis and Memcached; the broader community has implemented the interface for several additional backends. +The Apollo Server project includes the `apollo-server-caching` package, which defines an abstraction over key/value data stores like Redis and Memcached. This abstraction is used as a building block for several features such as the full-response cache implemented in `apollo-server-plugin-response-cache` and the caching HTTP client implemented in `apollo-datasource-rest`. The Apollo Server project maintains implementations of this interface for Redis and Memcached; the broader community has implemented the interface for several additional backends. However, there's really nothing GraphQL-specific about this interface. We've discovered that the [`keyv`](https://www.npmjs.com/package/keyv) project defines a nearly-identical interface. This project has support for many backends including Redis and Memcached. If there are any backends that have an `apollo-server-caching` implementation and no `keyv` implementation, it's very easy to write your own `keyv` implementation, or one could easily write a tiny class to wrap any existing `apollo-server-caching` implementation as a `keyv` implementation. @@ -83,7 +84,7 @@ While the `apollo-server-env` package used to provide a bunch of different polyf In the off-chance that such a package does not exist, we could maintain one ourselves, but with a more specific name like `@apollo/fetch-typings` and published from its own repository on a lifecycle not strictly tied to Apollo Server releases. -(One very possible answer would be to be all-in on `node-fetch`, in the sense that packages that want to run `fetch` directly depend on `node-fetch` and allow you to override the fetcher with fetcher options whose TypeScript types depend on those defined in `@types/node-fetch`. `apollo-server-env` depends on `node-fetch` today so it seems likely that this will work. We should verify that this continues to support swapping in certain popular fetch replacements such as `make-fetch-happen`. (One odd bit is that `node-fetch` v3 only supports being used from ESM so we are sticking to v2 for now and probably should for AS4 as well.) +(One very possible answer would be to be all-in on `node-fetch`, in the sense that packages that want to run `fetch` directly depend on `node-fetch` and allow you to override the fetcher with fetcher options whose TypeScript types depend on those defined in `@types/node-fetch`. `apollo-server-env` depends on `node-fetch` today so it seems likely that this will work. We should verify that this continues to support swapping in certain popular fetch replacements such as `make-fetch-happen`. (One odd bit is that `node-fetch` v3 only supports being used from ESM so we are sticking to v2 for now and probably should for AS4 as well.) ### Replace top-level `dataSources` option with a data sources plugin @@ -125,7 +126,7 @@ This could provide exactly the same functionality to data source implementations ### Move `apollo-datasource-rest` to its own repository -`apollo-datasource-rest` is a caching HTTP client for Node which uses our `apollo-server-caching` interface to talk to a cache. Other than the fact that it implements the `DataSource` interface, its code is pretty unrelated to the rest of Apollo Server, and the current Apollo Server team has not been actively maintaining it, despite the fact that it's a nice piece of software that many find valuable. +`apollo-datasource-rest` is a caching HTTP client for Node which uses our `apollo-server-caching` interface to talk to a cache. Other than the fact that it implements the `DataSource` interface, its code is pretty unrelated to the rest of Apollo Server, and the current Apollo Server team has not been actively maintaining it, despite the fact that it's a nice piece of software that many find valuable. Its version numbering is not particularly related to Apollo Serverโ€™s version number (as it is essentially unrelated code and backwards-incompatible changes to one package generally wonโ€™t cause backwards-incompatible changes to the other) but it is currently coupled to the Apollo Server release process: we canโ€™t easily release it without releasing AS and vice versa, and its CHANGELOG is confusingly intermingled with Apollo Server changes. (These are certainly fixable problems if we wanted.) @@ -135,14 +136,13 @@ Because it is semantically pretty independent from Apollo Server, we will move i ### Move plugins which have their own package to their own repositories -Some plugins, like the usage reporting plugin, are built in to Apollo Server; they currently live in `apollo-server-core` and will live in `@apollo/server` in AS4. Other plugins live in their own packages. These plugins will move to their own repositories. Specifically, this includes ~`apollo-server-plugin-operation-registry`~ (migrated to `@apollo/server-plugin-operation-registry`) and `apollo-server-plugin-response-cache`. +Some plugins, like the usage reporting plugin, are built in to Apollo Server; they currently live in `apollo-server-core` and will live in `@apollo/server` in AS4. Other plugins live in their own packages. These plugins will move to their own repositories. Specifically, this includes ~`apollo-server-plugin-operation-registry`~ (migrated to `@apollo/server-plugin-operation-registry`) and `apollo-server-plugin-response-cache`. (Because `apollo-server-plugin-response-cache` will have no dependencies other than `@apollo/server` and `graphql`, it might be reasonable to merge it into `@apollo/server` as well. That said, keeping it as a separate package means we can make interface improvements to it on a versioning lifecycle that doesn't have to be strictly synchronized with the main Apollo Server API, so a separate package and repository is probably best.) - ### Change usage reporting defaults backwards-incompatibly to send less data -In order to make usage reporting have better performance and less potential PII leakage by default, we should change the default usage reporting to send even less information by default. We previously changed usage reporting to make variable and HTTP header reporting opt-in. We should continue down this path to make sending error bodies in traces opt-in (though we should still probably track the number of errors by default). Furthermore, now that the [Unified Reporting](https://github.com/apollographql/apollo-server/pull/4142) and [referenced field usage](https://github.com/apollographql/apollo-server/issues/5708) projects are done, we can change the defaults to make *traces* be an opt-in feature (which gives you access to traces on the Operations page, field execution counts on the Fields page, and field latencies in Explorer and VSCode timing hints) that isnโ€™t on by default. This would mean that by default we would only send summarized statistics of operations, not any data about individual requests, and the only user-provided strings would be operation signatures (with literals removed as always). +In order to make usage reporting have better performance and less potential PII leakage by default, we should change the default usage reporting to send even less information by default. We previously changed usage reporting to make variable and HTTP header reporting opt-in. We should continue down this path to make sending error bodies in traces opt-in (though we should still probably track the number of errors by default). Furthermore, now that the [Unified Reporting](https://github.com/apollographql/apollo-server/pull/4142) and [referenced field usage](https://github.com/apollographql/apollo-server/issues/5708) projects are done, we can change the defaults to make _traces_ be an opt-in feature (which gives you access to traces on the Operations page, field execution counts on the Fields page, and field latencies in Explorer and VSCode timing hints) that isnโ€™t on by default. This would mean that by default we would only send summarized statistics of operations, not any data about individual requests, and the only user-provided strings would be operation signatures (with literals removed as always). ### Set the stage for GraphQL modes other than "one response per request" diff --git a/docs/README.md b/docs/README.md index 08926348265..c37c599b641 100644 --- a/docs/README.md +++ b/docs/README.md @@ -4,6 +4,6 @@ This is the documentation **source** for this repository. The **deployed** version of the documentation for this repository is available at: -* https://www.apollographql.com/docs/apollo-server/ +- https://www.apollographql.com/docs/apollo-server/ See the [docs site README](https://github.com/apollographql/docs) for local installation and development. diff --git a/docs/source/api/apollo-server.mdx b/docs/source/api/apollo-server.mdx index b547f0390a1..2d7db1d4ae9 100644 --- a/docs/source/api/apollo-server.mdx +++ b/docs/source/api/apollo-server.mdx @@ -1,9 +1,9 @@ --- -title: "API Reference: ApolloServer" +title: 'API Reference: ApolloServer' api_reference: true --- -This article documents the `ApolloServer` class from the `@apollo/server` package. You can use the `ApolloServer` class to create an instance of Apollo Server that you can then pass to a web framework integration function (e.g., `startStandaloneServer` or `expressMiddleware`). +This article documents the `ApolloServer` class from the `@apollo/server` package. You can use the `ApolloServer` class to create an instance of Apollo Server that you can then pass to a web framework integration function (e.g., `startStandaloneServer` or `expressMiddleware`). > Check out our [Getting Started](../getting-started) guide for an example of setting up Apollo Server! @@ -21,8 +21,8 @@ Takes an `options` object as a parameter. Supported fields of this object are de import { ApolloServer } from '@apollo/server'; const server = new ApolloServer({ - typeDefs, - resolvers, + typeDefs, + resolvers, }); ``` @@ -43,6 +43,7 @@ const server = new ApolloServer({ **Specifying a schema** + @@ -51,6 +52,7 @@ const server = new ApolloServer({ ##### `typeDefs` `string`, `DocumentNode`, or `Array` + @@ -59,24 +61,26 @@ A valid [Schema Definition Language](../schema/schema/#the-schema-definition-lan **Required** unless you provide a [`schema`](#schema) or a [`gateway`](#gateway). For an example, see [Define your GraphQL schema](../getting-started/#step-3-define-your-graphql-schema). + - ##### `resolvers` `Object` or `Array` + A map of functions that populate data for individual schema fields. Can also be an array of multiple maps that are merged. -While technically optional, if you are providing `typeDefs`, it is strongly recommended that you provide `resolvers` as well. +While technically optional, if you are providing `typeDefs`, it is strongly recommended that you provide `resolvers` as well. For details, see [Resolvers](../data/resolvers/). + @@ -86,16 +90,18 @@ For details, see [Resolvers](../data/resolvers/). ##### `schema` `Object` + -An executable GraphQL schema. Under the hood, Apollo Server automatically generates this field from [`typeDefs`](#typedefs) and [`resolvers`](#resolvers). +An executable GraphQL schema. Under the hood, Apollo Server automatically generates this field from [`typeDefs`](#typedefs) and [`resolvers`](#resolvers). This field is helpful if you are using: - - [Apollo Federation](https://www.apollographql.com/docs/federation/implementing-services/#generating-a-federated-schema), which uses the `buildFederatedSchema` function to generate its schema - - A function like `makeExecutableSchema` from [`graphql-tools`](https://www.graphql-tools.com/docs/generate-schema) to create your schema - - A code-first approach (i.e., instead of a schema-first approach) + +- [Apollo Federation](https://www.apollographql.com/docs/federation/implementing-services/#generating-a-federated-schema), which uses the `buildFederatedSchema` function to generate its schema +- A function like `makeExecutableSchema` from [`graphql-tools`](https://www.graphql-tools.com/docs/generate-schema) to create your schema +- A code-first approach (i.e., instead of a schema-first approach) @@ -106,6 +112,7 @@ This field is helpful if you are using: ##### `gateway` `Object` + @@ -119,6 +126,7 @@ You can use this field to integrate your server with [Apollo Gateway](/federatio **Schema options** + @@ -128,6 +136,7 @@ You can use this field to integrate your server with [Apollo Gateway](/federatio ##### `introspection` `boolean` + @@ -135,61 +144,65 @@ You can use this field to integrate your server with [Apollo Gateway](/federatio If `true`, enables [schema introspection](https://graphql.org/learn/introspection/) by clients. This is required to use tools that figure out your server's schema from talking to it directly, like Apollo Sandbox and GraphQL Playground. (It's not needed for the non-Sandbox version of Apollo Studio Explorer, which uses the schema published in the Studio schema registry instead.) The default value is `true`, **unless** the `NODE_ENV` environment variable is set to `production`. + - ##### `fieldResolver` `GraphQLFieldResolver` + A custom resolver that will replace Apollo Server's [default field resolvers](../data/resolvers/#default-resolvers). + - ##### `rootValue` `Any` or `Function` + A value or function called with the parsed `Document`, creating the root value passed to the GraphQL executor. Providing a function is useful if you want to use a different root value depending on the operation's details, such as whether it's a query or mutation. + - ##### `validationRules` `Array` + An array containing custom functions to use as additional [validation rules](https://github.com/graphql/graphql-js/tree/master/src/validation/rules) when validating the schema. + - ##### `documentStore` `KeyValueCache` or `null` + @@ -213,20 +226,21 @@ new ApolloServer({ sizeCalculation: InMemoryLRUCache.sizeCalculation, }), // ... -}) +}); ``` Pass `null` to disable this cache entirely. + - **Protocol options** + @@ -236,11 +250,13 @@ Pass `null` to disable this cache entirely. ##### `persistedQueries` `Object` or `false` + If you're using [automated persisted queries (APQ)](../performance/apq/), you can provide an object with `cache` and/or `ttl` fields to customize how Apollo Server stores the mapping between operation hashes and query strings, or provide `false` to disable APQ entirely. + @@ -250,16 +266,18 @@ If you're using [automated persisted queries (APQ)](../performance/apq/), you ca ##### `csrfPrevention` `boolean` or `Object` + -By default, the [CSRF prevention](../security/cors#preventing-cross-site-request-forgery-csrf) feature is enabled to protect Apollo Server from CSRF and XS-Search attacks. +By default, the [CSRF prevention](../security/cors#preventing-cross-site-request-forgery-csrf) feature is enabled to protect Apollo Server from CSRF and XS-Search attacks. This feature can prevent certain `GET` requests from executing GraphQL operations if those requests don't specify [certain headers](../security/cors/#why-use-cors). You can configure the headers that allow operation execution by passing a configuration object to this option (e.g., `csrfPrevention: { requestHeaders: ['special-header'] }`). If your server has clients that send `GET` requests and those clients **aren't** one of Apollo's client libraries (Web, iOS, Kotlin), you might need to modify the configuration of those clients to use this feature. For more details, see [the CSRF prevention documentation](../security/cors#preventing-cross-site-request-forgery-csrf). You can disable this recommended security feature by passing `false` to `csrfPrevention`. + @@ -269,10 +287,11 @@ You can disable this recommended security feature by passing `false` to `csrfPre ##### `formatError` `Function` + -Provide this function to transform the structure of error objects before they're sent to a client. +Provide this function to transform the structure of error objects before they're sent to a client. The `formatError` hook receives two arguments: the first is a [`GraphQLFormattedError`](https://github.com/graphql/graphql-js/blob/29bf39faa670effd3c1561a1512ec7767658a63b/src/error/GraphQLError.ts#L215) (to be spent with the response), and the second is the original error. This function should return a [`GraphQLFormattedError`](https://github.com/graphql/graphql-js/blob/29bf39faa670effd3c1561a1512ec7767658a63b/src/error/GraphQLError.ts#L215) object. @@ -285,6 +304,7 @@ The `formatError` hook receives two arguments: the first is a [`GraphQLFormatted ##### `apollo` `Object` + @@ -304,6 +324,7 @@ An object containing configuration options for connecting Apollo Server to [Apol ##### `allowBatchedHttpRequests` `boolean` + @@ -312,11 +333,11 @@ Controls whether to allow [Batching Queries](../workflow/requests/#batching) in - **Lifecycle options** + @@ -326,6 +347,7 @@ Controls whether to allow [Batching Queries](../workflow/requests/#batching) in ##### `cache` `KeyValueCache` + @@ -344,6 +366,7 @@ To learn more about configuring Apollo Server's cache, see [Configuring cache ba ##### `plugins` `Array` + @@ -356,13 +379,13 @@ You can _also_ add plugins to your server before you start it using the [`addPlu - ##### `stopOnTerminationSignals` `boolean` + @@ -377,11 +400,11 @@ You can also manually call `stop()` in other contexts. Note that `stop()` is asy - **Debugging options** + @@ -391,23 +414,25 @@ You can also manually call `stop()` in other contexts. Note that `stop()` is asy ##### `includeStacktraceInErrorResponses` `boolean` + -If `true`, stack traces are included in GraphQL responses when errors occur. +If `true`, stack traces are included in GraphQL responses when errors occur. Defaults to `true` unless the `NODE_ENV` environment variable is `production` or `test`. + - ##### `logger` [`Logger`](https://www.npmjs.com/package/@apollo/utils.logger) + @@ -416,20 +441,22 @@ An object to use for logging in place of `console`. If provided, this object mus If you provide this value, Apollo Server automatically logs all messages of _all_ severity levels (`debug` through `error`). It is the responsibility of the logger to determine how to handle logged messages of each level. This logger is automatically added to the `GraphQLRequestContext` object that's passed to all Apollo Server [plugin functions](/apollo-server/integrations/plugins/). + - ##### `parseOptions` `Object` + An object that specifies how your server parses GraphQL operations. [See `graphql-js` for the available configuration options](https://github.com/graphql/graphql-js/blob/9df90799299f40b596938aba15e88c4cd4f2d376/src/language/parser.ts#L77). + @@ -439,10 +466,12 @@ An object that specifies how your server parses GraphQL operations. [See `graphq ##### `nodeEnv` `string` + If this is set to any string value, use that value instead of the environment variable `NODE_ENV` for the features whose defaults depend on `NODE_ENV` (such as [`introspection`](#introspection)). Note that passing the empty string here is equivalent to running with the `NODE_ENV` environment variable unset. This is primarily meant for testing the effects of the `NODE_ENV` environment variable. + @@ -454,11 +483,12 @@ If this is set to any string value, use that value instead of the environment va The async `start` method instructs Apollo Server to prepare to handle incoming operations. > Call `start` **only** if you are using a framework integration for a non-serverless environment (e.g., [`expressMiddleware`](./express-middleware)). -> * If you're using a serverless framework integration (such as Lambda), you **shouldn't** call this method before passing your server into the integration function. Your serverless integration function will take care of starting your server for you. > -> * If you're using `startStandaloneServer` you do **not** need to start your server before [passing it directly to `startStandaloneServer`](./standalone). +> - If you're using a serverless framework integration (such as Lambda), you **shouldn't** call this method before passing your server into the integration function. Your serverless integration function will take care of starting your server for you. +> +> - If you're using `startStandaloneServer` you do **not** need to start your server before [passing it directly to `startStandaloneServer`](./standalone). -Always call `await server.start()` *before* passing your server into your integration function and starting to accept requests: +Always call `await server.start()` _before_ passing your server into your integration function and starting to accept requests: @@ -469,7 +499,8 @@ const server = new ApolloServer({ }); await server.start(); -app.use('/graphql', +app.use( + '/graphql', cors(), json(), expressMiddleware(server), @@ -489,7 +520,6 @@ The `start` method triggers the following actions: 1. If your server is a [federated gateway](https://www.apollographql.com/docs/federation/managed-federation/overview/), it attempts to fetch its schema. If the fetch fails, `start` throws an error. 2. Your server calls all of the [`serverWillStart` handlers](/apollo-server/integrations/plugins-event-reference/#serverwillstart) of your installed plugins. If any of these handlers throw an error, `start` throws an error. - ## `startInBackgroundHandlingStartupErrorsByLoggingAndFailingAllRequests` **Serverless** integrations handle starting an Apollo Server instance in the background by calling the `startInBackgroundHandlingStartupErrorsByLoggingAndFailingAllRequests` method. See [Building integrations](../integrations/building-integrations#ensure-successful-startup) for more details. @@ -503,13 +533,12 @@ You can pass a [`HTTPGraphQLRequest`](./integrations/building-integrations/#cons ```ts -const result = await server - .executeHTTPGraphQLRequest({ - httpGraphQLRequest: OurHttpGraphQLRequest, - context: async () => ({ - // token: ..., - }), - }); +const result = await server.executeHTTPGraphQLRequest({ + httpGraphQLRequest: OurHttpGraphQLRequest, + context: async () => ({ + // token: ..., + }), +}); ``` @@ -517,6 +546,7 @@ const result = await server For details and examples, see [Building Integrations](../integrations/building-integrations/#execute-the-graphql-request). ## `addPlugin` + You can use the `addPlugin` method to add plugins before your server is started. This is helpful when you want to add a plugin that accepts your initialized `ApolloServer` instance itself, like so: @@ -524,9 +554,7 @@ You can use the `addPlugin` method to add plugins before your server is started. ```ts const server = new ApolloServer({ typeDefs, - plugins: [ - makeFirstPlugin(), - ], + plugins: [makeFirstPlugin()], }); server.addPlugin(makeSecondPlugin(server)); @@ -568,13 +596,15 @@ const result = await server.executeOperation({ ``` The `executeOperation` method takes two arguments: -* The first argument is an object describing the GraphQL operation to be executed. - * Supported fields are listed in the table below. -* The second optional argument is used as the operation's [context value](../data/resolvers/#the-context-argument). Note, this argument is only optional if your server _doesn't_ expect a context value (i.e., your server uses the default context because you didn't explicitly provide another one). + +- The first argument is an object describing the GraphQL operation to be executed. + - Supported fields are listed in the table below. +- The second optional argument is used as the operation's [context value](../data/resolvers/#the-context-argument). Note, this argument is only optional if your server _doesn't_ expect a context value (i.e., your server uses the default context because you didn't explicitly provide another one). Below are the available fields for the first argument of `executeOperation`: ### Fields + @@ -590,11 +620,13 @@ Below are the available fields for the first argument of `executeOperation`: ##### `query` `string` or `DocumentNode` + @@ -604,6 +636,7 @@ Below are the available fields for the first argument of `executeOperation`: ##### `variables` `object` + @@ -629,6 +664,7 @@ If `query` contains more than one operation definition, you must provide this op ##### `extensions` `object` +
**Required**. The GraphQL operation to run. Note that you must use the `query` field even if the operation is a mutation. +
An object containing any GraphQL variables to use as argument values for the executed operation. @@ -616,10 +649,12 @@ An object containing any GraphQL variables to use as argument values for the exe ##### `operationName` `string` + If `query` contains more than one operation definition, you must provide this option to indicate which operation to execute. +
@@ -643,6 +679,7 @@ The `extensions` object is usually used to pass request metadata within your ser ##### `http` `HTTPGraphQLRequest` + @@ -655,8 +692,9 @@ An object implementing the [`HTTPGraphQLRequest`](https://github.com/apollograph
## `cache` + A public readonly field on `ApolloServer` that enables you to access your server's [cache](#cache). ## `logger` -A public readonly field on `ApolloServer` that enables you to access your server's [logger](#logger). \ No newline at end of file +A public readonly field on `ApolloServer` that enables you to access your server's [logger](#logger). diff --git a/docs/source/api/express-middleware.mdx b/docs/source/api/express-middleware.mdx index ea698ce0a72..69c7188adce 100644 --- a/docs/source/api/express-middleware.mdx +++ b/docs/source/api/express-middleware.mdx @@ -1,5 +1,5 @@ --- -title: "API Reference: expressMiddleware" +title: 'API Reference: expressMiddleware' api_reference: true --- @@ -7,11 +7,11 @@ This API reference documents Apollo Server 4's [Express](https://expressjs.com/) ## `expressMiddleware` -The `expressMiddleware` function enables you to attach Apollo Server to an Express server. +The `expressMiddleware` function enables you to attach Apollo Server to an Express server. The `expressMiddleware` function expects you to set up HTTP body parsing and CORS headers for your web framework. Specifically, you should install the [`body-parser`](https://www.npmjs.com/package/body-parser) and [`cors`](https://www.npmjs.com/package/cors) packages and use them to set up your Express app, as shown below. -> See [Configuring CORS](../../security/cors#specifying-origins) for guidance on configuring the CORS behavior of your project. +> See [Configuring CORS](../../security/cors#specifying-origins) for guidance on configuring the CORS behavior of your project. The `expressMiddleware` function accepts two arguments. The first **required** argument is an instance of `ApolloServer` that has been `start`ed: @@ -43,7 +43,7 @@ app.use( expressMiddleware(server), ); //highlight-end -``` +```
@@ -64,16 +64,16 @@ The `expressMiddleware` function's second optional argument is an _object_ for c - ##### `context` +##### `context` - `Function` +`Function` -An optional asynchronous [`context` initialization function](../data/resolvers#the-context-argument). - +An optional asynchronous [`context` initialization function](../data/resolvers#the-context-argument). + The `context` function should return an object that all your server's resolvers share during an operation's execution. This enables resolvers to share helpful context values, such as a database connection. The `context` function receives `req` and `res` options which are [`express.Request`](https://github.com/DefinitelyTyped/DefinitelyTyped/blob/2c4c1d0b106a1305c384cde84bb14bbf1a938d2c/types/express-serve-static-core/index.d.ts#L367) and [`express.Response`](https://github.com/DefinitelyTyped/DefinitelyTyped/blob/2c4c1d0b106a1305c384cde84bb14bbf1a938d2c/types/express-serve-static-core/index.d.ts#L659) objects. @@ -85,7 +85,7 @@ The `context` function receives `req` and `res` options which are [`express.Requ -## Example +## Example Below is a full example of setting up `expressMiddleware`: @@ -126,7 +126,8 @@ async function startApolloServer() { // Set up our Express middleware to handle CORS, body parsing, // and our expressMiddleware function. - app.use('/', + app.use( + '/', cors(), bodyParser.json(), // expressMiddleware accepts the same arguments: @@ -137,9 +138,11 @@ async function startApolloServer() { ); // Modified server startup - await new Promise(resolve => httpServer.listen({ port: 4000 }, resolve)); + await new Promise((resolve) => + httpServer.listen({ port: 4000 }, resolve), + ); console.log(`๐Ÿš€ Server ready at http://localhost:4000/`); } ``` -
\ No newline at end of file + diff --git a/docs/source/api/plugin/cache-control.mdx b/docs/source/api/plugin/cache-control.mdx index 6fb54366103..23a287810ce 100644 --- a/docs/source/api/plugin/cache-control.mdx +++ b/docs/source/api/plugin/cache-control.mdx @@ -1,5 +1,5 @@ --- -title: "API Reference: Cache control plugin" +title: 'API Reference: Cache control plugin' api_reference: true --- @@ -11,7 +11,7 @@ This plugin enables your GraphQL server to specify a cache policy at the field l > To use the `@cacheControl` directive, you must first [define it in your schema](../../performance/caching/#in-your-schema-static). -Apollo Server installs this plugin by default in all servers, with its default configuration. You typically do not have to install this plugin yourself; you only need to do so if you want to provide non-default configuration. +Apollo Server installs this plugin by default in all servers, with its default configuration. You typically do not have to install this plugin yourself; you only need to do so if you want to provide non-default configuration. If you want to configure the `ApolloServerPluginCacheControl` plugin, import it and pass it to your `ApolloServer` constructor's `plugins` array: @@ -48,9 +48,7 @@ import { ApolloServerPluginCacheControlDisabled } from '@apollo/server/plugin/di const server = new ApolloServer({ typeDefs, resolvers, - plugins: [ - ApolloServerPluginCacheControlDisabled(), - ], + plugins: [ApolloServerPluginCacheControlDisabled()], }); ``` @@ -76,6 +74,7 @@ The plugin doesn't affect your app much if you don't use the `@cacheControl` dir ###### `defaultMaxAge` `number` + @@ -92,6 +91,7 @@ This option was popular in Apollo Server 2 as a workaround for the problem solve ###### `calculateHttpHeaders` `boolean` + @@ -100,6 +100,5 @@ By default, the cache control plugin sets the `cache-control` HTTP response head - diff --git a/docs/source/api/plugin/drain-http-server.mdx b/docs/source/api/plugin/drain-http-server.mdx index 076574cb944..4bd638ac3d5 100644 --- a/docs/source/api/plugin/drain-http-server.mdx +++ b/docs/source/api/plugin/drain-http-server.mdx @@ -1,5 +1,5 @@ --- -title: "API Reference: Drain HTTP server plugin" +title: 'API Reference: Drain HTTP server plugin' api_reference: true --- @@ -21,8 +21,8 @@ Specifically, it will: - Wait for all connections to be closed - After a grace period, if any connections remain active, forcefully close them. - -This plugin is exported from the `@apollo/server` package. Here's a basic example of how to use it with Express: +{/* TODO(AS4) add link to other integration article once it exists */} +This plugin is exported from the `@apollo/server` package. Here's a basic example of how to use it with Express: @@ -52,14 +52,17 @@ async function startApolloServer() { plugins: [ApolloServerPluginDrainHttpServer({ httpServer })], }); await server.start(); - app.use('/graphql', + app.use( + '/graphql', cors(), json(), expressMiddleware(server, { context: async ({ req }) => ({ token: req.headers.token }), }), ); - await new Promise(resolve => httpServer.listen({ port: 4000 }, resolve)); + await new Promise((resolve) => + httpServer.listen({ port: 4000 }, resolve), + ); console.log(`๐Ÿš€ Server ready at http://localhost:4000/graphql`); return { server, app }; } @@ -85,10 +88,12 @@ async function startApolloServer() { ###### `httpServer` [`http.Server`](https://nodejs.org/api/http.html#http_class_http_server) + The server to drain; required. + @@ -98,10 +103,12 @@ The server to drain; required. ###### `stopGracePeriodMillis` `number` + How long to wait before forcefully closing non-idle connections. Defaults to `10_000` (ten seconds). + diff --git a/docs/source/api/plugin/inline-trace.mdx b/docs/source/api/plugin/inline-trace.mdx index 953b9fd7a7f..aa1c96c92da 100644 --- a/docs/source/api/plugin/inline-trace.mdx +++ b/docs/source/api/plugin/inline-trace.mdx @@ -1,5 +1,5 @@ --- -title: "API Reference: Inline trace plugin" +title: 'API Reference: Inline trace plugin' api_reference: true --- @@ -26,7 +26,9 @@ const server = new ApolloServer({ resolvers, plugins: [ ApolloServerPluginInlineTrace({ - includeErrors: { transform: (err) => (err.message.match(SENSITIVE_REGEX) ? null : err ) }, + includeErrors: { + transform: (err) => (err.message.match(SENSITIVE_REGEX) ? null : err), + }, }), ], }); @@ -45,9 +47,7 @@ import { ApolloServerPluginInlineTraceDisabled } from '@apollo/server/plugin/dis const server = new ApolloServer({ typeDefs, resolvers, - plugins: [ - ApolloServerPluginInlineTraceDisabled(), - ], + plugins: [ApolloServerPluginInlineTraceDisabled()], }); ``` @@ -75,19 +75,20 @@ When using Federation, you typically run this plugin in subgraphs and you run th ###### `includeErrors` `Object` + Provide this object to modify GraphQL operation errors before your server reports those errors in traces to Apollo Studio. Valid options are described in [Valid `includeErrors` object signatures](#valid-includeerrors-object-signatures). The default value is `{ masked: true }`, which means error messages are masked and extensions are omitted. This is a security measure to prevent sensitive data from potentially reaching Apollo servers. + - #### Valid `includeErrors` object signatures @@ -108,7 +109,7 @@ The default value is `{ masked: true }`, which means error messages are masked a @@ -137,10 +138,9 @@ If you provide this object, all error messages and extensions are included in tr The value of `transform` is a function that receives each error (`GraphQLError`) and must also return a `GraphQLError` object (or `null` to prevent Apollo Server from reporting a particular error entirely). The only properties of the reported error you can modify are its `message` and its `extensions`. See [Masking and logging errors](../../data/errors/#masking-and-logging-errors) for more details. + -
-If you provide this object, error messages are masked and extensions omitted in the traces sent to Apollo Studio. This is the default behavior. +If you provide this object, error messages are masked and extensions omitted in the traces sent to Apollo Studio. This is the default behavior.
- diff --git a/docs/source/api/plugin/landing-pages.mdx b/docs/source/api/plugin/landing-pages.mdx index a09fa6a03ff..377dd6533d9 100644 --- a/docs/source/api/plugin/landing-pages.mdx +++ b/docs/source/api/plugin/landing-pages.mdx @@ -1,5 +1,5 @@ --- -title: "API Reference: Landing page plugins" +title: 'API Reference: Landing page plugins' api_reference: true --- @@ -7,19 +7,19 @@ This API reference documents built-in plugins that add a landing page to Apollo This includes plugins for: -* The default landing page for [non-production environments](#default-non-production-landing-page) (`ApolloServerPluginLandingPageLocalDefault`) -* The default landing page for [production](#default-production-landing-page) (`ApolloServerPluginLandingPageProductionDefault`) -* Using [GraphQL Playground](#graphql-playground-landing-page) as a landing page (`ApolloServerPluginLandingPageGraphQLPlayground`) -* [Disabling the landing page entirely](#disabling-the-landing-page) +- The default landing page for [non-production environments](#default-non-production-landing-page) (`ApolloServerPluginLandingPageLocalDefault`) +- The default landing page for [production](#default-production-landing-page) (`ApolloServerPluginLandingPageProductionDefault`) +- Using [GraphQL Playground](#graphql-playground-landing-page) as a landing page (`ApolloServerPluginLandingPageGraphQLPlayground`) +- [Disabling the landing page entirely](#disabling-the-landing-page) -These plugins work by implementing the [`renderLandingPage`](../../integrations/plugins-event-reference/#renderlandingpage) plugin event, which serves an HTML page whenever a browser includes an `accept: text/html` header. Aside from these, you can also create a [custom plugin](../../integrations/plugins/) that renders a [custom landing page](../../testing/build-run-queries/#custom-landing-page). +These plugins work by implementing the [`renderLandingPage`](../../integrations/plugins-event-reference/#renderlandingpage) plugin event, which serves an HTML page whenever a browser includes an `accept: text/html` header. Aside from these, you can also create a [custom plugin](../../integrations/plugins/) that renders a [custom landing page](../../testing/build-run-queries/#custom-landing-page). ## Default behavior If you don't manually install any plugin that implements `renderLandingPage`, Apollo Server does the following by default: -* In non-production environments (`NODE_ENV` is not `production`), Apollo Server installs `ApolloServerPluginLandingPageLocalDefault`. -* In production environments (`NODE_ENV` _is_ `production`), Apollo Server installs `ApolloServerPluginLandingPageProductionDefault`. +- In non-production environments (`NODE_ENV` is not `production`), Apollo Server installs `ApolloServerPluginLandingPageLocalDefault`. +- In production environments (`NODE_ENV` _is_ `production`), Apollo Server installs `ApolloServerPluginLandingPageProductionDefault`. In either case, Apollo Server provides no configuration options to the plugin. You only need to install one of these plugins manually if you want to override its default configuration. @@ -31,7 +31,10 @@ To configure these default plugins while still using the same `NODE_ENV`-based l ```ts import { ApolloServer } from '@apollo/server'; -import { ApolloServerPluginLandingPageLocalDefault, ApolloServerPluginLandingPageProductionDefault } from '@apollo/server/plugin/landingPage/default'; +import { + ApolloServerPluginLandingPageLocalDefault, + ApolloServerPluginLandingPageProductionDefault, +} from '@apollo/server/plugin/landingPage/default'; const server = new ApolloServer({ typeDefs, @@ -46,7 +49,6 @@ const server = new ApolloServer({ : ApolloServerPluginLandingPageLocalDefault({ footer: false }), ], }); - ```
@@ -59,9 +61,10 @@ In non-production environments, Apollo Server 4's landing page is an embedded ve Apollo Sandbox -This landing page is designed for use in local development, where `NODE_ENV` is *not* set to `production`. +This landing page is designed for use in local development, where `NODE_ENV` is _not_ set to `production`. [Apollo Sandbox](https://studio.apollographql.com/sandbox) is a special mode of Apollo Studio used for local development, which doesn't require an Apollo account. Sandbox includes the [Apollo Studio Explorer](/studio/explorer/explorer), a powerful web IDE that enables you to build and run operations against your server (or any other reachable server). + ### Options @@ -80,6 +83,7 @@ This landing page is designed for use in local development, where `NODE_ENV` is ###### `version` `string` +
@@ -96,6 +100,7 @@ The current latest version is available at [this link](https://apollo-server-lan ###### `footer` `boolean` + @@ -110,6 +115,7 @@ If you aren't using the embedded Apollo Sandbox (i.e., you are using `{embed: fa ###### `document` `string` + @@ -126,6 +132,7 @@ If you omit this, the Explorer initially loads an example query based on your sc ###### `variables` `Record` + @@ -142,6 +149,7 @@ If provided, these variables should apply to the initial query you provide in `d ###### `headers` `Record` + @@ -156,6 +164,7 @@ An object containing initial HTTP header values to populate in the Explorer on l ###### `includeCookies` `boolean` + @@ -174,6 +183,7 @@ If you omit this, the Explorer defaults `includeCookies` to `false` or the curre ###### `embed` `boolean` + @@ -187,12 +197,16 @@ If you set this option to `false`, your server's landing page is a splash page c
- ## Default production landing page The `ApolloServerPluginLandingPageProductionDefault` shows a minimalist landing page: -Apollo Server default landing page +Apollo Server default landing page This landing page is designed for use in production. It provides a copyable command-line snippet showing how to run operations with your server. By default, the only visible reference to Apollo is a footer explaining how to customize the page. You can also configure it to add a link to query your graph with the [Apollo Explorer](https://www.apollographql.com/docs/studio/explorer). You can choose to embed the Apollo Explorer on your endpoint if you pass the `embed` [option](#embed-options). @@ -214,6 +228,7 @@ This landing page is designed for use in production. It provides a copyable comm ###### `version` `string` + @@ -230,6 +245,7 @@ The current latest version is available at [this link](https://apollo-server-lan ###### `footer` `boolean` + @@ -244,6 +260,7 @@ By default, the landing page displays a footer that links to the documentation t ###### `graphRef` `string` + @@ -260,6 +277,7 @@ To enable this link, you need to provide `graphRef` here even if you already pro ###### `document` `string` + @@ -276,6 +294,7 @@ If you omit this, the Explorer initially loads an example query based on your sc ###### `variables` `Record` + @@ -292,6 +311,7 @@ If provided, these variables should apply to the initial query you provide in `d ###### `headers` `Record` + @@ -306,6 +326,7 @@ An object containing initial HTTP header values to populate in the Explorer on l `boolean | ApolloServerPluginEmbedded` `LandingPageProductionConfigOptions` + @@ -326,6 +347,7 @@ You can configure the Explorer embedded on your Apollo Server endpoint with disp ###### `includeCookies` `boolean` + @@ -376,6 +398,7 @@ For supported subfields, see [`displayOptions` options](#embeddisplayoptions-opt ###### `persistExplorerState` `boolean` + @@ -391,8 +414,6 @@ The default value is `false`. - - ### `embed.displayOptions` options These are the fields you can include in the `displayOptions` option you pass to the embedded Explorer plugin: @@ -471,16 +492,12 @@ The GraphQL Playground plugin lives in its own `@apollo/server-plugin-landing-pa ```ts import { ApolloServer } from '@apollo/server'; -import { - ApolloServerPluginLandingPageGraphQLPlayground -} from "@apollo/server-plugin-landing-page-graphql-playground"; +import { ApolloServerPluginLandingPageGraphQLPlayground } from '@apollo/server-plugin-landing-page-graphql-playground'; const server = new ApolloServer({ typeDefs, resolvers, - plugins: [ - ApolloServerPluginLandingPageGraphQLPlayground(), - ], + plugins: [ApolloServerPluginLandingPageGraphQLPlayground()], }); ``` @@ -508,6 +525,7 @@ This plugin takes the same arguments as the [`renderPlaygroundPage` function](ht ###### `version` `string` + @@ -524,6 +542,7 @@ You can specify a different version here. ###### `endpoint` `string` + @@ -538,6 +557,7 @@ By default, GraphQL Playground connects to a GraphQL server hosted at the same U ###### `settings` `Object` + @@ -546,7 +566,6 @@ If specified, allows you to override the default values of GraphQL Playground's - diff --git a/docs/source/api/plugin/schema-reporting.mdx b/docs/source/api/plugin/schema-reporting.mdx index 0f115696d8e..85739385bdc 100644 --- a/docs/source/api/plugin/schema-reporting.mdx +++ b/docs/source/api/plugin/schema-reporting.mdx @@ -1,5 +1,5 @@ --- -title: "API Reference: Schema reporting plugin" +title: 'API Reference: Schema reporting plugin' api_reference: true --- @@ -13,7 +13,7 @@ This plugin enables your GraphQL server to register its latest schema with the A In order to use this plugin, you must configure your server with a graph API key, either with the `APOLLO_KEY` environment variable or by passing it directly to your `ApolloServer` constructor (e.g., `new ApolloServer({apollo: {key: KEY}})`). This is the same way you configure [usage reporting](./usage-reporting). -You must *explicitly enable* schema reporting. If you want to turn on schema reporting with its default configuration, you can set the `APOLLO_SCHEMA_REPORTING` environment variable to `true`. +You must _explicitly enable_ schema reporting. If you want to turn on schema reporting with its default configuration, you can set the `APOLLO_SCHEMA_REPORTING` environment variable to `true`. If you want to configure schema reporting (or prefer your setup to be via code rather than using environment variables), import the `ApolloServerPluginSchemaReporting` plugin and pass it to the `ApolloServer` constructor: @@ -26,9 +26,7 @@ import { ApolloServerPluginSchemaReporting } from '@apollo/server/plugin/schemaR const server = new ApolloServer({ typeDefs, resolvers, - plugins: [ - ApolloServerPluginSchemaReporting(), - ], + plugins: [ApolloServerPluginSchemaReporting()], }); ``` @@ -49,10 +47,10 @@ const server = new ApolloServer({ - ###### `initialDelayMaxMs` `number` + @@ -61,6 +59,7 @@ The schema reporter waits before starting reporting. By default, the report wait If this server runs in lambda or in other constrained environments it would be useful to decrease the schema reporting max wait time to be less than default. This number will be the max for the range in ms that the schema reporter will wait before starting to report. + @@ -70,25 +69,26 @@ This number will be the max for the range in ms that the schema reporter will wa ###### `overrideReportedSchema` `string` + Override the reported schema that is reported to the Apollo registry. This schema does not go through any normalizations and the string is directly sent to the Apollo registry. This can be useful for comments or other ordering and whitespace changes that get stripped when generating a `GraphQLSchema`. **If you pass this option to this plugin, you should explicitly configure [`ApolloServerPluginUsageReporting`](./usage-reporting/#overridereportedschema) and pass the same value to its `overrideReportedSchema` option.** This ensures that the schema ID associated with requests reported by the usage reporting plugin matches the schema ID that this plugin reports. For example: - + ```ts new ApolloServer({ plugins: [ ApolloServerPluginSchemaReporting({ - overrideReportedSchema: schema + overrideReportedSchema: schema, }), ApolloServerPluginUsageReporting({ - overrideReportedSchema: schema + overrideReportedSchema: schema, }), ], // ... -}) +}); ``` @@ -100,10 +100,12 @@ new ApolloServer({ ###### `endpointUrl` `string` + The URL to use for reporting schemas. Primarily for testing and internal Apollo use. + @@ -113,10 +115,12 @@ The URL to use for reporting schemas. Primarily for testing and internal Apollo ###### `fetcher` `typeof fetch` + Specifies which [Fetch API](https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API) function implementation to use when reporting schemas. + diff --git a/docs/source/api/plugin/usage-reporting.mdx b/docs/source/api/plugin/usage-reporting.mdx index 6e7087c4f0c..48c9e894b27 100644 --- a/docs/source/api/plugin/usage-reporting.mdx +++ b/docs/source/api/plugin/usage-reporting.mdx @@ -1,5 +1,5 @@ --- -title: "API Reference: Usage reporting plugin" +title: 'API Reference: Usage reporting plugin' api_reference: true --- @@ -31,7 +31,7 @@ const server = new ApolloServer({ plugins: [ ApolloServerPluginUsageReporting({ fieldLevelInstrumentation: 0.5, - }) + }), ], }); ``` @@ -55,6 +55,7 @@ Supported configuration options are listed below. **Configuring which data is sent to Apollo Studio** + @@ -64,6 +65,7 @@ Supported configuration options are listed below. ###### `sendVariableValues` `Object` + @@ -80,6 +82,7 @@ The default value is `{ none: true }`, which means **no** variable values are se ###### `sendHeaders` `Object` + @@ -96,6 +99,7 @@ The default value is `{ none: true }`, which means **no** header names or values ###### `sendErrors` `Object` + @@ -114,6 +118,7 @@ The default value is `{ masked: true }`, which means error messages are masked a ###### `fieldLevelInstrumentation` `async Function` or `number` + @@ -133,10 +138,10 @@ Providing a number `x` is equivalent to passing this function: **If the function returns `false` (or `0`):** -* Apollo Server _doesn't_ calculate per-field statistics for the associated operation. -* The operation _doesn't_ contribute to the "field executions" statistic on the Fields page in Studio, or to the execution timing hints displayed in the Explorer or in VS Code. -* The operation _doesn't_ produce a trace that can be viewed in the Traces section of the Operations page in Studio. -* The operation _does_ still contribute to most features of Studio, such as schema checks, the Operations page, and the "referencing operations" statistic on the Fields page. +- Apollo Server _doesn't_ calculate per-field statistics for the associated operation. +- The operation _doesn't_ contribute to the "field executions" statistic on the Fields page in Studio, or to the execution timing hints displayed in the Explorer or in VS Code. +- The operation _doesn't_ produce a trace that can be viewed in the Traces section of the Operations page in Studio. +- The operation _does_ still contribute to most features of Studio, such as schema checks, the Operations page, and the "referencing operations" statistic on the Fields page. (For more information about the difference between the "referencing operations" and "field executions" statistics, see [the Studio Fields page documentation](https://apollographql.com/docs/studio/metrics/field-usage/).) @@ -144,16 +149,16 @@ Returning `false` (or `0`) for some or all operations can improve your server's **If the function returns a positive number:** -* Apollo Server _does_ calculate per-field statistics for the associated operation, and it sends those statistics to Apollo Studio. -* Apollo Server sends Studio both an _observed_ execution count and an _estimated total_ execution count for each field. -* The _observed_ execution count is exactly how many times each field was resolved in the associated operation. -* The _estimated total_ execution count is the _observed_ execution count, _multiplied by the number returned by this function_. You can think of this returned number as an "estimation multiplier". +- Apollo Server _does_ calculate per-field statistics for the associated operation, and it sends those statistics to Apollo Studio. +- Apollo Server sends Studio both an _observed_ execution count and an _estimated total_ execution count for each field. +- The _observed_ execution count is exactly how many times each field was resolved in the associated operation. +- The _estimated total_ execution count is the _observed_ execution count, _multiplied by the number returned by this function_. You can think of this returned number as an "estimation multiplier". To determine the "estimation multiplier" that the function should return, take the reciprocal of the frequency with which the function returns a non-zero number for the associated operation. For example, if the function returns a non-zero number one out of every ten times for a particular operation, then the number it returns should be `10`. Your function can use different logic for different operations, such as to more frequently report rare operations than common operations. -Note that returning `true` here does *not* mean that the data derived from field-level instrumentation must be transmitted to Apollo Studio's servers in the form of a trace. The data can still be aggregated locally to statistics. Either way, this operation contributes to the "field executions" statistic in Studio, along with timing hints. +Note that returning `true` here does _not_ mean that the data derived from field-level instrumentation must be transmitted to Apollo Studio's servers in the form of a trace. The data can still be aggregated locally to statistics. Either way, this operation contributes to the "field executions" statistic in Studio, along with timing hints. The default value is a function that always returns `true`. @@ -166,6 +171,7 @@ The default value is a function that always returns `true`. ###### `includeRequest` `async Function` + @@ -188,6 +194,7 @@ By default, all requests are included in usage reports. ###### `generateClientInfo` `Function` + @@ -206,6 +213,7 @@ By default, the plugin attempts to obtain these values from the incoming request ###### `overrideReportedSchema` `string` + @@ -220,6 +228,7 @@ If you're using the `overrideReportedSchema` option with the [schema reporting p ###### `sendUnexecutableOperationDocuments` `Boolean` + @@ -232,6 +241,7 @@ Statistics about operations that your server cannot execute are not reported und **Configuring communication protocol** + @@ -241,6 +251,7 @@ Statistics about operations that your server cannot execute are not reported und ###### `sendReportsImmediately` `boolean` + @@ -259,10 +270,12 @@ Note that "immediately" does not mean _synchronously_ with completing the respon ###### `fetcher` `typeof fetch` + Specifies which [Fetch API](https://developer.mozilla.org/en-US/docs/Web/API/Fetch_API) function implementation to use when sending usage reports. + @@ -272,6 +285,7 @@ Specifies which [Fetch API](https://developer.mozilla.org/en-US/docs/Web/API/Fet ###### `reportIntervalMs` `number` + @@ -288,6 +302,7 @@ Regardless of this value, Apollo Server sends a trace report whenever the size o ###### `maxUncompressedReportSize` `number` + @@ -296,6 +311,7 @@ Apollo Server sends a trace report whenever the size of a pending batched trace Note that this is a rough limit that includes the size of serialized traces and signatures. It ignores the size of the report's header and some other top-level bytes. The default value is 4MB (`4194304`). + @@ -305,12 +321,14 @@ The default value is 4MB (`4194304`). ###### `maxAttempts` `number` + The maximum number of times Apollo Server should attempt to report each trace report, performing exponential backoff between attempts. The default value is `5`. + @@ -320,12 +338,14 @@ The default value is `5`. ###### `minimumRetryDelayMs` `number` + The minimum amount of backoff (in milliseconds) Apollo Server should perform before retrying a failed trace report. The default value is `100`. + @@ -335,6 +355,7 @@ The default value is `100`. ###### `logger` [`Logger`](https://www.npmjs.com/package/@apollo/utils.logger) + @@ -349,6 +370,7 @@ If you provide this object, the plugin sends it all log messages related to Apol ###### `reportErrorFunction` `Function` + @@ -363,6 +385,7 @@ By default, the plugin logs these errors to its specified `logger`. _Unlike_ the **Internal and non-recommended options** + @@ -372,10 +395,12 @@ By default, the plugin logs these errors to its specified `logger`. _Unlike_ the ###### `endpointUrl` `string` + The URL base that the plugin sends reports to (not including the path). This option only needs to be set for testing and Apollo-internal uses. + @@ -385,10 +410,12 @@ The URL base that the plugin sends reports to (not including the path). This opt ###### `debugPrintReports` `boolean` + If set, prints all reports as JSON when they are sent. (Note that for technical reasons, traces embedded in a report are printed separately when they are added to a report.) + @@ -398,10 +425,12 @@ If set, prints all reports as JSON when they are sent. (Note that for technical ###### `calculateSignature` `Function` + Specify this function to create a signature for a query. This option is not recommended, because Apollo's servers make assumptions about how the signature relates to the operation you executed. + @@ -410,28 +439,28 @@ Specify this function to create a signature for a query. This option is not reco #### Valid `sendVariableValues` object signatures -| Object | Description | -|--------|-------------| -| `{ none: true }` | If you provide this object, no GraphQL variable values are sent to Apollo Studio. This is the default behavior. | -| `{ all: true }` | If you provide this object, **all** GraphQL variable values are sent to Apollo Studio. | -| `{ onlyNames: ["apple", "orange"]}`| If you provide an object with this structure, only values of the GraphQL variables with names that appear in the array are sent to Apollo Studio. To filter individual fields of a variable that contains an input type, use the `transform` function below instead. Case-sensitive. | -| `{ exceptNames: ["apple", "orange"]}`| If you provide an object with this structure, all GraphQL variable values **except** values of the variables with names that appear in the array are sent to Apollo Studio. To filter individual fields of a variable that contains an input type, use the `transform` function below instead. Case-sensitive. | -| `{ transform: ({ variables, operationString)} => { ... } }` |

The value of `transform` is a function that takes the values of all GraphQL variables for an operation and the operation string. The function returns a new variables map containing values for the operation's variables that should be sent to Apollo Studio. This map does not need to contain all of the operation's variables, but it cannot _add_ variables to the map. You should not mutate `variables` itself or any of the values contained in it.

For security reasons, if an error occurs in the `transform` function, **all** variable values are replaced with `[PREDICATE_FUNCTION_ERROR]`.

| +| Object | Description | +| ----------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `{ none: true }` | If you provide this object, no GraphQL variable values are sent to Apollo Studio. This is the default behavior. | +| `{ all: true }` | If you provide this object, **all** GraphQL variable values are sent to Apollo Studio. | +| `{ onlyNames: ["apple", "orange"]}` | If you provide an object with this structure, only values of the GraphQL variables with names that appear in the array are sent to Apollo Studio. To filter individual fields of a variable that contains an input type, use the `transform` function below instead. Case-sensitive. | +| `{ exceptNames: ["apple", "orange"]}` | If you provide an object with this structure, all GraphQL variable values **except** values of the variables with names that appear in the array are sent to Apollo Studio. To filter individual fields of a variable that contains an input type, use the `transform` function below instead. Case-sensitive. | +| `{ transform: ({ variables, operationString)} => { ... } }` |

The value of `transform` is a function that takes the values of all GraphQL variables for an operation and the operation string. The function returns a new variables map containing values for the operation's variables that should be sent to Apollo Studio. This map does not need to contain all of the operation's variables, but it cannot _add_ variables to the map. You should not mutate `variables` itself or any of the values contained in it.

For security reasons, if an error occurs in the `transform` function, **all** variable values are replaced with `[PREDICATE_FUNCTION_ERROR]`.

| #### Valid `sendHeaders` object signatures -| Object | Description | -|--------|-------------| -| `{ none: true }` | If you provide this object, no request header names or values are sent to Apollo Studio. This is the default behavior. | -| `{ all: true }` | If you provide this object, **all** GraphQL header names and values are sent to Apollo Studio, except for the protected headers listed below. | -| `{ onlyNames: ["apple", "orange"]}`| If you provide an object with this structure, only names and values of the request headers with names that appear in the array are sent to Apollo Studio. Case-insensitive. | -| `{ exceptNames: ["apple", "orange"]}`| If you provide an object with this structure, all GraphQL header values **except** values of headers with names that appear in the array are sent to Apollo Studio. Case-insensitive. | +| Object | Description | +| ------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `{ none: true }` | If you provide this object, no request header names or values are sent to Apollo Studio. This is the default behavior. | +| `{ all: true }` | If you provide this object, **all** GraphQL header names and values are sent to Apollo Studio, except for the protected headers listed below. | +| `{ onlyNames: ["apple", "orange"]}` | If you provide an object with this structure, only names and values of the request headers with names that appear in the array are sent to Apollo Studio. Case-insensitive. | +| `{ exceptNames: ["apple", "orange"]}` | If you provide an object with this structure, all GraphQL header values **except** values of headers with names that appear in the array are sent to Apollo Studio. Case-insensitive. | **Note:** Regardless of your configuration, Apollo Server **never** sends the values of the following headers to Apollo Studio: - * `authorization` - * `cookie` - * `set-cookie` +- `authorization` +- `cookie` +- `set-cookie` #### Valid `sendErrors` object signatures @@ -453,7 +482,7 @@ Specify this function to create a signature for a query. This option is not reco -If you provide this object, error messages are masked and extensions omitted in the traces sent to Apollo Studio. This is the default behavior. +If you provide this object, error messages are masked and extensions omitted in the traces sent to Apollo Studio. This is the default behavior. @@ -482,16 +511,13 @@ If you provide this object, all error messages and extensions are included in th The value of `transform` is a function that receives each error (`GraphQLError`) and must also return a `GraphQLError` object (or `null` to prevent Apollo Server from reporting a particular error entirely). The only properties of the reported error you can modify are its `message` and its `extensions`. See [Masking and logging errors](../../data/errors/#masking-and-logging-errors) for more details. + - - - - ## Disabling the plugin If you _don't_ want to install the usage reporting plugin and you _are_ providing an API key to Apollo Server for other purposes, you can disable usage reporting by installing the `ApolloServerPluginUsageReportingDisabled` plugin, like so: @@ -505,9 +531,7 @@ import { ApolloServerPluginUsageReportingDisabled } from '@apollo/server/plugin/ const server = new ApolloServer({ typeDefs, resolvers, - plugins: [ - ApolloServerPluginUsageReportingDisabled(), - ], + plugins: [ApolloServerPluginUsageReportingDisabled()], }); ``` diff --git a/docs/source/api/standalone.mdx b/docs/source/api/standalone.mdx index 1c334584323..acdec0ab3f9 100644 --- a/docs/source/api/standalone.mdx +++ b/docs/source/api/standalone.mdx @@ -1,5 +1,5 @@ --- -title: "API Reference: startStandaloneServer" +title: 'API Reference: startStandaloneServer' api_reference: true --- @@ -7,7 +7,7 @@ This API reference documents the `startStandaloneServer` function. ## Overview -This `startStandaloneServer` function helps you get started with Apollo Server quickly. This function is recommended for all projects that don't require serverless support or a particular Node.js framework (such as Fastify). Under the hood, the `startStandaloneServer` function uses Apollo Server 4's Express integration (i.e., [`expressMiddleware`](./express-middleware)). +This `startStandaloneServer` function helps you get started with Apollo Server quickly. This function is recommended for all projects that don't require serverless support or a particular Node.js framework (such as Fastify). Under the hood, the `startStandaloneServer` function uses Apollo Server 4's Express integration (i.e., [`expressMiddleware`](./express-middleware)). Because it sets helpful defaults, this function is less configurable than other Apollo Server integrations. Complex projects might eventually need to [swap to using `expressMiddleware`](#swapping-to-expressmiddleware) (this process is straightforward). @@ -26,7 +26,7 @@ const server = new ApolloServer({ typeDefs, resolvers }); // `startStandaloneServer` returns a `Promise` with the // the URL that the server is listening on. const { url } = await startStandaloneServer(server); //highlight-line -``` +``` @@ -47,15 +47,15 @@ The `startStandaloneServer` function's second optional argument is an object for - ##### `context` +##### `context` - `Function` +`Function` -An optional asynchronous [`context` initialization function](../data/resolvers#the-context-argument). +An optional asynchronous [`context` initialization function](../data/resolvers#the-context-argument). The `context` function should return an object that all your server's resolvers share during an operation's execution. This enables resolvers to share helpful context values, such as a database connection. @@ -69,9 +69,9 @@ The `context` function receives `req` and `res` options which are `http.Incoming - ##### `listen` +##### `listen` - `Object` +`Object` @@ -80,6 +80,7 @@ The `context` function receives `req` and `res` options which are `http.Incoming An optional `listen` configuration object. The `listen` option accepts an object with the same properties as the [`net.Server.listen` _options object_](https://nodejs.org/api/net.html#serverlistenoptions-callback). If no `port` is specified, this defaults to using `{port: 4000}`. + @@ -87,7 +88,7 @@ If no `port` is specified, this defaults to using `{port: 4000}`. -### Example +### Example Below is a full example of setting up `startStandaloneServer`: @@ -147,6 +148,7 @@ async function startApolloServer() { console.log(`๐Ÿš€ Server ready at ${url}`); } ``` + To swap to using `expressMiddleware`, you'll first need to install the following packages so you'll be able to set up HTTP body parsing and CORS for your server: @@ -194,7 +196,8 @@ async function startApolloServer() { // Set up our Express middleware to handle CORS, body parsing, // and our expressMiddleware function. - app.use('/', + app.use( + '/', cors(), bodyParser.json(), // expressMiddleware accepts the same arguments: @@ -205,8 +208,11 @@ async function startApolloServer() { ); // Modified server startup - await new Promise(resolve => httpServer.listen({ port: 4000 }, resolve)); + await new Promise((resolve) => + httpServer.listen({ port: 4000 }, resolve), + ); console.log(`๐Ÿš€ Server ready at http://localhost:4000/`); } ``` - \ No newline at end of file + + diff --git a/docs/source/builtin-plugins.md b/docs/source/builtin-plugins.md index 02c1d2927fe..58ff8fbaa9a 100644 --- a/docs/source/builtin-plugins.md +++ b/docs/source/builtin-plugins.md @@ -10,14 +10,14 @@ You can also [create custom plugins](./integrations/plugins/). ## List of built-in plugins -| Name | Description | Location | -|------|---------|-------------| -| [Usage reporting](./api/plugin/usage-reporting/) | Gathers helpful operation usage data and reports it to [Apollo Studio](https://www.apollographql.com/docs/studio/) for visualization, alerting, and more. |`@apollo/server/plugin/usageReporting` | -| [Schema reporting](./api/plugin/schema-reporting/) | Automatically reports the server's schema to [Apollo Studio](/studio/) on startup to enable schema history and up-to-date metrics. | `@apollo/server/plugin/schemaReporting` | -| [Inline trace](./api/plugin/inline-trace/) | Used primarily by [federated subgraphs](https://www.apollographql.com/docs/federation/) to include operation trace data in responses to the gateway. | `@apollo/server/plugin/inlineTrace` | -| [Cache control](./api/plugin/cache-control/) | Calculates caching behavior for operation responses. | `@apollo/server/plugin/cacheControl` | -| [Landing page (multiple)](./api/plugin/landing-pages) | Handle displaying a default or custom landing page at Apollo Server's base URL. | `@apollo/server/plugin/landingPage/default` | -| [Draining an HTTP server](./api/plugin/drain-http-server) | Used to ensure your Node.js servers gracefully shut down. | `@apollo/server/plugin/drainHttpServer`| +| Name | Description | Location | +| --------------------------------------------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------- | +| [Usage reporting](./api/plugin/usage-reporting/) | Gathers helpful operation usage data and reports it to [Apollo Studio](https://www.apollographql.com/docs/studio/) for visualization, alerting, and more. | `@apollo/server/plugin/usageReporting` | +| [Schema reporting](./api/plugin/schema-reporting/) | Automatically reports the server's schema to [Apollo Studio](/studio/) on startup to enable schema history and up-to-date metrics. | `@apollo/server/plugin/schemaReporting` | +| [Inline trace](./api/plugin/inline-trace/) | Used primarily by [federated subgraphs](https://www.apollographql.com/docs/federation/) to include operation trace data in responses to the gateway. | `@apollo/server/plugin/inlineTrace` | +| [Cache control](./api/plugin/cache-control/) | Calculates caching behavior for operation responses. | `@apollo/server/plugin/cacheControl` | +| [Landing page (multiple)](./api/plugin/landing-pages) | Handle displaying a default or custom landing page at Apollo Server's base URL. | `@apollo/server/plugin/landingPage/default` | +| [Draining an HTTP server](./api/plugin/drain-http-server) | Used to ensure your Node.js servers gracefully shut down. | `@apollo/server/plugin/drainHttpServer` | ## Installing plugins @@ -26,7 +26,7 @@ You can install a plugin that isn't installed by default (or customize a default ```ts -import { ApolloServer } from "@apollo/server"; +import { ApolloServer } from '@apollo/server'; import { ApolloServerPluginUsageReporting } from '@apollo/server/plugin/usageReporting'; const server = new ApolloServer({ diff --git a/docs/source/data/errors.mdx b/docs/source/data/errors.mdx index 39c31acae51..23a17637690 100644 --- a/docs/source/data/errors.mdx +++ b/docs/source/data/errors.mdx @@ -3,7 +3,7 @@ title: Error handling description: Making errors actionable on the client and server --- - +{/* cSpell:ignore typenam */} Whenever Apollo Server encounters errors while processing a GraphQL operation, its response to the client includes an `errors` array containing each error that occurred. Each error in the array has an `extensions` field that provides additional useful information, including an error `code` and (while in development mode) a `stacktrace`. @@ -46,7 +46,7 @@ import { ApolloServerErrorCode } from '@apollo/server/errors'; if (error.extensions?.code === ApolloServerErrorCode.GRAPHQL_PARSE_FAILED) { // respond to the syntax error -} else if (error.extensions?.code === "MY_CUSTOM_CODE") { +} else if (error.extensions?.code === 'MY_CUSTOM_CODE') { // do something else } ``` @@ -328,7 +328,7 @@ The `stacktrace` error field is useful while developing and debugging your serve By default, Apollo Server _omits_ the `stacktrace` field if the `NODE_ENV` environment variable is set to either `production` or `test`. - +{/* TODO(AS4) link to API docs for includeStacktraceInErrorResponses */} You can override this default behavior by passing the `includeStacktraceInErrorResponses` option to the constructor of `ApolloServer`. If `includeStacktraceInErrorResponses` is `true`, `stacktrace` is always included. If it's `false`, `stacktrace` is always omitted. @@ -487,7 +487,7 @@ Note that returning `null`` also affects Studio's aggregated statistics about ho [As mentioned above](#for-client-responses), you can use the `unwrapResolverError` (from `@apollo/server/errors`) to remove the `GraphQLError` wrapping an original error. - +{/* TODO(AS4) Replace link once plugin docs are updated */} > **For federated graphs**, define your `transform` function in each subgraph's [inline trace plugin](../migration/#rewriteerror-plugin-option) to rewrite field errors. If you want to transform your gateway's parsing or validation errors, you can define your `transform` function in your gateway. @@ -609,8 +609,9 @@ The REDACTED doesn't have sufficient privileges. GraphQL, by design, does not use the same conventions from REST to communicate via HTTP verbs and status codes. Client information should be contained in the schema or as part of the standard response `errors` field. We recommend using the included [Error Codes](#built-in-error-codes) or [Custom Errors](#custom-errors) for error consistency rather than directly modifying the HTTP response. Apollo Server uses different HTTP status codes in various situations: -- If Apollo Server hasn't correctly started up or is in the process of shutting down, it responds with a 500 status code. - - The former can happen if you use a serverless integration and it sends requests to an Apollo Server instance that had an error on startup. The latter happens if you aren't properly [draining your server](/apollo-server/api/plugin/drain-http-server/#using-the-plugin). + +- If Apollo Server hasn't correctly started up or is in the process of shutting down, it responds with a 500 status code. +- The former can happen if you use a serverless integration and it sends requests to an Apollo Server instance that had an error on startup. The latter happens if you aren't properly [draining your server](/apollo-server/api/plugin/drain-http-server/#using-the-plugin). - If Apollo Server can't parse the request into a legal GraphQL document and validate it against your schema, it responds with a 400 status code. This can also happen with other request problems, such as if a client attempts to send a batched HTTP request when `allowBatchedHttpRequests` isn't enabled or if CSRF prevention blocks a request. - If a request uses an invalid HTTP method (`GET` with a mutation, or any HTTP method other than `GET` or `POST`), then Apollo Server responds with a 405 status code. - If your `context` function throws, Apollo Server responds with a 500 status code. @@ -645,9 +646,9 @@ const resolvers = { }, }, }); - } - } -} + }, + }, +}; ``` diff --git a/docs/source/data/fetching-data.mdx b/docs/source/data/fetching-data.mdx index b1ca89529b0..9a4e6ca7cd6 100644 --- a/docs/source/data/fetching-data.mdx +++ b/docs/source/data/fetching-data.mdx @@ -3,4 +3,4 @@ title: Fetching Data description: Fetching data from data sources besides REST --- - +{/* TODO(AS4) this whole article! */} diff --git a/docs/source/data/fetching-rest.mdx b/docs/source/data/fetching-rest.mdx index f6d66f3d806..bec5720870f 100644 --- a/docs/source/data/fetching-rest.mdx +++ b/docs/source/data/fetching-rest.mdx @@ -13,14 +13,13 @@ flowchart LR; subgraph ApolloServer; restDataSource(RESTDataSource); end - restDataSource --Fetches data--> restAPI; + restDataSource --Fetches data*/} restAPI; client(ApolloClient); - client --Sends query--> ApolloServer; + client --Sends query*/} ApolloServer; ``` - +{/* TODO(AS4) add this note back in when fetching data article is ready */} +{/* > For more information about fetching from data sources other than a REST API, see [Fetching Data](./fetching-data). */} ## Creating subclasses @@ -31,6 +30,7 @@ npm install @apollo/datasource-rest ``` Your server should define a separate subclass of `RESTDataSource` for each REST API it communicates with. Here's an example of a `RESTDataSource` subclass that defines two data-fetching methods, `getMovie` and `getMostViewedMovies`: + ```ts title="movies-api.ts" @@ -101,10 +101,11 @@ console.log(`๐Ÿš€ Server ready at ${url}`); - +{/* TODO(AS4) add link to context article once exists */} Apollo Server calls [the `context` initialization](./resolvers/#the-context-argument) function for _every incoming operation_. This means: + - For every operation, `context` returns an _object_ containing new instances of your `RESTDataSource` subclasses (in this case, `MoviesAPI` and `PersonalizationAPI`). -- The **`context` function should create a new instance of each `RESTDataSource` subclass for each operation.** +- The **`context` function should create a new instance of each `RESTDataSource` subclass for each operation.** Your resolvers can then access your data sources from the shared `context` object and use them to fetch data: @@ -128,7 +129,7 @@ const resolvers = { > ๐Ÿ“ฃ **New in Apollo Server 4**: Apollo Server no longer automatically provides its cache to data sources. [See here for more details](#datasources). -The `RESTDataSource` class can cache results if the REST API it fetches from specifies caching headers in its HTTP responses (e.g., [`cache-control`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Cache-Control)). +The `RESTDataSource` class can cache results if the REST API it fetches from specifies caching headers in its HTTP responses (e.g., [`cache-control`](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Cache-Control)). As shown in the above code snippet, by default, each `RESTDataSource` subclass accepts a `cache` argument (e.g., Apollo Server's default cache) to store the results of past fetches: @@ -201,7 +202,6 @@ const { url } = await startStandaloneServer(server, { - When running multiple instances of your server, you should use a shared cache backend. This enables one server instance to use the cached result from _another_ instance. > If you want to configure or replace Apollo Sever's default cache, see [Configuring external caching](../performance/cache-backends) for more details. @@ -229,7 +229,7 @@ class MoviesAPI extends RESTDataSource { async postMovie(movie) { return this.post( `movies`, // path - { body: { movie } }, // request body + { body: { movie } }, // request body ); } @@ -256,7 +256,6 @@ class MoviesAPI extends RESTDataSource { ); } } - ``` @@ -303,7 +302,10 @@ Data sources also have access to the GraphQL operation context, which is useful ```ts -import { RESTDataSource, WillSendRequestOptions } from '@apollo/datasource-rest'; +import { + RESTDataSource, + WillSendRequestOptions, +} from '@apollo/datasource-rest'; import type { KeyValueCache } from '@apollo/utils.keyvaluecache'; class PersonalizationAPI extends RESTDataSource { @@ -330,7 +332,10 @@ class PersonalizationAPI extends RESTDataSource { ```ts -import { RESTDataSource, WillSendRequestOptions } from '@apollo/datasource-rest'; +import { + RESTDataSource, + WillSendRequestOptions, +} from '@apollo/datasource-rest'; import type { KeyValueCache } from '@apollo/utils.keyvaluecache'; class PersonalizationAPI extends RESTDataSource { @@ -372,18 +377,18 @@ class PersonalizationAPI extends RESTDataSource { override async resolveURL(path: string, request: RequestOptions) { if (!this.baseURL) { - const addresses = await resolveSrv(path.split('/')[1] + '.service.consul'); + const addresses = await resolveSrv( + path.split('/')[1] + '.service.consul', + ); this.baseURL = addresses[0]; } return super.resolveURL(path, request); } } - ``` - ## Using with DataLoader The [DataLoader](https://github.com/graphql/dataloader) utility was designed for a specific use case: deduplicating and batching object loads from a data store. It provides a memoization cache, which avoids loading the same object multiple times during a single GraphQL request. It also combines loads that occur during a single tick of the event loop into a batched request that fetches multiple objects at once. @@ -404,7 +409,10 @@ We recommend that you restrict batching to requests that _can't_ be cached. In t ```ts import DataLoader from 'dataloader'; -import { RESTDataSource, WillSendRequestOptions } from '@apollo/datasource-rest'; +import { + RESTDataSource, + WillSendRequestOptions, +} from '@apollo/datasource-rest'; import type { KeyValueCache } from '@apollo/utils.keyvaluecache'; class PersonalizationAPI extends RESTDataSource { @@ -421,7 +429,9 @@ class PersonalizationAPI extends RESTDataSource { } private progressLoader = new DataLoader(async (ids) => { - const progressList = await this.get('progress', { params: { ids: ids.join(',') } }); + const progressList = await this.get('progress', { + params: { ids: ids.join(',') }, + }); return ids.map((id) => progressList.find((progress) => progress.id === id)); }); diff --git a/docs/source/data/resolvers.mdx b/docs/source/data/resolvers.mdx index 242b20bf53d..22322d08e59 100644 --- a/docs/source/data/resolvers.mdx +++ b/docs/source/data/resolvers.mdx @@ -159,7 +159,8 @@ console.log(`๐Ÿš€ Server listening at: ${url}`); Note that you can define your resolvers across as many different files and objects as you want, as long as you merge all of them into a single resolver map that's passed to the `ApolloServer` constructor. - +{/* (TODO(AS4) Add note to fetching from other data sources data once it's done */} + > To learn how to fetch data from a REST API, see [Fetching from REST](./fetching-rest/). ## Resolver chains @@ -229,9 +230,9 @@ The resulting resolver chain for this query matches the hierarchical structure o ```mermaid graph LR; - libraries("Query.libraries()") --> books("Library.books()"); - books --> author("Book.author()"); - author --> name("Author.name()"); + libraries("Query.libraries()") */} books("Library.books()"); + books */} author("Book.author()"); + author */} name("Author.name()"); ``` These resolvers execute in the order shown above, and they each pass their return value to the next resolver in the chain via the [`parent` argument](#resolver-arguments). @@ -357,10 +358,10 @@ Then the resolver chain looks like this: ```mermaid graph LR; - libraries("Query.libraries()") --> books("Library.books()"); - books --> title("Book.title()"); - books --> author("Book.author()"); - author --> name("Author.name()"); + libraries("Query.libraries()") */} books("Library.books()"); + books */} title("Book.title()"); + books */} author("Book.author()"); + author */} name("Author.name()"); ``` When a chain "diverges" like this, each subchain executes in parallel. @@ -371,16 +372,16 @@ Resolver functions are passed four arguments: `parent`, `args`, `context`, and ` > You can use any name for each argument in your code, but the Apollo docs use these names as a convention. Instead of `parent`, it's also common to use the parent type's name or `source`. -| Argument | Description | -|---|---| -| `parent` |

The return value of the resolver for this field's parent (i.e., the previous resolver in the [resolver chain](#resolver-chains)).

For resolvers of top-level fields with no parent (such as fields of `Query`), this value is obtained from the `rootValue` function passed to [Apollo Server's constructor](/apollo-server/api/apollo-server/#constructor).

| -| `args` |

An object that contains all GraphQL arguments provided for this field.

For example, when executing `query{ user(id: "4") }`, the `args` object passed to the `user` resolver is `{ "id": "4" }`.

| -| `context` |

An object shared across all resolvers that are executing for a particular operation. Use this to share per-operation state, including authentication information, dataloader instances, and anything else to track across resolvers.

See [The `context` argument](#the-context-argument) for more information.

| -| `info` |

Contains information about the operation's execution state, including the field name, the path to the field from the root, and more.

Its core fields are listed in the [GraphQL.js source code](https://github.com/graphql/graphql-js/blob/main/src/type/definition.ts#L977-L986). Apollo Server extends it with a [`cacheControl` field](/apollo-server/performance/caching/#in-your-resolvers-dynamic).

| +| Argument | Description | +| --------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `parent` |

The return value of the resolver for this field's parent (i.e., the previous resolver in the [resolver chain](#resolver-chains)).

For resolvers of top-level fields with no parent (such as fields of `Query`), this value is obtained from the `rootValue` function passed to [Apollo Server's constructor](/apollo-server/api/apollo-server/#constructor).

| +| `args` |

An object that contains all GraphQL arguments provided for this field.

For example, when executing `query{ user(id: "4") }`, the `args` object passed to the `user` resolver is `{ "id": "4" }`.

| +| `context` |

An object shared across all resolvers that are executing for a particular operation. Use this to share per-operation state, including authentication information, dataloader instances, and anything else to track across resolvers.

See [The `context` argument](#the-context-argument) for more information.

| +| `info` |

Contains information about the operation's execution state, including the field name, the path to the field from the root, and more.

Its core fields are listed in the [GraphQL.js source code](https://github.com/graphql/graphql-js/blob/main/src/type/definition.ts#L977-L986). Apollo Server extends it with a [`cacheControl` field](/apollo-server/performance/caching/#in-your-resolvers-dynamic).

| ### The `context` argument - +{/* (TODO(AS4) Add note to fetching data too once it's done */} The `context` argument is useful for passing things that any resolver might need, like [authentication scope](https://blog.apollographql.com/authorization-in-graphql-452b1c402a9), [sources for fetching data](./fetching-rest/), database connections, and custom fetch functions. If you're using [dataloaders to batch requests](./fetching-rest/#using-with-dataloader) across resolvers, you can attach them to the `context` as well. **Resolvers should never destructively modify the `context` argument.** This ensures consistency across all resolvers and prevents unexpected errors. @@ -396,18 +397,19 @@ import { GraphQLError } from 'graphql'; const resolvers = { Query: { - // Example resolver + // Example resolver adminExample: (parent, args, context, info) => { if (context.authScope !== ADMIN) { throw new GraphQLError('not admin!', { - extensions: { code: 'UNAUTHENTICATED' } + extensions: { code: 'UNAUTHENTICATED' }, }); } }, }, }; -interface MyContext { // Context typing +interface MyContext { + // Context typing authScope?: String; } @@ -419,23 +421,20 @@ const server = new ApolloServer({ const { url } = await startStandaloneServer(server, { // A named context function is required if you are not // using ApolloServer - context: async ({req, res}) => ({ - authScope: getScope(req.headers.authorization), - }) + context: async ({ req, res }) => ({ + authScope: getScope(req.headers.authorization), + }), }); - ```
> This example assumes you're using either the `startStandaloneServer` or `expressMiddleware`, both of which use Express under the hood. The fields of the object passed to your `context` function might differ if you're using a different integration. -The `context` function should be *asynchronous* and return an object, which is then accessible to your server's resolvers and plugins (via the `contextValue` field). +The `context` function should be _asynchronous_ and return an object, which is then accessible to your server's resolvers and plugins (via the `contextValue` field). - +{/* TODO (AS4): update these links once we have an article with other integration functions */} +{/* [For more details on Apollo Server integrations, see [Choosing an Apollo Server package](/apollo-server/api/apollo-server/#middleware-specific-context-fields). */} Because the `context` initialization function is asynchronous, you can use it to establish database connections and wait for other operations to complete: @@ -452,7 +451,7 @@ context: async () => ({ #### Throwing errors in `context` -By default, if your `context` function throws an error, Apollo Server returns that error to the user in a JSON response with an HTTP status code of 500. If the thrown error is not a `GraphQLError`, the error's message will be prepended with `"Context creation failed: "`. +By default, if your `context` function throws an error, Apollo Server returns that error to the user in a JSON response with an HTTP status code of 500. If the thrown error is not a `GraphQLError`, the error's message will be prepended with `"Context creation failed: "`. You can control the HTTP status code of an error by throwing a [`GraphQLError` with an `http` extension](./errors/#setting-http-status-code-and-headers). For example: @@ -475,18 +474,18 @@ context: async ({ req }) => { return { user, db }; }, -```` +``` ## Return values A resolver function's return value is treated differently by Apollo Server depending on its type: -| Type | Description | -|---|---| -| Scalar / object |

A resolver can return a single value or an object, as shown in [Defining a resolver](#defining-a-resolver). This return value is passed down to any nested resolvers via the `parent` argument.

| -| `Array` |

Return an array if and only if your schema indicates that the resolver's associated field contains a list.

After you return an array, Apollo Server executes nested resolvers for each item in the array.

| -| `null` / `undefined` |

Indicates that the value for the field could not be found.

If your schema indicates that this resolver's field is nullable, then the operation result has a `null` value at the field's position.

If this resolver's field is _not_ nullable, Apollo Server sets the field's _parent_ to `null`. If necessary, this process continues up the resolver chain until it reaches a field that _is_ nullable. This ensures that a response never includes a `null` value for a non-nullable field. When this happens, the response's `errors` property will be populated with relevant errors concerning the nullability of that field.

| -| [`Promise`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Using_promises) |

Resolvers can be asynchronous and perform async actions, such as fetching from a database or back-end API. To support this, a resolver can return a promise that resolves to any other supported return type.

| +| Type | Description | +| ----------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------ | +| Scalar / object |

A resolver can return a single value or an object, as shown in [Defining a resolver](#defining-a-resolver). This return value is passed down to any nested resolvers via the `parent` argument.

| +| `Array` |

Return an array if and only if your schema indicates that the resolver's associated field contains a list.

After you return an array, Apollo Server executes nested resolvers for each item in the array.

| +| `null` / `undefined` |

Indicates that the value for the field could not be found.

If your schema indicates that this resolver's field is nullable, then the operation result has a `null` value at the field's position.

If this resolver's field is _not_ nullable, Apollo Server sets the field's _parent_ to `null`. If necessary, this process continues up the resolver chain until it reaches a field that _is_ nullable. This ensures that a response never includes a `null` value for a non-nullable field. When this happens, the response's `errors` property will be populated with relevant errors concerning the nullability of that field.

| +| [`Promise`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Guide/Using_promises) |

Resolvers can be asynchronous and perform async actions, such as fetching from a database or back-end API. To support this, a resolver can return a promise that resolves to any other supported return type.

| ## Default resolvers @@ -497,10 +496,10 @@ The default resolver function uses the following logic: ```mermaid graph TB; parent("Does the parent argument have a
property with this resolver's exact name?"); - parent--No-->null("Return undefined"); - parent--Yes-->function("Is that property's value a function?"); - function--No-->return("Return the property's value"); - function--Yes-->call("Call the function and
return its return value"); + parent--No*/}null("Return undefined"); + parent--Yes*/}function("Is that property's value a function?"); + function--No*/}return("Return the property's value"); + function--Yes*/}call("Call the function and
return its return value"); ``` As an example, consider the following schema excerpt: diff --git a/docs/source/data/subscriptions.mdx b/docs/source/data/subscriptions.mdx index 5a799e09289..785b6cd3893 100644 --- a/docs/source/data/subscriptions.mdx +++ b/docs/source/data/subscriptions.mdx @@ -3,7 +3,7 @@ title: Subscriptions in Apollo Server description: Persistent GraphQL read operations --- ->**Apollo Server does not provide built-in support for subscriptions.** You can enable support for subscriptions as [described below](#enabling-subscriptions). +> **Apollo Server does not provide built-in support for subscriptions.** You can enable support for subscriptions as [described below](#enabling-subscriptions). > > **Subscriptions are not currently supported in [Apollo Federation](/federation/).** > @@ -42,7 +42,7 @@ subscription PostFeed { ## Enabling subscriptions - +{/* TODO(AS4): Replace link when there is an expressMiddleware article */} > Subscriptions are **not** supported by Apollo Server 4's `startStandaloneServer` function. To enable subscriptions, you must first [swap to using the `expressMiddleware` function](../migration#migrate-from-apollo-server-express) (or any other Apollo Server integration package that supports subscriptions). > @@ -249,7 +249,7 @@ npm install graphql-subscriptions A `PubSub` instance enables your server code to both `publish` events to a particular label and listen for events associated with a particular label. We can create a `PubSub` instance like so: -```ts +```ts import { PubSub } from 'graphql-subscriptions'; const pubsub = new PubSub(); @@ -259,7 +259,7 @@ const pubsub = new PubSub(); You can publish an event using the `publish` method of a `PubSub` instance: -```ts +```ts pubsub.publish('POST_CREATED', { postCreated: { author: 'Ali Baba', @@ -299,7 +299,7 @@ const resolvers = { Before we persist the new post's details in our datastore, we can `publish` an event that _also_ includes those details: -```ts +```ts const resolvers = { Mutation: { createPost(parent, args, context) { @@ -319,7 +319,7 @@ An [`AsyncIterator`](https://github.com/apollographql/graphql-subscriptions/blob You can create an `AsyncIterator` by calling the `asyncIterator` method of `PubSub` and passing in an array containing the names of the event labels that this `AsyncIterator` should listen for. -```ts +```ts pubsub.asyncIterator(['POST_CREATED']); ``` @@ -515,7 +515,7 @@ In Apollo Client, the `GraphQLWsLink` constructor supports adding information to Let's suppose we create our subscription client like so: -```ts +```ts import { GraphQLWsLink } from '@apollo/client/link/subscriptions'; import { createClient } from 'graphql-ws'; @@ -535,7 +535,7 @@ From there you can use the [`useServer.context` property](#operation-context) to For our example, we can use the `connectionParams.authentication` value provided by the client to look up the related user before passing that user along to our resolvers: -```ts +```ts const findUser = async (authToken) => { // Find a user by their auth token }; diff --git a/docs/source/deployment/azure-functions.mdx b/docs/source/deployment/azure-functions.mdx index 585e397b4f8..1c9631d2244 100644 --- a/docs/source/deployment/azure-functions.mdx +++ b/docs/source/deployment/azure-functions.mdx @@ -3,7 +3,7 @@ title: Deploying with Azure Functions description: Deploying your GraphQL server to Azure Functions --- - +{/* TODO(AS4) update when we have an Azure Functions integration to deploy */} This tutorial walks through setting up an example project using the [Azure Functions integration](https://www.npmjs.com/package/apollo-server-azure-functions) for Apollo Server. @@ -82,7 +82,7 @@ To set up the `apollo-server-azure-functions` library, replace the content of yo ```javascript const { ApolloServer, gql } = require('apollo-server-azure-functions'); const { - ApolloServerPluginLandingPageLocalDefault + ApolloServerPluginLandingPageLocalDefault, } = require('apollo-server-core'); // Schema definition. @@ -105,9 +105,7 @@ const server = new ApolloServer({ resolvers, csrfPrevention: true, cache: 'bounded', - plugins: [ - ApolloServerPluginLandingPageLocalDefault({ embed: true }), - ], + plugins: [ApolloServerPluginLandingPageLocalDefault({ embed: true })], }); exports.graphqlHandler = server.createHandler(); ``` @@ -115,8 +113,9 @@ exports.graphqlHandler = server.createHandler(); > See the [README](https://www.npmjs.com/package/apollo-server-azure-functions) for `apollo-server-azure-functions` for more information about this package. Next, we need to make a couple of changes to our `graphql/function.json` file: -- Change the output `name` to `$return` -- Add `options` to the list of `methods` (to ensure CORS works) + +- Change the output `name` to `$return` +- Add `options` to the list of `methods` (to ensure CORS works) Your `graphql/function.json` file should now look like this: @@ -129,11 +128,7 @@ Your `graphql/function.json` file should now look like this: "direction": "in", "name": "req", "route": "{*segments}", - "methods": [ - "get", - "post", - "options" - ] + "methods": ["get", "post", "options"] }, { "type": "http", @@ -201,6 +196,7 @@ func azure functionapp publish apollo-example-YOURNAME ``` Your terminal will output something similar to the following: + ```shell Getting site publishing info... Preparing archive... @@ -224,4 +220,3 @@ az group delete --name apollo-examples --yes ## Deploying to Azure with VS Code You can also publish to Azure directly from VS Code using the Azure Functions Extension. Refer to the documentation on [publishing to Azure from VS Code](https://docs.microsoft.com/en-us/azure/azure-functions/functions-create-first-function-vs-code#publish-the-project-to-azure) for more information. - diff --git a/docs/source/deployment/gcp-functions.mdx b/docs/source/deployment/gcp-functions.mdx index d9d824bb632..dfc3d73ea6f 100644 --- a/docs/source/deployment/gcp-functions.mdx +++ b/docs/source/deployment/gcp-functions.mdx @@ -2,7 +2,7 @@ title: Deploying with Google Cloud Functions --- - +{/* TODO(AS4) update when we have a Google Cloud Function integration to deploy */} This tutorial helps you deploy Apollo Server to Google Cloud Functions. It uses the following example function handler: @@ -11,7 +11,7 @@ This tutorial helps you deploy Apollo Server to Google Cloud Functions. It uses ```javascript title="index.js" const { ApolloServer, gql } = require('apollo-server-cloud-functions'); const { - ApolloServerPluginLandingPageLocalDefault + ApolloServerPluginLandingPageLocalDefault, } = require('apollo-server-core'); // Construct a schema, using GraphQL schema language @@ -33,9 +33,7 @@ const server = new ApolloServer({ resolvers, csrfPrevention: true, cache: 'bounded', - plugins: [ - ApolloServerPluginLandingPageLocalDefault({ embed: true }), - ], + plugins: [ApolloServerPluginLandingPageLocalDefault({ embed: true })], }); exports.handler = server.createHandler(); @@ -43,7 +41,6 @@ exports.handler = server.createHandler(); - ## Deploying from the Google Cloud Console ### 1. Configure the function @@ -77,7 +74,6 @@ Edit `package.json` so that it lists `apollo-server-cloud-functions` and `graphq Click **Deploy** to initiate deployment. Then, proceed to [Testing the function](#testing-the-function). - ## Deploying from your local machine Before proceeding, you need to set up the gcloud SDK: @@ -155,7 +151,7 @@ To obtain information about a currently executing Google Cloud Function (HTTP he ```javascript const { ApolloServer, gql } = require('apollo-server-cloud-functions'); const { - ApolloServerPluginLandingPageLocalDefault + ApolloServerPluginLandingPageLocalDefault, } = require('apollo-server-core'); // Construct a schema, using GraphQL schema language @@ -182,9 +178,7 @@ const server = new ApolloServer({ req, res, }), - plugins: [ - ApolloServerPluginLandingPageLocalDefault({ embed: true }), - ], + plugins: [ApolloServerPluginLandingPageLocalDefault({ embed: true })], }); exports.handler = server.createHandler(); diff --git a/docs/source/deployment/heroku.md b/docs/source/deployment/heroku.md index a4ae216ef22..605e01afe7b 100644 --- a/docs/source/deployment/heroku.md +++ b/docs/source/deployment/heroku.md @@ -2,7 +2,7 @@ title: Deploying with Heroku --- -> Heroku is planning to [phase out their free tier in the near future](https://blog.heroku.com/next-chapter). +> Heroku is planning to [phase out their free tier in the near future](https://blog.heroku.com/next-chapter). Heroku is a common platform-as-a-service solution that enables you to deploy Apollo Server and have a running GraphQL endpoint in a matter of minutes. @@ -32,6 +32,7 @@ Choose a name your app (this will be your ``) and click **Creat ## Setting up the project + You can set up your project using the `@apollo/server` library along with any of Apollo Server's other framework integrations (Express, Fastify, etc.). ### Manually setting the port @@ -98,14 +99,15 @@ $ git push heroku # specify your branch name, if necessary After deployment completes, your Apollo Server project is up and running! You can send a query to your Heroku-hosted GraphQL endpoint at `.herokuapp.com`. Some things to note: + - `git push heroku` does _not_ push to your `origin` remote or any other remote. You must run `git push` again separately. - By default, Heroku sets the `NODE_ENV` variable to `production`. If you wish to change this, run this command in your project directory: - ```shell - $ heroku config:set NODE_ENV=development - ``` + ```shell + $ heroku config:set NODE_ENV=development + ``` - Alternatively, you can [configure environment variables](./heroku/#configuring-environment-variables) through the Heroku dashboard. + Alternatively, you can [configure environment variables](./heroku/#configuring-environment-variables) through the Heroku dashboard. - Remember that introspection is disabled by default when Apollo Server is in a production environment, which prevents tools like Apollo Sandbox from working. diff --git a/docs/source/deployment/lambda.md b/docs/source/deployment/lambda.md index 81522c4af77..221e717b4da 100644 --- a/docs/source/deployment/lambda.md +++ b/docs/source/deployment/lambda.md @@ -38,7 +38,7 @@ Next, set up the schema's type definitions and resolvers, and pass them to the ` const { ApolloServer, gql } = require('apollo-server-lambda'); const { - ApolloServerPluginLandingPageLocalDefault + ApolloServerPluginLandingPageLocalDefault, } = require('apollo-server-core'); // Construct a schema, using GraphQL schema language @@ -60,9 +60,7 @@ const server = new ApolloServer({ resolvers, csrfPrevention: true, cache: 'bounded', - plugins: [ - ApolloServerPluginLandingPageLocalDefault({ embed: true }), - ], + plugins: [ApolloServerPluginLandingPageLocalDefault({ embed: true })], }); exports.graphqlHandler = server.createHandler(); @@ -103,6 +101,7 @@ functions: ``` ### Running Locally + Using the `serverless` CLI, we can invoke our function locally to make sure it is running properly. As with any GraphQL "server", we need to send an operation for the schema to run as an HTTP request. You can store a mock HTTP request locally in a `query.json` file: ```json @@ -162,6 +161,7 @@ First, it builds the functions, zips up the artifacts, and uploads the artifacts The resulting S3 buckets and Lambda functions can be viewed and managed after logging in to the [AWS Console](https://console.aws.amazon.com). + - To find the created S3 bucket, search the listed services for S3. For this example, the bucket created by Serverless was named `apollo-lambda-dev-serverlessdeploymentbucket-1s10e00wvoe5f` - To find the created Lambda function, search the listed services for `Lambda`. If the list of Lambda functions is empty, or missing the newly created function, double check the region at the top right of the screen. The default region for Serverless deployments is `us-east-1` (N. Virginia) @@ -181,7 +181,7 @@ exports.handler = server.createHandler({ app.use(someOtherMiddleware); app.use(middleware); return app; - } + }, }); ``` @@ -193,7 +193,7 @@ Because `apollo-server-lambda` is built on top of `apollo-server-express`, you c exports.handler = server.createHandler({ expressGetMiddlewareOptions: { disableHealthCheck: true, - } + }, }); ``` @@ -206,7 +206,7 @@ The `event` object contains the API Gateway event (HTTP headers, HTTP method, bo ```js const { ApolloServer, gql } = require('apollo-server-lambda'); const { - ApolloServerPluginLandingPageLocalDefault + ApolloServerPluginLandingPageLocalDefault, } = require('apollo-server-core'); // Construct a schema, using GraphQL schema language @@ -235,9 +235,7 @@ const server = new ApolloServer({ context, expressRequest: express.req, }), - plugins: [ - ApolloServerPluginLandingPageLocalDefault({ embed: true }), - ], + plugins: [ApolloServerPluginLandingPageLocalDefault({ embed: true })], }); exports.graphqlHandler = server.createHandler(); diff --git a/docs/source/getting-started.mdx b/docs/source/getting-started.mdx index 88fc4335d12..ef48bbcf78b 100644 --- a/docs/source/getting-started.mdx +++ b/docs/source/getting-started.mdx @@ -325,7 +325,10 @@ One of the most important concepts of GraphQL is that clients can choose to quer You can view and fork the complete example on Code Sandbox: - Edit server-getting-started + Edit server-getting-started ## Next steps diff --git a/docs/source/index.mdx b/docs/source/index.mdx index 3a378223c9a..aa998cd41c7 100644 --- a/docs/source/index.mdx +++ b/docs/source/index.mdx @@ -6,26 +6,30 @@ title: Apollo Server 4 (Alpha) > > [See what's new](./migration/)! > -> We are working on updating our documentation to reflect the changes introduced in Apollo Server 4. In this effort, we have temporarily omitted articles from this branch that aren't yet up to date. In the meantime, you can reference the [Apollo Server 3](/apollo-server) docs for in-depth information on Apollo Server's features. +> We are working on updating our documentation to reflect the changes introduced in Apollo Server 4. In this effort, we have temporarily omitted articles from this branch that aren't yet up to date. In the meantime, you can reference the [Apollo Server 3](/apollo-server) docs for in-depth information on Apollo Server's features. **Apollo Server is an [open-source](https://github.com/apollographql/apollo-server), spec-compliant GraphQL server** that's compatible with any GraphQL client, including [Apollo Client](/react). It's the best way to build a production-ready, self-documenting GraphQL API that can use data from any source. -Diagram showing Apollo Server bridging frontend and backend +Diagram showing Apollo Server bridging frontend and backend #### You can use Apollo Server as: -* The gateway for a [federated supergraph](/federation/) -* The GraphQL server for a [subgraph](/federation/subgraphs) in a federated supergraph - -* A [stand-alone GraphQL server](./migration#migrate-from-apollo-server) -* An add-on to your application's existing Node.js middleware (such as Express, AWS Lambda, or Fastify) +- The gateway for a [federated supergraph](/federation/) +- The GraphQL server for a [subgraph](/federation/subgraphs) in a federated supergraph + {/* TODO(AS4): replace links to new articles once they exist */} +- A [stand-alone GraphQL server](./migration#migrate-from-apollo-server) +- An add-on to your application's existing Node.js middleware (such as Express, AWS Lambda, or Fastify) #### Apollo Server provides: -* **Straightforward setup**, so your client developers can start fetching data quickly -* **Incremental adoption**, enabling you to add features as they're needed -* **Universal compatibility** with any data source, any build tool, and any GraphQL client -* **Production readiness**, enabling you to confidently run your graph in production +- **Straightforward setup**, so your client developers can start fetching data quickly +- **Incremental adoption**, enabling you to add features as they're needed +- **Universal compatibility** with any data source, any build tool, and any GraphQL client +- **Production readiness**, enabling you to confidently run your graph in production #### Ready to try it out? diff --git a/docs/source/integrations/building-integrations.md b/docs/source/integrations/building-integrations.md index a669877e4b6..e05576fa55f 100644 --- a/docs/source/integrations/building-integrations.md +++ b/docs/source/integrations/building-integrations.md @@ -1,9 +1,10 @@ --- title: Building Web Framework Integrations for Apollo Server -description: "" +description: '' --- + > This article is for _authors_ of web framework integrations. Before > building a new integration, we recommend seeing if there's > an integration for your framework of choice that suits your needs. @@ -12,12 +13,14 @@ One of the driving forces behind Apollo Server 4 is the creation of a stable, well-defined API for processing HTTP requests and responses. Apollo Server 4's API enables external collaborators, like you, to build integrations with Apollo Server in their web framework of choice. + ## Overview The primary responsibility of an Apollo Server integration is to translate requests and responses between a web framework's native format to the format used by `ApolloServer`. This article conceptually covers how to build an integration, using the [Express integration](https://github.com/apollographql/apollo-server/blob/version-4/packages/server/src/express4/index.ts) (i.e.,`expressMiddleware`) as an example. + > For more examples, see these Apollo Server 4 [integrations demos for Fastify and Lambda](https://github.com/apollographql/server-v4-integration-demos/tree/main/packages). ### Main function signature @@ -67,7 +70,7 @@ Apollo Server, like so: server.assertStarted('expressMiddleware()'); ``` -*Serverless* integrations don't require users to call `server.start()`; instead, a serverless integration calls the +_Serverless_ integrations don't require users to call `server.start()`; instead, a serverless integration calls the `startInBackgroundHandlingStartupErrorsByLoggingAndFailingAllRequests` method. Because serverless integrations handle starting their server instances, they also don't need to call the `assertStarted` method. ### Compute GraphQL Context @@ -106,6 +109,7 @@ Note, the `context` function is _called_ during the [execution step](#execute-th We recommend implementing your integration package as either a request handler or a framework plugin. Request handlers typically receive information about each request, including standard HTTP parts (i.e., `method`, `headers`, and `body`) and other useful contextual information. A request handler has 4 main responsibilities: + 1. [Parse the request](#parse-the-request) 2. [Construct an `HTTPGraphQLRequest` object](#construct-the-httpgraphqlrequest-object) from the incoming request 3. [Execute the GraphQL request](#execute-the-graphql-request) using Apollo Server @@ -135,6 +139,7 @@ Your integration should pass along whatever it parses to Apollo Server; Apollo S Apollo Server also accepts GraphQL queries [sent using `GET`](/apollo-server/requests) with query string parameters. Apollo Server expects a raw query string for these types of HTTP requests. Apollo Server is indifferent to whether or not the `?` is included at the beginning of your query string. Fragments (starting with `#`) at the end of a URL should not be included. Apollo Server 4's Express integration computes the query string using the request's full URL, like so: + ```ts import { parse } from 'url'; @@ -193,11 +198,10 @@ Using the `HTTPGraphQLRequest` we created above, we now execute the GraphQL request: ```ts -const result = await server - .executeHTTPGraphQLRequest({ - httpGraphQLRequest, - context: () => context({ req, res }), - }); +const result = await server.executeHTTPGraphQLRequest({ + httpGraphQLRequest, + context: () => context({ req, res }), +}); ``` In the above code snippet, the `httpGraphQLRequest` variable is our `HTTPGraphQLRequest` object. The `context` function is the [one we determined earlier](#compute-graphql-context) (either given to us by the user or our default context). Note how we pass the `req` and `res` objects we received from Express to the `context` function (as promised by our `ExpressContextFunctionArgument` type). diff --git a/docs/source/integrations/plugins-event-reference.mdx b/docs/source/integrations/plugins-event-reference.mdx index b1d48cb5731..953a8c66273 100644 --- a/docs/source/integrations/plugins-event-reference.mdx +++ b/docs/source/integrations/plugins-event-reference.mdx @@ -9,9 +9,9 @@ This reference describes the lifecycle events that your [custom Apollo Server pl Apollo Server fires two types of events that plugins can hook into: **server lifecycle events** and **request lifecycle events**. -* Server lifecycle events are high-level events related to the lifecycle of Apollo Server itself (e.g., [`serverWillStart`](#serverwillstart)). -* Request lifecycle events are associated with the lifecycle of a specific request. - * You define responses to these events _within_ the response to a `requestDidStart` event, as described in [Responding to request lifecycle events](./plugins#responding-to-request-lifecycle-events). +- Server lifecycle events are high-level events related to the lifecycle of Apollo Server itself (e.g., [`serverWillStart`](#serverwillstart)). +- Request lifecycle events are associated with the lifecycle of a specific request. + - You define responses to these events _within_ the response to a `requestDidStart` event, as described in [Responding to request lifecycle events](./plugins#responding-to-request-lifecycle-events). > With two exceptions, all plugin methods in Apollo Server are `async`. The first exception is `willResolveField`, which is called much more frequently than other plugin methods. The second exception is `schemaDidLoadOrUpdate`, where making the method `async` would introduce unclear ordering semantics around method executions. @@ -21,12 +21,12 @@ events** and **request lifecycle events**. The `serverWillStart` event fires when Apollo Server is preparing to start serving GraphQL requests. The server doesn't start until this asynchronous method completes. If it throws (i.e., if the `Promise` it returns is _rejected_), startup _fails_ and your server does not serve GraphQL operations. This helps you make sure all of your server's dependencies are available before attempting to begin serving requests. - +{/* TODO(AS4) add link to integration page when exists */} This event is fired at different times depending on which Apollo Server integration you're using: -* If you are using `startStandaloneServer`, it's fired when you invoke the `startStandaloneServer` function with your server instance. -* In non-serverless integrations like `expressMiddleware`, it's fired from the `start()` method. -* In serverless integrations, it's usually fired in response to the first incoming request. +- If you are using `startStandaloneServer`, it's fired when you invoke the `startStandaloneServer` function with your server instance. +- In non-serverless integrations like `expressMiddleware`, it's fired from the `start()` method. +- In serverless integrations, it's usually fired in response to the first incoming request. #### Example @@ -40,10 +40,10 @@ const server = new ApolloServer({ { async serverWillStart() { console.log('Server starting!'); - } - } - ] -}) + }, + }, + ], +}); ``` @@ -68,12 +68,12 @@ const server = new ApolloServer({ return { async drainServer() { await myCustomServer.drain(); - } - } - } - } - ] -}) + }, + }; + }, + }, + ], +}); ``` @@ -101,12 +101,12 @@ const server = new ApolloServer({ return { async serverWillStop() { clearInterval(interval); - } - } - } - } - ] -}) + }, + }; + }, + }, + ], +}); ``` @@ -162,23 +162,24 @@ For more landing page options, see [Changing the landing page](../workflow/build const server = new ApolloServer({ /* ... other necessary configuration ... */ - plugins: [ + plugins: [ { async serverWillStart() { return { async renderLandingPage() { - return { html: `Welcome to your server!` }; + return { + html: `Welcome to your server!`, + }; }, }; }, }, ], -}) +}); ``` - ### `requestDidStart` > **New in Apollo Server 4**: In Apollo Server 4, `requestDidStart` hooks are called in parallel rather than in series. @@ -210,13 +211,13 @@ const server = new ApolloServer({ // when parsing begins. The event is scoped within an // associated `requestDidStart` server lifecycle event. async parsingDidStart(requestContext) { - console.log('Parsing started!') + console.log('Parsing started!'); }, - } - } - } + }; + }, + }, ], -}) +}); ``` @@ -270,7 +271,7 @@ Note that not every event fires for every request (for example, `parsingDidStart ### `didResolveSource` The `didResolveSource` event is invoked after Apollo Server has determined the -`String`-representation of the incoming operation that it will act upon. In the +`String`-representation of the incoming operation that it will act upon. In the event that this `String` was not directly passed in from the client, this may be retrieved from a cache store (e.g., Automated Persisted Queries). @@ -370,7 +371,7 @@ executionDidStart?( ): Promise; ``` -`executionDidStart` may return an object with one or both of the methods `executionDidEnd` and `willResolveField`. `executionDidEnd` is treated like an end hook: it is called after execution with any errors that occurred. `willResolveField` is documented in the next section. +`executionDidStart` may return an object with one or both of the methods `executionDidEnd` and `willResolveField`. `executionDidEnd` is treated like an end hook: it is called after execution with any errors that occurred. `willResolveField` is documented in the next section. ### `willResolveField` @@ -398,25 +399,29 @@ const server = new ApolloServer({ return { async executionDidStart(executionRequestContext) { return { - willResolveField({source, args, contextValue, info}) { + willResolveField({ source, args, contextValue, info }) { const start = process.hrtime.bigint(); return (error, result) => { const end = process.hrtime.bigint(); - console.log(`Field ${info.parentType.name}.${info.fieldName} took ${end - start}ns`); + console.log( + `Field ${info.parentType.name}.${info.fieldName} took ${ + end - start + }ns`, + ); if (error) { console.log(`It failed with ${error}`); } else { console.log(`It returned ${result}`); } }; - } - } - } - } - } - } - ] -}) + }, + }; + }, + }; + }, + }, + ], +}); ``` diff --git a/docs/source/integrations/plugins.mdx b/docs/source/integrations/plugins.mdx index 8969bf41ff0..acf013a0b35 100644 --- a/docs/source/integrations/plugins.mdx +++ b/docs/source/integrations/plugins.mdx @@ -13,7 +13,6 @@ You can create your own Apollo Server plugins to perform custom operations in re Plugins are JavaScript objects that implement one or more functions that respond to events. Here's a basic plugin that responds to the `serverWillStart` event: - ```ts title="index.ts" @@ -26,7 +25,6 @@ const myPlugin = { - You can define a plugin in the same file where you initialize Apollo Server, or you can export it as a separate module: @@ -71,14 +69,14 @@ A plugin can respond to any combination of [supported events](./plugins-event-re Plugins can respond to the following events associated with the GraphQL request lifecycle: -* [`didResolveSource`](./plugins-event-reference/#didresolvesource) -* [`parsingDidStart`](./plugins-event-reference/#parsingdidstart) -* [`validationDidStart`](./plugins-event-reference/#validationdidstart) -* [`didResolveOperation`](./plugins-event-reference/#didresolveoperation) -* [`responseForOperation`](./plugins-event-reference/#responseforoperation) -* [`executionDidStart`](./plugins-event-reference/#executiondidstart) -* [`didEncounterErrors`](./plugins-event-reference/#didencountererrors) -* [`willSendResponse`](./plugins-event-reference/#willsendresponse) +- [`didResolveSource`](./plugins-event-reference/#didresolvesource) +- [`parsingDidStart`](./plugins-event-reference/#parsingdidstart) +- [`validationDidStart`](./plugins-event-reference/#validationdidstart) +- [`didResolveOperation`](./plugins-event-reference/#didresolveoperation) +- [`responseForOperation`](./plugins-event-reference/#responseforoperation) +- [`executionDidStart`](./plugins-event-reference/#executiondidstart) +- [`didEncounterErrors`](./plugins-event-reference/#didencountererrors) +- [`willSendResponse`](./plugins-event-reference/#willsendresponse) **However**, the way you define these functions is slightly different from the `serverWillStart` example above. First, your plugin must define the `requestDidStart` function: @@ -98,7 +96,7 @@ const myPlugin = { The `requestDidStart` event fires whenever Apollo Server receives a GraphQL request, _before_ any of the lifecycle events listed above. You can respond to this event just like you respond to `serverWillStart`, but you _also_ use this function - to define responses for a request's lifecycle events, like so: +to define responses for a request's lifecycle events, like so: @@ -114,8 +112,8 @@ const myPlugin = { async validationDidStart(requestContext) { console.log('Validation started!'); - } - } + }, + }; }, }; ``` @@ -135,33 +133,36 @@ The following diagram illustrates the sequence of events that fire for each requ ```mermaid graph TB; - request(requestDidStart) --> resolveSource(didResolveSource); - resolveSource --"Success"--> parsing(parsingDidStart*); - parsing --"Success"--> validation(validationDidStart*); - validation --"Success"--> resolveOperation(didResolveOperation); - resolveOperation --"Success"--> response(responseForOperation); + request(requestDidStart) */} resolveSource(didResolveSource); + resolveSource --"Success"*/} parsing(parsingDidStart*); + parsing --"Success"*/} validation(validationDidStart*); + validation --"Success"*/} resolveOperation(didResolveOperation); + resolveOperation --"Success"*/} response(responseForOperation); execution(executionDidStart*); resolveField(willResolveField*); errors(didEncounterErrors); - errors --> send; - response --"Response provided"--> send; - response --"No response provided"--> execution; - execution ---->|"Success"| send(willSendResponse); - execution --"(Fires once per resolver)"-->resolveField; + errors */} send; + response --"Response provided"*/} send; + response --"No response provided"*/} execution; + execution --*/}|"Success"| send(willSendResponse); + execution --"(Fires once per resolver)"*/}resolveField; class errors secondary; ``` -*The indicated events also support end hooks that are called when their associated step completes. + + *The indicated events also support end hooks that are + called when their associated step completes. + ### End hooks Event handlers for the following events can optionally return a function that is invoked after the corresponding lifecycle phase _ends_: -* [`parsingDidStart`](./plugins-event-reference/#parsingdidstart) -* [`validationDidStart`](./plugins-event-reference/#validationdidstart) -* [`willResolveField`](./plugins-event-reference/#willresolvefield) +- [`parsingDidStart`](./plugins-event-reference/#parsingdidstart) +- [`validationDidStart`](./plugins-event-reference/#validationdidstart) +- [`willResolveField`](./plugins-event-reference/#willresolvefield) The [`executionDidStart`](./plugins-event-reference/#executiondidstart) hook returns an _object_ containing an `executionDidEnd` function instead of just a function as an end hook. This is because the returned object can also contain `willResolveField`. @@ -180,16 +181,16 @@ const myPlugin = { if (err) { console.error(err); } - } + }; }, async validationDidStart() { // This end hook is unique in that it can receive an array of errors, // which will contain every validation error that occurred. return async (errs) => { if (errs) { - errs.forEach(err => console.error(err)); + errs.forEach((err) => console.error(err)); } - } + }; }, async executionDidStart() { return { @@ -197,12 +198,12 @@ const myPlugin = { if (err) { console.error(err); } - } + }, }; }, }; }, -} +}; ``` @@ -252,4 +253,4 @@ const server = new ApolloServer({ }); ``` - \ No newline at end of file + diff --git a/docs/source/migration.mdx b/docs/source/migration.mdx index 5fec6253317..156c27036c7 100644 --- a/docs/source/migration.mdx +++ b/docs/source/migration.mdx @@ -11,8 +11,9 @@ title: Migrating to Apollo Server 4 (Alpha) This major release focuses on improving Apollo Server's extensibility and making it simpler to use, maintain, and document. To learn more about the inspiration behind this release, see the [Apollo Server Roadmap](https://github.com/apollographql/apollo-server/blob/main/ROADMAP.md). The Apollo Server 4 alpha provides the following features, with more to come in the full release: -* A well-defined API with a stable HTTP abstraction, enabling contributors to easily [build and maintain integrations](./integrations/building-integrations) in their preferred frameworks. -* A new `@apollo/server` package, combining numerous [smaller packages](#packages-merged-into-apolloserver) and including the [`startStandaloneServer`](#migrate-from-apollo-server) and [`expressMiddleware`](#migrate-from-apollo-server-express) functions. + +- A well-defined API with a stable HTTP abstraction, enabling contributors to easily [build and maintain integrations](./integrations/building-integrations) in their preferred frameworks. +- A new `@apollo/server` package, combining numerous [smaller packages](#packages-merged-into-apolloserver) and including the [`startStandaloneServer`](#migrate-from-apollo-server) and [`expressMiddleware`](#migrate-from-apollo-server-express) functions. During Apollo Server 4's alpha, we are actively looking to gather feedback and [issues](https://github.com/apollographql/apollo-server/issues/new/choose) from community members and customers. @@ -42,17 +43,17 @@ For those migrating from Apollo Server 3 to Apollo Server 4, use the below flowc ```mermaid graph TB; server("Am I using the apollo-server package?"); - server--No-->express("Am I using the apollo-server-express package?"); - server--Yes-->useStandAlone("Use the startStandaloneServer function"); - express--No-->buildIntegration("You canโ€™t upgrade during the alpha yet*"); - express--Yes-->useExpressMiddleware("Use the expressMiddleware function"); + server--No*/}express("Am I using the apollo-server-express package?"); + server--Yes*/}useStandAlone("Use the startStandaloneServer function"); + express--No*/}buildIntegration("You canโ€™t upgrade during the alpha yet*"); + express--Yes*/}useExpressMiddleware("Use the expressMiddleware function"); class useStandAlone,useExpressMiddleware secondary; ``` - If you're currently using the `apollo-server` package, you should use the [`startStandaloneServer`](#migrate-from-apollo-server) function. - If you're currently using the `apollo-server-express` package, you should use the [`expressMiddleware`](#migrate-from-apollo-server-express) function. -The [`@apollo/server` package](https://www.npmjs.com/package/@apollo/server) exports these functions alongside the `ApolloServer` class. +The [`@apollo/server` package](https://www.npmjs.com/package/@apollo/server) exports these functions alongside the `ApolloServer` class. If you are using any other Apollo Server 3 framework integration package, you canโ€™t upgrade during the Apollo Server 4 alpha release _yet_. Please help us by [building new integrations](./integrations/building-integrations) or [discussing how to maintain existing integrations](https://github.com/apollographql/apollo-server/labels/integration-collaborators) to ensure there is an Apollo Server 4 integration for your favorite framework. @@ -137,17 +138,17 @@ The `startStandaloneServer` function accepts two arguments; the first is the ins - ##### `context` +##### `context` - `Function` +`Function` - An optional `context` initialization function. The `context` function receives `req` and `res` options ([see below for more details.](#context-initialization-function)). +An optional `context` initialization function. The `context` function receives `req` and `res` options ([see below for more details.](#context-initialization-function)). - In Apollo Server 3, you pass the `context` function to the constructor. In Apollo Server 4, you pass the `context` function to `startStandaloneServer`. +In Apollo Server 3, you pass the `context` function to the constructor. In Apollo Server 4, you pass the `context` function to `startStandaloneServer`. @@ -157,17 +158,18 @@ The `startStandaloneServer` function accepts two arguments; the first is the ins - ##### `listen` +##### `listen` - `Object` +`Object` - An optional `listen` configuration option. The `listen` option accepts an object with the same properties as the [`net.Server.listen` options object](https://nodejs.org/api/net.html#serverlistenoptions-callback). +An optional `listen` configuration option. The `listen` option accepts an object with the same properties as the [`net.Server.listen` options object](https://nodejs.org/api/net.html#serverlistenoptions-callback). + +For example, in Apollo Server 3, if you used `server.listen(4321)`, you'll now pass `listen: { port: 4321 }` to the `startStandaloneServer` function in Apollo Server 4. If you didn't pass any arguments to Apollo Server 3's `server.listen()` method; you don't need to specify this `listen` option. - For example, in Apollo Server 3, if you used `server.listen(4321)`, you'll now pass `listen: { port: 4321 }` to the `startStandaloneServer` function in Apollo Server 4. If you didn't pass any arguments to Apollo Server 3's `server.listen()` method; you don't need to specify this `listen` option. @@ -218,7 +220,9 @@ async function startApolloServer() { }); await server.start(); server.applyMiddleware({ app }); - await new Promise(resolve => httpServer.listen({ port: 4000 }, resolve)); + await new Promise((resolve) => + httpServer.listen({ port: 4000 }, resolve), + ); console.log(`๐Ÿš€ Server ready at http://localhost:4000${server.graphqlPath}`); } ``` @@ -253,71 +257,74 @@ async function startApolloServer() { plugins: [ApolloServerPluginDrainHttpServer({ httpServer })], }); await server.start(); - app.use('/graphql', + app.use( + '/graphql', cors(), json(), expressMiddleware(server, { context: async ({ req }) => ({ token: req.headers.token }), }), ); - await new Promise(resolve => httpServer.listen({ port: 4000 }, resolve)); + await new Promise((resolve) => + httpServer.listen({ port: 4000 }, resolve), + ); console.log(`๐Ÿš€ Server ready at http://localhost:4000/graphql`); } ``` - ### Removed integrations The Apollo Server core team no longer maintains the following integration packages in Apollo Server 4. We are [looking for collaborators](https://github.com/apollographql/apollo-server/labels/integration-collaborators) who actively use these frameworks to maintain Apollo Server 4 compatible integration packages. Apollo Server 4 removes the below integration packages: -* [`apollo-server-fastify`](https://www.npmjs.com/package/apollo-server-fastify) -* [`apollo-server-hapi`](https://www.npmjs.com/package/apollo-server-hapi) -* [`apollo-server-koa`](https://www.npmjs.com/package/apollo-server-koa) -* [`apollo-server-lambda`](https://www.npmjs.com/package/apollo-server-lambda) -* [`apollo-server-micro`](https://www.npmjs.com/package/apollo-server-micro) -* [`apollo-server-cloud-functions`](https://www.npmjs.com/package/apollo-server-cloud-functions) -* [`apollo-server-cloudflare`](https://www.npmjs.com/package/apollo-server-cloudflare) -* [`apollo-server-azure-functions`](https://www.npmjs.com/package/apollo-server-azure-functions) + +- [`apollo-server-fastify`](https://www.npmjs.com/package/apollo-server-fastify) +- [`apollo-server-hapi`](https://www.npmjs.com/package/apollo-server-hapi) +- [`apollo-server-koa`](https://www.npmjs.com/package/apollo-server-koa) +- [`apollo-server-lambda`](https://www.npmjs.com/package/apollo-server-lambda) +- [`apollo-server-micro`](https://www.npmjs.com/package/apollo-server-micro) +- [`apollo-server-cloud-functions`](https://www.npmjs.com/package/apollo-server-cloud-functions) +- [`apollo-server-cloudflare`](https://www.npmjs.com/package/apollo-server-cloudflare) +- [`apollo-server-azure-functions`](https://www.npmjs.com/package/apollo-server-azure-functions) In Apollo Server 3, the `apollo-server-express` package supported both Express and its older predecessor [Connect](https://github.com/senchalabs/connect). In Apollo Server 4, `expressMiddleware` no longer supports Connect. An interested developer could [build a Connect-specific middleware](./integrations/building-integrations), and a PR to this migration guide is welcome if someone does this! ### Packages merged into `@apollo/server` -As shown above, Apollo Server 4 combines the functionality of the `apollo-server`, `apollo-server-express`, and `apollo-server-core` packages into a new `@apollo/server` package. +As shown above, Apollo Server 4 combines the functionality of the `apollo-server`, `apollo-server-express`, and `apollo-server-core` packages into a new `@apollo/server` package. But wait: there's more! The `@apollo/server` package also combines the following packages: + - [`apollo-server-errors`](https://www.npmjs.com/package/apollo-server-errors) - [`apollo-server-plugin-base`](https://www.npmjs.com/package/apollo-server-plugin-base) - [`apollo-server-types`](https://www.npmjs.com/package/apollo-server-types) - ### Plugins are in deep imports -In Apollo Server 3, the `apollo-server-core` package exports built-in plugins, like `ApolloServerUsageReporting`, at the top level. To use these plugins, you must install *both* the `apollo-server-core` package and the package you use to import `ApolloServer` (e.g., `apollo-server` or `apollo-server-express`). +In Apollo Server 3, the `apollo-server-core` package exports built-in plugins, like `ApolloServerUsageReporting`, at the top level. To use these plugins, you must install _both_ the `apollo-server-core` package and the package you use to import `ApolloServer` (e.g., `apollo-server` or `apollo-server-express`). -In Apollo Server 4, these built-in plugins are part of the main `@apollo/server` package, which also imports the `ApolloServer` class. The `@apollo/server` package exports these built-in plugins with deep exports. This means you use deep imports for each built-in plugin, enabling you to evaluate only the plugin you use in your app and making it easier for bundlers to eliminate unused code. +In Apollo Server 4, these built-in plugins are part of the main `@apollo/server` package, which also imports the `ApolloServer` class. The `@apollo/server` package exports these built-in plugins with deep exports. This means you use deep imports for each built-in plugin, enabling you to evaluate only the plugin you use in your app and making it easier for bundlers to eliminate unused code. There's one exception: the plugin `ApolloServerPluginLandingPageGraphQLPlayground` has been moved to its own package `@apollo/server-plugin-landing-page-graphql-playground` which must be installed separately. (This plugin installs the [unmaintained](https://github.com/graphql/graphql-playground/issues/1143) project GraphQL Playground as a landing page, and is provided for compatibility with Apollo Server 2. We encourage you to switch to the [default landing page](/apollo-server/api/plugin/landing-pages), which installs the similar but the actively maintained Apollo Sandbox instead.) - Apollo Server exports the following plugins: +Apollo Server exports the following plugins: -| Plugin | Import path | -|--------|-------------| -| `ApolloServerPluginCacheControl` | `@apollo/server/plugin/cacheControl` | -| `ApolloServerPluginCacheControlDisabled` | `@apollo/server/plugin/disabled` | -| `ApolloServerPluginDrainHttpServer` | `@apollo/server/plugin/drainHttpServer` | -| `ApolloServerPluginInlineTrace` | `@apollo/server/plugin/inlineTrace` | -| `ApolloServerPluginInlineTraceDisabled` | `@apollo/server/plugin/disabled` | -| `ApolloServerPluginLandingPageDisabled` | `@apollo/server/plugin/disabled` | +| Plugin | Import path | +| ------------------------------------------------ | ------------------------------------------------------- | +| `ApolloServerPluginCacheControl` | `@apollo/server/plugin/cacheControl` | +| `ApolloServerPluginCacheControlDisabled` | `@apollo/server/plugin/disabled` | +| `ApolloServerPluginDrainHttpServer` | `@apollo/server/plugin/drainHttpServer` | +| `ApolloServerPluginInlineTrace` | `@apollo/server/plugin/inlineTrace` | +| `ApolloServerPluginInlineTraceDisabled` | `@apollo/server/plugin/disabled` | +| `ApolloServerPluginLandingPageDisabled` | `@apollo/server/plugin/disabled` | | `ApolloServerPluginLandingPageGraphQLPlayground` | `@apollo/server-plugin-landing-page-graphql-playground` | -| `ApolloServerPluginLandingPageLocalDefault` | `@apollo/server/plugin/landingPage/default` | -| `ApolloServerPluginLandingPageProductionDefault` | `@apollo/server/plugin/landingPage/default` | -| `ApolloServerPluginSchemaReporting` | `@apollo/server/plugin/schemaReporting` | -| `ApolloServerPluginUsageReporting` | `@apollo/server/plugin/usageReporting` | -| `ApolloServerPluginUsageReportingDisabled` | `@apollo/server/plugin/disabled` | +| `ApolloServerPluginLandingPageLocalDefault` | `@apollo/server/plugin/landingPage/default` | +| `ApolloServerPluginLandingPageProductionDefault` | `@apollo/server/plugin/landingPage/default` | +| `ApolloServerPluginSchemaReporting` | `@apollo/server/plugin/schemaReporting` | +| `ApolloServerPluginUsageReporting` | `@apollo/server/plugin/usageReporting` | +| `ApolloServerPluginUsageReportingDisabled` | `@apollo/server/plugin/disabled` | For example, replace this Apollo Server 3 code: @@ -379,7 +386,8 @@ For example, below, we use the `RESTDataSource` class to create a `DataSource` w import { RESTDataSource, RequestOptions } from 'apollo-datasource-rest'; import { ApolloServer } from 'apollo-server'; -class MoviesAPI extends RESTDataSource { //highlight-line +class MoviesAPI extends RESTDataSource { + //highlight-line override baseURL = 'https://movies-api.example.com/'; override willSendRequest(request: RequestOptions) { @@ -395,13 +403,14 @@ interface ContextValue { token: string; dataSources: { moviesAPI: MoviesAPI; - } -}; + }; +} const server = new ApolloServer({ typeDefs, resolvers, - context: ({ req: ExpressRequest }): Omit => { //highlight-line + context: ({ req: ExpressRequest }): Omit => { + //highlight-line return { token: getTokenFromRequest(req), }; @@ -425,13 +434,17 @@ Below is how you write the same code in Apollo Server 4. ```ts title="Apollo Server 4" -import { RESTDataSource, WillSendRequestOptions } from '@apollo/datasource-rest'; +import { + RESTDataSource, + WillSendRequestOptions, +} from '@apollo/datasource-rest'; // KeyValueCache is the type of Apollo server's default cache import type { KeyValueCache } from '@apollo/utils.keyvaluecache'; import { ApolloServer } from '@apollo/server'; import { startStandaloneServer } from '@apollo/server/standalone'; -class MoviesAPI extends RESTDataSource { // highlight-line +class MoviesAPI extends RESTDataSource { + // highlight-line override baseURL = 'https://movies-api.example.com/'; private token: string; @@ -490,7 +503,10 @@ If you want to access your entire context's value within your `DataSource`, you ```ts -import { RESTDataSource, WillSendRequestOptions } from '@apollo/datasource-rest'; //highlight-line +import { + RESTDataSource, + WillSendRequestOptions, +} from '@apollo/datasource-rest'; //highlight-line import { KeyValueCache } from '@apollo/utils.keyvaluecache'; import { ApolloServer } from '@apollo/server'; import { startStandaloneServer } from '@apollo/server/standalone'; @@ -509,7 +525,7 @@ class MoviesAPI extends RESTDataSource { request.headers['authorization'] = this.contextValue.token; } - async getMovie(id):Promise { + async getMovie(id): Promise { return this.get(`movies/${encodeURIComponent(id)}`); } } @@ -521,7 +537,13 @@ class ContextValue { moviesAPI: MoviesAPI; }; - constructor({ req, server }: { req: IncomingMessage; server: ApolloServer }) { + constructor({ + req, + server, + }: { + req: IncomingMessage; + server: ApolloServer; + }) { this.token = getTokenFromRequest(req); const { cache } = server; this.dataSources = { @@ -543,10 +565,9 @@ await startStandaloneServer(server, { - ### `modules` -In Apollo Server 3, there are [several ways](https://github.com/apollographql/apollo-server/issues/6062) to provide your `ApolloServer` instance with a schema. One of the most common ways is to provide `typeDefs` and `resolvers` options (each of which can optionally be an array). Another way is using the `modules` option with an array of objects, each object containing `typeDefs` and `resolvers` keys. Under the hood, these two options use entirely different logic to do the same thing. +In Apollo Server 3, there are [several ways](https://github.com/apollographql/apollo-server/issues/6062) to provide your `ApolloServer` instance with a schema. One of the most common ways is to provide `typeDefs` and `resolvers` options (each of which can optionally be an array). Another way is using the `modules` option with an array of objects, each object containing `typeDefs` and `resolvers` keys. Under the hood, these two options use entirely different logic to do the same thing. To simplify its API, Apollo Server 4 removes the `modules` constructor option. You can replace any previous usage of `modules` with the following syntax: @@ -560,6 +581,7 @@ new ApolloServer({ Additionally, the corresponding `GraphQLSchemaModule` TypeScript type is no longer exported. ### `mocks` and `mockEntireSchema` + In Apollo Server 3, the `mocks` and `mockEntireSchema` constructor options enable Apollo Server to return simulated data for GraphQL operations based on your server's schema. Under the hood, Apollo Server 3's mocking functionality is provided via an outdated version of the [`@graphql-tools/mocks`](https://www.npmjs.com/package/@graphql-tools/mock) library. Apollo Server 4 removes both the `mocks` and `mockEntireSchema` constructor options. You can instead directly incorporate the `@graphql-tools/mock` package into your app, enabling you to get the most up-to-date mocking features. For more details on configuring mocks, see the [`@graphql-tools/mocks` docs](https://www.graphql-tools.com/docs/mocking). @@ -574,7 +596,7 @@ new ApolloServer({ }); ``` -```ts title="Apollo Server 4" +```ts title="Apollo Server 4" import { addMocksToSchema } from '@graphql-tools/mock'; import { makeExecutableSchema } from '@graphql-tools/schema'; @@ -647,13 +669,13 @@ new ApolloServer({ - ### `debug` In Apollo Server 3, the `debug` constructor option (which defaults to `true` unless the `NODE_ENV` environment variable is either `production` or `test`) controls several unrelated aspects of Apollo Server: + - If `debug` is `true`, GraphQL responses with errors include stack traces. -- If `debug` is `true` and `ApolloServer` uses the default `logger`, Apollo Server prints all `DEBUG` log-level messages. - - Apollo Server 3 rarely sends messages at the `DEBUG` level, so this primarily affects plugins that use the provided `logger` to send `DEBUG` messages. +- If `debug` is `true` and `ApolloServer` uses the default `logger`, Apollo Server prints all `DEBUG` log-level messages. + - Apollo Server 3 rarely sends messages at the `DEBUG` level, so this primarily affects plugins that use the provided `logger` to send `DEBUG` messages. - The `debug` flag is also available to plugins on `GraphQLRequestContext` to use as they wish. Apollo Server 4 removes the `debug` constructor option. In its place is a new `includeStacktraceInErrorResponses` option which controls its namesake feature. Like `debug`, this option defaults to `true` unless the `NODE_ENV` environment variable is either `production` or `test`. @@ -674,7 +696,9 @@ Additionally, if your app or a plugin uses `DEBUG`-level log messages and your s import loglevel from 'loglevel'; const logger = loglevel.getLogger('apollo-server'); -logger.setLevel(shouldShowDebugMessages ? loglevel.levels.DEBUG : loglevel.levels.INFO); +logger.setLevel( + shouldShowDebugMessages ? loglevel.levels.DEBUG : loglevel.levels.INFO, +); const server = new ApolloServer({ logger, // ... @@ -731,7 +755,7 @@ new ApolloServer({ // as the operation actually executed. if ('data' in response.result) { response.result.extensions = { - ...(response.result.extensions), + ...response.result.extensions, hello: 'world', }; } @@ -782,7 +806,6 @@ new ApolloServer({ - ## Removed features Several small features have been removed from Apollo Server 4. @@ -793,7 +816,7 @@ In Apollo Server 3, the health check feature supports a simple `HTTP`-level heal Apollo Server 4 no longer supports built-in health checks. We found that running a trivial GraphQL query was a better way of checking the status of your server, because a query ensures your server successfully serves traffic _and_ performs GraphQL operations. -Every GraphQL server supports a trivial query that requests the [`__typename`](/apollo-server/schema/schema/#the-__typename-field) of the top-level `Query` type. This means every GraphQL server can respond to a `GET` request to a URL, such as: +Every GraphQL server supports a trivial query that requests the [`__typename`](/apollo-server/schema/schema/#the-__typename-field) of the top-level `Query` type. This means every GraphQL server can respond to a `GET` request to a URL, such as: ```bash https://your.server/?query=%7B__typename%7D @@ -807,9 +830,9 @@ If you want a health check for your HTTP server unrelated to the health of the G In Apollo Server 3, many framework integrations enable you to use the `path` option to configure the [URL path](/apollo-server/api/apollo-server/#path) where Apollo Server processes requests. By default, the `path` option uses the `/graphql` URL path. -In Apollo Server 4, you should use your framework's routing feature to mount your integration at the URL path where you want Apollo Server to process requests. For example, if you are using `apollo-server-express` in Apollo Server 3 and would like to continue using the default `/graphql` path, you should now mount the `expressMiddleware` function at the `/graphql` path. +In Apollo Server 4, you should use your framework's routing feature to mount your integration at the URL path where you want Apollo Server to process requests. For example, if you are using `apollo-server-express` in Apollo Server 3 and would like to continue using the default `/graphql` path, you should now mount the `expressMiddleware` function at the `/graphql` path. -> Apollo Server 3's batteries-included `apollo-server` package, replaced by `startStandaloneServer` in Apollo Server 4, serves all URLs (i.e., rather than only listening on `/graphql`). +> Apollo Server 3's batteries-included `apollo-server` package, replaced by `startStandaloneServer` in Apollo Server 4, serves all URLs (i.e., rather than only listening on `/graphql`). ### `body-parser` and `cors` @@ -823,7 +846,7 @@ Note that [`startStandaloneServer`](#migrate-from-apollo-server) sets up body pa Apollo Server 3 depends on the [`graphql-tag`](https://www.npmjs.com/package/graphql-tag) npm package and re-exports its `gql` template literal tag. The `gql` tag is essentially a caching wrapper around `graphql-js`'s parser, and most IDEs know to treat the contents of `gql` strings as GraphQL. -Apollo Server 4 does not depend on the `graphql-tag` library, nor does it export the `gql` tag. If you want to continue using the `gql` tag, you can directly install `graphql-tag` into your app, then update your import, replacing this line: +Apollo Server 4 does not depend on the `graphql-tag` library, nor does it export the `gql` tag. If you want to continue using the `gql` tag, you can directly install `graphql-tag` into your app, then update your import, replacing this line: ```ts import { gql } from 'apollo-server'; @@ -835,14 +858,14 @@ with this line: import gql from 'graphql-tag'; ``` -The `apollo-server` package exports `gql` as a named export, whereas the `gql` tag is the default export for `graphql-tag`. - +The `apollo-server` package exports `gql` as a named export, whereas the `gql` tag is the default export for `graphql-tag`. ### `ApolloError` Apollo Server 4 removes both `ApolloError` and `toApolloError` in favor of using `GraphQLError`. The `graphql` package exports `GraphQLError`, and you can use it like so: + ```ts import { GraphQLError } from 'graphql'; @@ -853,6 +876,7 @@ throw new GraphQLError(message, { ``` If you used the optional `code` argument with `ApolloError`: + ``` throw new ApolloError(message, 'YOUR_ERROR_CODE'); ``` @@ -863,23 +887,23 @@ you should now pass your error code to `GraphQLError`'s `extensions` option; see Apollo Server 3 exports several error classes. Apollo Server uses some of these error classes in specific situations (e.g., `SyntaxError`, `ValidationError`, and `UserInputError`), while other classes (`ForbiddenError` and `AuthenticationError`) are for users to use in their apps. All of these error classes are subclasses of the main `ApolloError` class. -In Apollo Server 4, [`ApolloError` no longer exists](#apolloerror), so Apollo Server doesn't export specific error classes. Instead, you can create your own error codes using `graphql`'s `GraphQLError` class. Additionally, Apollo Server now provides an enum of error codes ([`ApolloServerErrorCode`](https://github.com/apollographql/apollo-server/blob/version-4/packages/server/src/errors/index.ts)) that you can check against to see if a given error is one of the types recognized by Apollo Server. +In Apollo Server 4, [`ApolloError` no longer exists](#apolloerror), so Apollo Server doesn't export specific error classes. Instead, you can create your own error codes using `graphql`'s `GraphQLError` class. Additionally, Apollo Server now provides an enum of error codes ([`ApolloServerErrorCode`](https://github.com/apollographql/apollo-server/blob/version-4/packages/server/src/errors/index.ts)) that you can check against to see if a given error is one of the types recognized by Apollo Server. In Apollo Server 3, you can throw a new `ForbiddenError`, like so: ```ts import { ForbiddenError } from 'apollo-server'; -throw new ForbiddenError("my message", { myExtension: "foo" }) +throw new ForbiddenError('my message', { myExtension: 'foo' }); ``` In Apollo Server 4, you should define your own error using `GraphQLError`, like so: ```ts import { GraphQLError } from 'graphql'; -throw new GraphQLError("my message", { +throw new GraphQLError('my message', { extensions: { code: 'FORBIDDEN', - myExtension: "foo", + myExtension: 'foo', }, }); ``` @@ -917,7 +941,7 @@ If you are using `requestAgent` in Apollo Server 3, you can use the `node-fetch` So, where you previously wrote: ```ts -ApolloServerPluginUsageReporting({ requestAgent }) +ApolloServerPluginUsageReporting({ requestAgent }); ``` You can now write: @@ -925,10 +949,11 @@ You can now write: ```ts import fetch from 'node-fetch'; ApolloServerPluginUsageReporting({ - fetcher: (url, options) => fetch(url, { - ...options, - agent: requestAgent, - }), + fetcher: (url, options) => + fetch(url, { + ...options, + agent: requestAgent, + }), }); ``` @@ -947,13 +972,13 @@ So, where you previously wrote: new ApolloServer({ plugins: [ApolloServerPluginUsageReporting({ rewriteError })], // ... -}) +}); // subgraphs new ApolloServer({ plugins: [ApolloServerPluginInlineTrace({ rewriteError })], // ... -}) +}); ``` you can now write: @@ -961,22 +986,25 @@ you can now write: ```ts // monoliths new ApolloServer({ - plugins: [ApolloServerPluginUsageReporting({ - sendErrors: { transform: rewriteError }, - })], + plugins: [ + ApolloServerPluginUsageReporting({ + sendErrors: { transform: rewriteError }, + }), + ], // ... -}) +}); // subgraphs new ApolloServer({ - plugins: [ApolloServerPluginInlineTrace({ - includeErrors: { transform: rewriteError }, - })], + plugins: [ + ApolloServerPluginInlineTrace({ + includeErrors: { transform: rewriteError }, + }), + ], // ... -}) +}); ``` - ### Doubly-escaped `variables` and `extensions` in requests Apollo Server 3 and 4 both accept `POST` requests with a JSON body. @@ -990,7 +1018,8 @@ For example, below is a valid query: ```json { - "query": "{ __typename }", "extensions": { "foo": 1 } + "query": "{ __typename }", + "extensions": { "foo": 1 } } ``` @@ -998,18 +1027,18 @@ Whereas this query would be invalid: ```json { - "query": "{ __typename }", "extensions": "{ \"foo\": 1 }" + "query": "{ __typename }", + "extensions": "{ \"foo\": 1 }" } ``` - ## Changed features ### New approach to serverless frameworks In Apollo Server 3, our approach to creating serverless frameworks involves subclassing `ApolloServer` and overriding the [`serverlessFramework()`](https://github.com/apollographql/apollo-server/blob/5188b1ee408b5e2a983662b0f3a15283c071e522/packages/apollo-server-core/src/ApolloServer.ts#L813) method. -In Apollo Server 4, serverless integrations differentiate themselves by using the `startInBackgroundHandlingStartupErrorsByLoggingAndFailingAllRequests` method. The length of this function's name discourages its use when building non-serverless apps. +In Apollo Server 4, serverless integrations differentiate themselves by using the `startInBackgroundHandlingStartupErrorsByLoggingAndFailingAllRequests` method. The length of this function's name discourages its use when building non-serverless apps. Users of serverless integrations shouldn't call any start-related functions before passing in an `ApolloServer` instance: @@ -1039,8 +1068,8 @@ const server = new ApolloServer({ resolvers, csrfPrevention: true, context: ({ req }) => ({ - authScope: getScope(req.headers.authorization) - }) + authScope: getScope(req.headers.authorization), + }), }); ``` @@ -1063,11 +1092,11 @@ const server = new ApolloServer({ const { url } = await startStandaloneServer(server, { // A named context function is required if you are not // using ApolloServer - context: async ({req, res}) => ({ + context: async ({ req, res }) => ({ token: await getTokenForRequest(req), }), - listen: { port: 4000 } -}) + listen: { port: 4000 }, +}); ``` @@ -1102,7 +1131,7 @@ app.use( -In the [`expressMiddleware`](#migrate-from-apollo-server-express) function, the `req` and `res` objects passed to the `context` function are `express.Request` and `express.Response` types. In the [`startStandaloneServer`](#migrate-from-apollo-server) function, the `req` and `res` objects are `http.IncomingMessage` and `http.ServerResponse` types. If you need to use Express-specific properties in your `context` function, use `expressMiddleware`. +In the [`expressMiddleware`](#migrate-from-apollo-server-express) function, the `req` and `res` objects passed to the `context` function are `express.Request` and `express.Response` types. In the [`startStandaloneServer`](#migrate-from-apollo-server) function, the `req` and `res` objects are `http.IncomingMessage` and `http.ServerResponse` types. If you need to use Express-specific properties in your `context` function, use `expressMiddleware`. ### `executeOperation` accepts context value @@ -1118,7 +1147,7 @@ So a test for Apollo Server 3 that looks like this: ```ts {13-17} const server = new ApolloServer({ - typeDefs: "type Query { hello: String!}", + typeDefs: 'type Query { hello: String!}', resolvers: { Query: { hello: (_, __, context) => `Hello ${context.name}!`, @@ -1127,13 +1156,16 @@ const server = new ApolloServer({ context: async ({ req }) => ({ name: req.headers.name }), }); -const { result } = await server.executeOperation({ - query: 'query helloContext { hello }', -}, { - // A half-hearted attempt at making something vaguely like an express.Request, - // and not bothering to make the express.Response at all. - req: { headers: { name: 'world' } }, -}); +const { result } = await server.executeOperation( + { + query: 'query helloContext { hello }', + }, + { + // A half-hearted attempt at making something vaguely like an express.Request, + // and not bothering to make the express.Response at all. + req: { headers: { name: 'world' } }, + }, +); expect(result.data?.hello).toBe('Hello world!'); // -> true ``` @@ -1150,7 +1182,7 @@ interface MyContext { } const server = new ApolloServer({ - typeDefs: "type Query { hello: String!}", + typeDefs: 'type Query { hello: String!}', resolvers: { Query: { hello: (_, __, context) => `Hello ${context.name}!`, @@ -1158,11 +1190,14 @@ const server = new ApolloServer({ }, }); -const { result } = await server.executeOperation({ - query: 'query helloContext { hello }', -}, { - name: 'world', -}); +const { result } = await server.executeOperation( + { + query: 'query helloContext { hello }', + }, + { + name: 'world', + }, +); expect(result.data?.hello).toBe('Hello world!'); // -> true ``` @@ -1176,7 +1211,7 @@ expect(result.data?.hello).toBe('Hello world!'); // -> true Apollo Server 3 supports the `formatError` hook, which has the following signature: ```ts -(error: GraphQLError) => GraphQLFormattedError +(error: GraphQLError) => GraphQLFormattedError; ``` This hook receives an `error` already altered by Apollo Server 3, and differs from the initially thrown error. @@ -1184,7 +1219,8 @@ This hook receives an `error` already altered by Apollo Server 3, and differs fr In Apollo Server 4, this becomes: ```ts -(formattedError: GraphQLFormattedError, error: unknown) => GraphQLFormattedError +(formattedError: GraphQLFormattedError, error: unknown) => + GraphQLFormattedError; ``` Above, `formattedError` is the default JSON object sent in the response according to the [GraphQL specification](https://spec.graphql.org/draft/#sec-Errors), and `error` is the originally thrown error. If you need a field from the original error that isn't in `GraphQLFormattedError`, you can access that value from the `error` argument. @@ -1222,13 +1258,13 @@ new ApolloServer({ #### `error.extensions.exception` is removed -When Apollo Server 3 formats an error, it may add an extension called `exception`. This extension is an object with a field for every *enumerable* property of the originally thrown error. (This does not apply if the originally thrown error was already a `GraphQLError`.) In addition, [when in dev/debug mode](#debug), `exception` contains an array of strings called `stacktrace`. +When Apollo Server 3 formats an error, it may add an extension called `exception`. This extension is an object with a field for every _enumerable_ property of the originally thrown error. (This does not apply if the originally thrown error was already a `GraphQLError`.) In addition, [when in dev/debug mode](#debug), `exception` contains an array of strings called `stacktrace`. For example, if this code runs in a resolver: ```ts -const e = new Error("hello"); -e.extraProperty = "bye"; +const e = new Error('hello'); +e.extraProperty = 'bye'; throw e; ``` @@ -1272,10 +1308,7 @@ If you'd like your errors to be formatted like they are in Apollo Server 3 (with ```ts -function formatError( - formattedError: GraphQLFormattedError, - error: unknown, -) { +function formatError(formattedError: GraphQLFormattedError, error: unknown) { const originalError = unwrapResolverError(error); const exception: Record = { ...(typeof originalError === 'object' ? originalError : null), @@ -1298,9 +1331,7 @@ function formatError( -Apollo Server 3.5.0 and newer included a TypeScript `declare module` declaration that teaches TypeScript that `error.extensions.exception.stacktrace` is an array of strings on *all* `GraphQLError` objects. Apollo Server 4 does not provide a replacement for this: that is, we do not tell TypeScript the type of `error.extensions.code` or `error.extensions.stacktrace`. (The Apollo Server 3 `declare module` declaration also incorrectly teaches TypeScript that `error.extensions.exception.code` is a string, which should have been `error.extensions.code` instead.) - - +Apollo Server 3.5.0 and newer included a TypeScript `declare module` declaration that teaches TypeScript that `error.extensions.exception.stacktrace` is an array of strings on _all_ `GraphQLError` objects. Apollo Server 4 does not provide a replacement for this: that is, we do not tell TypeScript the type of `error.extensions.code` or `error.extensions.stacktrace`. (The Apollo Server 3 `declare module` declaration also incorrectly teaches TypeScript that `error.extensions.exception.code` is a string, which should have been `error.extensions.code` instead.) ### Improvements to error handling outside of resolvers @@ -1310,7 +1341,7 @@ Apollo Server 4 now returns all non-landing-page-related responses as `applicati ```json disableCopy { - "errors":[{"message": "..."}] + "errors": [{ "message": "..." }] } ``` @@ -1318,24 +1349,23 @@ Additionally, the [`formatError` hook](/apollo-server/data/errors/#for-client-re Apollo Server 4 also introduces new plugin hooks `startupDidFail`, `contextCreationDidFail`, `invalidRequestWasReceived`, and `unexpectedErrorProcessingRequest`, enabling plugins to observe errors in new settings. -In Apollo Server 3, if your `context` function throws, then the string `"Context creation failed: "` is *always* prepended to its message, and the error is rendered with HTTP status code 500 (if the error is a GraphQLError with `extensions.code` equal to `INTERNAL_SERVER_ERROR`) or 400. You cannot select a different HTTP status code or control HTTP response headers. +In Apollo Server 3, if your `context` function throws, then the string `"Context creation failed: "` is _always_ prepended to its message, and the error is rendered with HTTP status code 500 (if the error is a GraphQLError with `extensions.code` equal to `INTERNAL_SERVER_ERROR`) or 400. You cannot select a different HTTP status code or control HTTP response headers. In Apollo Server 4, if either the `resolveOperation` or `execute` function throws an error, that error is rendered with the HTTP status code 500 (rather than 400). Note that the `execute` function commonly returns a non-empty list of errors rather than throwing an explicit error. In Apollo Server 4, if your `context` function throws, the string `"Context creation failed: "` is only prepended to the message if the thrown error was not a `GraphQLError`. There is no special-casing of `extensions.code`; instead, you can use [`extensions.http`](./data/errors/#setting-http-status-code-and-headers) to set the HTTP status code or headers. If this extension is not provided, the status code defaults to 500 (not 400). - ### Warning for servers without draining Versions of Apollo Server 3.2 and above add a "draining" phase to server shutdown, enabling a server to complete in-progress operations before continuing to shut down. Without this draining phase, operations can reach your server even after it has stopped, causing those operations to fail. In Apollo Server 4, if your server _hasn't_ set up draining and it receives an operation as the server is shutting down, the server logs a warning before failing that operation. -If you are using the `startStandaloneServer` function, your server drains automatically. If you are using `expressMiddleware` or another `http.Server`-based web server, you can add draining using the [`ApolloServerPluginDrainHttpServer` plugin](/apollo-server/api/plugin/drain-http-server/#using-the-plugin). +If you are using the `startStandaloneServer` function, your server drains automatically. If you are using `expressMiddleware` or another `http.Server`-based web server, you can add draining using the [`ApolloServerPluginDrainHttpServer` plugin](/apollo-server/api/plugin/drain-http-server/#using-the-plugin). ### `CacheScope` type -In Apollo Server 4, `CacheScope` is now a union of strings (`PUBLIC` or `PRIVATE`) rather than an enum: +In Apollo Server 4, `CacheScope` is now a union of strings (`PUBLIC` or `PRIVATE`) rather than an enum: ```ts export type CacheScope = 'PUBLIC' | 'PRIVATE'; @@ -1345,7 +1375,6 @@ You can no longer type `CacheScope.Public` or `CacheScope.Private`. Instead, jus You can now import `CacheScope` from the new `@apollo/cache-control-types` package (instead of importing it from an Apollo Server package). This enables libraries that work with multiple GraphQL servers (such as `@apollo/subgraph`) to refer to `CacheScope` without depending on `@apollo/server`. - ### `parseOptions` only affects operation parsing In Apollo Server 3, the `parseOptions` constructor option is used to modify how GraphQL parsing works in two unrelated places: when parsing GraphQL operations, and when parsing the schema if the schema is provided via `typeDefs`. If you are using `typeDefs`, you cannot control these options (such as `noLocation`) independently. In addition, the TypeScript definition of the `parseOptions` option uses a type (from the `@graphql-tools/schema` package whose `makeExecutableSchema` function implements the `typeDefs` option) that contains options such as `assumeValidSDL` which are only relevant for parsing schemas. @@ -1368,7 +1397,6 @@ and you would like to continue to apply the same options to both operation and s ```ts import { makeExecutableSchema } from '@graphql-tools/schema'; - const parseOptions = { noLocation: true }; new ApolloServer({ schema: makeExecutableSchema({ @@ -1394,7 +1422,7 @@ new ApolloServer({ Most plugin API hooks take a `GraphQLRequestContext` object as their first argument. Apollo Server 4 makes several changes to the `GraphQLRequestContext` object. -The `context` field has been renamed `contextValue` for consistency with the `graphql-js` API and to help differentiate from the `context` option of integration functions (the *function* which returns a context value). +The `context` field has been renamed `contextValue` for consistency with the `graphql-js` API and to help differentiate from the `context` option of integration functions (the _function_ which returns a context value). The `GraphQLRequestContext.logger` field is now `readonly`. If you depended on the ability to change the `logger`, please file an issue. @@ -1402,12 +1430,11 @@ Apollo Server 4 removes the `schemaHash` field from `GraphQLRequestContext`. Thi Apollo Server 4 removes the `debug` field from `GraphQLRequestContext` because `ApolloServer` no longer has a [vague `debug` option](#debug). There is no direct replacement for this field. If this is a problem for you, please open a GitHub issue, and we can find an appropriate improvement. - ### Fields on `GraphQLServerContext` Apollo Server 4 makes several changes to the `GraphQLServerContext` object. -Apollo Server 4 renames the TypeScript type for the argument to the `serverWillStart` plugin hook from `GraphQLServiceContext` to `GraphQLServerContext`, for consistency with the hook name. +Apollo Server 4 renames the TypeScript type for the argument to the `serverWillStart` plugin hook from `GraphQLServiceContext` to `GraphQLServerContext`, for consistency with the hook name. Apollo Server 4 removes the `schemaHash` field (see the [previous section](#fields-on-graphqlrequestcontext) for details). @@ -1436,7 +1463,7 @@ export interface GraphQLResponse { } ``` -Additionally, the `data` and `extensions` fields are both type `Record`, rather than `Record`. +Additionally, the `data` and `extensions` fields are both type `Record`, rather than `Record`. The value of `http.headers` is now a `Map` rather than a Fetch API `Headers` object. All keys in this map must be lower-case; if you insert any header name with capital letters, it will throw. @@ -1455,10 +1482,7 @@ For example, if your Apollo Server 3 code looked like this: ```ts const server = new ApolloServer({ typeDefs, - plugins: [ - makeFirstPlugin, - () => makeSecondPlugin(server), - ], + plugins: [makeFirstPlugin, () => makeSecondPlugin(server)], }); ``` @@ -1471,9 +1495,7 @@ then your Apollo Server 4 code can look like this: ```ts const server = new ApolloServer({ typeDefs, - plugins: [ - makeFirstPlugin(), - ], + plugins: [makeFirstPlugin()], }); server.addPlugin(makeSecondPlugin(server)); ``` @@ -1484,7 +1506,7 @@ server.addPlugin(makeSecondPlugin(server)); In Apollo Server 4, `requestDidStart` hooks are called in parallel rather than in series. -Apollo Server 4 more consistently handles errors thrown by multiple plugin hooks. Each error is wrapped in an "Unexpected error handling request" error and invoked using the new `unexpectedErrorProcessingRequest` plugin hook. +Apollo Server 4 more consistently handles errors thrown by multiple plugin hooks. Each error is wrapped in an "Unexpected error handling request" error and invoked using the new `unexpectedErrorProcessingRequest` plugin hook. ### Custom `gateway` and `GraphQLDataSource` implementations @@ -1498,27 +1520,26 @@ In Apollo Server 3, your `gateway` may define either `onSchemaChange` or the new In Apollo Server 3, the `GatewayInterface.load` method returns `Promise`, which contains a `schema` and an `executor`. Apollo Server 4 renames `GraphQLServiceConfig` to `GatewayLoadResult` (exported from `@apollo/server-gateway-interface`), which now only has an `executor` field. You can use the `onSchemaLoadOrUpdate` hook if you want to receive the schema. -In Apollo Server 3, the `executor` function took an argument of type `GraphQLRequestContextExecutionDidStart`. While Apollo Server 4 still has a type with this name, that type is *not* the argument to the `executor`. Instead, the argument to the executor has type `GatewayGraphQLRequestContext` (exported from `@apollo/server-gateway-interface`). The structure of this data type matches the structure of `GraphQLRequestContextExecutionDidStart` from *Apollo Server 3*, not the structure in Apollo Server 4. +In Apollo Server 3, the `executor` function took an argument of type `GraphQLRequestContextExecutionDidStart`. While Apollo Server 4 still has a type with this name, that type is _not_ the argument to the `executor`. Instead, the argument to the executor has type `GatewayGraphQLRequestContext` (exported from `@apollo/server-gateway-interface`). The structure of this data type matches the structure of `GraphQLRequestContextExecutionDidStart` from _Apollo Server 3_, not the structure in Apollo Server 4. Similarly, if you create a custom `GraphQLDataSource` type (returned from `@apollo/gateway`'s `buildService` hook), the argument to its `process` method has changed from being Apollo Server 3's `GraphQLRequestContext` to the same `GatewayGraphQLRequestContext`. (For clarity: `GraphQLDataSource` is the class which Apollo Gateway uses to talk to subgraphs; it is unrelated to the Apollo Server 3 [`dataSources` option](#datasources).) Additionally, the following types have been renamed and are now exported from `@apollo/server-gateway-interface`: + - `GraphQLExecutor` is now `GatewayExecutor` - `SchemaLoadOrUpdateCallback` is now `GatewaySchemaLoadOrUpdateCallback` - `Unsubscriber` is now `GatewayUnsubscriber` -With the exception of requiring `onSchemaLoadOrUpdate`, all the changes described above are about the *names* and exporting packages of the TypeScript types; the actual runtime API between Apollo Server and Apollo Gateway is unchanged in Apollo Server 4. That is, you should just have to update type declarations, not the runtime code itself. +With the exception of requiring `onSchemaLoadOrUpdate`, all the changes described above are about the _names_ and exporting packages of the TypeScript types; the actual runtime API between Apollo Server and Apollo Gateway is unchanged in Apollo Server 4. That is, you should just have to update type declarations, not the runtime code itself. ## Changes to defaults Apollo Server 3 introduced several recommended features after the initial v3.0.0 release, but these features were turned off by default for backward compatibility. In Apollo Server 4, the recommended behavior _is_ the default. In each case, you can still configure your server to match the default behavior of Apollo Server 3 if you want to. - ### CSRF prevention is on by default Apollo Server 3.7 added a recommended security feature called CSRF prevention, which you can enable with the constructor option `csrfPrevention: true`. In Apollo Server 4, `true` is the default value. If you want to disable this recommended security feature, pass `csrfPrevention: false`. For more information about CSRF prevention and CORS, see [Configuring CORS](/apollo-server/security/cors). - ### HTTP batching is off by default Apollo Server supports [batching HTTP requests](/apollo-server/requests/#batching), enabling a single HTTP request to execute multiple GraphQL operations. In Apollo Server 3, support for HTTP batching was on by default. @@ -1527,7 +1548,6 @@ In Apollo Server 4, you must explicitly enable this feature by passing `allowBat Not all GraphQL clients support HTTP batching, and batched requests will not support incremental delivery when Apollo Server implements that feature. HTTP batching can help performance by sharing a `context` object across operations, but it can make it harder to understand the amount of work any given request does. - ### Default cache is bounded Each Apollo Server has a cache backend used in several features, including APQs, the response cache plugin, and `RESTDataSource`. Apollo Server uses an in-memory cache by default, but you can configure it to use a different backend (such as Redis or Memcached) using the `cache` constructor option. @@ -1537,8 +1557,9 @@ In Apollo Server 3, the default cache is an _unbounded_ in-memory cache. This ca In Apollo Server 4, the default cache is a _bounded_ in-memory cache backend (which _is safe_ for production use). This is equivalent to passing `cache: 'bounded'` in Apollo Server 3.9 or newer. If you want to customize the cache Apollo Server uses, Apollo provides two wrapper packages to help with this process: -* [`@apollo/utils.keyvadapter`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyvAdapter) - provides a [`KeyvAdapter`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyvAdapter#keyvadapter-class) wrapper class to use alongside the [`keyv`](https://www.npmjs.com/package/keyv) package. -* [`@apollo/utils.keyvaluecache`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyValueCache) - provides both the [`KeyValueCache`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyValueCache#keyvaluecache-interface) TypeScript interface and a [`InMemoryLRUCache`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyValueCache#inmemorylrucache) class (a wrapper around the `lru-cache` package). + +- [`@apollo/utils.keyvadapter`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyvAdapter) - provides a [`KeyvAdapter`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyvAdapter#keyvadapter-class) wrapper class to use alongside the [`keyv`](https://www.npmjs.com/package/keyv) package. +- [`@apollo/utils.keyvaluecache`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyValueCache) - provides both the [`KeyValueCache`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyValueCache#keyvaluecache-interface) TypeScript interface and a [`InMemoryLRUCache`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyValueCache#inmemorylrucache) class (a wrapper around the `lru-cache` package). For examples of using both `KeyvAdapter` and `InMemoryLRUCache`, see [Configuring external caching](/apollo-server/performance/cache-backends#configuring-external-caching). @@ -1557,17 +1578,15 @@ new ApolloServer({ cache: new KeyvAdapter(new Keyv()), // ... }); - ``` - ### Local landing page defaults to Embedded Apollo Sandbox In Apollo Server 3, the default development landing page is a splash page containing a link to the Apollo Sandbox (hosted at `https://studio.apollographql.com/`). This Sandbox only works if your server's CORS configuration allows the origin `https://studio.apollographql.com/`. The [`ApolloServerPluginLandingPageLocalDefault`](/apollo-server/testing/build-run-queries/#configuring-the-default-landing-page) plugin enables you to embed Apollo Sandbox directly on your server's landing page. Passing `embed: true` to the `ApolloServerPluginLandingPageLocalDefault` plugin allows your Sandbox to make same-origin requests to your server with no additional CORS configuration. -In Apollo Server 4, the default development landing page is the *embedded* Apollo Sandbox. Note that nothing changes about the default production landing page. +In Apollo Server 4, the default development landing page is the _embedded_ Apollo Sandbox. Note that nothing changes about the default production landing page. To use the splash page from Apollo Server 3, you can add the following to your Apollo Server 4 constructor: @@ -1575,46 +1594,51 @@ To use the splash page from Apollo Server 3, you can add the following to your A ```ts import { ApolloServer } from '@apollo/server'; -import { ApolloServerPluginLandingPageLocalDefault, ApolloServerPluginLandingPageProductionDefault } - from '@apollo/server/plugin/landingPage/default'; +import { + ApolloServerPluginLandingPageLocalDefault, + ApolloServerPluginLandingPageProductionDefault, +} from '@apollo/server/plugin/landingPage/default'; new ApolloServer({ // ... plugins: [ process.env.NODE_ENV === 'production' ? ApolloServerPluginLandingPageProductionDefault() - : ApolloServerPluginLandingPageLocalDefault({ embed: false }) + : ApolloServerPluginLandingPageLocalDefault({ embed: false }), ], }); ``` - ### Usage reporting and inline trace plugins mask errors by default In Apollo Server 3, traces sent to Apollo's servers from monolith servers by the usage reporting plugin contain the full message and extensions of every GraphQL error that occurs in the operation by default. Similarly, inline traces sent from subgraphs to Apollo Gateways (which are then sent to Apollo's servers) contain full error details by default. You can modify or drop these errors with `rewriteError` options to the appropriate plugins. -In Apollo Server 4, error details are *not* included in traces by default. By default, error messages are replaced with `` and error extensions are replaced with a single extension `maskedBy` naming the plugin which performed the masking (`ApolloServerPluginUsageReporting` or `ApolloServerPluginInlineTrace`). +In Apollo Server 4, error details are _not_ included in traces by default. By default, error messages are replaced with `` and error extensions are replaced with a single extension `maskedBy` naming the plugin which performed the masking (`ApolloServerPluginUsageReporting` or `ApolloServerPluginInlineTrace`). To restore the Apollo Server 3 behavior, you can pass `{ unmodified: true }` to an option on each plugin: ```ts // monoliths new ApolloServer({ - plugins: [ApolloServerPluginUsageReporting({ - sendErrors: { unmodified: true }, - })], + plugins: [ + ApolloServerPluginUsageReporting({ + sendErrors: { unmodified: true }, + }), + ], // ... -}) +}); // subgraphs new ApolloServer({ - plugins: [ApolloServerPluginInlineTrace({ - includeErrors: { unmodified: true }, - })], + plugins: [ + ApolloServerPluginInlineTrace({ + includeErrors: { unmodified: true }, + }), + ], // ... -}) +}); ``` (As [described above](#rewriteerror-plugin-option), the `rewriteError` option has been replaced by a `transform` option on `sendErrors` or `includeErrors`.) @@ -1622,13 +1646,13 @@ new ApolloServer({ ## Renamed packages The following packages have been renamed in Apollo Server 4: - - `apollo-datasource-rest` is now [`@apollo/datasource-rest`](https://www.npmjs.com/package/@apollo/datasource-rest). - - `apollo-server-plugin-response-cache` is now [`@apollo/server-plugin-response-cache`](https://www.npmjs.com/package/@apollo/server-plugin-response-cache). - - `apollo-server-plugin-operation-registry` is now [`@apollo/server-plugin-operation-registry`](https://www.npmjs.com/package/@apollo/server-plugin-operation-registry). - - `apollo-reporting-protobuf` (an internal implementation detail for the usage reporting plugin) is now [`@apollo/usage-reporting-protobuf`](https://www.npmjs.com/package/@apollo/usage-reporting-protobuf). -Note that once Apollo Server 4 is released, all actively maintained Apollo packages will start with `@apollo/`. This leaves the `apollo-` namespace open for community integration packages (e.g., `apollo-server-integration-fastify`). +- `apollo-datasource-rest` is now [`@apollo/datasource-rest`](https://www.npmjs.com/package/@apollo/datasource-rest). +- `apollo-server-plugin-response-cache` is now [`@apollo/server-plugin-response-cache`](https://www.npmjs.com/package/@apollo/server-plugin-response-cache). +- `apollo-server-plugin-operation-registry` is now [`@apollo/server-plugin-operation-registry`](https://www.npmjs.com/package/@apollo/server-plugin-operation-registry). +- `apollo-reporting-protobuf` (an internal implementation detail for the usage reporting plugin) is now [`@apollo/usage-reporting-protobuf`](https://www.npmjs.com/package/@apollo/usage-reporting-protobuf). +Note that once Apollo Server 4 is released, all actively maintained Apollo packages will start with `@apollo/`. This leaves the `apollo-` namespace open for community integration packages (e.g., `apollo-server-integration-fastify`). ## TypeScript type changes @@ -1636,7 +1660,7 @@ Several Apollo Server 4 changes only affect TypeScript typings, not runtime beha ### Improved typing for `context` -In Apollo Server 3, you never explicitly specify the type of your context value when setting up your server. This means there is no compile-time check to ensure your `context` function return type matches the type of your context value (read by your resolvers and plugins). `ApolloServer` has a generic parameter, but that parameter is the type of the *arguments passed* to your `context` function, _not_ the type of your app's context value. +In Apollo Server 3, you never explicitly specify the type of your context value when setting up your server. This means there is no compile-time check to ensure your `context` function return type matches the type of your context value (read by your resolvers and plugins). `ApolloServer` has a generic parameter, but that parameter is the type of the _arguments passed_ to your `context` function, _not_ the type of your app's context value. In Apollo Server 4, you specify the type of your context value as a generic parameter to `ApolloServer`. This gives you proper `context` typing throughout, ensuring that the type returned from your `context` function matches the type available in your resolvers and plugins. For example: @@ -1688,7 +1712,7 @@ The `@apollo/utils.fetcher` package has a more precise name and only supports ar In Apollo Server 3, you could import the `CacheScope`, `CacheHint`, `CacheAnnotation`, `CachePolicy`, and `ResolveInfoCacheControl` types from your chosen Apollo Server package. -In Apollo Server 4, the new `@apollo/cache-control-types` package exports the [`CacheScope`](#cachescope-type), `CacheHint`, `CacheAnnotation`, `CachePolicy`, and `ResolveInfoCacheControl` types. This enables libraries that work with multiple GraphQL servers (such as `@apollo/subgraph`) to refer to these types without depending on `@apollo/server`. +In Apollo Server 4, the new `@apollo/cache-control-types` package exports the [`CacheScope`](#cachescope-type), `CacheHint`, `CacheAnnotation`, `CachePolicy`, and `ResolveInfoCacheControl` types. This enables libraries that work with multiple GraphQL servers (such as `@apollo/subgraph`) to refer to these types without depending on `@apollo/server`. Apollo Server 4 no longer uses the `declare module` TypeScript feature to declare that all `GraphQLResolveInfo` objects (i.e., the `info` argument to resolvers) have a `cacheControl` field. Instead, `@apollo/cache-control-types` provides a `GraphQLResolveInfoWithCacheControl` interface that you can cast `info` to (if you don't want run-time validation), or if you do want runtime validation, you can use the `maybeCacheControlFromInfo` and `cacheControlFromInfo` functions. @@ -1721,13 +1745,13 @@ The `CacheAnnotation` type is no longer exported from any package. This section lists the TypeScript-only types (i.e., interfaces, not classes) that Apollo Server 4 changes (not including those mentioned elsewhere in this article). -Apollo Server 4 changes the name of the constructor options type from `Config` to `ApolloServerOptions`. In Apollo Server 3, some integration packages export their own versions of this type (e.g., `ApolloServerExpressConfig`). In Apollo Server 4, there is only one `ApolloServer` type with only one constructor, so these additional types are no longer necessary. +Apollo Server 4 changes the name of the constructor options type from `Config` to `ApolloServerOptions`. In Apollo Server 3, some integration packages export their own versions of this type (e.g., `ApolloServerExpressConfig`). In Apollo Server 4, there is only one `ApolloServer` type with only one constructor, so these additional types are no longer necessary. Two types in `apollo-server-express` now have more explicit names exported from `@apollo/server/express4`. `GetMiddlewareOptions` is now `ExpressMiddlewareOptions` and `ExpressContext` is now `ExpressContextFunctionArgument`. ### Removed types -This section lists the TypeScript-only types (i.e., interfaces, not classes) that Apollo Server 4 removes (not including those mentioned elsewhere in this article). +This section lists the TypeScript-only types (i.e., interfaces, not classes) that Apollo Server 4 removes (not including those mentioned elsewhere in this article). In Apollo Server 3, the `GraphQLOptions` type was internally used to create integrations and was exported for technical reasons; it is now gone in Apollo Server 4. diff --git a/docs/source/monitoring/health-checks.md b/docs/source/monitoring/health-checks.md index 80d7867f7a9..2a92d242e74 100644 --- a/docs/source/monitoring/health-checks.md +++ b/docs/source/monitoring/health-checks.md @@ -3,7 +3,7 @@ title: Health checks description: Determining the health status of Apollo Server --- -> **Apollo Server 4 no longer [supports built-in health checks](../migration/#health-checks)**. Instead, we recommend performing [GraphQL-level health checks](#graphql-level-health-checks) to ensure your server successfully serves traffic _and_ performs GraphQL operations. +> **Apollo Server 4 no longer [supports built-in health checks](../migration/#health-checks)**. Instead, we recommend performing [GraphQL-level health checks](#graphql-level-health-checks) to ensure your server successfully serves traffic _and_ performs GraphQL operations. Load balancers often use health checks to determine if a server is available and ready to serve traffic. @@ -11,7 +11,7 @@ Load balancers often use health checks to determine if a server is available and The easiest way to determine if your GraphQL server is healthy is to run a GraphQL operation. -Every GraphQL server supports a trivial query that requests the [`__typename`](../schema/schema/#the-__typename-field) of the top-level `Query` type. This means every GraphQL server can respond to a `GET` request to a URL such as: +Every GraphQL server supports a trivial query that requests the [`__typename`](../schema/schema/#the-__typename-field) of the top-level `Query` type. This means every GraphQL server can respond to a `GET` request to a URL such as: ``` https://your.server/graphql?query=%7B__typename%7D @@ -21,4 +21,4 @@ Note that this health check will run an actual GraphQL operation. If your server > Sending an `apollo-require-preflight: true` header alongside your health check ensures that Apollo Server's [CSRF prevention](../security/cors/#preventing-cross-site-request-forgery-csrf) feature won't block it. -If you want to create a health check for your HTTP server that is _unrelated_ to the health of the GraphQL execution engine (i.e., such as [Apollo Server 3's health check feature](/apollo-server/v3/monitoring/health-checks)), you can add a `GET` handler that always succeeds to your web framework. \ No newline at end of file +If you want to create a health check for your HTTP server that is _unrelated_ to the health of the GraphQL execution engine (i.e., such as [Apollo Server 3's health check feature](/apollo-server/v3/monitoring/health-checks)), you can add a `GET` handler that always succeeds to your web framework. diff --git a/docs/source/monitoring/metrics.mdx b/docs/source/monitoring/metrics.mdx index 1d984335ae2..863ff52e7a1 100644 --- a/docs/source/monitoring/metrics.mdx +++ b/docs/source/monitoring/metrics.mdx @@ -29,7 +29,7 @@ $ APOLLO_KEY=YOUR_API_KEY APOLLO_GRAPH_REF=my-graph@my-variant \ #### Communicating with Studio - +{/* TODO(AS4) replace this link once updated plugin api page */} By default, Apollo Server aggregates your traces and sends them in batches to Studio every minute. This behavior is highly configurable, and you can change the parameters in the [Usage Reporting plugin's configuration](/apollo-server/api/plugin/usage-reporting/#custom-installation). @@ -39,10 +39,10 @@ Apollo Studio's [client awareness feature](/studio/client-awareness/) enables yo of your clients. To enable this, your clients need to include some or all of the following identifying information in the headers of GraphQL requests they send to Apollo Server: -| Identifier | Header Name (default) | Example Value | -|----|----|----| -| Client name | `apollographql-client-name` | `iOS Native` | -| Client version | `apollographql-client-version` | `1.0.1` | +| Identifier | Header Name (default) | Example Value | +| -------------- | ------------------------------ | ------------- | +| Client name | `apollographql-client-name` | `iOS Native` | +| Client version | `apollographql-client-version` | `1.0.1` | Each of these fields can have any string value that's useful for your application. To simplify the browsing and sorting of your client data in Studio, a three-part version number (such as `1.0.1`) is recommended for client versions. @@ -69,23 +69,21 @@ const server = new ApolloServer({ plugins: [ //highlight-start ApolloServerPluginUsageReporting({ - generateClientInfo: ({ - request - }) => { + generateClientInfo: ({ request }) => { const headers = request.http && request.http.headers; - if(headers) { + if (headers) { return { - clientName: headers["apollographql-client-name"], - clientVersion: headers["apollographql-client-version"], + clientName: headers['apollographql-client-name'], + clientVersion: headers['apollographql-client-version'], }; } else { return { - clientName: "Unknown Client", - clientVersion: "Unversioned", + clientName: 'Unknown Client', + clientVersion: 'Unversioned', }; } }, - }) + }), ], //highlight-end }); diff --git a/docs/source/performance/cache-backends.mdx b/docs/source/performance/cache-backends.mdx index e2c1de8d3f7..84dee2f0db9 100644 --- a/docs/source/performance/cache-backends.mdx +++ b/docs/source/performance/cache-backends.mdx @@ -7,7 +7,7 @@ Many Apollo Server features take advantage of a cache backend (these features in You can specify a cache backend by passing a `cache` option to the `ApolloServer` constructor. Your specified cache backend must implement the [`KeyValueCache`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyValueCache#keyvaluecache-interface) interface from the `@apollo/utils.keyvaluecache` package. -There are many cache backend implementations to choose from, including several implementations provided by Apollo. For example, Apollo maintains an implementation of `InMemoryLRUCache` in the `@apollo/utils.keyvaluecache` package. Apollo also provides a wrapper class for the [`keyv` package](https://www.npmjs.com/package/keyv) (which implements several cache backends) named [`KeyvAdapter`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyvAdapter#keyvadapter-class) in the `@apollo/utils.keyvadapter` package. +There are many cache backend implementations to choose from, including several implementations provided by Apollo. For example, Apollo maintains an implementation of `InMemoryLRUCache` in the `@apollo/utils.keyvaluecache` package. Apollo also provides a wrapper class for the [`keyv` package](https://www.npmjs.com/package/keyv) (which implements several cache backends) named [`KeyvAdapter`](https://github.com/apollographql/apollo-utils/tree/main/packages/keyvAdapter#keyvadapter-class) in the `@apollo/utils.keyvadapter` package. ## Configuring in-memory caching @@ -52,11 +52,13 @@ Apollo no longer maintains any caching backends directly. Instead, we recommend `KeyvAdapter` wraps a `Keyv` instance and implements the `KeyValueCache` interface which is required by Apollo Server. You can use the `KeyvAdapter` class to wrap a `Keyv` instance and provide it to the `cache` option of the `ApolloServer` constructor like so: 1. Install the required packages + ```bash npm install keyv @apollo/utils.keyvadapter ``` 2. Configure the Apollo Server `cache` + ```ts import Keyv from 'keyv'; import { KeyvAdapter } from '@apollo/utils.keyvadapter'; @@ -72,6 +74,7 @@ const server = new ApolloServer({ If your requirements are specialized or you'd prefer to implement your own cache backend, you can implement the `KeyValueCache` interface and pass it to the `ApolloServer` constructor directly. The `KeyValueCache` interface is shown below: + ```ts interface KeyValueCache { get(key: string): Promise; @@ -89,38 +92,41 @@ options argument is passed through to the `ioredis.Redis` constructor. See the available options. Start by installing the required packages: + ``` npm install keyv @keyv/redis @apollo/utils.keyvadapter ``` ### Single instance + ```ts -import Keyv from "keyv"; -import { KeyvAdapter } from "@apollo/utils.keyvadapter"; +import Keyv from 'keyv'; +import { KeyvAdapter } from '@apollo/utils.keyvadapter'; const server = new ApolloServer({ typeDefs, resolvers, - cache: new KeyvAdapter(new Keyv("redis://user:pass@localhost:6379")), // highlight-line + cache: new KeyvAdapter(new Keyv('redis://user:pass@localhost:6379')), // highlight-line }); ``` ### Redis Sentinel + ```ts -import Keyv from "keyv"; -import { KeyvAdapter } from "@apollo/utils.keyvadapter"; +import Keyv from 'keyv'; +import { KeyvAdapter } from '@apollo/utils.keyvadapter'; const server = new ApolloServer({ typeDefs, resolvers, // highlight-start cache: new KeyvAdapter( - new Keyv("redis://user:pass@localhost:6379", { + new Keyv('redis://user:pass@localhost:6379', { sentinels: [ - { host: "localhost", port: 26379 }, - { host: "localhost", port: 26380 }, + { host: 'localhost', port: 26379 }, + { host: 'localhost', port: 26380 }, ], - }) + }), ), // highlight-end }); @@ -134,20 +140,21 @@ Instead, we can create our own `ioredis.Cluster` instance and pass that to docs](https://github.com/luin/ioredis#cluster) for a list of available options. Start by installing the packages we'll need: + ``` npm install keyv @keyv/redis ioredis @apollo/utils.keyvadapter ``` ```ts -import Keyv from "keyv"; -import KeyvRedis from "@keyv/redis"; -import Redis from "ioredis"; -import { KeyvAdapter } from "@apollo/utils.keyvadapter"; +import Keyv from 'keyv'; +import KeyvRedis from '@keyv/redis'; +import Redis from 'ioredis'; +import { KeyvAdapter } from '@apollo/utils.keyvadapter'; // highlight-start const cluster = new Redis.Cluster([ - { host: "localhost", port: 26379 }, - { host: "localhost", port: 26380 }, + { host: 'localhost', port: 26379 }, + { host: 'localhost', port: 26380 }, ]); // highlight-end @@ -163,7 +170,7 @@ const server = new ApolloServer({ ``` > Note the `disableBatchReads` option. This disables batching which isn't -supported by `ioredis.Cluster`. +> supported by `ioredis.Cluster`. ## Configuring Memcache @@ -172,21 +179,21 @@ options argument is passed to `memjs.Client.create()`. See the [`memjs` docs](https://memjs.netlify.app/#section-3) for a list of available options. Start by installing the required packages: + ``` npm install keyv @keyv/memcache @apollo/utils.keyvadapter ``` ```ts -import Keyv from "keyv"; -import KeyvMemcache from "@keyv/memcache"; -import { KeyvAdapter } from "@apollo/utils.keyvadapter"; +import Keyv from 'keyv'; +import KeyvMemcache from '@keyv/memcache'; +import { KeyvAdapter } from '@apollo/utils.keyvadapter'; // servers is a comma-separated list of strings // highlight-start -const servers = [ - "user:pass@localhost:11211", - "user:pass@localhost:11222" -].join(","); +const servers = ['user:pass@localhost:11211', 'user:pass@localhost:11222'].join( + ',', +); const memcache = new KeyvMemcache(servers, { retries: 10, diff --git a/docs/source/performance/caching.md b/docs/source/performance/caching.md index bf25196494e..d7bf0abbf2f 100644 --- a/docs/source/performance/caching.md +++ b/docs/source/performance/caching.md @@ -53,10 +53,10 @@ If you don't add these definitions, Apollo Server throws an `Unknown directive " The `@cacheControl` directive accepts the following arguments: -| Name | Description | -|------|-------------| -| `maxAge` | The maximum amount of time the field's cached value is valid, in seconds. The default value is `0`, but you can [set a different default](#setting-a-different-default-maxage). | -| `scope` | If `PRIVATE`, the field's value is specific to a single user. The default value is `PUBLIC`. See also [Identifying users for `PRIVATE` responses](#identifying-users-for-private-responses). | +| Name | Description | +| --------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `maxAge` | The maximum amount of time the field's cached value is valid, in seconds. The default value is `0`, but you can [set a different default](#setting-a-different-default-maxage). | +| `scope` | If `PRIVATE`, the field's value is specific to a single user. The default value is `PUBLIC`. See also [Identifying users for `PRIVATE` responses](#identifying-users-for-private-responses). | | `inheritMaxAge` | If `true`, this field inherits the `maxAge` of its parent field instead of using the [default `maxAge`](#setting-a-different-default-maxage). Do not provide `maxAge` if you provide this argument. | Use `@cacheControl` for fields that should usually be cached with the same settings. If caching settings might change at runtime, you can use the [dynamic method](#in-your-resolvers-dynamic). @@ -128,7 +128,7 @@ You can decide how to cache a particular field's result _while_ you're resolving The `cacheControl` object includes a `setCacheHint` method, which you call like so: -```ts +```ts const resolvers = { Query: { post: (_, { id }, _, info) => { @@ -208,7 +208,7 @@ import { ApolloServerPluginCacheControl } from '@apollo/server/plugin/cacheContr const server = new ApolloServer({ // ...other options... - plugins: [ApolloServerPluginCacheControl({ defaultMaxAge: 5 })], // 5 seconds + plugins: [ApolloServerPluginCacheControl({ defaultMaxAge: 5 })], // 5 seconds }); ``` @@ -251,7 +251,8 @@ Let's look at some queries and their resulting `maxAge` values: # maxAge: 0 # Query.book doesn't set a maxAge and it's a root field (default 0). query GetBookTitle { - book { # 0 + book { + # 0 cachedTitle # 30 } } @@ -260,7 +261,8 @@ query GetBookTitle { # Query.cachedBook has a maxAge of 60, and Book.title is a scalar, so it # inherits maxAge from its parent by default. query GetCachedBookTitle { - cachedBook { # 60 + cachedBook { + # 60 title # inherits } } @@ -269,7 +271,8 @@ query GetCachedBookTitle { # Query.cachedBook has a maxAge of 60, but Book.cachedTitle has # a maxAge of 30. query GetCachedBookCachedTitle { - cachedBook { # 60 + cachedBook { + # 60 cachedTitle # 30 } } @@ -279,8 +282,10 @@ query GetCachedBookCachedTitle { # inheritMaxAge from its parent, and Book.title is a scalar # that inherits maxAge from its parent by default. query GetReaderBookTitle { - reader { # 40 - book { # inherits + reader { + # 40 + book { + # inherits title # inherits } } @@ -469,9 +474,9 @@ This enables you to cache different responses for logged-in and logged-out users In addition to [the `sessionId` function](#identifying-users-for-private-responses), you can provide the following functions to your `responseCachePlugin` to configure cache reads and writes. Each of these functions takes a `GraphQLRequestContext` (representing the incoming operation) as a parameter. -| Function | Description | -|----------|-------------| -| `extraCacheKeyData` | This function's return value (any JSON-stringifiable object) is added to the key for the cached response. For example, if your API includes translatable text, this function can return a string derived from `requestContext.request.http.headers.get('accept-language')`. | -| `shouldReadFromCache` | If this function returns `false`, Apollo Server _skips_ the cache for the incoming operation, even if a valid response is available. | -| `shouldWriteToCache` | If this function returns `false`, Apollo Server doesn't cache its response for the incoming operation, even if the response's `maxAge` is greater than `0`. | -| `generateCacheKey` | Customize generation of the cache key. By default, this is the SHA256 hash of the JSON encoding of an object containing relevant data. | +| Function | Description | +| --------------------- | --------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | +| `extraCacheKeyData` | This function's return value (any JSON-stringifiable object) is added to the key for the cached response. For example, if your API includes translatable text, this function can return a string derived from `requestContext.request.http.headers.get('accept-language')`. | +| `shouldReadFromCache` | If this function returns `false`, Apollo Server _skips_ the cache for the incoming operation, even if a valid response is available. | +| `shouldWriteToCache` | If this function returns `false`, Apollo Server doesn't cache its response for the incoming operation, even if the response's `maxAge` is greater than `0`. | +| `generateCacheKey` | Customize generation of the cache key. By default, this is the SHA256 hash of the JSON encoding of an object containing relevant data. | diff --git a/docs/source/schema/creating-directives.mdx b/docs/source/schema/creating-directives.mdx index 414a0c67032..7abe677eda5 100644 --- a/docs/source/schema/creating-directives.mdx +++ b/docs/source/schema/creating-directives.mdx @@ -20,10 +20,8 @@ type Query { > See an example implementation of this directive on CodeSandbox: > > -> alt="Edit upper-case-directive" -> src="https://codesandbox.io/static/img/play-codesandbox.svg" -> /> +> {/* prettier-ignore */} +> Edit upper-case-directive > When you start up your app, you can use directives to transform your executable schema's behavior before you provide that schema to Apollo Server. For example, you can modify the resolver function for any decorated field (for the schema above, it could transform the `hello` resolver's original result to uppercase). @@ -339,7 +337,12 @@ function upperDirectiveTransformer(schema, directiveName) { // Replace the original resolver with a function that *first* calls // the original resolver, then converts its result to upper case - fieldConfig.resolve = async function (source, args, contextValue, info) { + fieldConfig.resolve = async function ( + source, + args, + contextValue, + info, + ) { const result = await resolve(source, args, context, info); if (typeof result === 'string') { return result.toUpperCase(); diff --git a/docs/source/schema/directives.md b/docs/source/schema/directives.md index 53048507190..b4eb177a22a 100644 --- a/docs/source/schema/directives.md +++ b/docs/source/schema/directives.md @@ -79,8 +79,8 @@ The [GraphQL spec](https://spec.graphql.org/June2018/#sec-Type-System.Directives The [GraphQL specification](http://spec.graphql.org/June2018/#sec-Type-System.Directives) defines the following default directives: -| Directive | Description | -|-----------|-------------| -| `@deprecated(reason: String)` | Marks the schema definition of a field or enum value as deprecated with an optional reason. | -| `@skip(if: Boolean!)` | If `true`, the decorated field or fragment in an operation is _not_ resolved by the GraphQL server. | -| `@include(if: Boolean!)` | If `false`, the decorated field or fragment in an operation is _not_ resolved by the GraphQL server. | +| Directive | Description | +| ----------------------------- | ---------------------------------------------------------------------------------------------------- | +| `@deprecated(reason: String)` | Marks the schema definition of a field or enum value as deprecated with an optional reason. | +| `@skip(if: Boolean!)` | If `true`, the decorated field or fragment in an operation is _not_ resolved by the GraphQL server. | +| `@include(if: Boolean!)` | If `false`, the decorated field or fragment in an operation is _not_ resolved by the GraphQL server. | diff --git a/docs/source/security/authentication.mdx b/docs/source/security/authentication.mdx index dabd07b7efd..171284f14a8 100644 --- a/docs/source/security/authentication.mdx +++ b/docs/source/security/authentication.mdx @@ -14,7 +14,7 @@ Before we can correctly control access to data, we have to authenticate a user. The example below extracts a user token from the HTTP `Authorization` header included in each operation request. It then fetches the corresponding user object for that token and adds that object to [the `context` object](../data/resolvers/#the-context-argument) that's passed to every executed resolver. Each resolver can then use this object to determine what data the user has access to. - +{/* TODO(AS4) Add note back in about where to find integration specific context arguments */} @@ -42,7 +42,6 @@ const { url } = await startStandaloneServer(server, { // For `startStandaloneServer`, the `req` and `res` objects are // `http.IncomingMessage` and `http.ServerResponse` types. context: async ({ req, res }) => { - // Get the user token from the headers. const token = req.headers.authorization || ''; @@ -75,7 +74,7 @@ Once we have information about the user making a request, the most basic thing w We should use this method only on highly restrictive environments that provide no public access to the API whatsoever, like an internal tool or an independent microservice that shouldn't be exposed to the public. To perform this kind of authorization, we can modify the `context` function: - +{/* TODO(AS4) check back and see if throwing errors in context changes this? */} @@ -164,7 +163,7 @@ Because our resolvers have access to everything in the context, an important que As our server gets more complex, there will probably be multiple places in the schema that need to fetch the same kind of data. In our last example, you may have noticed the return array was replaced with a call to `context.models.User.getAll()`. - +{/* TODO(AS4) add link back in for data sources */} As always, we recommend moving the actual data fetching and transformation logic from your resolvers to [data sources](../data/fetching-rest/) or model objects that each represent a concept from your application: `User`, `Post`, etc. This allows you to make your resolvers a thin routing layer, and put all of your business logic in one place. diff --git a/docs/source/security/cors.mdx b/docs/source/security/cors.mdx index d643f6ed06f..c691eb2d803 100644 --- a/docs/source/security/cors.mdx +++ b/docs/source/security/cors.mdx @@ -7,7 +7,7 @@ description: Control access to your server's resources [Cross-Origin Resource Sharing](https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS) (CORS) is an HTTP-header-based protocol that enables a server to dictate which origins can access its resources. Put another way, your server can specify which websites can tell a user's browser to talk to your server, and precisely which types of HTTP requests are allowed. - +{/* TODO(AS4) replace link with API link */} The [`startStandaloneServer`](../migration#migrate-from-apollo-server) function's CORS configuration is _unalterable_ and enables any website on the internet to tell a user's browser to connect to your server. [Depending on your use case,](#choosing-cors-options-for-your-project) you might need to further [customize your CORS behavior](#passing-credentials-with-cors) to ensure your server's security. To do so, you'll first need to swap to using [`expressMiddleware`](../migration#migrate-from-apollo-server-express) (or any other Apollo Server integration). > โš ๏ธ If your app is only visible on a private network and uses network separation for security, `startStandaloneServer`'s CORS behavior is **not secure**. See [Specifying origins](#specifying-origins) for more information. @@ -57,7 +57,7 @@ Depending on what you're building, the origins you specify in your CORS configur If your browser is running your API on a private network (i.e., not on the public internet) and it relies on the privacy of that network for security, **we strongly recommend [specifying which origins](#configuring-cors-options-for-apollo-server)** can access your server's resources. - +{/* TODO(AS4) swap api link in for startStandaloneServer */} Specifically, the [`startStandaloneServer`](../migration#migrate-from-apollo-server) function's CORS behavior is **not secure** in this context. Instead, we recommend swapping to another Apollo Server integration to [customize your server's CORS behavior](#configuring-cors-options-for-apollo-server) by specifying origins. If you don't, while your personal computer is on your private network, a script on any website could potentially make your browser talk to your private API. [Some browsers, such as Chrome, have features under development](https://wicg.github.io/private-network-access/) to solve this problem. But in the meantime, all servers on private networks should _always_ specify origins in their CORS configuration. @@ -79,26 +79,29 @@ For examples, see [Passing credentials with CORS](#passing-credentials-with-cors If you create an API on the public internet to serve resources to your _own_ websites or apps, you might want to [specify which origins](#configuring-cors-options-for-apollo-server) can access your server's resources. Explicitly specifying origins can provide an extra level of security. #### Public or embedded APIs - + +{/* TODO(AS4) replace link for api page */} If you create a public API or an API to embed in websites you don't control yourself, you probably want to allow _all_ origins to access your server's resources. You can use the [`startStandaloneServer`](../migration#migrate-from-apollo-server)'s ACAO value (the wildcard `*`) in these situations, allowing requests from any origin. > Using the [wildcard (`*`)](https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Access-Control-Allow-Origin#directives) value for the ACAO header enables _any_ website to tell a user's browser to send an arbitrary request (without cookies or other credentials) to your server and read that server's response. #### None of the above - +{/* TODO(AS4) swap api link in for startStandaloneServer */} If your application doesn't fit into any of the above categories, [`startStandaloneServer`](../migration#migrate-from-apollo-server)'s CORS behavior should suit your use case. You can always choose to swap to another Apollo Server integration later to [customize your CORS configuration](#configuring-cors-options-for-apollo-server). ## Configuring CORS options for Apollo Server - + +{/* TODO(AS4) replace link with API link */} + > ๐Ÿ“ฃ **New in Apollo Server 4**: if you are using an Apollo Server integration (e.g., `expressMiddleware`), you are responsible for [setting up CORS for your web framework](../migration#body-parser-and-cors). Apollo Server's standalone server (i.e., `startStandaloneServer`) serves the `Access-Control-Allow-Origin` HTTP header with the wildcard value (`*`). This allows scripts on any origin to make requests, _without cookies_, to the server and read its responses. > If you need to pass credentials to your server (e.g., via cookies), you can't use the wildcard value (`*`) for your origin. You _must_ provide specific origins. For more details, see [Passing credentials with CORS](#passing-credentials-with-cors). - -The [`startStandaloneServer` function](../migration#migrate-from-apollo-server) **doesn't support** configuring your server's CORS behavior. If you want to customize your server's CORS behavior (e.g., by specifying origins or passing cookies), swap to using [`expressMiddleware`](../migration#migrate-from-apollo-server-express) (or any other Apollo Server integration). +{/* TODO(AS4) replace link with API link */} +The [`startStandaloneServer` function](../migration#migrate-from-apollo-server) **doesn't support** configuring your server's CORS behavior. If you want to customize your server's CORS behavior (e.g., by specifying origins or passing cookies), swap to using [`expressMiddleware`](../migration#migrate-from-apollo-server-express) (or any other Apollo Server integration). Below, we set up and customize the CORS behavior for our `expressMiddleware` function using the [`cors` package](https://github.com/expressjs/cors#configuration-options): @@ -130,13 +133,20 @@ async function startApolloServer() { app.use( '/graphql', // highlight-start - cors({ origin: ['https://www.your-app.example', 'https://studio.apollographql.com'] }), + cors({ + origin: [ + 'https://www.your-app.example', + 'https://studio.apollographql.com', + ], + }), // highlight-end json(), expressMiddleware(server), ); - await new Promise((resolve) => httpServer.listen({ port: 4000 }, resolve)); + await new Promise((resolve) => + httpServer.listen({ port: 4000 }, resolve), + ); console.log(`๐Ÿš€ Server ready at http://localhost:4000/graphql`); } ``` @@ -147,14 +157,15 @@ async function startApolloServer() { Using the `cors` package directly, we can configure the `Access-Control-Allow-Origin` header using the [`origin` option](https://github.com/expressjs/cors#configuration-options). The example above enables CORS requests from `https://www.your-app.example`, along with `https://studio.apollographql.com`. -> Note: if you plan to use [Apollo Studio Explorer](https://www.apollographql.com/docs/studio/explorer/explorer/) as a GraphQL web IDE, you should include `https://studio.apollographql.com` in your list of valid origins. However, if you plan to embed the [Explorer](https://www.apollographql.com/docs/studio/explorer/embed-explorer/) or use [Apollo Sandbox](https://www.apollographql.com/docs/studio/explorer/sandbox), you *don't* need to specify Studio's URL in your CORS origins because requests will go through the page embedding Studio. +> Note: if you plan to use [Apollo Studio Explorer](https://www.apollographql.com/docs/studio/explorer/explorer/) as a GraphQL web IDE, you should include `https://studio.apollographql.com` in your list of valid origins. However, if you plan to embed the [Explorer](https://www.apollographql.com/docs/studio/explorer/embed-explorer/) or use [Apollo Sandbox](https://www.apollographql.com/docs/studio/explorer/sandbox), you _don't_ need to specify Studio's URL in your CORS origins because requests will go through the page embedding Studio. If you're using another integration of Apollo Server, you can add and configure CORS for your server using your framework's standard functionality. You can also choose to omit CORS middleware entirely to disable cross-origin requests. This is [recommended for subgraphs in a federated graph](/federation/subgraphs/#securing-your-subgraphs). ### Passing credentials with CORS - + +{/* TODO(AS4) replace link to API page for startStandaloneServer */} > โš ๏ธ The [`startStandaloneServer`](../migration#migrate-from-apollo-server) function's CORS behavior is _unalterable_. To pass credentials via cookies, you must first swap to another Apollo Server integration. @@ -214,7 +225,8 @@ By default, Apollo Server 4 has a CSRF prevention feature enabled. This means yo Note that all HTTP header names are case-insensitive. - +{/* TODO(AS4) Update the below link to new api page */} + > CSRF prevention only applies to requests that will execute GraphQL operations, not to requests that would load [landing pages](/apollo-server/api/plugin/landing-pages). HTTP requests that satisfy none of the conditions above will be rejected with a 400 status code and a message clearly explaining which headers need to be added in order to make the request succeed. @@ -238,8 +250,8 @@ The [third-party `graphql-upload` package](/apollo-server/data/file-uploads) has The `graphql-upload` package adds a special middleware that parses `POST` requests with a `Content-Type` of `multipart/form-data`. This is one of the three special `Content-Type`s that can be set on [simple requests](https://developer.mozilla.org/en-US/docs/Web/HTTP/CORS#simple_requests), enabling your server to process mutations sent in simple requests. -Apollo Server 4's default [CSRF prevention feature](#preventing-cross-site-request-forgery-csrf) blocks those attempting to use the `graphql-upload` package. **If you use `graphql-upload` you should keep the CSRF prevention feature enabled**, and configure your upload clients to send a non-empty `Apollo-Require-Preflight` header. +Apollo Server 4's default [CSRF prevention feature](#preventing-cross-site-request-forgery-csrf) blocks those attempting to use the `graphql-upload` package. **If you use `graphql-upload` you should keep the CSRF prevention feature enabled**, and configure your upload clients to send a non-empty `Apollo-Require-Preflight` header. -For example, if you use the [`apollo-upload-client`](https://github.com/jaydenseric/apollo-upload-client) package with Apollo Client Web, pass `{headers: {'Apollo-Require-Preflight': 'true'}}` to `createUploadLink`. +For example, if you use the [`apollo-upload-client`](https://github.com/jaydenseric/apollo-upload-client) package with Apollo Client Web, pass `{headers: {'Apollo-Require-Preflight': 'true'}}` to `createUploadLink`. For more information about file upload best practices, see [our blog post](https://www.apollographql.com/blog/backend/file-uploads/file-upload-best-practices/). diff --git a/docs/source/security/terminating-ssl.mdx b/docs/source/security/terminating-ssl.mdx index 2b4c4e6d8c2..1a939d9ae34 100644 --- a/docs/source/security/terminating-ssl.mdx +++ b/docs/source/security/terminating-ssl.mdx @@ -4,7 +4,7 @@ title: Terminating SSL Most production environments use a load balancer or HTTP proxy (such as nginx) to perform SSL termination on behalf of web applications in that environment. - +{/* TODO (AS4) replace link with expressMiddleware article (once it exists) */} If you're using Apollo Server in an application that must perform its _own_ SSL termination, you can use the `https` module with the [`expressMiddleware` function](../migration#migrate-from-apollo-server-express). Here's an example that uses HTTPS in production and HTTP in development: @@ -66,9 +66,14 @@ async function startApolloServer() { httpServer = http.createServer(app); } - await new Promise((resolve) => httpServer.listen({ port: config.port }, resolve)); + await new Promise((resolve) => + httpServer.listen({ port: config.port }, resolve), + ); - console.log('๐Ÿš€ Server ready at', `http${config.ssl ? 's' : ''}://${config.hostname}:${config.port}/graphql`); + console.log( + '๐Ÿš€ Server ready at', + `http${config.ssl ? 's' : ''}://${config.hostname}:${config.port}/graphql`, + ); return { server, app }; } diff --git a/docs/source/testing/mocking.md b/docs/source/testing/mocking.md index 9fff88b3a76..61ee584a27f 100644 --- a/docs/source/testing/mocking.md +++ b/docs/source/testing/mocking.md @@ -171,7 +171,7 @@ console.log(`๐Ÿš€ Server listening at: ${url}`); You can also use `mocks` to define object types and the fields belonging to those object types (much like a [resolver map](../data/resolvers/#base-syntax)). In the below example, our mocked `Person` object calls a function returning an object with fields that contain _other_ functions: -```ts +```ts // importing the casual library const casual = require('casual'); @@ -245,4 +245,4 @@ const { url } = await startStandaloneServer(server, { listen: { port: 4000 } }); console.log(`๐Ÿš€ Server listening at: ${url}`); ``` -Above, the `resolved` query now uses its defined resolver, so it returns the string `Resolved`. \ No newline at end of file +Above, the `resolved` query now uses its defined resolver, so it returns the string `Resolved`. diff --git a/docs/source/testing/testing.mdx b/docs/source/testing/testing.mdx index f5c14a5e7b5..3f60267ad3e 100644 --- a/docs/source/testing/testing.mdx +++ b/docs/source/testing/testing.mdx @@ -14,7 +14,7 @@ There are two main options for integration testing with Apollo Server: Apollo Server's `executeOperation` method enables you to run operations through the request pipeline _without_ sending an HTTP request. - +{/* TODO(AS4) add link once the API article is updated */} The `executeOperation` method accepts the following arguments: - An object that describes the GraphQL operation to execute. @@ -64,7 +64,7 @@ You don't need to start your server before calling `executeOperation`. The serve To expand on the example above, here's a full integration test being run against a test instance of `ApolloServer`. This test imports all of the important pieces to test (`typeDefs`, `resolvers`, `dataSources`) and creates a new instance of `ApolloServer`. - +{/* TODO(AS4) remove once RESTDataSource is up and ready */} > โš ๏ธ The Apollo Server 4 alpha doesn't currently support using [`RESTDataSource`](../migration#datasources), a class commonly used to fetch data from a database or a REST API. This feature is in active development, but in the meantime the below code snippet doesn't work as described. @@ -124,8 +124,8 @@ Instead of bypassing the HTTP layer, you might want to fully run your server and Instead, you can run operations against your server using a combination of any HTTP or GraphQL client such as [`supertest`](https://www.npmjs.com/package/supertest) or [Apollo Client's HTTP Link](/react/api/link/apollo-link-http/) . - - +{/* TODO(AS4) double check if this package is going to be updated for AS4 */} +{/* There are also community packages available such as [`apollo-server-integration-testing`](https://www.npmjs.com/package/apollo-server-integration-testing), which uses mocked Express request and response objects. */} Below is an example of writing an end-to-end test using the `@apollo/server` and `supertest` packages: @@ -180,4 +180,4 @@ You can also view and fork this complete example on CodeSandbox: src="https://codesandbox.io/static/img/play-codesandbox.svg" /> -
\ No newline at end of file +
diff --git a/docs/source/workflow/build-run-queries.mdx b/docs/source/workflow/build-run-queries.mdx index 0b204fc9b71..8ec8164e436 100644 --- a/docs/source/workflow/build-run-queries.mdx +++ b/docs/source/workflow/build-run-queries.mdx @@ -27,7 +27,7 @@ For this reason, if you choose to [change your Apollo Server landing page](#chan ## Changing the landing page - +{/* TODO(AS4) replace GraphQL Playground link */} You can change the landing page that's served from Apollo Server's base URL. You can choose to [configure the default landing page](#configuring-the-default-landing-page), serve [GraphQL Playground](/apollo-server/api/plugin/landing-pages/#graphql-playground-landing-page) (a legacy open-source GraphQL IDE), create a completely [custom landing page](#custom-landing-page), or you can [disable the landing page entirely](#disabling-the-landing-page). @@ -115,4 +115,4 @@ const server = new ApolloServer({ plugins: [ApolloServerPluginLandingPageDisabled()], // highlight-end }); -``` \ No newline at end of file +``` diff --git a/packages/integration-testsuite/README.md b/packages/integration-testsuite/README.md index 7eba3ab3fca..0f7d3a80639 100644 --- a/packages/integration-testsuite/README.md +++ b/packages/integration-testsuite/README.md @@ -14,14 +14,15 @@ you intend to support. This package imposes dependency requirements on your project, however it should only require they be installed as `devDependencies`: -* `@apollo/server`'s version must match the version of the test suite. -* The test suite expects you to be running `jest@28`. It's possible that other + +- `@apollo/server`'s version must match the version of the test suite. +- The test suite expects you to be running `jest@28`. It's possible that other versions of Jest may be compatible, but this use case is unsupported and might lead to unexpected behavior. It's fine for your project to use a testing framework other than Jest, but you'll still need to configure Jest in your project in order to run the test suite (so you'll have two test runners configured in your project). Because of this, we recommend using only Jest in your project for simplicity. -* `graphql` must be installed in your project in `peerDependencies` and your +- `graphql` must be installed in your project in `peerDependencies` and your version range should match that of `@apollo/server`. The test suite package's `graphql` dependency will match that of Apollo Server's. diff --git a/packages/plugin-response-cache/README.md b/packages/plugin-response-cache/README.md index 41b7edcae89..97c60bc5349 100644 --- a/packages/plugin-response-cache/README.md +++ b/packages/plugin-response-cache/README.md @@ -9,5 +9,4 @@ This Apollo Server response cache plugin implements a full GraphQL query respons This cache is a full query cache: cached responses are only used for identical requests. - See [the docs](https://www.apollographql.com/docs/apollo-server/performance/caching/) for details. diff --git a/packages/server/README.md b/packages/server/README.md index 78ae997f9df..6e73d617582 100644 --- a/packages/server/README.md +++ b/packages/server/README.md @@ -6,21 +6,20 @@ **Apollo Server is an [open-source](https://github.com/apollographql/apollo-server), spec-compliant GraphQL server** that's compatible with any GraphQL client, including [Apollo Client](https://www.apollographql.com/docs/react). It's the best way to build a production-ready, self-documenting GraphQL API that can use data from any source. - You can use Apollo Server as: -* A stand-alone GraphQL server -* The GraphQL server for a [subgraph](https://www.apollographql.com/docs/federation/subgraphs/) in a federated supergraph -* The gateway for a [federated supergraph](https://www.apollographql.com/docs/federation/) +- A stand-alone GraphQL server +- The GraphQL server for a [subgraph](https://www.apollographql.com/docs/federation/subgraphs/) in a federated supergraph +- The gateway for a [federated supergraph](https://www.apollographql.com/docs/federation/) Apollo Server provides a simple API for integrating with any Node.js web framework or serverless environment. The `@apollo/server` package itself ships with a standalone zero-dependency web server, and a middleware implementation for [the Express web framework](https://expressjs.com/). Integrations with other environments are community-maintained. Apollo Server provides: -* **Straightforward setup**, so your client developers can start fetching data quickly -* **Incremental adoption**, enabling you to add features as they're needed -* **Universal compatibility** with any data source, any build tool, and any GraphQL client -* **Production readiness**, enabling you to confidently run your graph in production +- **Straightforward setup**, so your client developers can start fetching data quickly +- **Incremental adoption**, enabling you to add features as they're needed +- **Universal compatibility** with any data source, any build tool, and any GraphQL client +- **Production readiness**, enabling you to confidently run your graph in production This `@apollo/server` package is new with Apollo Server 4. Previous major versions of Apollo Server used a set of package names starting with `apollo-server`, such as `apollo-server`, `apollo-server-express`, `apollo-server-core`, etc. @@ -28,7 +27,6 @@ This `@apollo/server` package is new with Apollo Server 4. Previous major versio Full documentation for Apollo Server is available on [our documentation site](https://www.apollographql.com/docs/apollo-server/). This README shows the basics of getting a server running (both standalone and with Express), but most features are only documented on our docs site. - ## Getting started: standalone server > You can also check out the [getting started](https://www.apollographql.com/docs/apollo-server/getting-started) guide in the Apollo Server docs for more details, including examples in both TypeScript and JavaScript. @@ -78,7 +76,6 @@ node server.mjs Open the URL it prints in a web browser. It will show [Apollo Sandbox](https://www.apollographql.com/docs/studio/explorer/sandbox/), a web-based tool for running GraphQL operations. Try running the operation `query { hello }`! - ## Getting started: Express middleware Apollo Server's built-in Express middleware lets you run your GraphQL server as part of an app built with [Express](https://expressjs.com/), the most popular web framework for Node. @@ -94,7 +91,7 @@ Then, write the following to `server.mjs`. (By using the `.mjs` extension, Node ```js import { ApolloServer } from '@apollo/server'; import { expressMiddleware } from '@apollo/server/express4'; -import { ApolloServerPluginDrainHttpServer } from '@apollo/server/plugin/drainHttpServer' +import { ApolloServerPluginDrainHttpServer } from '@apollo/server/plugin/drainHttpServer'; import express from 'express'; import http from 'http'; import cors from 'cors'; @@ -125,11 +122,7 @@ const server = new ApolloServer({ }); await server.start(); -app.use( - cors(), - bodyParser.json(), - expressMiddleware(server), -); +app.use(cors(), bodyParser.json(), expressMiddleware(server)); await new Promise((resolve) => httpServer.listen({ port: 4000 }, resolve)); console.log(`๐Ÿš€ Server ready at http://localhost:4000`); diff --git a/packages/usage-reporting-protobuf/README.md b/packages/usage-reporting-protobuf/README.md index 779af67632d..14556b0ad44 100644 --- a/packages/usage-reporting-protobuf/README.md +++ b/packages/usage-reporting-protobuf/README.md @@ -1,20 +1,20 @@ # `apollo-reporting-protobuf` -> **Note:** The Apollo usage reporting API is subject to change. We strongly +> **Note:** The Apollo usage reporting API is subject to change. We strongly > encourage developers to contact Apollo support at `support@apollographql.com` > to discuss their use case prior to building their own reporting agent using > this module. This module provides JavaScript/TypeScript [Protocol buffer](https://developers.google.com/protocol-buffers/) definitions -for the Apollo usage reporting API. These definitions are generated for +for the Apollo usage reporting API. These definitions are generated for consumption from the `reports.proto` file which is defined internally within Apollo. ## Development > **Note:** Due to a dependency on Unix tools (e.g. `bash`, `grep`, etc.), the -> development of this module requires a Unix system. There is no reason why +> development of this module requires a Unix system. There is no reason why > this can't be avoided, the time just hasn't been taken to make those changes. > We'd happily accept a PR which makes the appropriate changes! @@ -27,8 +27,7 @@ generated with the `generate` npm script. The root of the repository provides some `devDependencies` necessary to build these definitionsย and the `prepare` npm script is invoked programmatically via the monorepo tooling (e.g. Lerna) thanks to _this_ module's `postinstall` -script. Therefore, when making changes to this module, run scripts via `npx -lerna run SCRIPTNAME` in the **root** of this monorepo in order to update the +script. Therefore, when making changes to this module, run scripts via `npx lerna run SCRIPTNAME` in the **root** of this monorepo in order to update the definitions in _this_ module. To update `reports.proto` to the current version recognized by the Studio usage From a3c2f913ab40ca9ad473d9165d30042cc805d261 Mon Sep 17 00:00:00 2001 From: Trevor Scheer Date: Fri, 16 Sep 2022 10:52:44 -0700 Subject: [PATCH 4/6] Skip prettifying changesets which are generated --- .github/APOLLO_RELEASE_TEMPLATE.md | 6 +++--- .prettierignore | 1 + 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/.github/APOLLO_RELEASE_TEMPLATE.md b/.github/APOLLO_RELEASE_TEMPLATE.md index ea34db8b478..7bd878063a2 100644 --- a/.github/APOLLO_RELEASE_TEMPLATE.md +++ b/.github/APOLLO_RELEASE_TEMPLATE.md @@ -1,11 +1,11 @@ Release X.Y.Z -As with [release PRs in the past](https://github.com/apollographql/apollo-server/issues?q=label%3A%22%F0%9F%8F%97+release%22+is%3Aclosed), this is a PR tracking a `release-x.y.z` branch for an upcoming release of Apollo Server. ๐Ÿ™Œ The version in the title of this PR should correspond to the appropriate branch. +As with [release PRs in the past](https://github.com/apollographql/apollo-server/issues?q=label%3A%22%F0%9F%8F%97+release%22+is%3Aclosed), this is a PR tracking a `release-x.y.z` branch for an upcoming release of Apollo Server. ๐Ÿ™Œ The version in the title of this PR should correspond to the appropriate branch. Check the appropriate milestone (to the right) for more details on what we hope to get into this release! -The intention of these release branches is to gather changes which are intended to land in a specific version (again, indicated by the subject of this PR). Release branches allow additional clarity into what is being staged, provide a forum for comments from the community pertaining to the release's stability, and to facilitate the creation of pre-releases (e.g. `alpha`, `beta`, `rc`) without affecting the `main` branch. +The intention of these release branches is to gather changes which are intended to land in a specific version (again, indicated by the subject of this PR). Release branches allow additional clarity into what is being staged, provide a forum for comments from the community pertaining to the release's stability, and to facilitate the creation of pre-releases (e.g. `alpha`, `beta`, `rc`) without affecting the `main` branch. -PRs for new features might be opened against or re-targeted to this branch by the project maintainers. The `main` branch may be periodically merged into this branch up until the point in time that this branch is being prepared for release. Depending on the size of the release, this may be once it reaches RC (release candidate) stage with an `-rc.x` release suffix. Some less substantial releases may be short-lived and may never have pre-release versions. +PRs for new features might be opened against or re-targeted to this branch by the project maintainers. The `main` branch may be periodically merged into this branch up until the point in time that this branch is being prepared for release. Depending on the size of the release, this may be once it reaches RC (release candidate) stage with an `-rc.x` release suffix. Some less substantial releases may be short-lived and may never have pre-release versions. When this version is officially released onto the `latest` npm tag, this PR will be merged into `main`. diff --git a/.prettierignore b/.prettierignore index 88e1849c7df..d2f18be08b7 100644 --- a/.prettierignore +++ b/.prettierignore @@ -7,5 +7,6 @@ dist/ # Don't format generated files! **/generated/** +.changeset/* .volta From a57784911dbf3845a5841d88928c4b9b6455bce9 Mon Sep 17 00:00:00 2001 From: Trevor Scheer Date: Fri, 16 Sep 2022 10:53:06 -0700 Subject: [PATCH 5/6] changeset --- .changeset/eight-cheetahs-camp.md | 2 ++ 1 file changed, 2 insertions(+) create mode 100644 .changeset/eight-cheetahs-camp.md diff --git a/.changeset/eight-cheetahs-camp.md b/.changeset/eight-cheetahs-camp.md new file mode 100644 index 00000000000..a845151cc84 --- /dev/null +++ b/.changeset/eight-cheetahs-camp.md @@ -0,0 +1,2 @@ +--- +--- From 562e82ec8fe7e05976ae56aa29bd6abf2c39a909 Mon Sep 17 00:00:00 2001 From: Trevor Scheer Date: Fri, 16 Sep 2022 14:01:07 -0700 Subject: [PATCH 6/6] test horrible comment style --- docs/source/index.mdx | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/docs/source/index.mdx b/docs/source/index.mdx index aa998cd41c7..4f98b6ecacc 100644 --- a/docs/source/index.mdx +++ b/docs/source/index.mdx @@ -20,7 +20,9 @@ title: Apollo Server 4 (Alpha) - The gateway for a [federated supergraph](/federation/) - The GraphQL server for a [subgraph](/federation/subgraphs) in a federated supergraph - {/* TODO(AS4): replace links to new articles once they exist */} + +<>{/* TODO(AS4): replace links to new articles once they exist */} + - A [stand-alone GraphQL server](./migration#migrate-from-apollo-server) - An add-on to your application's existing Node.js middleware (such as Express, AWS Lambda, or Fastify)