@preprio/prepr-nextjs 2.2.3 → 2.2.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/middleware/index.cjs +1 -1
- package/dist/middleware/index.cjs.map +1 -1
- package/dist/middleware/index.js +1 -1
- package/dist/middleware/index.js.map +1 -1
- package/dist/server/index.cjs +1 -1
- package/dist/server/index.cjs.map +1 -1
- package/dist/server/index.js +1 -1
- package/dist/server/index.js.map +1 -1
- package/package.json +1 -1
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
'use strict';var functions=require('@vercel/functions'),server=require('next/server');var h="2.2.
|
|
1
|
+
'use strict';var functions=require('@vercel/functions'),server=require('next/server');var h="2.2.4";function k(r,n,P){var l,m,x,u,g;let e,i;n&&"headers"in n?(e=n,i=P):(e=server.NextResponse.next(),i=n),r.nextUrl.searchParams.forEach((t,s)=>{switch(s){case "utm_source":e.headers.set("Prepr-Context-utm_source",t);break;case "utm_medium":e.headers.set("Prepr-Context-utm_medium",t);break;case "utm_term":e.headers.set("Prepr-Context-utm_term",t);break;case "utm_content":e.headers.set("Prepr-Context-utm_content",t);break;case "utm_campaign":e.headers.set("Prepr-Context-utm_campaign",t);break}});let o=r.headers.get("referer");o&&e.headers.set("Prepr-Context-initial_referral",o),e.headers.set("Prepr-Package",h);let d=functions.ipAddress(r)||null;r.headers.get("Cf-Connecting-Ip")&&(d=r.headers.get("Cf-Connecting-Ip")),d&&e.headers.set("Prepr-Visitor-IP",d);let c=(l=r.cookies.get("hubspotutk"))==null?void 0:l.value;c&&e.headers.set("Prepr-Hubspot-Id",c);let p=(m=r.cookies.get("__prepr_uid"))==null?void 0:m.value;if(p||(p=crypto.randomUUID(),e.cookies.set("__prepr_uid",p,{maxAge:1*365*24*60}),e.headers.set("Prepr-Customer-Id-Created","true")),e.headers.set("Prepr-Customer-Id",p),!(i!=null&&i.preview)||process.env.PREPR_ENV!=="preview"||!(r.nextUrl.searchParams.has("prepr_preview_segment")||r.nextUrl.searchParams.has("prepr_preview_ab"))&&!(((x=r.cookies.get("Prepr-Preview-Mode"))==null?void 0:x.value)!=="false"))return e;e.headers.set("Prepr-Preview-Bar","true");let a=r.nextUrl.searchParams.get("prepr_hide_bar")==="true";if(!a){let t=(u=r.cookies.get("Prepr-Segments"))==null?void 0:u.value;t&&e.headers.set("Prepr-Segments",t);let s=(g=r.cookies.get("Prepr-ABtesting"))==null?void 0:g.value;s&&e.headers.set("Prepr-ABtesting",s);}return r.nextUrl.searchParams.forEach((t,s)=>{s==="prepr_preview_ab"&&(e.headers.set("Prepr-ABtesting",t),a||e.cookies.set("Prepr-ABtesting",t)),s==="prepr_preview_segment"&&(e.headers.set("Prepr-Segments",t),a||e.cookies.set("Prepr-Segments",t));}),e}module.exports=k;//# sourceMappingURL=index.cjs.map
|
|
2
2
|
//# sourceMappingURL=index.cjs.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../package.json","../../src/middleware/index.ts"],"names":["version","createPreprMiddleware","request","responseOrOptions","options","_a","_b","_c","_d","_e","response","finalOptions","NextResponse","value","key","referrer","ip","ipAddress","hutkCookie","cookie","isLivePreview","segmentCookie","abCookie"],"mappings":"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","file":"index.cjs","sourcesContent":["{\n \"name\": \"@preprio/prepr-nextjs\",\n \"version\": \"2.2.3\",\n \"description\": \"Next.js package for Prepr CMS preview functionality with advanced debugging and visual editing capabilities\",\n \"main\": \"dist/react/index.cjs\",\n \"types\": \"./dist/react/index.d.ts\",\n \"module\": \"./dist/react/index.js\",\n \"type\": \"module\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"clean\": \"rm -rf dist\",\n \"check\": \"tsc --noEmit && eslint src --ext .ts,.tsx && prettier --check \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"fix\": \"eslint src --ext .ts,.tsx --fix && prettier --write \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"changeset\": \"changeset\",\n \"version\": \"changeset version\",\n \"release\": \"pnpm run build && changeset publish\",\n \"prepublishOnly\": \"pnpm run check && pnpm run build\"\n },\n \"exports\": {\n \"./middleware\": {\n \"import\": \"./dist/middleware/index.js\",\n \"types\": \"./dist/middleware/index.d.ts\",\n \"require\": \"./dist/middleware/index.cjs\"\n },\n \"./server\": {\n \"import\": \"./dist/server/index.js\",\n \"types\": \"./dist/server/index.d.ts\",\n \"require\": \"./dist/server/index.cjs\"\n },\n \"./react\": {\n \"import\": \"./dist/react/index.js\",\n \"types\": \"./dist/react/index.d.ts\",\n \"require\": \"./dist/react/index.cjs\"\n },\n \"./utils\": {\n \"import\": \"./dist/utils/index.js\",\n \"types\": \"./dist/utils/index.d.ts\",\n \"require\": \"./dist/utils/index.cjs\"\n },\n \"./types\": {\n \"import\": \"./dist/types/index.js\",\n \"types\": \"./dist/types/index.d.ts\",\n \"require\": \"./dist/types/index.cjs\"\n },\n \"./index.css\": {\n \"import\": \"./dist/index.css\",\n \"require\": \"./dist/index.css\"\n }\n },\n \"files\": [\n \"dist\",\n \"package.json\"\n ],\n \"keywords\": [\n \"prepr\",\n \"cms\",\n \"nextjs\",\n \"preview\",\n \"visual-editing\",\n \"headless-cms\",\n \"react\",\n \"typescript\",\n \"debug\",\n \"stega\"\n ],\n \"author\": \"Preprio\",\n \"license\": \"MIT\",\n \"packageManager\": \"pnpm@10.5.2\",\n \"devDependencies\": {\n \"@changesets/cli\": \"^2.30.0\",\n \"@eslint/js\": \"^9.39.2\",\n \"@types/node\": \"^25.4.0\",\n \"@types/react\": \"19.2.14\",\n \"@types/react-dom\": \"19.2.3\",\n \"@typescript-eslint/eslint-plugin\": \"^8.57.0\",\n \"@typescript-eslint/parser\": \"^8.57.0\",\n \"autoprefixer\": \"^10.4.27\",\n \"cssnano\": \"^7.1.3\",\n \"eslint\": \"^9.39.2\",\n \"eslint-config-prettier\": \"^10.1.8\",\n \"eslint-plugin-prettier\": \"^5.5.5\",\n \"eslint-plugin-react\": \"^7.37.5\",\n \"eslint-plugin-react-hooks\": \"^7.0.1\",\n \"next\": \"16.1.6\",\n \"postcss\": \"^8.5.8\",\n \"prettier\": \"^3.8.1\",\n \"prettier-plugin-tailwindcss\": \"^0.7.2\",\n \"react\": \"^19.2.4\",\n \"react-dom\": \"^19.2.4\",\n \"tailwindcss\": \"^3.4.17\",\n \"tsup\": \"^8.5.1\",\n \"typescript\": \"^5.9.3\"\n },\n \"peerDependencies\": {\n \"next\": \"^16.0.3 || ^15.0.5 || ^15.1.9 || ^15.2.6 || ^15.3.6 || ^15.4.8 || ^15.5.7 || ^14.0.0 || ^13.0.0\",\n \"react\": \"^19.0.0 || ^18.0.0 || ^17.0.0 \",\n \"react-dom\": \"^19.0.0 || ^18.0.0 || ^17.0.0\"\n },\n \"dependencies\": {\n \"@headlessui/react\": \"^2.2.9\",\n \"@vercel/functions\": \"^3.4.3\",\n \"@vercel/stega\": \"^1.0.0\",\n \"clsx\": \"^2.1.1\",\n \"postcss-cli\": \"^11.0.1\",\n \"tailwind-merge\": \"^3.5.0\",\n \"zustand\": \"^5.0.11\"\n }\n}\n","import { ipAddress } from '@vercel/functions';\nimport { NextRequest, NextResponse } from 'next/server';\nimport { version } from '../../package.json';\n\nexport interface PreprMiddlewareOptions {\n preview?: boolean;\n}\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param response - NextResponse object to chain with\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n response: NextResponse,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Implementation of createPreprMiddleware with function overloads\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n responseOrOptions?: NextResponse | PreprMiddlewareOptions,\n options?: PreprMiddlewareOptions\n): NextResponse {\n let response: NextResponse;\n let finalOptions: PreprMiddlewareOptions | undefined;\n\n // Handle overloads\n if (responseOrOptions && 'headers' in responseOrOptions) {\n // Second parameter is NextResponse\n response = responseOrOptions;\n finalOptions = options;\n } else {\n // Second parameter is options or undefined\n response = NextResponse.next();\n finalOptions = responseOrOptions as PreprMiddlewareOptions | undefined;\n }\n\n // Map over search params and set headers\n request.nextUrl.searchParams.forEach((value, key) => {\n switch (key) {\n case 'utm_source':\n response.headers.set('Prepr-Context-utm_source', value);\n break;\n case 'utm_medium':\n response.headers.set('Prepr-Context-utm_medium', value);\n break;\n case 'utm_term':\n response.headers.set('Prepr-Context-utm_term', value);\n break;\n case 'utm_content':\n response.headers.set('Prepr-Context-utm_content', value);\n break;\n case 'utm_campaign':\n response.headers.set('Prepr-Context-utm_campaign', value);\n break;\n }\n });\n\n // Set initial referral header\n const referrer = request.headers.get('referer');\n if (referrer) {\n response.headers.set('Prepr-Context-initial_referral', referrer);\n }\n\n // Set Prepr version header\n response.headers.set('Prepr-Package', version);\n\n let ip: string | null = ipAddress(request) || null;\n\n if (request.headers.get('Cf-Connecting-Ip')) {\n ip = request.headers.get('Cf-Connecting-Ip');\n }\n\n if (ip) {\n response.headers.set('Prepr-Visitor-IP', ip);\n }\n\n // Set HubSpot cookie header\n const hutkCookie = request.cookies.get('hubspotutk')?.value;\n if (hutkCookie) {\n response.headers.set('Prepr-Hubspot-Id', hutkCookie);\n }\n\n // Check for existing Prepr UID cookie or create a new one\n let cookie = request.cookies.get('__prepr_uid')?.value;\n if (!cookie) {\n cookie = crypto.randomUUID();\n response.cookies.set('__prepr_uid', cookie, {\n maxAge: 1 * 365 * 24 * 60, // Set for one year\n });\n response.headers.set('Prepr-Customer-Id-Created', 'true');\n }\n\n // Set the Prepr Customer ID header\n response.headers.set('Prepr-Customer-Id', cookie);\n\n // If preview mode is not enabled, return the response\n if (!finalOptions?.preview || process.env.PREPR_ENV !== 'preview') {\n return response;\n }\n\n // Preview query params always take priority — when the CMS dashboard\n // loads the site in an iframe it controls segments via query params,\n // regardless of the user's Prepr-Preview-Mode cookie in the browser.\n const hasPreviewParams =\n request.nextUrl.searchParams.has('prepr_preview_segment') ||\n request.nextUrl.searchParams.has('prepr_preview_ab');\n\n if (!hasPreviewParams) {\n // Respect preview mode toggle cookie from client\n const previewModeCookie = request.cookies.get('Prepr-Preview-Mode')?.value;\n const previewModeEnabled = previewModeCookie !== 'false';\n\n if (!previewModeEnabled) {\n return response;\n }\n }\n\n // If preview mode is enabled, set additional headers\n response.headers.set('Prepr-Preview-Bar', 'true');\n\n // When loaded inside the Prepr live preview iframe, prepr_hide_bar=true is\n // always present in the URL. In that context, cookies must never be used —\n // the live preview controls segments/variants exclusively via query params.\n // If no query params are present, the default (no segment/variant) should\n // be shown, not whatever the editor's browser cookie happens to contain.\n const isLivePreview =\n request.nextUrl.searchParams.get('prepr_hide_bar') === 'true';\n\n if (!isLivePreview) {\n // Set Prepr Preview Segment and AB test from cookies\n const segmentCookie = request.cookies.get('Prepr-Segments')?.value;\n if (segmentCookie) {\n response.headers.set('Prepr-Segments', segmentCookie);\n }\n\n const abCookie = request.cookies.get('Prepr-ABtesting')?.value;\n if (abCookie) {\n response.headers.set('Prepr-ABtesting', abCookie);\n }\n }\n\n // Set Prepr Preview Segment and AB test headers from query params\n request.nextUrl.searchParams.forEach((value, key) => {\n if (key === 'prepr_preview_ab') {\n response.headers.set('Prepr-ABtesting', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-ABtesting', value);\n }\n }\n\n if (key === 'prepr_preview_segment') {\n response.headers.set('Prepr-Segments', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-Segments', value);\n }\n }\n });\n\n return response;\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../../package.json","../../src/middleware/index.ts"],"names":["version","createPreprMiddleware","request","responseOrOptions","options","_a","_b","_c","_d","_e","response","finalOptions","NextResponse","value","key","referrer","ip","ipAddress","hutkCookie","cookie","isLivePreview","segmentCookie","abCookie"],"mappings":"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","file":"index.cjs","sourcesContent":["{\n \"name\": \"@preprio/prepr-nextjs\",\n \"version\": \"2.2.4\",\n \"description\": \"Next.js package for Prepr CMS preview functionality with advanced debugging and visual editing capabilities\",\n \"main\": \"dist/react/index.cjs\",\n \"types\": \"./dist/react/index.d.ts\",\n \"module\": \"./dist/react/index.js\",\n \"type\": \"module\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"clean\": \"rm -rf dist\",\n \"check\": \"tsc --noEmit && eslint src --ext .ts,.tsx && prettier --check \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"fix\": \"eslint src --ext .ts,.tsx --fix && prettier --write \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"changeset\": \"changeset\",\n \"version\": \"changeset version\",\n \"release\": \"pnpm run build && changeset publish\",\n \"prepublishOnly\": \"pnpm run check && pnpm run build\"\n },\n \"exports\": {\n \"./middleware\": {\n \"import\": \"./dist/middleware/index.js\",\n \"types\": \"./dist/middleware/index.d.ts\",\n \"require\": \"./dist/middleware/index.cjs\"\n },\n \"./server\": {\n \"import\": \"./dist/server/index.js\",\n \"types\": \"./dist/server/index.d.ts\",\n \"require\": \"./dist/server/index.cjs\"\n },\n \"./react\": {\n \"import\": \"./dist/react/index.js\",\n \"types\": \"./dist/react/index.d.ts\",\n \"require\": \"./dist/react/index.cjs\"\n },\n \"./utils\": {\n \"import\": \"./dist/utils/index.js\",\n \"types\": \"./dist/utils/index.d.ts\",\n \"require\": \"./dist/utils/index.cjs\"\n },\n \"./types\": {\n \"import\": \"./dist/types/index.js\",\n \"types\": \"./dist/types/index.d.ts\",\n \"require\": \"./dist/types/index.cjs\"\n },\n \"./index.css\": {\n \"import\": \"./dist/index.css\",\n \"require\": \"./dist/index.css\"\n }\n },\n \"files\": [\n \"dist\",\n \"package.json\"\n ],\n \"keywords\": [\n \"prepr\",\n \"cms\",\n \"nextjs\",\n \"preview\",\n \"visual-editing\",\n \"headless-cms\",\n \"react\",\n \"typescript\",\n \"debug\",\n \"stega\"\n ],\n \"author\": \"Preprio\",\n \"license\": \"MIT\",\n \"packageManager\": \"pnpm@10.5.2\",\n \"devDependencies\": {\n \"@changesets/cli\": \"^2.30.0\",\n \"@eslint/js\": \"^9.39.2\",\n \"@types/node\": \"^25.4.0\",\n \"@types/react\": \"19.2.14\",\n \"@types/react-dom\": \"19.2.3\",\n \"@typescript-eslint/eslint-plugin\": \"^8.57.0\",\n \"@typescript-eslint/parser\": \"^8.57.0\",\n \"autoprefixer\": \"^10.4.27\",\n \"cssnano\": \"^7.1.3\",\n \"eslint\": \"^9.39.2\",\n \"eslint-config-prettier\": \"^10.1.8\",\n \"eslint-plugin-prettier\": \"^5.5.5\",\n \"eslint-plugin-react\": \"^7.37.5\",\n \"eslint-plugin-react-hooks\": \"^7.0.1\",\n \"next\": \"16.1.6\",\n \"postcss\": \"^8.5.8\",\n \"prettier\": \"^3.8.1\",\n \"prettier-plugin-tailwindcss\": \"^0.7.2\",\n \"react\": \"^19.2.4\",\n \"react-dom\": \"^19.2.4\",\n \"tailwindcss\": \"^3.4.17\",\n \"tsup\": \"^8.5.1\",\n \"typescript\": \"^5.9.3\"\n },\n \"peerDependencies\": {\n \"next\": \"^16.0.3 || ^15.0.5 || ^15.1.9 || ^15.2.6 || ^15.3.6 || ^15.4.8 || ^15.5.7 || ^14.0.0 || ^13.0.0\",\n \"react\": \"^19.0.0 || ^18.0.0 || ^17.0.0 \",\n \"react-dom\": \"^19.0.0 || ^18.0.0 || ^17.0.0\"\n },\n \"pnpm\": {\n \"overrides\": {\n \"fast-xml-parser\": \"^5.5.0\"\n }\n },\n \"dependencies\": {\n \"@headlessui/react\": \"^2.2.9\",\n \"@vercel/functions\": \"^3.4.3\",\n \"@vercel/stega\": \"^1.0.0\",\n \"clsx\": \"^2.1.1\",\n \"postcss-cli\": \"^11.0.1\",\n \"tailwind-merge\": \"^3.5.0\",\n \"zustand\": \"^5.0.11\"\n }\n}\n","import { ipAddress } from '@vercel/functions';\nimport { NextRequest, NextResponse } from 'next/server';\nimport { version } from '../../package.json';\n\nexport interface PreprMiddlewareOptions {\n preview?: boolean;\n}\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param response - NextResponse object to chain with\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n response: NextResponse,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Implementation of createPreprMiddleware with function overloads\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n responseOrOptions?: NextResponse | PreprMiddlewareOptions,\n options?: PreprMiddlewareOptions\n): NextResponse {\n let response: NextResponse;\n let finalOptions: PreprMiddlewareOptions | undefined;\n\n // Handle overloads\n if (responseOrOptions && 'headers' in responseOrOptions) {\n // Second parameter is NextResponse\n response = responseOrOptions;\n finalOptions = options;\n } else {\n // Second parameter is options or undefined\n response = NextResponse.next();\n finalOptions = responseOrOptions as PreprMiddlewareOptions | undefined;\n }\n\n // Map over search params and set headers\n request.nextUrl.searchParams.forEach((value, key) => {\n switch (key) {\n case 'utm_source':\n response.headers.set('Prepr-Context-utm_source', value);\n break;\n case 'utm_medium':\n response.headers.set('Prepr-Context-utm_medium', value);\n break;\n case 'utm_term':\n response.headers.set('Prepr-Context-utm_term', value);\n break;\n case 'utm_content':\n response.headers.set('Prepr-Context-utm_content', value);\n break;\n case 'utm_campaign':\n response.headers.set('Prepr-Context-utm_campaign', value);\n break;\n }\n });\n\n // Set initial referral header\n const referrer = request.headers.get('referer');\n if (referrer) {\n response.headers.set('Prepr-Context-initial_referral', referrer);\n }\n\n // Set Prepr version header\n response.headers.set('Prepr-Package', version);\n\n let ip: string | null = ipAddress(request) || null;\n\n if (request.headers.get('Cf-Connecting-Ip')) {\n ip = request.headers.get('Cf-Connecting-Ip');\n }\n\n if (ip) {\n response.headers.set('Prepr-Visitor-IP', ip);\n }\n\n // Set HubSpot cookie header\n const hutkCookie = request.cookies.get('hubspotutk')?.value;\n if (hutkCookie) {\n response.headers.set('Prepr-Hubspot-Id', hutkCookie);\n }\n\n // Check for existing Prepr UID cookie or create a new one\n let cookie = request.cookies.get('__prepr_uid')?.value;\n if (!cookie) {\n cookie = crypto.randomUUID();\n response.cookies.set('__prepr_uid', cookie, {\n maxAge: 1 * 365 * 24 * 60, // Set for one year\n });\n response.headers.set('Prepr-Customer-Id-Created', 'true');\n }\n\n // Set the Prepr Customer ID header\n response.headers.set('Prepr-Customer-Id', cookie);\n\n // If preview mode is not enabled, return the response\n if (!finalOptions?.preview || process.env.PREPR_ENV !== 'preview') {\n return response;\n }\n\n // Preview query params always take priority — when the CMS dashboard\n // loads the site in an iframe it controls segments via query params,\n // regardless of the user's Prepr-Preview-Mode cookie in the browser.\n const hasPreviewParams =\n request.nextUrl.searchParams.has('prepr_preview_segment') ||\n request.nextUrl.searchParams.has('prepr_preview_ab');\n\n if (!hasPreviewParams) {\n // Respect preview mode toggle cookie from client\n const previewModeCookie = request.cookies.get('Prepr-Preview-Mode')?.value;\n const previewModeEnabled = previewModeCookie !== 'false';\n\n if (!previewModeEnabled) {\n return response;\n }\n }\n\n // If preview mode is enabled, set additional headers\n response.headers.set('Prepr-Preview-Bar', 'true');\n\n // When loaded inside the Prepr live preview iframe, prepr_hide_bar=true is\n // always present in the URL. In that context, cookies must never be used —\n // the live preview controls segments/variants exclusively via query params.\n // If no query params are present, the default (no segment/variant) should\n // be shown, not whatever the editor's browser cookie happens to contain.\n const isLivePreview =\n request.nextUrl.searchParams.get('prepr_hide_bar') === 'true';\n\n if (!isLivePreview) {\n // Set Prepr Preview Segment and AB test from cookies\n const segmentCookie = request.cookies.get('Prepr-Segments')?.value;\n if (segmentCookie) {\n response.headers.set('Prepr-Segments', segmentCookie);\n }\n\n const abCookie = request.cookies.get('Prepr-ABtesting')?.value;\n if (abCookie) {\n response.headers.set('Prepr-ABtesting', abCookie);\n }\n }\n\n // Set Prepr Preview Segment and AB test headers from query params\n request.nextUrl.searchParams.forEach((value, key) => {\n if (key === 'prepr_preview_ab') {\n response.headers.set('Prepr-ABtesting', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-ABtesting', value);\n }\n }\n\n if (key === 'prepr_preview_segment') {\n response.headers.set('Prepr-Segments', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-Segments', value);\n }\n }\n });\n\n return response;\n}\n"]}
|
package/dist/middleware/index.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import {ipAddress}from'@vercel/functions';import {NextResponse}from'next/server';var h="2.2.
|
|
1
|
+
import {ipAddress}from'@vercel/functions';import {NextResponse}from'next/server';var h="2.2.4";function k(r,n,P){var l,m,x,u,g;let e,i;n&&"headers"in n?(e=n,i=P):(e=NextResponse.next(),i=n),r.nextUrl.searchParams.forEach((t,s)=>{switch(s){case "utm_source":e.headers.set("Prepr-Context-utm_source",t);break;case "utm_medium":e.headers.set("Prepr-Context-utm_medium",t);break;case "utm_term":e.headers.set("Prepr-Context-utm_term",t);break;case "utm_content":e.headers.set("Prepr-Context-utm_content",t);break;case "utm_campaign":e.headers.set("Prepr-Context-utm_campaign",t);break}});let o=r.headers.get("referer");o&&e.headers.set("Prepr-Context-initial_referral",o),e.headers.set("Prepr-Package",h);let d=ipAddress(r)||null;r.headers.get("Cf-Connecting-Ip")&&(d=r.headers.get("Cf-Connecting-Ip")),d&&e.headers.set("Prepr-Visitor-IP",d);let c=(l=r.cookies.get("hubspotutk"))==null?void 0:l.value;c&&e.headers.set("Prepr-Hubspot-Id",c);let p=(m=r.cookies.get("__prepr_uid"))==null?void 0:m.value;if(p||(p=crypto.randomUUID(),e.cookies.set("__prepr_uid",p,{maxAge:1*365*24*60}),e.headers.set("Prepr-Customer-Id-Created","true")),e.headers.set("Prepr-Customer-Id",p),!(i!=null&&i.preview)||process.env.PREPR_ENV!=="preview"||!(r.nextUrl.searchParams.has("prepr_preview_segment")||r.nextUrl.searchParams.has("prepr_preview_ab"))&&!(((x=r.cookies.get("Prepr-Preview-Mode"))==null?void 0:x.value)!=="false"))return e;e.headers.set("Prepr-Preview-Bar","true");let a=r.nextUrl.searchParams.get("prepr_hide_bar")==="true";if(!a){let t=(u=r.cookies.get("Prepr-Segments"))==null?void 0:u.value;t&&e.headers.set("Prepr-Segments",t);let s=(g=r.cookies.get("Prepr-ABtesting"))==null?void 0:g.value;s&&e.headers.set("Prepr-ABtesting",s);}return r.nextUrl.searchParams.forEach((t,s)=>{s==="prepr_preview_ab"&&(e.headers.set("Prepr-ABtesting",t),a||e.cookies.set("Prepr-ABtesting",t)),s==="prepr_preview_segment"&&(e.headers.set("Prepr-Segments",t),a||e.cookies.set("Prepr-Segments",t));}),e}export{k as default};//# sourceMappingURL=index.js.map
|
|
2
2
|
//# sourceMappingURL=index.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../package.json","../../src/middleware/index.ts"],"names":["version","createPreprMiddleware","request","responseOrOptions","options","_a","_b","_c","_d","_e","response","finalOptions","NextResponse","value","key","referrer","ip","ipAddress","hutkCookie","cookie","isLivePreview","segmentCookie","abCookie"],"mappings":"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","file":"index.js","sourcesContent":["{\n \"name\": \"@preprio/prepr-nextjs\",\n \"version\": \"2.2.3\",\n \"description\": \"Next.js package for Prepr CMS preview functionality with advanced debugging and visual editing capabilities\",\n \"main\": \"dist/react/index.cjs\",\n \"types\": \"./dist/react/index.d.ts\",\n \"module\": \"./dist/react/index.js\",\n \"type\": \"module\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"clean\": \"rm -rf dist\",\n \"check\": \"tsc --noEmit && eslint src --ext .ts,.tsx && prettier --check \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"fix\": \"eslint src --ext .ts,.tsx --fix && prettier --write \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"changeset\": \"changeset\",\n \"version\": \"changeset version\",\n \"release\": \"pnpm run build && changeset publish\",\n \"prepublishOnly\": \"pnpm run check && pnpm run build\"\n },\n \"exports\": {\n \"./middleware\": {\n \"import\": \"./dist/middleware/index.js\",\n \"types\": \"./dist/middleware/index.d.ts\",\n \"require\": \"./dist/middleware/index.cjs\"\n },\n \"./server\": {\n \"import\": \"./dist/server/index.js\",\n \"types\": \"./dist/server/index.d.ts\",\n \"require\": \"./dist/server/index.cjs\"\n },\n \"./react\": {\n \"import\": \"./dist/react/index.js\",\n \"types\": \"./dist/react/index.d.ts\",\n \"require\": \"./dist/react/index.cjs\"\n },\n \"./utils\": {\n \"import\": \"./dist/utils/index.js\",\n \"types\": \"./dist/utils/index.d.ts\",\n \"require\": \"./dist/utils/index.cjs\"\n },\n \"./types\": {\n \"import\": \"./dist/types/index.js\",\n \"types\": \"./dist/types/index.d.ts\",\n \"require\": \"./dist/types/index.cjs\"\n },\n \"./index.css\": {\n \"import\": \"./dist/index.css\",\n \"require\": \"./dist/index.css\"\n }\n },\n \"files\": [\n \"dist\",\n \"package.json\"\n ],\n \"keywords\": [\n \"prepr\",\n \"cms\",\n \"nextjs\",\n \"preview\",\n \"visual-editing\",\n \"headless-cms\",\n \"react\",\n \"typescript\",\n \"debug\",\n \"stega\"\n ],\n \"author\": \"Preprio\",\n \"license\": \"MIT\",\n \"packageManager\": \"pnpm@10.5.2\",\n \"devDependencies\": {\n \"@changesets/cli\": \"^2.30.0\",\n \"@eslint/js\": \"^9.39.2\",\n \"@types/node\": \"^25.4.0\",\n \"@types/react\": \"19.2.14\",\n \"@types/react-dom\": \"19.2.3\",\n \"@typescript-eslint/eslint-plugin\": \"^8.57.0\",\n \"@typescript-eslint/parser\": \"^8.57.0\",\n \"autoprefixer\": \"^10.4.27\",\n \"cssnano\": \"^7.1.3\",\n \"eslint\": \"^9.39.2\",\n \"eslint-config-prettier\": \"^10.1.8\",\n \"eslint-plugin-prettier\": \"^5.5.5\",\n \"eslint-plugin-react\": \"^7.37.5\",\n \"eslint-plugin-react-hooks\": \"^7.0.1\",\n \"next\": \"16.1.6\",\n \"postcss\": \"^8.5.8\",\n \"prettier\": \"^3.8.1\",\n \"prettier-plugin-tailwindcss\": \"^0.7.2\",\n \"react\": \"^19.2.4\",\n \"react-dom\": \"^19.2.4\",\n \"tailwindcss\": \"^3.4.17\",\n \"tsup\": \"^8.5.1\",\n \"typescript\": \"^5.9.3\"\n },\n \"peerDependencies\": {\n \"next\": \"^16.0.3 || ^15.0.5 || ^15.1.9 || ^15.2.6 || ^15.3.6 || ^15.4.8 || ^15.5.7 || ^14.0.0 || ^13.0.0\",\n \"react\": \"^19.0.0 || ^18.0.0 || ^17.0.0 \",\n \"react-dom\": \"^19.0.0 || ^18.0.0 || ^17.0.0\"\n },\n \"dependencies\": {\n \"@headlessui/react\": \"^2.2.9\",\n \"@vercel/functions\": \"^3.4.3\",\n \"@vercel/stega\": \"^1.0.0\",\n \"clsx\": \"^2.1.1\",\n \"postcss-cli\": \"^11.0.1\",\n \"tailwind-merge\": \"^3.5.0\",\n \"zustand\": \"^5.0.11\"\n }\n}\n","import { ipAddress } from '@vercel/functions';\nimport { NextRequest, NextResponse } from 'next/server';\nimport { version } from '../../package.json';\n\nexport interface PreprMiddlewareOptions {\n preview?: boolean;\n}\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param response - NextResponse object to chain with\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n response: NextResponse,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Implementation of createPreprMiddleware with function overloads\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n responseOrOptions?: NextResponse | PreprMiddlewareOptions,\n options?: PreprMiddlewareOptions\n): NextResponse {\n let response: NextResponse;\n let finalOptions: PreprMiddlewareOptions | undefined;\n\n // Handle overloads\n if (responseOrOptions && 'headers' in responseOrOptions) {\n // Second parameter is NextResponse\n response = responseOrOptions;\n finalOptions = options;\n } else {\n // Second parameter is options or undefined\n response = NextResponse.next();\n finalOptions = responseOrOptions as PreprMiddlewareOptions | undefined;\n }\n\n // Map over search params and set headers\n request.nextUrl.searchParams.forEach((value, key) => {\n switch (key) {\n case 'utm_source':\n response.headers.set('Prepr-Context-utm_source', value);\n break;\n case 'utm_medium':\n response.headers.set('Prepr-Context-utm_medium', value);\n break;\n case 'utm_term':\n response.headers.set('Prepr-Context-utm_term', value);\n break;\n case 'utm_content':\n response.headers.set('Prepr-Context-utm_content', value);\n break;\n case 'utm_campaign':\n response.headers.set('Prepr-Context-utm_campaign', value);\n break;\n }\n });\n\n // Set initial referral header\n const referrer = request.headers.get('referer');\n if (referrer) {\n response.headers.set('Prepr-Context-initial_referral', referrer);\n }\n\n // Set Prepr version header\n response.headers.set('Prepr-Package', version);\n\n let ip: string | null = ipAddress(request) || null;\n\n if (request.headers.get('Cf-Connecting-Ip')) {\n ip = request.headers.get('Cf-Connecting-Ip');\n }\n\n if (ip) {\n response.headers.set('Prepr-Visitor-IP', ip);\n }\n\n // Set HubSpot cookie header\n const hutkCookie = request.cookies.get('hubspotutk')?.value;\n if (hutkCookie) {\n response.headers.set('Prepr-Hubspot-Id', hutkCookie);\n }\n\n // Check for existing Prepr UID cookie or create a new one\n let cookie = request.cookies.get('__prepr_uid')?.value;\n if (!cookie) {\n cookie = crypto.randomUUID();\n response.cookies.set('__prepr_uid', cookie, {\n maxAge: 1 * 365 * 24 * 60, // Set for one year\n });\n response.headers.set('Prepr-Customer-Id-Created', 'true');\n }\n\n // Set the Prepr Customer ID header\n response.headers.set('Prepr-Customer-Id', cookie);\n\n // If preview mode is not enabled, return the response\n if (!finalOptions?.preview || process.env.PREPR_ENV !== 'preview') {\n return response;\n }\n\n // Preview query params always take priority — when the CMS dashboard\n // loads the site in an iframe it controls segments via query params,\n // regardless of the user's Prepr-Preview-Mode cookie in the browser.\n const hasPreviewParams =\n request.nextUrl.searchParams.has('prepr_preview_segment') ||\n request.nextUrl.searchParams.has('prepr_preview_ab');\n\n if (!hasPreviewParams) {\n // Respect preview mode toggle cookie from client\n const previewModeCookie = request.cookies.get('Prepr-Preview-Mode')?.value;\n const previewModeEnabled = previewModeCookie !== 'false';\n\n if (!previewModeEnabled) {\n return response;\n }\n }\n\n // If preview mode is enabled, set additional headers\n response.headers.set('Prepr-Preview-Bar', 'true');\n\n // When loaded inside the Prepr live preview iframe, prepr_hide_bar=true is\n // always present in the URL. In that context, cookies must never be used —\n // the live preview controls segments/variants exclusively via query params.\n // If no query params are present, the default (no segment/variant) should\n // be shown, not whatever the editor's browser cookie happens to contain.\n const isLivePreview =\n request.nextUrl.searchParams.get('prepr_hide_bar') === 'true';\n\n if (!isLivePreview) {\n // Set Prepr Preview Segment and AB test from cookies\n const segmentCookie = request.cookies.get('Prepr-Segments')?.value;\n if (segmentCookie) {\n response.headers.set('Prepr-Segments', segmentCookie);\n }\n\n const abCookie = request.cookies.get('Prepr-ABtesting')?.value;\n if (abCookie) {\n response.headers.set('Prepr-ABtesting', abCookie);\n }\n }\n\n // Set Prepr Preview Segment and AB test headers from query params\n request.nextUrl.searchParams.forEach((value, key) => {\n if (key === 'prepr_preview_ab') {\n response.headers.set('Prepr-ABtesting', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-ABtesting', value);\n }\n }\n\n if (key === 'prepr_preview_segment') {\n response.headers.set('Prepr-Segments', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-Segments', value);\n }\n }\n });\n\n return response;\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../../package.json","../../src/middleware/index.ts"],"names":["version","createPreprMiddleware","request","responseOrOptions","options","_a","_b","_c","_d","_e","response","finalOptions","NextResponse","value","key","referrer","ip","ipAddress","hutkCookie","cookie","isLivePreview","segmentCookie","abCookie"],"mappings":"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","file":"index.js","sourcesContent":["{\n \"name\": \"@preprio/prepr-nextjs\",\n \"version\": \"2.2.4\",\n \"description\": \"Next.js package for Prepr CMS preview functionality with advanced debugging and visual editing capabilities\",\n \"main\": \"dist/react/index.cjs\",\n \"types\": \"./dist/react/index.d.ts\",\n \"module\": \"./dist/react/index.js\",\n \"type\": \"module\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"clean\": \"rm -rf dist\",\n \"check\": \"tsc --noEmit && eslint src --ext .ts,.tsx && prettier --check \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"fix\": \"eslint src --ext .ts,.tsx --fix && prettier --write \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"changeset\": \"changeset\",\n \"version\": \"changeset version\",\n \"release\": \"pnpm run build && changeset publish\",\n \"prepublishOnly\": \"pnpm run check && pnpm run build\"\n },\n \"exports\": {\n \"./middleware\": {\n \"import\": \"./dist/middleware/index.js\",\n \"types\": \"./dist/middleware/index.d.ts\",\n \"require\": \"./dist/middleware/index.cjs\"\n },\n \"./server\": {\n \"import\": \"./dist/server/index.js\",\n \"types\": \"./dist/server/index.d.ts\",\n \"require\": \"./dist/server/index.cjs\"\n },\n \"./react\": {\n \"import\": \"./dist/react/index.js\",\n \"types\": \"./dist/react/index.d.ts\",\n \"require\": \"./dist/react/index.cjs\"\n },\n \"./utils\": {\n \"import\": \"./dist/utils/index.js\",\n \"types\": \"./dist/utils/index.d.ts\",\n \"require\": \"./dist/utils/index.cjs\"\n },\n \"./types\": {\n \"import\": \"./dist/types/index.js\",\n \"types\": \"./dist/types/index.d.ts\",\n \"require\": \"./dist/types/index.cjs\"\n },\n \"./index.css\": {\n \"import\": \"./dist/index.css\",\n \"require\": \"./dist/index.css\"\n }\n },\n \"files\": [\n \"dist\",\n \"package.json\"\n ],\n \"keywords\": [\n \"prepr\",\n \"cms\",\n \"nextjs\",\n \"preview\",\n \"visual-editing\",\n \"headless-cms\",\n \"react\",\n \"typescript\",\n \"debug\",\n \"stega\"\n ],\n \"author\": \"Preprio\",\n \"license\": \"MIT\",\n \"packageManager\": \"pnpm@10.5.2\",\n \"devDependencies\": {\n \"@changesets/cli\": \"^2.30.0\",\n \"@eslint/js\": \"^9.39.2\",\n \"@types/node\": \"^25.4.0\",\n \"@types/react\": \"19.2.14\",\n \"@types/react-dom\": \"19.2.3\",\n \"@typescript-eslint/eslint-plugin\": \"^8.57.0\",\n \"@typescript-eslint/parser\": \"^8.57.0\",\n \"autoprefixer\": \"^10.4.27\",\n \"cssnano\": \"^7.1.3\",\n \"eslint\": \"^9.39.2\",\n \"eslint-config-prettier\": \"^10.1.8\",\n \"eslint-plugin-prettier\": \"^5.5.5\",\n \"eslint-plugin-react\": \"^7.37.5\",\n \"eslint-plugin-react-hooks\": \"^7.0.1\",\n \"next\": \"16.1.6\",\n \"postcss\": \"^8.5.8\",\n \"prettier\": \"^3.8.1\",\n \"prettier-plugin-tailwindcss\": \"^0.7.2\",\n \"react\": \"^19.2.4\",\n \"react-dom\": \"^19.2.4\",\n \"tailwindcss\": \"^3.4.17\",\n \"tsup\": \"^8.5.1\",\n \"typescript\": \"^5.9.3\"\n },\n \"peerDependencies\": {\n \"next\": \"^16.0.3 || ^15.0.5 || ^15.1.9 || ^15.2.6 || ^15.3.6 || ^15.4.8 || ^15.5.7 || ^14.0.0 || ^13.0.0\",\n \"react\": \"^19.0.0 || ^18.0.0 || ^17.0.0 \",\n \"react-dom\": \"^19.0.0 || ^18.0.0 || ^17.0.0\"\n },\n \"pnpm\": {\n \"overrides\": {\n \"fast-xml-parser\": \"^5.5.0\"\n }\n },\n \"dependencies\": {\n \"@headlessui/react\": \"^2.2.9\",\n \"@vercel/functions\": \"^3.4.3\",\n \"@vercel/stega\": \"^1.0.0\",\n \"clsx\": \"^2.1.1\",\n \"postcss-cli\": \"^11.0.1\",\n \"tailwind-merge\": \"^3.5.0\",\n \"zustand\": \"^5.0.11\"\n }\n}\n","import { ipAddress } from '@vercel/functions';\nimport { NextRequest, NextResponse } from 'next/server';\nimport { version } from '../../package.json';\n\nexport interface PreprMiddlewareOptions {\n preview?: boolean;\n}\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param response - NextResponse object to chain with\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n response: NextResponse,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Implementation of createPreprMiddleware with function overloads\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n responseOrOptions?: NextResponse | PreprMiddlewareOptions,\n options?: PreprMiddlewareOptions\n): NextResponse {\n let response: NextResponse;\n let finalOptions: PreprMiddlewareOptions | undefined;\n\n // Handle overloads\n if (responseOrOptions && 'headers' in responseOrOptions) {\n // Second parameter is NextResponse\n response = responseOrOptions;\n finalOptions = options;\n } else {\n // Second parameter is options or undefined\n response = NextResponse.next();\n finalOptions = responseOrOptions as PreprMiddlewareOptions | undefined;\n }\n\n // Map over search params and set headers\n request.nextUrl.searchParams.forEach((value, key) => {\n switch (key) {\n case 'utm_source':\n response.headers.set('Prepr-Context-utm_source', value);\n break;\n case 'utm_medium':\n response.headers.set('Prepr-Context-utm_medium', value);\n break;\n case 'utm_term':\n response.headers.set('Prepr-Context-utm_term', value);\n break;\n case 'utm_content':\n response.headers.set('Prepr-Context-utm_content', value);\n break;\n case 'utm_campaign':\n response.headers.set('Prepr-Context-utm_campaign', value);\n break;\n }\n });\n\n // Set initial referral header\n const referrer = request.headers.get('referer');\n if (referrer) {\n response.headers.set('Prepr-Context-initial_referral', referrer);\n }\n\n // Set Prepr version header\n response.headers.set('Prepr-Package', version);\n\n let ip: string | null = ipAddress(request) || null;\n\n if (request.headers.get('Cf-Connecting-Ip')) {\n ip = request.headers.get('Cf-Connecting-Ip');\n }\n\n if (ip) {\n response.headers.set('Prepr-Visitor-IP', ip);\n }\n\n // Set HubSpot cookie header\n const hutkCookie = request.cookies.get('hubspotutk')?.value;\n if (hutkCookie) {\n response.headers.set('Prepr-Hubspot-Id', hutkCookie);\n }\n\n // Check for existing Prepr UID cookie or create a new one\n let cookie = request.cookies.get('__prepr_uid')?.value;\n if (!cookie) {\n cookie = crypto.randomUUID();\n response.cookies.set('__prepr_uid', cookie, {\n maxAge: 1 * 365 * 24 * 60, // Set for one year\n });\n response.headers.set('Prepr-Customer-Id-Created', 'true');\n }\n\n // Set the Prepr Customer ID header\n response.headers.set('Prepr-Customer-Id', cookie);\n\n // If preview mode is not enabled, return the response\n if (!finalOptions?.preview || process.env.PREPR_ENV !== 'preview') {\n return response;\n }\n\n // Preview query params always take priority — when the CMS dashboard\n // loads the site in an iframe it controls segments via query params,\n // regardless of the user's Prepr-Preview-Mode cookie in the browser.\n const hasPreviewParams =\n request.nextUrl.searchParams.has('prepr_preview_segment') ||\n request.nextUrl.searchParams.has('prepr_preview_ab');\n\n if (!hasPreviewParams) {\n // Respect preview mode toggle cookie from client\n const previewModeCookie = request.cookies.get('Prepr-Preview-Mode')?.value;\n const previewModeEnabled = previewModeCookie !== 'false';\n\n if (!previewModeEnabled) {\n return response;\n }\n }\n\n // If preview mode is enabled, set additional headers\n response.headers.set('Prepr-Preview-Bar', 'true');\n\n // When loaded inside the Prepr live preview iframe, prepr_hide_bar=true is\n // always present in the URL. In that context, cookies must never be used —\n // the live preview controls segments/variants exclusively via query params.\n // If no query params are present, the default (no segment/variant) should\n // be shown, not whatever the editor's browser cookie happens to contain.\n const isLivePreview =\n request.nextUrl.searchParams.get('prepr_hide_bar') === 'true';\n\n if (!isLivePreview) {\n // Set Prepr Preview Segment and AB test from cookies\n const segmentCookie = request.cookies.get('Prepr-Segments')?.value;\n if (segmentCookie) {\n response.headers.set('Prepr-Segments', segmentCookie);\n }\n\n const abCookie = request.cookies.get('Prepr-ABtesting')?.value;\n if (abCookie) {\n response.headers.set('Prepr-ABtesting', abCookie);\n }\n }\n\n // Set Prepr Preview Segment and AB test headers from query params\n request.nextUrl.searchParams.forEach((value, key) => {\n if (key === 'prepr_preview_ab') {\n response.headers.set('Prepr-ABtesting', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-ABtesting', value);\n }\n }\n\n if (key === 'prepr_preview_segment') {\n response.headers.set('Prepr-Segments', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-Segments', value);\n }\n }\n });\n\n return response;\n}\n"]}
|
package/dist/server/index.cjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
'use strict';var headers=require('next/headers'),functions=require('@vercel/functions'),server=require('next/server');var p=(r,s,t)=>new Promise((e,o)=>{var l=n=>{try{c(t.next(n));}catch(
|
|
1
|
+
'use strict';var headers=require('next/headers'),functions=require('@vercel/functions'),server=require('next/server');var p=(r,s,t)=>new Promise((e,o)=>{var l=n=>{try{c(t.next(n));}catch(u){o(u);}},m=n=>{try{c(t.throw(n));}catch(u){o(u);}},c=n=>n.done?e(n.value):Promise.resolve(n.value).then(l,m);c((t=t.apply(r,s)).next());});var y="2.2.4";var b={version:y};function k(r,s,t){var x,f,h,w,v;let e,o;s&&"headers"in s?(e=s,o=t):(e=server.NextResponse.next(),o=s),r.nextUrl.searchParams.forEach((i,a)=>{switch(a){case "utm_source":e.headers.set("Prepr-Context-utm_source",i);break;case "utm_medium":e.headers.set("Prepr-Context-utm_medium",i);break;case "utm_term":e.headers.set("Prepr-Context-utm_term",i);break;case "utm_content":e.headers.set("Prepr-Context-utm_content",i);break;case "utm_campaign":e.headers.set("Prepr-Context-utm_campaign",i);break}});let l=r.headers.get("referer");l&&e.headers.set("Prepr-Context-initial_referral",l),e.headers.set("Prepr-Package",y);let m=functions.ipAddress(r)||null;r.headers.get("Cf-Connecting-Ip")&&(m=r.headers.get("Cf-Connecting-Ip")),m&&e.headers.set("Prepr-Visitor-IP",m);let c=(x=r.cookies.get("hubspotutk"))==null?void 0:x.value;c&&e.headers.set("Prepr-Hubspot-Id",c);let n=(f=r.cookies.get("__prepr_uid"))==null?void 0:f.value;if(n||(n=crypto.randomUUID(),e.cookies.set("__prepr_uid",n,{maxAge:1*365*24*60}),e.headers.set("Prepr-Customer-Id-Created","true")),e.headers.set("Prepr-Customer-Id",n),!(o!=null&&o.preview)||process.env.PREPR_ENV!=="preview"||!(r.nextUrl.searchParams.has("prepr_preview_segment")||r.nextUrl.searchParams.has("prepr_preview_ab"))&&!(((h=r.cookies.get("Prepr-Preview-Mode"))==null?void 0:h.value)!=="false"))return e;e.headers.set("Prepr-Preview-Bar","true");let g=r.nextUrl.searchParams.get("prepr_hide_bar")==="true";if(!g){let i=(w=r.cookies.get("Prepr-Segments"))==null?void 0:w.value;i&&e.headers.set("Prepr-Segments",i);let a=(v=r.cookies.get("Prepr-ABtesting"))==null?void 0:v.value;a&&e.headers.set("Prepr-ABtesting",a);}return r.nextUrl.searchParams.forEach((i,a)=>{a==="prepr_preview_ab"&&(e.headers.set("Prepr-ABtesting",i),g||e.cookies.set("Prepr-ABtesting",i)),a==="prepr_preview_segment"&&(e.headers.set("Prepr-Segments",i),g||e.cookies.set("Prepr-Segments",i));}),e}var d=class extends Error{constructor(t,e,o,l){super(t);this.code=e;this.context=o;this.originalError=l;this.name="PreprError";}};function P(r){return p(this,null,function*(){return (yield headers.headers()).get(r)})}function $(){return p(this,null,function*(){return P("prepr-customer-id")})}function S(){return p(this,null,function*(){return P("Prepr-Segments")})}function C(){return p(this,null,function*(){return P("Prepr-ABtesting")})}function q(){return p(this,null,function*(){let r={};return (yield headers.headers()).forEach((t,e)=>{(e.startsWith("prepr")||e.startsWith("Prepr"))&&(r[e]=t);}),r})}function N(r){return r?r.startsWith("https://")?{valid:true}:{valid:false,error:"Token must be a valid HTTPS URL"}:{valid:false,error:"Token is required"}}function M(){return process.env.PREPR_ENV==="preview"}function z(r){if(!r)return null;try{let s=new URL(r);if(s.hostname!=="graphql.prepr.io")return null;let t=s.pathname.split("/"),e=t[t.length-1];return e&&e.length>0?e:null}catch(s){return null}}function T(r){return p(this,null,function*(){let s=N(r);if(!s.valid)throw new d(s.error,"INVALID_TOKEN","getPreprEnvironmentSegments");try{let t=yield fetch(r,{headers:{"User-Agent":`Prepr-Preview-Bar/${I()}`,"Content-Type":"application/json"},method:"POST",body:JSON.stringify({query:`{
|
|
2
2
|
_Segments {
|
|
3
3
|
_id
|
|
4
4
|
name
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../package.json","../../src/middleware/index.ts","../../src/server/index.ts"],"names":["version","package_default","createPreprMiddleware","request","responseOrOptions","options","_a","_b","_c","_d","_e","response","finalOptions","NextResponse","value","key","referrer","ip","ipAddress","hutkCookie","cookie","isLivePreview","segmentCookie","abCookie","PreprError","message","code","context","originalError","getPreprHeader","name","__async","headers","getPreprUUID","getActiveSegment","getActiveVariant","getPreprHeaders","preprHeaders","validatePreprToken","token","isPreviewMode","extractAccessToken","graphqlUrl","url","pathParts","e","getPreprEnvironmentSegments","validation","getPackageVersion","json","error","getToolbarProps","data","activeSegment","activeVariant"],"mappings":"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","file":"index.cjs","sourcesContent":["{\n \"name\": \"@preprio/prepr-nextjs\",\n \"version\": \"2.2.3\",\n \"description\": \"Next.js package for Prepr CMS preview functionality with advanced debugging and visual editing capabilities\",\n \"main\": \"dist/react/index.cjs\",\n \"types\": \"./dist/react/index.d.ts\",\n \"module\": \"./dist/react/index.js\",\n \"type\": \"module\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"clean\": \"rm -rf dist\",\n \"check\": \"tsc --noEmit && eslint src --ext .ts,.tsx && prettier --check \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"fix\": \"eslint src --ext .ts,.tsx --fix && prettier --write \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"changeset\": \"changeset\",\n \"version\": \"changeset version\",\n \"release\": \"pnpm run build && changeset publish\",\n \"prepublishOnly\": \"pnpm run check && pnpm run build\"\n },\n \"exports\": {\n \"./middleware\": {\n \"import\": \"./dist/middleware/index.js\",\n \"types\": \"./dist/middleware/index.d.ts\",\n \"require\": \"./dist/middleware/index.cjs\"\n },\n \"./server\": {\n \"import\": \"./dist/server/index.js\",\n \"types\": \"./dist/server/index.d.ts\",\n \"require\": \"./dist/server/index.cjs\"\n },\n \"./react\": {\n \"import\": \"./dist/react/index.js\",\n \"types\": \"./dist/react/index.d.ts\",\n \"require\": \"./dist/react/index.cjs\"\n },\n \"./utils\": {\n \"import\": \"./dist/utils/index.js\",\n \"types\": \"./dist/utils/index.d.ts\",\n \"require\": \"./dist/utils/index.cjs\"\n },\n \"./types\": {\n \"import\": \"./dist/types/index.js\",\n \"types\": \"./dist/types/index.d.ts\",\n \"require\": \"./dist/types/index.cjs\"\n },\n \"./index.css\": {\n \"import\": \"./dist/index.css\",\n \"require\": \"./dist/index.css\"\n }\n },\n \"files\": [\n \"dist\",\n \"package.json\"\n ],\n \"keywords\": [\n \"prepr\",\n \"cms\",\n \"nextjs\",\n \"preview\",\n \"visual-editing\",\n \"headless-cms\",\n \"react\",\n \"typescript\",\n \"debug\",\n \"stega\"\n ],\n \"author\": \"Preprio\",\n \"license\": \"MIT\",\n \"packageManager\": \"pnpm@10.5.2\",\n \"devDependencies\": {\n \"@changesets/cli\": \"^2.30.0\",\n \"@eslint/js\": \"^9.39.2\",\n \"@types/node\": \"^25.4.0\",\n \"@types/react\": \"19.2.14\",\n \"@types/react-dom\": \"19.2.3\",\n \"@typescript-eslint/eslint-plugin\": \"^8.57.0\",\n \"@typescript-eslint/parser\": \"^8.57.0\",\n \"autoprefixer\": \"^10.4.27\",\n \"cssnano\": \"^7.1.3\",\n \"eslint\": \"^9.39.2\",\n \"eslint-config-prettier\": \"^10.1.8\",\n \"eslint-plugin-prettier\": \"^5.5.5\",\n \"eslint-plugin-react\": \"^7.37.5\",\n \"eslint-plugin-react-hooks\": \"^7.0.1\",\n \"next\": \"16.1.6\",\n \"postcss\": \"^8.5.8\",\n \"prettier\": \"^3.8.1\",\n \"prettier-plugin-tailwindcss\": \"^0.7.2\",\n \"react\": \"^19.2.4\",\n \"react-dom\": \"^19.2.4\",\n \"tailwindcss\": \"^3.4.17\",\n \"tsup\": \"^8.5.1\",\n \"typescript\": \"^5.9.3\"\n },\n \"peerDependencies\": {\n \"next\": \"^16.0.3 || ^15.0.5 || ^15.1.9 || ^15.2.6 || ^15.3.6 || ^15.4.8 || ^15.5.7 || ^14.0.0 || ^13.0.0\",\n \"react\": \"^19.0.0 || ^18.0.0 || ^17.0.0 \",\n \"react-dom\": \"^19.0.0 || ^18.0.0 || ^17.0.0\"\n },\n \"dependencies\": {\n \"@headlessui/react\": \"^2.2.9\",\n \"@vercel/functions\": \"^3.4.3\",\n \"@vercel/stega\": \"^1.0.0\",\n \"clsx\": \"^2.1.1\",\n \"postcss-cli\": \"^11.0.1\",\n \"tailwind-merge\": \"^3.5.0\",\n \"zustand\": \"^5.0.11\"\n }\n}\n","import { ipAddress } from '@vercel/functions';\nimport { NextRequest, NextResponse } from 'next/server';\nimport { version } from '../../package.json';\n\nexport interface PreprMiddlewareOptions {\n preview?: boolean;\n}\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param response - NextResponse object to chain with\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n response: NextResponse,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Implementation of createPreprMiddleware with function overloads\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n responseOrOptions?: NextResponse | PreprMiddlewareOptions,\n options?: PreprMiddlewareOptions\n): NextResponse {\n let response: NextResponse;\n let finalOptions: PreprMiddlewareOptions | undefined;\n\n // Handle overloads\n if (responseOrOptions && 'headers' in responseOrOptions) {\n // Second parameter is NextResponse\n response = responseOrOptions;\n finalOptions = options;\n } else {\n // Second parameter is options or undefined\n response = NextResponse.next();\n finalOptions = responseOrOptions as PreprMiddlewareOptions | undefined;\n }\n\n // Map over search params and set headers\n request.nextUrl.searchParams.forEach((value, key) => {\n switch (key) {\n case 'utm_source':\n response.headers.set('Prepr-Context-utm_source', value);\n break;\n case 'utm_medium':\n response.headers.set('Prepr-Context-utm_medium', value);\n break;\n case 'utm_term':\n response.headers.set('Prepr-Context-utm_term', value);\n break;\n case 'utm_content':\n response.headers.set('Prepr-Context-utm_content', value);\n break;\n case 'utm_campaign':\n response.headers.set('Prepr-Context-utm_campaign', value);\n break;\n }\n });\n\n // Set initial referral header\n const referrer = request.headers.get('referer');\n if (referrer) {\n response.headers.set('Prepr-Context-initial_referral', referrer);\n }\n\n // Set Prepr version header\n response.headers.set('Prepr-Package', version);\n\n let ip: string | null = ipAddress(request) || null;\n\n if (request.headers.get('Cf-Connecting-Ip')) {\n ip = request.headers.get('Cf-Connecting-Ip');\n }\n\n if (ip) {\n response.headers.set('Prepr-Visitor-IP', ip);\n }\n\n // Set HubSpot cookie header\n const hutkCookie = request.cookies.get('hubspotutk')?.value;\n if (hutkCookie) {\n response.headers.set('Prepr-Hubspot-Id', hutkCookie);\n }\n\n // Check for existing Prepr UID cookie or create a new one\n let cookie = request.cookies.get('__prepr_uid')?.value;\n if (!cookie) {\n cookie = crypto.randomUUID();\n response.cookies.set('__prepr_uid', cookie, {\n maxAge: 1 * 365 * 24 * 60, // Set for one year\n });\n response.headers.set('Prepr-Customer-Id-Created', 'true');\n }\n\n // Set the Prepr Customer ID header\n response.headers.set('Prepr-Customer-Id', cookie);\n\n // If preview mode is not enabled, return the response\n if (!finalOptions?.preview || process.env.PREPR_ENV !== 'preview') {\n return response;\n }\n\n // Preview query params always take priority — when the CMS dashboard\n // loads the site in an iframe it controls segments via query params,\n // regardless of the user's Prepr-Preview-Mode cookie in the browser.\n const hasPreviewParams =\n request.nextUrl.searchParams.has('prepr_preview_segment') ||\n request.nextUrl.searchParams.has('prepr_preview_ab');\n\n if (!hasPreviewParams) {\n // Respect preview mode toggle cookie from client\n const previewModeCookie = request.cookies.get('Prepr-Preview-Mode')?.value;\n const previewModeEnabled = previewModeCookie !== 'false';\n\n if (!previewModeEnabled) {\n return response;\n }\n }\n\n // If preview mode is enabled, set additional headers\n response.headers.set('Prepr-Preview-Bar', 'true');\n\n // When loaded inside the Prepr live preview iframe, prepr_hide_bar=true is\n // always present in the URL. In that context, cookies must never be used —\n // the live preview controls segments/variants exclusively via query params.\n // If no query params are present, the default (no segment/variant) should\n // be shown, not whatever the editor's browser cookie happens to contain.\n const isLivePreview =\n request.nextUrl.searchParams.get('prepr_hide_bar') === 'true';\n\n if (!isLivePreview) {\n // Set Prepr Preview Segment and AB test from cookies\n const segmentCookie = request.cookies.get('Prepr-Segments')?.value;\n if (segmentCookie) {\n response.headers.set('Prepr-Segments', segmentCookie);\n }\n\n const abCookie = request.cookies.get('Prepr-ABtesting')?.value;\n if (abCookie) {\n response.headers.set('Prepr-ABtesting', abCookie);\n }\n }\n\n // Set Prepr Preview Segment and AB test headers from query params\n request.nextUrl.searchParams.forEach((value, key) => {\n if (key === 'prepr_preview_ab') {\n response.headers.set('Prepr-ABtesting', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-ABtesting', value);\n }\n }\n\n if (key === 'prepr_preview_segment') {\n response.headers.set('Prepr-Segments', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-Segments', value);\n }\n }\n });\n\n return response;\n}\n","import { headers } from 'next/headers';\nimport {\n PreprToolbarProps,\n PreprSegment,\n PreprHeaderName,\n PreprErrorCode,\n} from '../types';\nimport pjson from '../../package.json';\nimport createPreprMiddleware from '../middleware';\n\n/**\n * Custom error class for Prepr-related errors\n */\nexport class PreprError extends Error {\n constructor(\n message: string,\n public readonly code: PreprErrorCode,\n public readonly context?: string,\n public readonly originalError?: Error\n ) {\n super(message);\n this.name = 'PreprError';\n }\n}\n\n/**\n * Internal helper to get a specific Prepr header value\n * @param name - The header name to retrieve\n * @returns The header value or null if not found\n */\nasync function getPreprHeader(name: PreprHeaderName): Promise<string | null> {\n const headersList = await headers();\n return headersList.get(name);\n}\n\n/**\n * Returns the Prepr Customer ID from the headers\n * @returns Prepr Customer ID\n */\nexport async function getPreprUUID(): Promise<string | null> {\n return getPreprHeader('prepr-customer-id');\n}\n\n/**\n * Returns the active segment from the headers\n * @returns Active segment\n */\nexport async function getActiveSegment(): Promise<string | null> {\n return getPreprHeader('Prepr-Segments');\n}\n\n/**\n * Returns the active variant from the headers\n * @returns Active variant\n */\nexport async function getActiveVariant(): Promise<string | null> {\n return getPreprHeader('Prepr-ABtesting');\n}\n\n/**\n * Helper function to retrieve all Prepr headers\n * @returns Object with Prepr headers\n */\nexport async function getPreprHeaders(): Promise<Record<string, string>> {\n const preprHeaders: Record<string, string> = {};\n const headersList = await headers();\n\n headersList.forEach((value, key) => {\n if (key.startsWith('prepr') || key.startsWith('Prepr')) {\n preprHeaders[key] = value;\n }\n });\n\n return preprHeaders;\n}\n\n/**\n * Validates a Prepr GraphQL token\n * @param token - The token to validate\n * @returns Validation result with error details if invalid\n */\nexport function validatePreprToken(token: string): {\n valid: boolean;\n error?: string;\n} {\n if (!token) {\n return { valid: false, error: 'Token is required' };\n }\n if (!token.startsWith('https://')) {\n return { valid: false, error: 'Token must be a valid HTTPS URL' };\n }\n return { valid: true };\n}\n\n/**\n * Checks if the current environment is in preview mode\n * @returns True if in preview mode\n */\nexport function isPreviewMode(): boolean {\n return process.env.PREPR_ENV === 'preview';\n}\n\n/**\n * Extracts the access token from a Prepr GraphQL URL\n * @param graphqlUrl - The full Prepr GraphQL URL\n * @returns The access token or null if invalid\n * @example\n * ```typescript\n * const token = extractAccessToken('https://graphql.prepr.io/abc123')\n * // Returns: 'abc123'\n * ```\n */\nexport function extractAccessToken(graphqlUrl: string): string | null {\n if (!graphqlUrl) return null;\n\n try {\n const url = new URL(graphqlUrl);\n if (url.hostname !== 'graphql.prepr.io') return null;\n\n const pathParts = url.pathname.split('/');\n const token = pathParts[pathParts.length - 1];\n\n return token && token.length > 0 ? token : null;\n } catch {\n return null;\n }\n}\n\n/**\n * Fetches the segments from the Prepr API\n * @param token Prepr GraphQL URL with scope 'segments'\n * @returns Array of PreprSegment\n * @throws PreprError if the request fails\n */\nexport async function getPreprEnvironmentSegments(\n token: string\n): Promise<PreprSegment[]> {\n const validation = validatePreprToken(token);\n if (!validation.valid) {\n throw new PreprError(\n validation.error!,\n 'INVALID_TOKEN',\n 'getPreprEnvironmentSegments'\n );\n }\n\n try {\n const response = await fetch(token, {\n headers: {\n 'User-Agent': `Prepr-Preview-Bar/${getPackageVersion()}`,\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n body: JSON.stringify({\n query: `{\n _Segments {\n _id\n name\n }\n }`,\n }),\n });\n\n if (!response.ok) {\n throw new PreprError(\n `HTTP ${response.status}: ${response.statusText}`,\n 'HTTP_ERROR',\n 'getPreprEnvironmentSegments'\n );\n }\n\n const json = await response.json();\n\n if (!json || !json.data || !json.data._Segments) {\n throw new PreprError(\n 'Invalid response format from Prepr API',\n 'INVALID_RESPONSE',\n 'getPreprEnvironmentSegments'\n );\n }\n\n return json.data._Segments as PreprSegment[];\n } catch (error) {\n if (error instanceof PreprError) {\n throw error;\n }\n throw new PreprError(\n 'Failed to fetch segments from Prepr API',\n 'FETCH_ERROR',\n 'getPreprEnvironmentSegments',\n error instanceof Error ? error : new Error(String(error))\n );\n }\n}\n\n/**\n * Fetches all the necessary previewbar props\n * @param token Prepr GraphQL URL with scope 'segments'\n * @returns Object with activeSegment, activeVariant and data\n */\nexport async function getToolbarProps(\n token: string\n): Promise<PreprToolbarProps> {\n let data: PreprSegment[] = [];\n let activeSegment: string | null = null;\n let activeVariant: string | null = null;\n\n // Prevent unnecessary function calling in production\n if (isPreviewMode()) {\n try {\n data = await getPreprEnvironmentSegments(token);\n activeSegment = await getActiveSegment();\n activeVariant = await getActiveVariant();\n } catch (error) {\n // In preview mode, we should still return props even if API fails\n console.error('Failed to fetch toolbar props:', error);\n // Return empty data to prevent toolbar from crashing\n data = [];\n }\n }\n\n return {\n activeSegment,\n activeVariant,\n data,\n };\n}\n\nfunction getPackageVersion() {\n return pjson.version;\n}\n\nexport { createPreprMiddleware };\n"]}
|
|
1
|
+
{"version":3,"sources":["../../package.json","../../src/middleware/index.ts","../../src/server/index.ts"],"names":["version","package_default","createPreprMiddleware","request","responseOrOptions","options","_a","_b","_c","_d","_e","response","finalOptions","NextResponse","value","key","referrer","ip","ipAddress","hutkCookie","cookie","isLivePreview","segmentCookie","abCookie","PreprError","message","code","context","originalError","getPreprHeader","name","__async","headers","getPreprUUID","getActiveSegment","getActiveVariant","getPreprHeaders","preprHeaders","validatePreprToken","token","isPreviewMode","extractAccessToken","graphqlUrl","url","pathParts","e","getPreprEnvironmentSegments","validation","getPackageVersion","json","error","getToolbarProps","data","activeSegment","activeVariant"],"mappings":"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","file":"index.cjs","sourcesContent":["{\n \"name\": \"@preprio/prepr-nextjs\",\n \"version\": \"2.2.4\",\n \"description\": \"Next.js package for Prepr CMS preview functionality with advanced debugging and visual editing capabilities\",\n \"main\": \"dist/react/index.cjs\",\n \"types\": \"./dist/react/index.d.ts\",\n \"module\": \"./dist/react/index.js\",\n \"type\": \"module\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"clean\": \"rm -rf dist\",\n \"check\": \"tsc --noEmit && eslint src --ext .ts,.tsx && prettier --check \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"fix\": \"eslint src --ext .ts,.tsx --fix && prettier --write \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"changeset\": \"changeset\",\n \"version\": \"changeset version\",\n \"release\": \"pnpm run build && changeset publish\",\n \"prepublishOnly\": \"pnpm run check && pnpm run build\"\n },\n \"exports\": {\n \"./middleware\": {\n \"import\": \"./dist/middleware/index.js\",\n \"types\": \"./dist/middleware/index.d.ts\",\n \"require\": \"./dist/middleware/index.cjs\"\n },\n \"./server\": {\n \"import\": \"./dist/server/index.js\",\n \"types\": \"./dist/server/index.d.ts\",\n \"require\": \"./dist/server/index.cjs\"\n },\n \"./react\": {\n \"import\": \"./dist/react/index.js\",\n \"types\": \"./dist/react/index.d.ts\",\n \"require\": \"./dist/react/index.cjs\"\n },\n \"./utils\": {\n \"import\": \"./dist/utils/index.js\",\n \"types\": \"./dist/utils/index.d.ts\",\n \"require\": \"./dist/utils/index.cjs\"\n },\n \"./types\": {\n \"import\": \"./dist/types/index.js\",\n \"types\": \"./dist/types/index.d.ts\",\n \"require\": \"./dist/types/index.cjs\"\n },\n \"./index.css\": {\n \"import\": \"./dist/index.css\",\n \"require\": \"./dist/index.css\"\n }\n },\n \"files\": [\n \"dist\",\n \"package.json\"\n ],\n \"keywords\": [\n \"prepr\",\n \"cms\",\n \"nextjs\",\n \"preview\",\n \"visual-editing\",\n \"headless-cms\",\n \"react\",\n \"typescript\",\n \"debug\",\n \"stega\"\n ],\n \"author\": \"Preprio\",\n \"license\": \"MIT\",\n \"packageManager\": \"pnpm@10.5.2\",\n \"devDependencies\": {\n \"@changesets/cli\": \"^2.30.0\",\n \"@eslint/js\": \"^9.39.2\",\n \"@types/node\": \"^25.4.0\",\n \"@types/react\": \"19.2.14\",\n \"@types/react-dom\": \"19.2.3\",\n \"@typescript-eslint/eslint-plugin\": \"^8.57.0\",\n \"@typescript-eslint/parser\": \"^8.57.0\",\n \"autoprefixer\": \"^10.4.27\",\n \"cssnano\": \"^7.1.3\",\n \"eslint\": \"^9.39.2\",\n \"eslint-config-prettier\": \"^10.1.8\",\n \"eslint-plugin-prettier\": \"^5.5.5\",\n \"eslint-plugin-react\": \"^7.37.5\",\n \"eslint-plugin-react-hooks\": \"^7.0.1\",\n \"next\": \"16.1.6\",\n \"postcss\": \"^8.5.8\",\n \"prettier\": \"^3.8.1\",\n \"prettier-plugin-tailwindcss\": \"^0.7.2\",\n \"react\": \"^19.2.4\",\n \"react-dom\": \"^19.2.4\",\n \"tailwindcss\": \"^3.4.17\",\n \"tsup\": \"^8.5.1\",\n \"typescript\": \"^5.9.3\"\n },\n \"peerDependencies\": {\n \"next\": \"^16.0.3 || ^15.0.5 || ^15.1.9 || ^15.2.6 || ^15.3.6 || ^15.4.8 || ^15.5.7 || ^14.0.0 || ^13.0.0\",\n \"react\": \"^19.0.0 || ^18.0.0 || ^17.0.0 \",\n \"react-dom\": \"^19.0.0 || ^18.0.0 || ^17.0.0\"\n },\n \"pnpm\": {\n \"overrides\": {\n \"fast-xml-parser\": \"^5.5.0\"\n }\n },\n \"dependencies\": {\n \"@headlessui/react\": \"^2.2.9\",\n \"@vercel/functions\": \"^3.4.3\",\n \"@vercel/stega\": \"^1.0.0\",\n \"clsx\": \"^2.1.1\",\n \"postcss-cli\": \"^11.0.1\",\n \"tailwind-merge\": \"^3.5.0\",\n \"zustand\": \"^5.0.11\"\n }\n}\n","import { ipAddress } from '@vercel/functions';\nimport { NextRequest, NextResponse } from 'next/server';\nimport { version } from '../../package.json';\n\nexport interface PreprMiddlewareOptions {\n preview?: boolean;\n}\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param response - NextResponse object to chain with\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n response: NextResponse,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Implementation of createPreprMiddleware with function overloads\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n responseOrOptions?: NextResponse | PreprMiddlewareOptions,\n options?: PreprMiddlewareOptions\n): NextResponse {\n let response: NextResponse;\n let finalOptions: PreprMiddlewareOptions | undefined;\n\n // Handle overloads\n if (responseOrOptions && 'headers' in responseOrOptions) {\n // Second parameter is NextResponse\n response = responseOrOptions;\n finalOptions = options;\n } else {\n // Second parameter is options or undefined\n response = NextResponse.next();\n finalOptions = responseOrOptions as PreprMiddlewareOptions | undefined;\n }\n\n // Map over search params and set headers\n request.nextUrl.searchParams.forEach((value, key) => {\n switch (key) {\n case 'utm_source':\n response.headers.set('Prepr-Context-utm_source', value);\n break;\n case 'utm_medium':\n response.headers.set('Prepr-Context-utm_medium', value);\n break;\n case 'utm_term':\n response.headers.set('Prepr-Context-utm_term', value);\n break;\n case 'utm_content':\n response.headers.set('Prepr-Context-utm_content', value);\n break;\n case 'utm_campaign':\n response.headers.set('Prepr-Context-utm_campaign', value);\n break;\n }\n });\n\n // Set initial referral header\n const referrer = request.headers.get('referer');\n if (referrer) {\n response.headers.set('Prepr-Context-initial_referral', referrer);\n }\n\n // Set Prepr version header\n response.headers.set('Prepr-Package', version);\n\n let ip: string | null = ipAddress(request) || null;\n\n if (request.headers.get('Cf-Connecting-Ip')) {\n ip = request.headers.get('Cf-Connecting-Ip');\n }\n\n if (ip) {\n response.headers.set('Prepr-Visitor-IP', ip);\n }\n\n // Set HubSpot cookie header\n const hutkCookie = request.cookies.get('hubspotutk')?.value;\n if (hutkCookie) {\n response.headers.set('Prepr-Hubspot-Id', hutkCookie);\n }\n\n // Check for existing Prepr UID cookie or create a new one\n let cookie = request.cookies.get('__prepr_uid')?.value;\n if (!cookie) {\n cookie = crypto.randomUUID();\n response.cookies.set('__prepr_uid', cookie, {\n maxAge: 1 * 365 * 24 * 60, // Set for one year\n });\n response.headers.set('Prepr-Customer-Id-Created', 'true');\n }\n\n // Set the Prepr Customer ID header\n response.headers.set('Prepr-Customer-Id', cookie);\n\n // If preview mode is not enabled, return the response\n if (!finalOptions?.preview || process.env.PREPR_ENV !== 'preview') {\n return response;\n }\n\n // Preview query params always take priority — when the CMS dashboard\n // loads the site in an iframe it controls segments via query params,\n // regardless of the user's Prepr-Preview-Mode cookie in the browser.\n const hasPreviewParams =\n request.nextUrl.searchParams.has('prepr_preview_segment') ||\n request.nextUrl.searchParams.has('prepr_preview_ab');\n\n if (!hasPreviewParams) {\n // Respect preview mode toggle cookie from client\n const previewModeCookie = request.cookies.get('Prepr-Preview-Mode')?.value;\n const previewModeEnabled = previewModeCookie !== 'false';\n\n if (!previewModeEnabled) {\n return response;\n }\n }\n\n // If preview mode is enabled, set additional headers\n response.headers.set('Prepr-Preview-Bar', 'true');\n\n // When loaded inside the Prepr live preview iframe, prepr_hide_bar=true is\n // always present in the URL. In that context, cookies must never be used —\n // the live preview controls segments/variants exclusively via query params.\n // If no query params are present, the default (no segment/variant) should\n // be shown, not whatever the editor's browser cookie happens to contain.\n const isLivePreview =\n request.nextUrl.searchParams.get('prepr_hide_bar') === 'true';\n\n if (!isLivePreview) {\n // Set Prepr Preview Segment and AB test from cookies\n const segmentCookie = request.cookies.get('Prepr-Segments')?.value;\n if (segmentCookie) {\n response.headers.set('Prepr-Segments', segmentCookie);\n }\n\n const abCookie = request.cookies.get('Prepr-ABtesting')?.value;\n if (abCookie) {\n response.headers.set('Prepr-ABtesting', abCookie);\n }\n }\n\n // Set Prepr Preview Segment and AB test headers from query params\n request.nextUrl.searchParams.forEach((value, key) => {\n if (key === 'prepr_preview_ab') {\n response.headers.set('Prepr-ABtesting', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-ABtesting', value);\n }\n }\n\n if (key === 'prepr_preview_segment') {\n response.headers.set('Prepr-Segments', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-Segments', value);\n }\n }\n });\n\n return response;\n}\n","import { headers } from 'next/headers';\nimport {\n PreprToolbarProps,\n PreprSegment,\n PreprHeaderName,\n PreprErrorCode,\n} from '../types';\nimport pjson from '../../package.json';\nimport createPreprMiddleware from '../middleware';\n\n/**\n * Custom error class for Prepr-related errors\n */\nexport class PreprError extends Error {\n constructor(\n message: string,\n public readonly code: PreprErrorCode,\n public readonly context?: string,\n public readonly originalError?: Error\n ) {\n super(message);\n this.name = 'PreprError';\n }\n}\n\n/**\n * Internal helper to get a specific Prepr header value\n * @param name - The header name to retrieve\n * @returns The header value or null if not found\n */\nasync function getPreprHeader(name: PreprHeaderName): Promise<string | null> {\n const headersList = await headers();\n return headersList.get(name);\n}\n\n/**\n * Returns the Prepr Customer ID from the headers\n * @returns Prepr Customer ID\n */\nexport async function getPreprUUID(): Promise<string | null> {\n return getPreprHeader('prepr-customer-id');\n}\n\n/**\n * Returns the active segment from the headers\n * @returns Active segment\n */\nexport async function getActiveSegment(): Promise<string | null> {\n return getPreprHeader('Prepr-Segments');\n}\n\n/**\n * Returns the active variant from the headers\n * @returns Active variant\n */\nexport async function getActiveVariant(): Promise<string | null> {\n return getPreprHeader('Prepr-ABtesting');\n}\n\n/**\n * Helper function to retrieve all Prepr headers\n * @returns Object with Prepr headers\n */\nexport async function getPreprHeaders(): Promise<Record<string, string>> {\n const preprHeaders: Record<string, string> = {};\n const headersList = await headers();\n\n headersList.forEach((value, key) => {\n if (key.startsWith('prepr') || key.startsWith('Prepr')) {\n preprHeaders[key] = value;\n }\n });\n\n return preprHeaders;\n}\n\n/**\n * Validates a Prepr GraphQL token\n * @param token - The token to validate\n * @returns Validation result with error details if invalid\n */\nexport function validatePreprToken(token: string): {\n valid: boolean;\n error?: string;\n} {\n if (!token) {\n return { valid: false, error: 'Token is required' };\n }\n if (!token.startsWith('https://')) {\n return { valid: false, error: 'Token must be a valid HTTPS URL' };\n }\n return { valid: true };\n}\n\n/**\n * Checks if the current environment is in preview mode\n * @returns True if in preview mode\n */\nexport function isPreviewMode(): boolean {\n return process.env.PREPR_ENV === 'preview';\n}\n\n/**\n * Extracts the access token from a Prepr GraphQL URL\n * @param graphqlUrl - The full Prepr GraphQL URL\n * @returns The access token or null if invalid\n * @example\n * ```typescript\n * const token = extractAccessToken('https://graphql.prepr.io/abc123')\n * // Returns: 'abc123'\n * ```\n */\nexport function extractAccessToken(graphqlUrl: string): string | null {\n if (!graphqlUrl) return null;\n\n try {\n const url = new URL(graphqlUrl);\n if (url.hostname !== 'graphql.prepr.io') return null;\n\n const pathParts = url.pathname.split('/');\n const token = pathParts[pathParts.length - 1];\n\n return token && token.length > 0 ? token : null;\n } catch {\n return null;\n }\n}\n\n/**\n * Fetches the segments from the Prepr API\n * @param token Prepr GraphQL URL with scope 'segments'\n * @returns Array of PreprSegment\n * @throws PreprError if the request fails\n */\nexport async function getPreprEnvironmentSegments(\n token: string\n): Promise<PreprSegment[]> {\n const validation = validatePreprToken(token);\n if (!validation.valid) {\n throw new PreprError(\n validation.error!,\n 'INVALID_TOKEN',\n 'getPreprEnvironmentSegments'\n );\n }\n\n try {\n const response = await fetch(token, {\n headers: {\n 'User-Agent': `Prepr-Preview-Bar/${getPackageVersion()}`,\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n body: JSON.stringify({\n query: `{\n _Segments {\n _id\n name\n }\n }`,\n }),\n });\n\n if (!response.ok) {\n throw new PreprError(\n `HTTP ${response.status}: ${response.statusText}`,\n 'HTTP_ERROR',\n 'getPreprEnvironmentSegments'\n );\n }\n\n const json = await response.json();\n\n if (!json || !json.data || !json.data._Segments) {\n throw new PreprError(\n 'Invalid response format from Prepr API',\n 'INVALID_RESPONSE',\n 'getPreprEnvironmentSegments'\n );\n }\n\n return json.data._Segments as PreprSegment[];\n } catch (error) {\n if (error instanceof PreprError) {\n throw error;\n }\n throw new PreprError(\n 'Failed to fetch segments from Prepr API',\n 'FETCH_ERROR',\n 'getPreprEnvironmentSegments',\n error instanceof Error ? error : new Error(String(error))\n );\n }\n}\n\n/**\n * Fetches all the necessary previewbar props\n * @param token Prepr GraphQL URL with scope 'segments'\n * @returns Object with activeSegment, activeVariant and data\n */\nexport async function getToolbarProps(\n token: string\n): Promise<PreprToolbarProps> {\n let data: PreprSegment[] = [];\n let activeSegment: string | null = null;\n let activeVariant: string | null = null;\n\n // Prevent unnecessary function calling in production\n if (isPreviewMode()) {\n try {\n data = await getPreprEnvironmentSegments(token);\n activeSegment = await getActiveSegment();\n activeVariant = await getActiveVariant();\n } catch (error) {\n // In preview mode, we should still return props even if API fails\n console.error('Failed to fetch toolbar props:', error);\n // Return empty data to prevent toolbar from crashing\n data = [];\n }\n }\n\n return {\n activeSegment,\n activeVariant,\n data,\n };\n}\n\nfunction getPackageVersion() {\n return pjson.version;\n}\n\nexport { createPreprMiddleware };\n"]}
|
package/dist/server/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {headers}from'next/headers';import {ipAddress}from'@vercel/functions';import {NextResponse}from'next/server';var p=(r,s,t)=>new Promise((e,o)=>{var l=n=>{try{c(t.next(n));}catch(
|
|
1
|
+
import {headers}from'next/headers';import {ipAddress}from'@vercel/functions';import {NextResponse}from'next/server';var p=(r,s,t)=>new Promise((e,o)=>{var l=n=>{try{c(t.next(n));}catch(u){o(u);}},m=n=>{try{c(t.throw(n));}catch(u){o(u);}},c=n=>n.done?e(n.value):Promise.resolve(n.value).then(l,m);c((t=t.apply(r,s)).next());});var y="2.2.4";var b={version:y};function k(r,s,t){var x,f,h,w,v;let e,o;s&&"headers"in s?(e=s,o=t):(e=NextResponse.next(),o=s),r.nextUrl.searchParams.forEach((i,a)=>{switch(a){case "utm_source":e.headers.set("Prepr-Context-utm_source",i);break;case "utm_medium":e.headers.set("Prepr-Context-utm_medium",i);break;case "utm_term":e.headers.set("Prepr-Context-utm_term",i);break;case "utm_content":e.headers.set("Prepr-Context-utm_content",i);break;case "utm_campaign":e.headers.set("Prepr-Context-utm_campaign",i);break}});let l=r.headers.get("referer");l&&e.headers.set("Prepr-Context-initial_referral",l),e.headers.set("Prepr-Package",y);let m=ipAddress(r)||null;r.headers.get("Cf-Connecting-Ip")&&(m=r.headers.get("Cf-Connecting-Ip")),m&&e.headers.set("Prepr-Visitor-IP",m);let c=(x=r.cookies.get("hubspotutk"))==null?void 0:x.value;c&&e.headers.set("Prepr-Hubspot-Id",c);let n=(f=r.cookies.get("__prepr_uid"))==null?void 0:f.value;if(n||(n=crypto.randomUUID(),e.cookies.set("__prepr_uid",n,{maxAge:1*365*24*60}),e.headers.set("Prepr-Customer-Id-Created","true")),e.headers.set("Prepr-Customer-Id",n),!(o!=null&&o.preview)||process.env.PREPR_ENV!=="preview"||!(r.nextUrl.searchParams.has("prepr_preview_segment")||r.nextUrl.searchParams.has("prepr_preview_ab"))&&!(((h=r.cookies.get("Prepr-Preview-Mode"))==null?void 0:h.value)!=="false"))return e;e.headers.set("Prepr-Preview-Bar","true");let g=r.nextUrl.searchParams.get("prepr_hide_bar")==="true";if(!g){let i=(w=r.cookies.get("Prepr-Segments"))==null?void 0:w.value;i&&e.headers.set("Prepr-Segments",i);let a=(v=r.cookies.get("Prepr-ABtesting"))==null?void 0:v.value;a&&e.headers.set("Prepr-ABtesting",a);}return r.nextUrl.searchParams.forEach((i,a)=>{a==="prepr_preview_ab"&&(e.headers.set("Prepr-ABtesting",i),g||e.cookies.set("Prepr-ABtesting",i)),a==="prepr_preview_segment"&&(e.headers.set("Prepr-Segments",i),g||e.cookies.set("Prepr-Segments",i));}),e}var d=class extends Error{constructor(t,e,o,l){super(t);this.code=e;this.context=o;this.originalError=l;this.name="PreprError";}};function P(r){return p(this,null,function*(){return (yield headers()).get(r)})}function $(){return p(this,null,function*(){return P("prepr-customer-id")})}function S(){return p(this,null,function*(){return P("Prepr-Segments")})}function C(){return p(this,null,function*(){return P("Prepr-ABtesting")})}function q(){return p(this,null,function*(){let r={};return (yield headers()).forEach((t,e)=>{(e.startsWith("prepr")||e.startsWith("Prepr"))&&(r[e]=t);}),r})}function N(r){return r?r.startsWith("https://")?{valid:true}:{valid:false,error:"Token must be a valid HTTPS URL"}:{valid:false,error:"Token is required"}}function M(){return process.env.PREPR_ENV==="preview"}function z(r){if(!r)return null;try{let s=new URL(r);if(s.hostname!=="graphql.prepr.io")return null;let t=s.pathname.split("/"),e=t[t.length-1];return e&&e.length>0?e:null}catch(s){return null}}function T(r){return p(this,null,function*(){let s=N(r);if(!s.valid)throw new d(s.error,"INVALID_TOKEN","getPreprEnvironmentSegments");try{let t=yield fetch(r,{headers:{"User-Agent":`Prepr-Preview-Bar/${I()}`,"Content-Type":"application/json"},method:"POST",body:JSON.stringify({query:`{
|
|
2
2
|
_Segments {
|
|
3
3
|
_id
|
|
4
4
|
name
|
package/dist/server/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../../package.json","../../src/middleware/index.ts","../../src/server/index.ts"],"names":["version","package_default","createPreprMiddleware","request","responseOrOptions","options","_a","_b","_c","_d","_e","response","finalOptions","NextResponse","value","key","referrer","ip","ipAddress","hutkCookie","cookie","isLivePreview","segmentCookie","abCookie","PreprError","message","code","context","originalError","getPreprHeader","name","__async","headers","getPreprUUID","getActiveSegment","getActiveVariant","getPreprHeaders","preprHeaders","validatePreprToken","token","isPreviewMode","extractAccessToken","graphqlUrl","url","pathParts","e","getPreprEnvironmentSegments","validation","getPackageVersion","json","error","getToolbarProps","data","activeSegment","activeVariant"],"mappings":"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","file":"index.js","sourcesContent":["{\n \"name\": \"@preprio/prepr-nextjs\",\n \"version\": \"2.2.3\",\n \"description\": \"Next.js package for Prepr CMS preview functionality with advanced debugging and visual editing capabilities\",\n \"main\": \"dist/react/index.cjs\",\n \"types\": \"./dist/react/index.d.ts\",\n \"module\": \"./dist/react/index.js\",\n \"type\": \"module\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"clean\": \"rm -rf dist\",\n \"check\": \"tsc --noEmit && eslint src --ext .ts,.tsx && prettier --check \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"fix\": \"eslint src --ext .ts,.tsx --fix && prettier --write \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"changeset\": \"changeset\",\n \"version\": \"changeset version\",\n \"release\": \"pnpm run build && changeset publish\",\n \"prepublishOnly\": \"pnpm run check && pnpm run build\"\n },\n \"exports\": {\n \"./middleware\": {\n \"import\": \"./dist/middleware/index.js\",\n \"types\": \"./dist/middleware/index.d.ts\",\n \"require\": \"./dist/middleware/index.cjs\"\n },\n \"./server\": {\n \"import\": \"./dist/server/index.js\",\n \"types\": \"./dist/server/index.d.ts\",\n \"require\": \"./dist/server/index.cjs\"\n },\n \"./react\": {\n \"import\": \"./dist/react/index.js\",\n \"types\": \"./dist/react/index.d.ts\",\n \"require\": \"./dist/react/index.cjs\"\n },\n \"./utils\": {\n \"import\": \"./dist/utils/index.js\",\n \"types\": \"./dist/utils/index.d.ts\",\n \"require\": \"./dist/utils/index.cjs\"\n },\n \"./types\": {\n \"import\": \"./dist/types/index.js\",\n \"types\": \"./dist/types/index.d.ts\",\n \"require\": \"./dist/types/index.cjs\"\n },\n \"./index.css\": {\n \"import\": \"./dist/index.css\",\n \"require\": \"./dist/index.css\"\n }\n },\n \"files\": [\n \"dist\",\n \"package.json\"\n ],\n \"keywords\": [\n \"prepr\",\n \"cms\",\n \"nextjs\",\n \"preview\",\n \"visual-editing\",\n \"headless-cms\",\n \"react\",\n \"typescript\",\n \"debug\",\n \"stega\"\n ],\n \"author\": \"Preprio\",\n \"license\": \"MIT\",\n \"packageManager\": \"pnpm@10.5.2\",\n \"devDependencies\": {\n \"@changesets/cli\": \"^2.30.0\",\n \"@eslint/js\": \"^9.39.2\",\n \"@types/node\": \"^25.4.0\",\n \"@types/react\": \"19.2.14\",\n \"@types/react-dom\": \"19.2.3\",\n \"@typescript-eslint/eslint-plugin\": \"^8.57.0\",\n \"@typescript-eslint/parser\": \"^8.57.0\",\n \"autoprefixer\": \"^10.4.27\",\n \"cssnano\": \"^7.1.3\",\n \"eslint\": \"^9.39.2\",\n \"eslint-config-prettier\": \"^10.1.8\",\n \"eslint-plugin-prettier\": \"^5.5.5\",\n \"eslint-plugin-react\": \"^7.37.5\",\n \"eslint-plugin-react-hooks\": \"^7.0.1\",\n \"next\": \"16.1.6\",\n \"postcss\": \"^8.5.8\",\n \"prettier\": \"^3.8.1\",\n \"prettier-plugin-tailwindcss\": \"^0.7.2\",\n \"react\": \"^19.2.4\",\n \"react-dom\": \"^19.2.4\",\n \"tailwindcss\": \"^3.4.17\",\n \"tsup\": \"^8.5.1\",\n \"typescript\": \"^5.9.3\"\n },\n \"peerDependencies\": {\n \"next\": \"^16.0.3 || ^15.0.5 || ^15.1.9 || ^15.2.6 || ^15.3.6 || ^15.4.8 || ^15.5.7 || ^14.0.0 || ^13.0.0\",\n \"react\": \"^19.0.0 || ^18.0.0 || ^17.0.0 \",\n \"react-dom\": \"^19.0.0 || ^18.0.0 || ^17.0.0\"\n },\n \"dependencies\": {\n \"@headlessui/react\": \"^2.2.9\",\n \"@vercel/functions\": \"^3.4.3\",\n \"@vercel/stega\": \"^1.0.0\",\n \"clsx\": \"^2.1.1\",\n \"postcss-cli\": \"^11.0.1\",\n \"tailwind-merge\": \"^3.5.0\",\n \"zustand\": \"^5.0.11\"\n }\n}\n","import { ipAddress } from '@vercel/functions';\nimport { NextRequest, NextResponse } from 'next/server';\nimport { version } from '../../package.json';\n\nexport interface PreprMiddlewareOptions {\n preview?: boolean;\n}\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param response - NextResponse object to chain with\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n response: NextResponse,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Implementation of createPreprMiddleware with function overloads\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n responseOrOptions?: NextResponse | PreprMiddlewareOptions,\n options?: PreprMiddlewareOptions\n): NextResponse {\n let response: NextResponse;\n let finalOptions: PreprMiddlewareOptions | undefined;\n\n // Handle overloads\n if (responseOrOptions && 'headers' in responseOrOptions) {\n // Second parameter is NextResponse\n response = responseOrOptions;\n finalOptions = options;\n } else {\n // Second parameter is options or undefined\n response = NextResponse.next();\n finalOptions = responseOrOptions as PreprMiddlewareOptions | undefined;\n }\n\n // Map over search params and set headers\n request.nextUrl.searchParams.forEach((value, key) => {\n switch (key) {\n case 'utm_source':\n response.headers.set('Prepr-Context-utm_source', value);\n break;\n case 'utm_medium':\n response.headers.set('Prepr-Context-utm_medium', value);\n break;\n case 'utm_term':\n response.headers.set('Prepr-Context-utm_term', value);\n break;\n case 'utm_content':\n response.headers.set('Prepr-Context-utm_content', value);\n break;\n case 'utm_campaign':\n response.headers.set('Prepr-Context-utm_campaign', value);\n break;\n }\n });\n\n // Set initial referral header\n const referrer = request.headers.get('referer');\n if (referrer) {\n response.headers.set('Prepr-Context-initial_referral', referrer);\n }\n\n // Set Prepr version header\n response.headers.set('Prepr-Package', version);\n\n let ip: string | null = ipAddress(request) || null;\n\n if (request.headers.get('Cf-Connecting-Ip')) {\n ip = request.headers.get('Cf-Connecting-Ip');\n }\n\n if (ip) {\n response.headers.set('Prepr-Visitor-IP', ip);\n }\n\n // Set HubSpot cookie header\n const hutkCookie = request.cookies.get('hubspotutk')?.value;\n if (hutkCookie) {\n response.headers.set('Prepr-Hubspot-Id', hutkCookie);\n }\n\n // Check for existing Prepr UID cookie or create a new one\n let cookie = request.cookies.get('__prepr_uid')?.value;\n if (!cookie) {\n cookie = crypto.randomUUID();\n response.cookies.set('__prepr_uid', cookie, {\n maxAge: 1 * 365 * 24 * 60, // Set for one year\n });\n response.headers.set('Prepr-Customer-Id-Created', 'true');\n }\n\n // Set the Prepr Customer ID header\n response.headers.set('Prepr-Customer-Id', cookie);\n\n // If preview mode is not enabled, return the response\n if (!finalOptions?.preview || process.env.PREPR_ENV !== 'preview') {\n return response;\n }\n\n // Preview query params always take priority — when the CMS dashboard\n // loads the site in an iframe it controls segments via query params,\n // regardless of the user's Prepr-Preview-Mode cookie in the browser.\n const hasPreviewParams =\n request.nextUrl.searchParams.has('prepr_preview_segment') ||\n request.nextUrl.searchParams.has('prepr_preview_ab');\n\n if (!hasPreviewParams) {\n // Respect preview mode toggle cookie from client\n const previewModeCookie = request.cookies.get('Prepr-Preview-Mode')?.value;\n const previewModeEnabled = previewModeCookie !== 'false';\n\n if (!previewModeEnabled) {\n return response;\n }\n }\n\n // If preview mode is enabled, set additional headers\n response.headers.set('Prepr-Preview-Bar', 'true');\n\n // When loaded inside the Prepr live preview iframe, prepr_hide_bar=true is\n // always present in the URL. In that context, cookies must never be used —\n // the live preview controls segments/variants exclusively via query params.\n // If no query params are present, the default (no segment/variant) should\n // be shown, not whatever the editor's browser cookie happens to contain.\n const isLivePreview =\n request.nextUrl.searchParams.get('prepr_hide_bar') === 'true';\n\n if (!isLivePreview) {\n // Set Prepr Preview Segment and AB test from cookies\n const segmentCookie = request.cookies.get('Prepr-Segments')?.value;\n if (segmentCookie) {\n response.headers.set('Prepr-Segments', segmentCookie);\n }\n\n const abCookie = request.cookies.get('Prepr-ABtesting')?.value;\n if (abCookie) {\n response.headers.set('Prepr-ABtesting', abCookie);\n }\n }\n\n // Set Prepr Preview Segment and AB test headers from query params\n request.nextUrl.searchParams.forEach((value, key) => {\n if (key === 'prepr_preview_ab') {\n response.headers.set('Prepr-ABtesting', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-ABtesting', value);\n }\n }\n\n if (key === 'prepr_preview_segment') {\n response.headers.set('Prepr-Segments', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-Segments', value);\n }\n }\n });\n\n return response;\n}\n","import { headers } from 'next/headers';\nimport {\n PreprToolbarProps,\n PreprSegment,\n PreprHeaderName,\n PreprErrorCode,\n} from '../types';\nimport pjson from '../../package.json';\nimport createPreprMiddleware from '../middleware';\n\n/**\n * Custom error class for Prepr-related errors\n */\nexport class PreprError extends Error {\n constructor(\n message: string,\n public readonly code: PreprErrorCode,\n public readonly context?: string,\n public readonly originalError?: Error\n ) {\n super(message);\n this.name = 'PreprError';\n }\n}\n\n/**\n * Internal helper to get a specific Prepr header value\n * @param name - The header name to retrieve\n * @returns The header value or null if not found\n */\nasync function getPreprHeader(name: PreprHeaderName): Promise<string | null> {\n const headersList = await headers();\n return headersList.get(name);\n}\n\n/**\n * Returns the Prepr Customer ID from the headers\n * @returns Prepr Customer ID\n */\nexport async function getPreprUUID(): Promise<string | null> {\n return getPreprHeader('prepr-customer-id');\n}\n\n/**\n * Returns the active segment from the headers\n * @returns Active segment\n */\nexport async function getActiveSegment(): Promise<string | null> {\n return getPreprHeader('Prepr-Segments');\n}\n\n/**\n * Returns the active variant from the headers\n * @returns Active variant\n */\nexport async function getActiveVariant(): Promise<string | null> {\n return getPreprHeader('Prepr-ABtesting');\n}\n\n/**\n * Helper function to retrieve all Prepr headers\n * @returns Object with Prepr headers\n */\nexport async function getPreprHeaders(): Promise<Record<string, string>> {\n const preprHeaders: Record<string, string> = {};\n const headersList = await headers();\n\n headersList.forEach((value, key) => {\n if (key.startsWith('prepr') || key.startsWith('Prepr')) {\n preprHeaders[key] = value;\n }\n });\n\n return preprHeaders;\n}\n\n/**\n * Validates a Prepr GraphQL token\n * @param token - The token to validate\n * @returns Validation result with error details if invalid\n */\nexport function validatePreprToken(token: string): {\n valid: boolean;\n error?: string;\n} {\n if (!token) {\n return { valid: false, error: 'Token is required' };\n }\n if (!token.startsWith('https://')) {\n return { valid: false, error: 'Token must be a valid HTTPS URL' };\n }\n return { valid: true };\n}\n\n/**\n * Checks if the current environment is in preview mode\n * @returns True if in preview mode\n */\nexport function isPreviewMode(): boolean {\n return process.env.PREPR_ENV === 'preview';\n}\n\n/**\n * Extracts the access token from a Prepr GraphQL URL\n * @param graphqlUrl - The full Prepr GraphQL URL\n * @returns The access token or null if invalid\n * @example\n * ```typescript\n * const token = extractAccessToken('https://graphql.prepr.io/abc123')\n * // Returns: 'abc123'\n * ```\n */\nexport function extractAccessToken(graphqlUrl: string): string | null {\n if (!graphqlUrl) return null;\n\n try {\n const url = new URL(graphqlUrl);\n if (url.hostname !== 'graphql.prepr.io') return null;\n\n const pathParts = url.pathname.split('/');\n const token = pathParts[pathParts.length - 1];\n\n return token && token.length > 0 ? token : null;\n } catch {\n return null;\n }\n}\n\n/**\n * Fetches the segments from the Prepr API\n * @param token Prepr GraphQL URL with scope 'segments'\n * @returns Array of PreprSegment\n * @throws PreprError if the request fails\n */\nexport async function getPreprEnvironmentSegments(\n token: string\n): Promise<PreprSegment[]> {\n const validation = validatePreprToken(token);\n if (!validation.valid) {\n throw new PreprError(\n validation.error!,\n 'INVALID_TOKEN',\n 'getPreprEnvironmentSegments'\n );\n }\n\n try {\n const response = await fetch(token, {\n headers: {\n 'User-Agent': `Prepr-Preview-Bar/${getPackageVersion()}`,\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n body: JSON.stringify({\n query: `{\n _Segments {\n _id\n name\n }\n }`,\n }),\n });\n\n if (!response.ok) {\n throw new PreprError(\n `HTTP ${response.status}: ${response.statusText}`,\n 'HTTP_ERROR',\n 'getPreprEnvironmentSegments'\n );\n }\n\n const json = await response.json();\n\n if (!json || !json.data || !json.data._Segments) {\n throw new PreprError(\n 'Invalid response format from Prepr API',\n 'INVALID_RESPONSE',\n 'getPreprEnvironmentSegments'\n );\n }\n\n return json.data._Segments as PreprSegment[];\n } catch (error) {\n if (error instanceof PreprError) {\n throw error;\n }\n throw new PreprError(\n 'Failed to fetch segments from Prepr API',\n 'FETCH_ERROR',\n 'getPreprEnvironmentSegments',\n error instanceof Error ? error : new Error(String(error))\n );\n }\n}\n\n/**\n * Fetches all the necessary previewbar props\n * @param token Prepr GraphQL URL with scope 'segments'\n * @returns Object with activeSegment, activeVariant and data\n */\nexport async function getToolbarProps(\n token: string\n): Promise<PreprToolbarProps> {\n let data: PreprSegment[] = [];\n let activeSegment: string | null = null;\n let activeVariant: string | null = null;\n\n // Prevent unnecessary function calling in production\n if (isPreviewMode()) {\n try {\n data = await getPreprEnvironmentSegments(token);\n activeSegment = await getActiveSegment();\n activeVariant = await getActiveVariant();\n } catch (error) {\n // In preview mode, we should still return props even if API fails\n console.error('Failed to fetch toolbar props:', error);\n // Return empty data to prevent toolbar from crashing\n data = [];\n }\n }\n\n return {\n activeSegment,\n activeVariant,\n data,\n };\n}\n\nfunction getPackageVersion() {\n return pjson.version;\n}\n\nexport { createPreprMiddleware };\n"]}
|
|
1
|
+
{"version":3,"sources":["../../package.json","../../src/middleware/index.ts","../../src/server/index.ts"],"names":["version","package_default","createPreprMiddleware","request","responseOrOptions","options","_a","_b","_c","_d","_e","response","finalOptions","NextResponse","value","key","referrer","ip","ipAddress","hutkCookie","cookie","isLivePreview","segmentCookie","abCookie","PreprError","message","code","context","originalError","getPreprHeader","name","__async","headers","getPreprUUID","getActiveSegment","getActiveVariant","getPreprHeaders","preprHeaders","validatePreprToken","token","isPreviewMode","extractAccessToken","graphqlUrl","url","pathParts","e","getPreprEnvironmentSegments","validation","getPackageVersion","json","error","getToolbarProps","data","activeSegment","activeVariant"],"mappings":"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","file":"index.js","sourcesContent":["{\n \"name\": \"@preprio/prepr-nextjs\",\n \"version\": \"2.2.4\",\n \"description\": \"Next.js package for Prepr CMS preview functionality with advanced debugging and visual editing capabilities\",\n \"main\": \"dist/react/index.cjs\",\n \"types\": \"./dist/react/index.d.ts\",\n \"module\": \"./dist/react/index.js\",\n \"type\": \"module\",\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"clean\": \"rm -rf dist\",\n \"check\": \"tsc --noEmit && eslint src --ext .ts,.tsx && prettier --check \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"fix\": \"eslint src --ext .ts,.tsx --fix && prettier --write \\\"src/**/*.{ts,tsx,js,jsx,json,md}\\\"\",\n \"changeset\": \"changeset\",\n \"version\": \"changeset version\",\n \"release\": \"pnpm run build && changeset publish\",\n \"prepublishOnly\": \"pnpm run check && pnpm run build\"\n },\n \"exports\": {\n \"./middleware\": {\n \"import\": \"./dist/middleware/index.js\",\n \"types\": \"./dist/middleware/index.d.ts\",\n \"require\": \"./dist/middleware/index.cjs\"\n },\n \"./server\": {\n \"import\": \"./dist/server/index.js\",\n \"types\": \"./dist/server/index.d.ts\",\n \"require\": \"./dist/server/index.cjs\"\n },\n \"./react\": {\n \"import\": \"./dist/react/index.js\",\n \"types\": \"./dist/react/index.d.ts\",\n \"require\": \"./dist/react/index.cjs\"\n },\n \"./utils\": {\n \"import\": \"./dist/utils/index.js\",\n \"types\": \"./dist/utils/index.d.ts\",\n \"require\": \"./dist/utils/index.cjs\"\n },\n \"./types\": {\n \"import\": \"./dist/types/index.js\",\n \"types\": \"./dist/types/index.d.ts\",\n \"require\": \"./dist/types/index.cjs\"\n },\n \"./index.css\": {\n \"import\": \"./dist/index.css\",\n \"require\": \"./dist/index.css\"\n }\n },\n \"files\": [\n \"dist\",\n \"package.json\"\n ],\n \"keywords\": [\n \"prepr\",\n \"cms\",\n \"nextjs\",\n \"preview\",\n \"visual-editing\",\n \"headless-cms\",\n \"react\",\n \"typescript\",\n \"debug\",\n \"stega\"\n ],\n \"author\": \"Preprio\",\n \"license\": \"MIT\",\n \"packageManager\": \"pnpm@10.5.2\",\n \"devDependencies\": {\n \"@changesets/cli\": \"^2.30.0\",\n \"@eslint/js\": \"^9.39.2\",\n \"@types/node\": \"^25.4.0\",\n \"@types/react\": \"19.2.14\",\n \"@types/react-dom\": \"19.2.3\",\n \"@typescript-eslint/eslint-plugin\": \"^8.57.0\",\n \"@typescript-eslint/parser\": \"^8.57.0\",\n \"autoprefixer\": \"^10.4.27\",\n \"cssnano\": \"^7.1.3\",\n \"eslint\": \"^9.39.2\",\n \"eslint-config-prettier\": \"^10.1.8\",\n \"eslint-plugin-prettier\": \"^5.5.5\",\n \"eslint-plugin-react\": \"^7.37.5\",\n \"eslint-plugin-react-hooks\": \"^7.0.1\",\n \"next\": \"16.1.6\",\n \"postcss\": \"^8.5.8\",\n \"prettier\": \"^3.8.1\",\n \"prettier-plugin-tailwindcss\": \"^0.7.2\",\n \"react\": \"^19.2.4\",\n \"react-dom\": \"^19.2.4\",\n \"tailwindcss\": \"^3.4.17\",\n \"tsup\": \"^8.5.1\",\n \"typescript\": \"^5.9.3\"\n },\n \"peerDependencies\": {\n \"next\": \"^16.0.3 || ^15.0.5 || ^15.1.9 || ^15.2.6 || ^15.3.6 || ^15.4.8 || ^15.5.7 || ^14.0.0 || ^13.0.0\",\n \"react\": \"^19.0.0 || ^18.0.0 || ^17.0.0 \",\n \"react-dom\": \"^19.0.0 || ^18.0.0 || ^17.0.0\"\n },\n \"pnpm\": {\n \"overrides\": {\n \"fast-xml-parser\": \"^5.5.0\"\n }\n },\n \"dependencies\": {\n \"@headlessui/react\": \"^2.2.9\",\n \"@vercel/functions\": \"^3.4.3\",\n \"@vercel/stega\": \"^1.0.0\",\n \"clsx\": \"^2.1.1\",\n \"postcss-cli\": \"^11.0.1\",\n \"tailwind-merge\": \"^3.5.0\",\n \"zustand\": \"^5.0.11\"\n }\n}\n","import { ipAddress } from '@vercel/functions';\nimport { NextRequest, NextResponse } from 'next/server';\nimport { version } from '../../package.json';\n\nexport interface PreprMiddlewareOptions {\n preview?: boolean;\n}\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Middleware to set Prepr headers for personalization.\n *\n * @overload\n * @param request - NextRequest object\n * @param response - NextResponse object to chain with\n * @param options - Options object\n * @returns NextResponse with Prepr headers set\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n response: NextResponse,\n options?: PreprMiddlewareOptions\n): NextResponse;\n\n/**\n * Implementation of createPreprMiddleware with function overloads\n */\nexport default function createPreprMiddleware(\n request: NextRequest,\n responseOrOptions?: NextResponse | PreprMiddlewareOptions,\n options?: PreprMiddlewareOptions\n): NextResponse {\n let response: NextResponse;\n let finalOptions: PreprMiddlewareOptions | undefined;\n\n // Handle overloads\n if (responseOrOptions && 'headers' in responseOrOptions) {\n // Second parameter is NextResponse\n response = responseOrOptions;\n finalOptions = options;\n } else {\n // Second parameter is options or undefined\n response = NextResponse.next();\n finalOptions = responseOrOptions as PreprMiddlewareOptions | undefined;\n }\n\n // Map over search params and set headers\n request.nextUrl.searchParams.forEach((value, key) => {\n switch (key) {\n case 'utm_source':\n response.headers.set('Prepr-Context-utm_source', value);\n break;\n case 'utm_medium':\n response.headers.set('Prepr-Context-utm_medium', value);\n break;\n case 'utm_term':\n response.headers.set('Prepr-Context-utm_term', value);\n break;\n case 'utm_content':\n response.headers.set('Prepr-Context-utm_content', value);\n break;\n case 'utm_campaign':\n response.headers.set('Prepr-Context-utm_campaign', value);\n break;\n }\n });\n\n // Set initial referral header\n const referrer = request.headers.get('referer');\n if (referrer) {\n response.headers.set('Prepr-Context-initial_referral', referrer);\n }\n\n // Set Prepr version header\n response.headers.set('Prepr-Package', version);\n\n let ip: string | null = ipAddress(request) || null;\n\n if (request.headers.get('Cf-Connecting-Ip')) {\n ip = request.headers.get('Cf-Connecting-Ip');\n }\n\n if (ip) {\n response.headers.set('Prepr-Visitor-IP', ip);\n }\n\n // Set HubSpot cookie header\n const hutkCookie = request.cookies.get('hubspotutk')?.value;\n if (hutkCookie) {\n response.headers.set('Prepr-Hubspot-Id', hutkCookie);\n }\n\n // Check for existing Prepr UID cookie or create a new one\n let cookie = request.cookies.get('__prepr_uid')?.value;\n if (!cookie) {\n cookie = crypto.randomUUID();\n response.cookies.set('__prepr_uid', cookie, {\n maxAge: 1 * 365 * 24 * 60, // Set for one year\n });\n response.headers.set('Prepr-Customer-Id-Created', 'true');\n }\n\n // Set the Prepr Customer ID header\n response.headers.set('Prepr-Customer-Id', cookie);\n\n // If preview mode is not enabled, return the response\n if (!finalOptions?.preview || process.env.PREPR_ENV !== 'preview') {\n return response;\n }\n\n // Preview query params always take priority — when the CMS dashboard\n // loads the site in an iframe it controls segments via query params,\n // regardless of the user's Prepr-Preview-Mode cookie in the browser.\n const hasPreviewParams =\n request.nextUrl.searchParams.has('prepr_preview_segment') ||\n request.nextUrl.searchParams.has('prepr_preview_ab');\n\n if (!hasPreviewParams) {\n // Respect preview mode toggle cookie from client\n const previewModeCookie = request.cookies.get('Prepr-Preview-Mode')?.value;\n const previewModeEnabled = previewModeCookie !== 'false';\n\n if (!previewModeEnabled) {\n return response;\n }\n }\n\n // If preview mode is enabled, set additional headers\n response.headers.set('Prepr-Preview-Bar', 'true');\n\n // When loaded inside the Prepr live preview iframe, prepr_hide_bar=true is\n // always present in the URL. In that context, cookies must never be used —\n // the live preview controls segments/variants exclusively via query params.\n // If no query params are present, the default (no segment/variant) should\n // be shown, not whatever the editor's browser cookie happens to contain.\n const isLivePreview =\n request.nextUrl.searchParams.get('prepr_hide_bar') === 'true';\n\n if (!isLivePreview) {\n // Set Prepr Preview Segment and AB test from cookies\n const segmentCookie = request.cookies.get('Prepr-Segments')?.value;\n if (segmentCookie) {\n response.headers.set('Prepr-Segments', segmentCookie);\n }\n\n const abCookie = request.cookies.get('Prepr-ABtesting')?.value;\n if (abCookie) {\n response.headers.set('Prepr-ABtesting', abCookie);\n }\n }\n\n // Set Prepr Preview Segment and AB test headers from query params\n request.nextUrl.searchParams.forEach((value, key) => {\n if (key === 'prepr_preview_ab') {\n response.headers.set('Prepr-ABtesting', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-ABtesting', value);\n }\n }\n\n if (key === 'prepr_preview_segment') {\n response.headers.set('Prepr-Segments', value);\n // Don't write live preview selections back into the editor's cookies\n if (!isLivePreview) {\n response.cookies.set('Prepr-Segments', value);\n }\n }\n });\n\n return response;\n}\n","import { headers } from 'next/headers';\nimport {\n PreprToolbarProps,\n PreprSegment,\n PreprHeaderName,\n PreprErrorCode,\n} from '../types';\nimport pjson from '../../package.json';\nimport createPreprMiddleware from '../middleware';\n\n/**\n * Custom error class for Prepr-related errors\n */\nexport class PreprError extends Error {\n constructor(\n message: string,\n public readonly code: PreprErrorCode,\n public readonly context?: string,\n public readonly originalError?: Error\n ) {\n super(message);\n this.name = 'PreprError';\n }\n}\n\n/**\n * Internal helper to get a specific Prepr header value\n * @param name - The header name to retrieve\n * @returns The header value or null if not found\n */\nasync function getPreprHeader(name: PreprHeaderName): Promise<string | null> {\n const headersList = await headers();\n return headersList.get(name);\n}\n\n/**\n * Returns the Prepr Customer ID from the headers\n * @returns Prepr Customer ID\n */\nexport async function getPreprUUID(): Promise<string | null> {\n return getPreprHeader('prepr-customer-id');\n}\n\n/**\n * Returns the active segment from the headers\n * @returns Active segment\n */\nexport async function getActiveSegment(): Promise<string | null> {\n return getPreprHeader('Prepr-Segments');\n}\n\n/**\n * Returns the active variant from the headers\n * @returns Active variant\n */\nexport async function getActiveVariant(): Promise<string | null> {\n return getPreprHeader('Prepr-ABtesting');\n}\n\n/**\n * Helper function to retrieve all Prepr headers\n * @returns Object with Prepr headers\n */\nexport async function getPreprHeaders(): Promise<Record<string, string>> {\n const preprHeaders: Record<string, string> = {};\n const headersList = await headers();\n\n headersList.forEach((value, key) => {\n if (key.startsWith('prepr') || key.startsWith('Prepr')) {\n preprHeaders[key] = value;\n }\n });\n\n return preprHeaders;\n}\n\n/**\n * Validates a Prepr GraphQL token\n * @param token - The token to validate\n * @returns Validation result with error details if invalid\n */\nexport function validatePreprToken(token: string): {\n valid: boolean;\n error?: string;\n} {\n if (!token) {\n return { valid: false, error: 'Token is required' };\n }\n if (!token.startsWith('https://')) {\n return { valid: false, error: 'Token must be a valid HTTPS URL' };\n }\n return { valid: true };\n}\n\n/**\n * Checks if the current environment is in preview mode\n * @returns True if in preview mode\n */\nexport function isPreviewMode(): boolean {\n return process.env.PREPR_ENV === 'preview';\n}\n\n/**\n * Extracts the access token from a Prepr GraphQL URL\n * @param graphqlUrl - The full Prepr GraphQL URL\n * @returns The access token or null if invalid\n * @example\n * ```typescript\n * const token = extractAccessToken('https://graphql.prepr.io/abc123')\n * // Returns: 'abc123'\n * ```\n */\nexport function extractAccessToken(graphqlUrl: string): string | null {\n if (!graphqlUrl) return null;\n\n try {\n const url = new URL(graphqlUrl);\n if (url.hostname !== 'graphql.prepr.io') return null;\n\n const pathParts = url.pathname.split('/');\n const token = pathParts[pathParts.length - 1];\n\n return token && token.length > 0 ? token : null;\n } catch {\n return null;\n }\n}\n\n/**\n * Fetches the segments from the Prepr API\n * @param token Prepr GraphQL URL with scope 'segments'\n * @returns Array of PreprSegment\n * @throws PreprError if the request fails\n */\nexport async function getPreprEnvironmentSegments(\n token: string\n): Promise<PreprSegment[]> {\n const validation = validatePreprToken(token);\n if (!validation.valid) {\n throw new PreprError(\n validation.error!,\n 'INVALID_TOKEN',\n 'getPreprEnvironmentSegments'\n );\n }\n\n try {\n const response = await fetch(token, {\n headers: {\n 'User-Agent': `Prepr-Preview-Bar/${getPackageVersion()}`,\n 'Content-Type': 'application/json',\n },\n method: 'POST',\n body: JSON.stringify({\n query: `{\n _Segments {\n _id\n name\n }\n }`,\n }),\n });\n\n if (!response.ok) {\n throw new PreprError(\n `HTTP ${response.status}: ${response.statusText}`,\n 'HTTP_ERROR',\n 'getPreprEnvironmentSegments'\n );\n }\n\n const json = await response.json();\n\n if (!json || !json.data || !json.data._Segments) {\n throw new PreprError(\n 'Invalid response format from Prepr API',\n 'INVALID_RESPONSE',\n 'getPreprEnvironmentSegments'\n );\n }\n\n return json.data._Segments as PreprSegment[];\n } catch (error) {\n if (error instanceof PreprError) {\n throw error;\n }\n throw new PreprError(\n 'Failed to fetch segments from Prepr API',\n 'FETCH_ERROR',\n 'getPreprEnvironmentSegments',\n error instanceof Error ? error : new Error(String(error))\n );\n }\n}\n\n/**\n * Fetches all the necessary previewbar props\n * @param token Prepr GraphQL URL with scope 'segments'\n * @returns Object with activeSegment, activeVariant and data\n */\nexport async function getToolbarProps(\n token: string\n): Promise<PreprToolbarProps> {\n let data: PreprSegment[] = [];\n let activeSegment: string | null = null;\n let activeVariant: string | null = null;\n\n // Prevent unnecessary function calling in production\n if (isPreviewMode()) {\n try {\n data = await getPreprEnvironmentSegments(token);\n activeSegment = await getActiveSegment();\n activeVariant = await getActiveVariant();\n } catch (error) {\n // In preview mode, we should still return props even if API fails\n console.error('Failed to fetch toolbar props:', error);\n // Return empty data to prevent toolbar from crashing\n data = [];\n }\n }\n\n return {\n activeSegment,\n activeVariant,\n data,\n };\n}\n\nfunction getPackageVersion() {\n return pjson.version;\n}\n\nexport { createPreprMiddleware };\n"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@preprio/prepr-nextjs",
|
|
3
|
-
"version": "2.2.
|
|
3
|
+
"version": "2.2.4",
|
|
4
4
|
"description": "Next.js package for Prepr CMS preview functionality with advanced debugging and visual editing capabilities",
|
|
5
5
|
"main": "dist/react/index.cjs",
|
|
6
6
|
"types": "./dist/react/index.d.ts",
|