@fastify/autoload
Advanced tools
| const pluginRegister = async (fastify) => { | ||
| fastify.addHook('onRequest', async (request) => { | ||
| request.hooksUsed.push('global') | ||
| }) | ||
| } | ||
| export default pluginRegister |
| const pluginRegister = async (fastify) => { | ||
| fastify.addHook('onRequest', async (request) => { | ||
| request.hooksUsed.push('first') | ||
| }) | ||
| } | ||
| export default pluginRegister |
| const routes = async (fastify) => { | ||
| fastify.get('/first', async (request) => { | ||
| return { hooksUsed: request.hooksUsed } | ||
| }) | ||
| } | ||
| export default routes |
| const pluginRegister = async (fastify) => { | ||
| fastify.addHook('onRequest', async (request) => { | ||
| request.hooksUsed.push('fourth') | ||
| }) | ||
| } | ||
| export default pluginRegister |
| const routes = async (fastify) => { | ||
| fastify.get('/fourth', async (request) => { | ||
| return { hooksUsed: request.hooksUsed } | ||
| }) | ||
| } | ||
| export default routes |
| const routes = async (fastify) => { | ||
| fastify.get('/global', async (request) => { | ||
| return { hooksUsed: request.hooksUsed } | ||
| }) | ||
| } | ||
| export default routes |
| // This folder is not used directly by the test, but in the previous implementation, the last hook used would affect the outcome. | ||
| // This folder ensures that the test fails if the fix is reverted or modified incorrectly. | ||
| const pluginRegister = async (fastify) => { | ||
| fastify.addHook('onRequest', async (request) => { | ||
| request.hooksUsed.push('second') | ||
| }) | ||
| } | ||
| export default pluginRegister |
| // This folder is not used directly by the test, but in the previous implementation, the last hook used would affect the outcome. | ||
| // This folder ensures that the test fails if the fix is reverted or modified incorrectly. | ||
| const routes = async (fastify) => { | ||
| fastify.get('/second', async (request) => { | ||
| return { hooksUsed: request.hooksUsed } | ||
| }) | ||
| } | ||
| export default routes |
| 'use strict' | ||
| const { beforeEach, afterEach, describe, it } = require('node:test') | ||
| const assert = require('node:assert') | ||
| const path = require('node:path') | ||
| const Fastify = require('fastify') | ||
| const autoLoad = require('../../../') | ||
| const startApp = async (autoloadConfig) => { | ||
| const app = Fastify() | ||
| app.addHook('onRequest', async (request) => { | ||
| request.hooksUsed = [] | ||
| }) | ||
| app.register(autoLoad, { | ||
| dir: path.join(__dirname, 'routes'), | ||
| autoHooks: true, | ||
| ...autoloadConfig, | ||
| }) | ||
| app.decorateRequest('hooksUsed') | ||
| await app.ready() | ||
| return app | ||
| } | ||
| describe('Issue 453 tests', function () { | ||
| describe('cascadeHooks === false', () => { | ||
| describe('dirNameRoutePrefix === true not interfere with auto hooks', () => { | ||
| let app | ||
| beforeEach(async function () { | ||
| app = await startApp({ | ||
| cascadeHooks: false, | ||
| dirNameRoutePrefix: true | ||
| }) | ||
| }) | ||
| afterEach(async function () { | ||
| await app.close() | ||
| }) | ||
| it('should only use global hook in global route', async function () { | ||
| const res = await app.inject({ url: '/global' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global'] }) | ||
| }) | ||
| it('should only use child hook in child route', async function () { | ||
| const res = await app.inject({ url: '/first/first' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['first'] }) | ||
| }) | ||
| it('should only use grandchild hook in grandchild route', async function () { | ||
| const res = await app.inject({ url: '/first/fourth/fourth' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['fourth'] }) | ||
| }) | ||
| }) | ||
| describe('dirNameRoutePrefix === false not interfere with auto hooks', () => { | ||
| let app | ||
| beforeEach(async function () { | ||
| app = await startApp({ | ||
| cascadeHooks: false, | ||
| dirNameRoutePrefix: false | ||
| }) | ||
| }) | ||
| afterEach(async function () { | ||
| await app.close() | ||
| }) | ||
| it('should only use global hook in global route', async function () { | ||
| const res = await app.inject({ url: '/global' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global'] }) | ||
| }) | ||
| it('should only use child hook in child route', async function () { | ||
| const res = await app.inject({ url: '/first' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['first'] }) | ||
| }) | ||
| it('should only use grandchild hook in grandchild route', async function () { | ||
| const res = await app.inject({ url: '/fourth' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['fourth'] }) | ||
| }) | ||
| }) | ||
| describe('dirNameRoutePrefix === () => false not interfere with auto hooks', () => { | ||
| let app | ||
| beforeEach(async function () { | ||
| app = await startApp({ | ||
| cascadeHooks: false, | ||
| dirNameRoutePrefix: () => { | ||
| return false | ||
| } | ||
| }) | ||
| }) | ||
| afterEach(async function () { | ||
| await app.close() | ||
| }) | ||
| it('should only use global hook in global route', async function () { | ||
| const res = await app.inject({ url: '/global' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global'] }) | ||
| }) | ||
| it('should only use child hook in child route', async function () { | ||
| const res = await app.inject({ url: '/first' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['first'] }) | ||
| }) | ||
| it('should only use grandchild hook in grandchild route', async function () { | ||
| const res = await app.inject({ url: '/fourth' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['fourth'] }) | ||
| }) | ||
| }) | ||
| }) | ||
| describe('cascadeHooks === true', () => { | ||
| describe('dirNameRoutePrefix === true not interfere with auto hooks', () => { | ||
| let app | ||
| beforeEach(async function () { | ||
| app = await startApp({ | ||
| cascadeHooks: true, | ||
| dirNameRoutePrefix: true | ||
| }) | ||
| }) | ||
| afterEach(async function () { | ||
| await app.close() | ||
| }) | ||
| it('should only use global hook in global route', async function () { | ||
| const res = await app.inject({ url: '/global' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global'] }) | ||
| }) | ||
| it('should use hooks till child in child route', async function () { | ||
| const res = await app.inject({ url: '/first/first' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global', 'first'] }) | ||
| }) | ||
| it('should use hooks till grandchild in grandchild route', async function () { | ||
| const res = await app.inject({ url: '/first/fourth/fourth' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global', 'first', 'fourth'] }) | ||
| }) | ||
| }) | ||
| describe('dirNameRoutePrefix === false not interfere with auto hooks', () => { | ||
| let app | ||
| beforeEach(async function () { | ||
| app = await startApp({ | ||
| cascadeHooks: true, | ||
| dirNameRoutePrefix: false | ||
| }) | ||
| }) | ||
| afterEach(async function () { | ||
| await app.close() | ||
| }) | ||
| it('should only use global hook in global route', async function () { | ||
| const res = await app.inject({ url: '/global' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global'] }) | ||
| }) | ||
| it('should use hooks till child in child route', async function () { | ||
| const res = await app.inject({ url: '/first' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global', 'first'] }) | ||
| }) | ||
| it('should use hooks till grandchild in grandchild route', async function () { | ||
| const res = await app.inject({ url: '/fourth' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global', 'first', 'fourth'] }) | ||
| }) | ||
| }) | ||
| describe('dirNameRoutePrefix === () => false not interfere with auto hooks', () => { | ||
| let app | ||
| beforeEach(async function () { | ||
| app = await startApp({ | ||
| cascadeHooks: true, | ||
| dirNameRoutePrefix: () => { | ||
| return false | ||
| } | ||
| }) | ||
| }) | ||
| afterEach(async function () { | ||
| await app.close() | ||
| }) | ||
| it('should only use global hook in global route', async function () { | ||
| const res = await app.inject({ url: '/global' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global'] }) | ||
| }) | ||
| it('should use hooks till child in child route', async function () { | ||
| const res = await app.inject({ url: '/first' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global', 'first'] }) | ||
| }) | ||
| it('should use hooks till grandchild in grandchild route', async function () { | ||
| const res = await app.inject({ url: '/fourth' }) | ||
| assert.strictEqual(res.statusCode, 200) | ||
| assert.deepStrictEqual(JSON.parse(res.body), { hooksUsed: ['global', 'first', 'fourth'] }) | ||
| }) | ||
| }) | ||
| }) | ||
| }) |
@@ -17,2 +17,5 @@ name: CI | ||
| permissions: | ||
| contents: read | ||
| jobs: | ||
@@ -19,0 +22,0 @@ test: |
+12
-12
@@ -11,3 +11,3 @@ 'use strict' | ||
| const pluginTree = { | ||
| [prefix || '/']: { hooks: [], plugins: [] } | ||
| [dir]: { hooks: [], plugins: [] } | ||
| } | ||
@@ -22,4 +22,4 @@ | ||
| // check to see if hooks or plugins have been added to this prefix, initialize if not | ||
| if (!pluginTree[prefix]) { | ||
| pluginTree[prefix] = { hooks: [], plugins: [] } | ||
| if (!pluginTree[dir]) { | ||
| pluginTree[dir] = { hooks: [], plugins: [] } | ||
| } | ||
@@ -29,3 +29,3 @@ | ||
| const currentDirHooks = findCurrentDirHooks(pluginTree, { dir, dirEntries, hooks, opts, prefix }) | ||
| const currentDirHooks = findCurrentDirHooks(pluginTree, { dir, dirEntries, hooks, opts }) | ||
@@ -47,3 +47,3 @@ const { indexDirEntry, hasNoDirectory } = processIndexDirEntryIfExists(pluginTree, { dirEntries, opts, dir, prefix }) | ||
| function findCurrentDirHooks (pluginTree, { dir, dirEntries, hooks, opts, prefix }) { | ||
| function findCurrentDirHooks (pluginTree, { dir, dirEntries, hooks, opts }) { | ||
| if (!opts.autoHooks) return [] | ||
@@ -72,3 +72,3 @@ | ||
| pluginTree[prefix || '/'].hooks = currentDirHooks | ||
| pluginTree[dir].hooks = currentDirHooks | ||
@@ -86,3 +86,3 @@ return currentDirHooks | ||
| handleTypeScriptSupport(file, language, true) | ||
| accumulatePlugin({ file, type, opts, pluginTree, prefix }) | ||
| accumulatePlugin({ dir, file, type, opts, pluginTree, prefix }) | ||
@@ -107,3 +107,3 @@ const hasNoDirectory = dirEntries.every((dirEntry) => !dirEntry.isDirectory()) | ||
| } else if (dirEntry.isFile() && opts.scriptPattern.test(dirEntry.name)) { | ||
| processFile(pluginTree, { file, opts, dirEntry, pluginTree, prefix }) | ||
| processFile(pluginTree, { dir, file, opts, dirEntry, pluginTree, prefix }) | ||
| } | ||
@@ -129,3 +129,3 @@ } | ||
| function processFile (pluginTree, { file, opts, dirEntry, prefix }) { | ||
| function processFile (pluginTree, { dir, file, opts, dirEntry, prefix }) { | ||
| const { language, type } = getScriptType(file, opts.packageType) | ||
@@ -136,7 +136,7 @@ handleTypeScriptSupport(file, language) | ||
| if (!opts.autoHooksPattern.test(dirEntry.name)) { | ||
| accumulatePlugin({ file, type, opts, pluginTree, prefix }) | ||
| accumulatePlugin({ dir, file, type, opts, pluginTree, prefix }) | ||
| } | ||
| } | ||
| function accumulatePlugin ({ file, type, opts, pluginTree, prefix }) { | ||
| function accumulatePlugin ({ dir, file, type, opts, pluginTree, prefix }) { | ||
| // Replace backward slash to forward slash for consistent behavior between windows and posix. | ||
@@ -152,3 +152,3 @@ const filePath = '/' + relative(opts.dir, file).replace(/\\/gu, '/') | ||
| pluginTree[prefix || '/'].plugins.push({ file, type, prefix }) | ||
| pluginTree[dir].plugins.push({ file, type, prefix }) | ||
| } | ||
@@ -155,0 +155,0 @@ |
+1
-1
| { | ||
| "name": "@fastify/autoload", | ||
| "version": "6.2.0", | ||
| "version": "6.3.0", | ||
| "description": "Require all plugins in a directory", | ||
@@ -5,0 +5,0 @@ "main": "index.js", |
+2
-2
@@ -18,5 +18,5 @@ # @fastify/autoload | ||
| | ---------------|-----------------| | ||
| | `^6.x` | `^5.x` | | ||
| | `>=6.x` | `^5.x` | | ||
| | `^5.x` | `^4.x` | | ||
| | `^2.x` | `^3.x` | | ||
| | `>=2.x <5.x` | `^3.x` | | ||
| | `^1.x` | `^2.x` | | ||
@@ -23,0 +23,0 @@ | `^1.x` | `^1.x` | |
Potential vulnerability
Supply chain riskInitial human review suggests the presence of a vulnerability in this package. It is pending further analysis and confirmation.
Potential vulnerability
Supply chain riskInitial human review suggests the presence of a vulnerability in this package. It is pending further analysis and confirmation.
173180
5.85%284
3.27%4580
5.63%