diff --git a/server/index.ts b/server/index.ts index 3cbe675ce..732c8fcc6 100644 --- a/server/index.ts +++ b/server/index.ts @@ -64,12 +64,6 @@ app.use((_, res, next) => { next() }) -app.get([/^\/img\/.*/, /^\/favicons\/.*/], (_req, res) => { - // if we made it past the express.static for these, then we're missing something. - // So we'll just send a 404 and won't bother calling other middleware. - return res.status(404).send('Not found') -}) - morgan.token('url', (req) => { try { return decodeURIComponent(req.url ?? '') @@ -156,6 +150,13 @@ if (!ALLOW_INDEXING) { }) } +// Requests for files in /img and /favicons that made it past the static file +// middleware are missing something. So we'll just send a 404 and won't bother +// calling other middleware. +const missingFileHandler: express.RequestHandler = (_req, res) => { + res.status(404).send('Not found') +} + if (IS_DEV) { console.log('Starting development server') const viteDevServer = await import('vite').then((vite) => @@ -167,6 +168,7 @@ if (IS_DEV) { }), ) app.use(viteDevServer.middlewares) + app.get([/^\/img\/.*/, /^\/favicons\/.*/], missingFileHandler) app.use(async (req, res, next) => { try { const source = await viteDevServer.ssrLoadModule('./server/app.ts') @@ -192,6 +194,7 @@ if (IS_DEV) { // Everything else (like favicon.ico) is cached for an hour. You may want to be // more aggressive with this caching. app.use(express.static('build/client', { maxAge: '1h' })) + app.get([/^\/img\/.*/, /^\/favicons\/.*/], missingFileHandler) app.use(await import(BUILD_PATH).then((mod) => mod.app)) } diff --git a/tests/e2e/static-files.test.ts b/tests/e2e/static-files.test.ts new file mode 100644 index 000000000..0f76c787f --- /dev/null +++ b/tests/e2e/static-files.test.ts @@ -0,0 +1,20 @@ +import { expect, test } from '#tests/playwright-utils.ts' + +test('files in public/img and public/favicons are served', async ({ + request, +}) => { + for (const path of [ + '/img/user.png', + '/favicons/android-chrome-192x192.png', + ]) { + const response = await request.get(path) + expect(response.status(), `${path} should be served`).toBe(200) + } +}) + +test('missing files in /img and /favicons return 404', async ({ request }) => { + for (const path of ['/img/missing.png', '/favicons/missing.png']) { + const response = await request.get(path) + expect(response.status(), `${path} should 404`).toBe(404) + } +})