[og] Derive the preview origin from the request

SITE_ORIGIN is a constant defaulting to https://bitvid.network, so the unstable
deployment advertised production's canonical URL and, worse, a twitter:player
pointing at production's embed -- testing a preview link silently exercised the
live site.

Build shareUrl, embedUrl and the fallback card from the request's own
proto+host instead, so every deployment (production, unstable, preview) is
self-consistent. BITVID_SITE_ORIGIN remains the fallback when the host header
is absent.

Co-Authored-By: Claude Opus 5 (1M context) <[email protected]>
This commit is contained in:
thePR0M3TH3ANandClaude Opus 5 committed 2026-07-28 14:48:32 -04:00
1 parent 04075ff56b
commit c0d006a5fc
1 file changed
+23 -7
+23 -7
View File
@@ -135,11 +135,17 @@ export default async function handler(req, res) {
const requestUrl = new URL(req.url || "/", `${proto}://${host}`); const requestUrl = new URL(req.url || "/", `${proto}://${host}`);
const pointer = requestUrl.searchParams.get("v") || ""; const pointer = requestUrl.searchParams.get("v") || "";
// Derive the origin from the REQUEST, not from a constant. Otherwise every
// non-production deployment (unstable, previews) advertises production's
// canonical URL and — worse — a twitter:player pointing at production's
// embed, so testing a preview link silently exercises the live site.
const origin = `${proto}://${host}`;
const shareUrl = pointer const shareUrl = pointer
? `${SITE_ORIGIN}/?v=${encodeURIComponent(pointer)}` ? `${origin}/?v=${encodeURIComponent(pointer)}`
: SITE_ORIGIN; : origin;
const embedUrl = pointer const embedUrl = pointer
? `${SITE_ORIGIN}/embed.html?pointer=${encodeURIComponent(pointer)}` ? `${origin}/embed.html?pointer=${encodeURIComponent(pointer)}`
: ""; : "";
const renderFallback = (reason) => { const renderFallback = (reason) => {
@@ -149,7 +155,11 @@ export default async function handler(req, res) {
res.setHeader("Cache-Control", "public, s-maxage=300, stale-while-revalidate=600"); res.setHeader("Cache-Control", "public, s-maxage=300, stale-while-revalidate=600");
res.setHeader("X-Bitvid-OG", reason); res.setHeader("X-Bitvid-OG", reason);
res.status(200).send( res.status(200).send(
renderOgHtml({ video: null, shareUrl, fallback: FALLBACK }) renderOgHtml({
video: null,
shareUrl,
fallback: { ...FALLBACK, url: origin, image: `${origin}/assets/jpg/bitvid.jpg` },
})
); );
}; };
@@ -242,9 +252,15 @@ export default async function handler(req, res) {
res.setHeader("Content-Type", "text/html; charset=utf-8"); res.setHeader("Content-Type", "text/html; charset=utf-8");
res.setHeader("Cache-Control", "public, s-maxage=300, stale-while-revalidate=600"); res.setHeader("Cache-Control", "public, s-maxage=300, stale-while-revalidate=600");
res.setHeader("X-Bitvid-OG", "video"); res.setHeader("X-Bitvid-OG", "video");
res res.status(200).send(
.status(200) renderOgHtml({
.send(renderOgHtml({ video, shareUrl, embedUrl, fallback: FALLBACK, gate })); video,
shareUrl,
embedUrl,
fallback: { ...FALLBACK, url: origin, image: `${origin}/assets/jpg/bitvid.jpg` },
gate,
})
);
} catch (err) { } catch (err) {
renderFallback("error"); renderFallback("error");
} finally { } finally {