bundle-offers-app/app/routes/proxy.$handle.tsx
metatroncubeswdev 365e45406a Bundle Offers Shopify app: discount function, admin, storefront, deploy stack
Rust discount function (one automatic discount evaluating all offers in priority
order, parity with the Odoo engine), React Router admin with Polaris, theme app
extension and app proxy pages, webhooks incl. GDPR, managed-pricing limits, and
a Docker Compose stack (Postgres + Caddy HTTPS) for a single VPS.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-13 21:35:58 -04:00

29 lines
1.6 KiB
TypeScript

// /apps/bundles/{handle} (app proxy): bundle page (F13, F14). Guests welcome; not running -> 404;
// renamed offer -> 301 to the current handle.
import type { LoaderFunctionArgs } from "react-router";
import { redirect } from "react-router";
import { authenticate } from "../shopify.server";
import db from "../db.server";
import { PROXY_CACHE, runningOffersForShop } from "../lib/proxy.server";
import { bundlePageLiquid, notFoundLiquid, proxyBase } from "../lib/storefront.server";
export const loader = async ({ request, params }: LoaderFunctionArgs) => {
const { liquid } = await authenticate.public.appProxy(request);
const url = new URL(request.url);
const shop = url.searchParams.get("shop") || "";
const base = proxyBase(url.searchParams.get("path_prefix"));
const handle = (params.handle || "").toLowerCase();
const locale = request.headers.get("accept-language")?.split(",")[0]?.split("-")[0] || null;
const data = await runningOffersForShop(shop, request.headers.get("x-shopify-country") || null);
if (!data) return liquid(notFoundLiquid(base), { status: 404 });
const offer = data.running.find((o) => o.handle === handle);
if (offer) return liquid(bundlePageLiquid(offer, data.ctx, locale), { headers: { "Cache-Control": PROXY_CACHE } });
const renamed = await db.offer.findFirst({ where: { shopId: data.shop.id, oldHandles: { has: handle } }, select: { id: true, handle: true } });
if (renamed && data.running.some((o) => o.id === renamed.id)) {
return redirect(`${base}/${renamed.handle}`, 301);
}
return liquid(notFoundLiquid(base), { status: 404 });
};