diff --git a/.changeset/clean-carpets-battle.md b/.changeset/clean-carpets-battle.md new file mode 100644 index 0000000000..68fe85e653 --- /dev/null +++ b/.changeset/clean-carpets-battle.md @@ -0,0 +1,5 @@ +--- +'astro': patch +--- + +Fix `/_image` endpoint not being prefixed with the `base` path in build SSR diff --git a/packages/astro/src/assets/services/service.ts b/packages/astro/src/assets/services/service.ts index 5c19ce3d9f..910f0f0a82 100644 --- a/packages/astro/src/assets/services/service.ts +++ b/packages/astro/src/assets/services/service.ts @@ -1,4 +1,5 @@ import { AstroError, AstroErrorData } from '../../core/errors/index.js'; +import { joinPaths } from '../../core/path.js'; import { VALID_OPTIMIZABLE_FORMATS } from '../consts.js'; import { isESMImportedImage } from '../internal.js'; import type { ImageOutputFormat, ImageTransform } from '../types.js'; @@ -195,7 +196,7 @@ export const baseService: Omit = { options.quality && searchParams.append('q', options.quality.toString()); options.format && searchParams.append('f', options.format); - return '/_image?' + searchParams; + return joinPaths(import.meta.env.BASE_URL, '/_image?') + searchParams; }, parseURL(url) { const params = url.searchParams; diff --git a/packages/astro/test/core-image.test.js b/packages/astro/test/core-image.test.js index 7417b48955..10ec46001d 100644 --- a/packages/astro/test/core-image.test.js +++ b/packages/astro/test/core-image.test.js @@ -447,6 +447,27 @@ describe('astro:image', () => { expect(src.length).to.be.greaterThan(0); expect(src.startsWith('/blog')).to.be.true; }); + + it('has base path prefix in SSR', async () => { + const fixtureWithBase = await loadFixture({ + root: './fixtures/core-image-ssr/', + output: 'server', + adapter: testAdapter(), + experimental: { + assets: true, + }, + base: '/blog', + }); + await fixtureWithBase.build(); + const app = await fixtureWithBase.loadTestAdapterApp(); + const request = new Request('http://example.com/blog/'); + const response = await app.render(request); + expect(response.status).to.equal(200); + const html = await response.text(); + const $ = cheerio.load(html); + const src = $('#local img').attr('src'); + expect(src.startsWith('/blog')).to.be.true; + }); }); describe('build ssg', () => {