diff --git a/packages/astro/src/@types/astro.ts b/packages/astro/src/@types/astro.ts
index bb37c4989..f4988e043 100644
--- a/packages/astro/src/@types/astro.ts
+++ b/packages/astro/src/@types/astro.ts
@@ -738,6 +738,28 @@ export interface AstroUserConfig {
* ```
*/
serverEntry?: string;
+ /**
+ * @docs
+ * @name build.redirects
+ * @type {boolean}
+ * @default `true`
+ * @description
+ * Specifies whether redirects will be output to HTML during the build.
+ * This option only applies to `output: 'static'` mode; in SSR redirects
+ * are treated the same as all responses.
+ *
+ * This option is mostly meant to be used by adapters that have special
+ * configuration files for redirects and do not need/want HTML based redirects.
+ *
+ * ```js
+ * {
+ * build: {
+ * redirects: false
+ * }
+ * }
+ * ```
+ */
+ redirects?: boolean;
};
/**
diff --git a/packages/astro/src/core/build/generate.ts b/packages/astro/src/core/build/generate.ts
index 6f22d5914..21da35d5b 100644
--- a/packages/astro/src/core/build/generate.ts
+++ b/packages/astro/src/core/build/generate.ts
@@ -564,6 +564,10 @@ async function generatePath(
switch(true) {
case (response.status >= 300 && response.status < 400): {
+ // If redirects is set to false, don't output the HTML
+ if(!opts.settings.config.build.redirects) {
+ return;
+ }
const location = getRedirectLocationOrThrow(response.headers);
body = `
Redirecting to: ${location}
diff --git a/packages/astro/src/core/config/schema.ts b/packages/astro/src/core/config/schema.ts
index 4573d8810..a6badbe2f 100644
--- a/packages/astro/src/core/config/schema.ts
+++ b/packages/astro/src/core/config/schema.ts
@@ -22,6 +22,7 @@ const ASTRO_CONFIG_DEFAULTS: AstroUserConfig & any = {
server: './dist/server/',
assets: '_astro',
serverEntry: 'entry.mjs',
+ redirects: true,
},
compressHTML: false,
server: {
@@ -116,6 +117,7 @@ export const AstroConfigSchema = z.object({
assets: z.string().optional().default(ASTRO_CONFIG_DEFAULTS.build.assets),
assetsPrefix: z.string().optional(),
serverEntry: z.string().optional().default(ASTRO_CONFIG_DEFAULTS.build.serverEntry),
+ redirects: z.boolean().optional().default(ASTRO_CONFIG_DEFAULTS.build.redirects),
})
.optional()
.default({}),
@@ -279,6 +281,7 @@ export function createRelativeSchema(cmd: string, fileProtocolRoot: URL) {
assets: z.string().optional().default(ASTRO_CONFIG_DEFAULTS.build.assets),
assetsPrefix: z.string().optional(),
serverEntry: z.string().optional().default(ASTRO_CONFIG_DEFAULTS.build.serverEntry),
+ redirects: z.boolean().optional().default(ASTRO_CONFIG_DEFAULTS.build.redirects),
})
.optional()
.default({}),
diff --git a/packages/astro/test/redirects.test.js b/packages/astro/test/redirects.test.js
index df041baa2..05357b449 100644
--- a/packages/astro/test/redirects.test.js
+++ b/packages/astro/test/redirects.test.js
@@ -119,4 +119,29 @@ describe('Astro.redirect', () => {
expect(html).to.include('url=/');
});
});
+
+ describe('config.build.redirects = false', () => {
+ before(async () => {
+ process.env.STATIC_MODE = true;
+ fixture = await loadFixture({
+ root: './fixtures/ssr-redirect/',
+ output: 'static',
+ redirects: {
+ '/one': '/'
+ },
+ build: {
+ redirects: false
+ }
+ });
+ await fixture.build();
+ });
+
+ it('Does not output redirect HTML', async () => {
+ let oneHtml = undefined;
+ try {
+ oneHtml = await fixture.readFile('/one/index.html');
+ } catch {}
+ expect(oneHtml).be.an('undefined');
+ })
+ })
});
diff --git a/packages/integrations/cloudflare/src/index.ts b/packages/integrations/cloudflare/src/index.ts
index 0b8b5f415..ca755432e 100644
--- a/packages/integrations/cloudflare/src/index.ts
+++ b/packages/integrations/cloudflare/src/index.ts
@@ -51,6 +51,7 @@ export default function createIntegration(args?: Options): AstroIntegration {
client: new URL(`.${config.base}`, config.outDir),
server: new URL(`.${SERVER_BUILD_FOLDER}`, config.outDir),
serverEntry: '_worker.mjs',
+ redirects: false,
},
});
},
diff --git a/packages/integrations/netlify/src/integration-static.ts b/packages/integrations/netlify/src/integration-static.ts
index bb989b532..8814f9d2a 100644
--- a/packages/integrations/netlify/src/integration-static.ts
+++ b/packages/integrations/netlify/src/integration-static.ts
@@ -7,6 +7,14 @@ export function netlifyStatic(): AstroIntegration {
return {
name: '@astrojs/netlify',
hooks: {
+ 'astro:config:setup': ({ updateConfig }) => {
+ updateConfig({
+ build: {
+ // Do not output HTML redirects because we are building a `_redirects` file.
+ redirects: false,
+ },
+ });
+ },
'astro:config:done': ({ config }) => {
_config = config;
},
diff --git a/packages/integrations/vercel/src/static/adapter.ts b/packages/integrations/vercel/src/static/adapter.ts
index 0b3579cdd..e0cc14322 100644
--- a/packages/integrations/vercel/src/static/adapter.ts
+++ b/packages/integrations/vercel/src/static/adapter.ts
@@ -43,6 +43,7 @@ export default function vercelStatic({
outDir,
build: {
format: 'directory',
+ redirects: false,
},
vite: {
define: viteDefine,