@prismicio/next 2.3.3-canary.2d3b06a → 2.3.3-canary.6340cef

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.
@@ -17,14 +17,20 @@ const simulatorManager = new _prismicio_simulator_kit.SimulatorManager();
17
17
  */
18
18
  const SliceSimulator = ({ children, background, zIndex, className }) => {
19
19
  const [message, setMessage] = (0, react.useState)(() => (0, _prismicio_simulator_kit.getDefaultMessage)());
20
+ const [trustedState, setTrustedState] = (0, react.useState)(null);
20
21
  const router = (0, next_navigation_js.useRouter)();
21
22
  const state = typeof window !== "undefined" ? new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY) : void 0;
22
- const hasSlices = require_getSlices.getSlices(state).length > 0;
23
+ const hasSlices = state != null && state === trustedState && require_getSlices.getSlices(state).length > 0;
24
+ (0, react.useEffect)(() => {
25
+ if (process.env.NODE_ENV === "development") setTrustedState(new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY));
26
+ }, []);
23
27
  (0, react.useEffect)(() => {
24
28
  simulatorManager.state.on(_prismicio_simulator_kit.StateEventType.Slices, (newSlices) => {
29
+ const nextState = lz_string.default.compressToEncodedURIComponent(JSON.stringify(newSlices));
25
30
  const url = new URL(window.location.href);
26
- url.searchParams.set(STATE_PARAMS_KEY, lz_string.default.compressToEncodedURIComponent(JSON.stringify(newSlices)));
31
+ url.searchParams.set(STATE_PARAMS_KEY, nextState);
27
32
  window.history.replaceState(null, "", url);
33
+ setTrustedState(nextState);
28
34
  setTimeout(() => router.refresh(), 0);
29
35
  }, "simulator-slices");
30
36
  simulatorManager.state.on(_prismicio_simulator_kit.StateEventType.Message, (newMessage) => setMessage(newMessage), "simulator-message");
@@ -1 +1 @@
1
- {"version":3,"file":"SliceSimulator.cjs","names":["SimulatorManager","useState","getDefaultMessage","useRouter","getSlices","StateEventType","lzString","SliceSimulatorWrapper"],"sources":["../src/SliceSimulator.tsx"],"sourcesContent":["\"use client\"\n\nimport { SimulatorManager, StateEventType, getDefaultMessage } from \"@prismicio/simulator/kit\"\nimport type { SliceSimulatorProps as BaseSliceSimulatorProps } from \"@prismicio/simulator/kit\"\nimport lzString from \"lz-string\"\nimport { useRouter } from \"next/navigation\"\nimport { useEffect, useState } from \"react\"\nimport type { FC, ReactNode } from \"react\"\n\nimport { getSlices } from \"./getSlices\"\nimport { SliceSimulatorWrapper } from \"./SliceSimulatorWrapper\"\n\nconst STATE_PARAMS_KEY = \"state\"\n\nconst simulatorManager = new SimulatorManager()\n\n/** Parameters provided to the Slice Simulator page. */\nexport type SliceSimulatorParams = {\n\tsearchParams: Promise<{\n\t\tstate?: string\n\t}>\n}\n\nexport type SliceSimulatorProps = BaseSliceSimulatorProps & {\n\tchildren: ReactNode\n\tclassName?: string\n}\n\n/**\n * Simulate slices in isolation. The slice simulator enables live slice development in Slice Machine\n * and live previews in the Page Builder.\n */\nexport const SliceSimulator: FC<SliceSimulatorProps> = ({\n\tchildren,\n\tbackground,\n\tzIndex,\n\tclassName,\n}) => {\n\tconst [message, setMessage] = useState(() => getDefaultMessage())\n\tconst router = useRouter()\n\n\tconst state =\n\t\ttypeof window !== \"undefined\"\n\t\t\t? new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY)\n\t\t\t: undefined\n\tconst hasSlices = getSlices(state).length > 0\n\n\tuseEffect(() => {\n\t\tsimulatorManager.state.on(\n\t\t\tStateEventType.Slices,\n\t\t\t(newSlices) => {\n\t\t\t\tconst url = new URL(window.location.href)\n\t\t\t\turl.searchParams.set(\n\t\t\t\t\tSTATE_PARAMS_KEY,\n\t\t\t\t\tlzString.compressToEncodedURIComponent(JSON.stringify(newSlices)),\n\t\t\t\t)\n\n\t\t\t\twindow.history.replaceState(null, \"\", url)\n\t\t\t\t// Wait until the next tick to prevent URL state race conditions.\n\t\t\t\tsetTimeout(() => router.refresh(), 0)\n\t\t\t},\n\t\t\t\"simulator-slices\",\n\t\t)\n\t\tsimulatorManager.state.on(\n\t\t\tStateEventType.Message,\n\t\t\t(newMessage) => setMessage(newMessage),\n\t\t\t\"simulator-message\",\n\t\t)\n\n\t\tsimulatorManager.init()\n\n\t\treturn () => {\n\t\t\tsimulatorManager.state.off(StateEventType.Slices, \"simulator-slices\")\n\n\t\t\tsimulatorManager.state.off(StateEventType.Message, \"simulator-message\")\n\t\t}\n\t}, [router])\n\n\treturn (\n\t\t<SliceSimulatorWrapper\n\t\t\tmessage={message}\n\t\t\thasSlices={hasSlices}\n\t\t\tbackground={background}\n\t\t\tzIndex={zIndex}\n\t\t\tclassName={className}\n\t\t>\n\t\t\t{children}\n\t\t</SliceSimulatorWrapper>\n\t)\n}\n"],"mappings":";;;;;;;;;;;AAYA,MAAM,mBAAmB;AAEzB,MAAM,mBAAmB,IAAIA,yBAAAA,iBAAiB;;;;;AAkB9C,MAAa,kBAA2C,EACvD,UACA,YACA,QACA,gBACK;CACL,MAAM,CAAC,SAAS,eAAA,GAAcC,MAAAA,SAAAA,QAAAA,GAAeC,yBAAAA,kBAAAA,CAAkB,CAAC;CAChE,MAAM,UAAA,GAASC,mBAAAA,UAAAA,CAAU;CAEzB,MAAM,QACL,OAAO,WAAW,cACf,IAAI,IAAI,OAAO,SAAS,IAAI,CAAC,CAAC,aAAa,IAAI,gBAAgB,IAC/D,KAAA;CACJ,MAAM,YAAYC,kBAAAA,UAAU,KAAK,CAAC,CAAC,SAAS;CAE5C,CAAA,GAAA,MAAA,UAAA,OAAgB;EACf,iBAAiB,MAAM,GACtBC,yBAAAA,eAAe,SACd,cAAc;GACd,MAAM,MAAM,IAAI,IAAI,OAAO,SAAS,IAAI;GACxC,IAAI,aAAa,IAChB,kBACAC,UAAAA,QAAS,8BAA8B,KAAK,UAAU,SAAS,CAAC,CACjE;GAEA,OAAO,QAAQ,aAAa,MAAM,IAAI,GAAG;GAEzC,iBAAiB,OAAO,QAAQ,GAAG,CAAC;EACrC,GACA,kBACD;EACA,iBAAiB,MAAM,GACtBD,yBAAAA,eAAe,UACd,eAAe,WAAW,UAAU,GACrC,mBACD;EAEA,iBAAiB,KAAK;EAEtB,aAAa;GACZ,iBAAiB,MAAM,IAAIA,yBAAAA,eAAe,QAAQ,kBAAkB;GAEpE,iBAAiB,MAAM,IAAIA,yBAAAA,eAAe,SAAS,mBAAmB;EACvE;CACD,GAAG,CAAC,MAAM,CAAC;CAEX,OACC,iBAAA,GAAA,kBAAA,IAAA,CAACE,8BAAAA,uBAAD;EACU;EACE;EACC;EACJ;EACG;EAEV;CACqB,CAAA;AAEzB"}
1
+ {"version":3,"file":"SliceSimulator.cjs","names":["SimulatorManager","useState","getDefaultMessage","useRouter","getSlices","StateEventType","lzString","SliceSimulatorWrapper"],"sources":["../src/SliceSimulator.tsx"],"sourcesContent":["\"use client\"\n\nimport { SimulatorManager, StateEventType, getDefaultMessage } from \"@prismicio/simulator/kit\"\nimport type { SliceSimulatorProps as BaseSliceSimulatorProps } from \"@prismicio/simulator/kit\"\nimport lzString from \"lz-string\"\nimport { useRouter } from \"next/navigation\"\nimport { useEffect, useState } from \"react\"\nimport type { FC, ReactNode } from \"react\"\n\nimport { getSlices } from \"./getSlices\"\nimport { SliceSimulatorWrapper } from \"./SliceSimulatorWrapper\"\n\nconst STATE_PARAMS_KEY = \"state\"\n\nconst simulatorManager = new SimulatorManager()\n\n/** Parameters provided to the Slice Simulator page. */\nexport type SliceSimulatorParams = {\n\tsearchParams: Promise<{\n\t\tstate?: string\n\t}>\n}\n\nexport type SliceSimulatorProps = BaseSliceSimulatorProps & {\n\tchildren: ReactNode\n\tclassName?: string\n}\n\n/**\n * Simulate slices in isolation. The slice simulator enables live slice development in Slice Machine\n * and live previews in the Page Builder.\n */\nexport const SliceSimulator: FC<SliceSimulatorProps> = ({\n\tchildren,\n\tbackground,\n\tzIndex,\n\tclassName,\n}) => {\n\tconst [message, setMessage] = useState(() => getDefaultMessage())\n\tconst [trustedState, setTrustedState] = useState<string | null>(null)\n\tconst router = useRouter()\n\n\tconst state =\n\t\ttypeof window !== \"undefined\"\n\t\t\t? new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY)\n\t\t\t: undefined\n\t// Only render state this page received from Slice Machine or the Page\n\t// Builder. The `state` URL parameter on its own can be set by anyone.\n\tconst hasSlices = state != null && state === trustedState && getSlices(state).length > 0\n\n\tuseEffect(() => {\n\t\t// `@prismicio/simulator` accepts messages from any origin in development,\n\t\t// so the URL is as trustworthy as a message there. Trusting it keeps\n\t\t// slices visible when the dev server fully reloads the page. It is set\n\t\t// after hydration so the first render matches the server.\n\t\tif (process.env.NODE_ENV === \"development\") {\n\t\t\t// oxlint-disable-next-line react/set-state-in-effect\n\t\t\tsetTrustedState(new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY))\n\t\t}\n\t}, [])\n\n\tuseEffect(() => {\n\t\tsimulatorManager.state.on(\n\t\t\tStateEventType.Slices,\n\t\t\t(newSlices) => {\n\t\t\t\tconst nextState = lzString.compressToEncodedURIComponent(JSON.stringify(newSlices))\n\t\t\t\tconst url = new URL(window.location.href)\n\t\t\t\turl.searchParams.set(STATE_PARAMS_KEY, nextState)\n\n\t\t\t\twindow.history.replaceState(null, \"\", url)\n\t\t\t\tsetTrustedState(nextState)\n\t\t\t\t// Wait until the next tick to prevent URL state race conditions.\n\t\t\t\tsetTimeout(() => router.refresh(), 0)\n\t\t\t},\n\t\t\t\"simulator-slices\",\n\t\t)\n\t\tsimulatorManager.state.on(\n\t\t\tStateEventType.Message,\n\t\t\t(newMessage) => setMessage(newMessage),\n\t\t\t\"simulator-message\",\n\t\t)\n\n\t\tsimulatorManager.init()\n\n\t\treturn () => {\n\t\t\tsimulatorManager.state.off(StateEventType.Slices, \"simulator-slices\")\n\n\t\t\tsimulatorManager.state.off(StateEventType.Message, \"simulator-message\")\n\t\t}\n\t}, [router])\n\n\treturn (\n\t\t<SliceSimulatorWrapper\n\t\t\tmessage={message}\n\t\t\thasSlices={hasSlices}\n\t\t\tbackground={background}\n\t\t\tzIndex={zIndex}\n\t\t\tclassName={className}\n\t\t>\n\t\t\t{children}\n\t\t</SliceSimulatorWrapper>\n\t)\n}\n"],"mappings":";;;;;;;;;;;AAYA,MAAM,mBAAmB;AAEzB,MAAM,mBAAmB,IAAIA,yBAAAA,iBAAiB;;;;;AAkB9C,MAAa,kBAA2C,EACvD,UACA,YACA,QACA,gBACK;CACL,MAAM,CAAC,SAAS,eAAA,GAAcC,MAAAA,SAAAA,QAAAA,GAAeC,yBAAAA,kBAAAA,CAAkB,CAAC;CAChE,MAAM,CAAC,cAAc,oBAAA,GAAmBD,MAAAA,SAAAA,CAAwB,IAAI;CACpE,MAAM,UAAA,GAASE,mBAAAA,UAAAA,CAAU;CAEzB,MAAM,QACL,OAAO,WAAW,cACf,IAAI,IAAI,OAAO,SAAS,IAAI,CAAC,CAAC,aAAa,IAAI,gBAAgB,IAC/D,KAAA;CAGJ,MAAM,YAAY,SAAS,QAAQ,UAAU,gBAAgBC,kBAAAA,UAAU,KAAK,CAAC,CAAC,SAAS;CAEvF,CAAA,GAAA,MAAA,UAAA,OAAgB;EAKf,IAAI,QAAQ,IAAI,aAAa,eAE5B,gBAAgB,IAAI,IAAI,OAAO,SAAS,IAAI,CAAC,CAAC,aAAa,IAAI,gBAAgB,CAAC;CAElF,GAAG,CAAC,CAAC;CAEL,CAAA,GAAA,MAAA,UAAA,OAAgB;EACf,iBAAiB,MAAM,GACtBC,yBAAAA,eAAe,SACd,cAAc;GACd,MAAM,YAAYC,UAAAA,QAAS,8BAA8B,KAAK,UAAU,SAAS,CAAC;GAClF,MAAM,MAAM,IAAI,IAAI,OAAO,SAAS,IAAI;GACxC,IAAI,aAAa,IAAI,kBAAkB,SAAS;GAEhD,OAAO,QAAQ,aAAa,MAAM,IAAI,GAAG;GACzC,gBAAgB,SAAS;GAEzB,iBAAiB,OAAO,QAAQ,GAAG,CAAC;EACrC,GACA,kBACD;EACA,iBAAiB,MAAM,GACtBD,yBAAAA,eAAe,UACd,eAAe,WAAW,UAAU,GACrC,mBACD;EAEA,iBAAiB,KAAK;EAEtB,aAAa;GACZ,iBAAiB,MAAM,IAAIA,yBAAAA,eAAe,QAAQ,kBAAkB;GAEpE,iBAAiB,MAAM,IAAIA,yBAAAA,eAAe,SAAS,mBAAmB;EACvE;CACD,GAAG,CAAC,MAAM,CAAC;CAEX,OACC,iBAAA,GAAA,kBAAA,IAAA,CAACE,8BAAAA,uBAAD;EACU;EACE;EACC;EACJ;EACG;EAEV;CACqB,CAAA;AAEzB"}
@@ -15,14 +15,20 @@ const simulatorManager = new SimulatorManager();
15
15
  */
16
16
  const SliceSimulator = ({ children, background, zIndex, className }) => {
17
17
  const [message, setMessage] = useState(() => getDefaultMessage());
18
+ const [trustedState, setTrustedState] = useState(null);
18
19
  const router = useRouter();
19
20
  const state = typeof window !== "undefined" ? new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY) : void 0;
20
- const hasSlices = getSlices(state).length > 0;
21
+ const hasSlices = state != null && state === trustedState && getSlices(state).length > 0;
22
+ useEffect(() => {
23
+ if (process.env.NODE_ENV === "development") setTrustedState(new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY));
24
+ }, []);
21
25
  useEffect(() => {
22
26
  simulatorManager.state.on(StateEventType.Slices, (newSlices) => {
27
+ const nextState = lzString.compressToEncodedURIComponent(JSON.stringify(newSlices));
23
28
  const url = new URL(window.location.href);
24
- url.searchParams.set(STATE_PARAMS_KEY, lzString.compressToEncodedURIComponent(JSON.stringify(newSlices)));
29
+ url.searchParams.set(STATE_PARAMS_KEY, nextState);
25
30
  window.history.replaceState(null, "", url);
31
+ setTrustedState(nextState);
26
32
  setTimeout(() => router.refresh(), 0);
27
33
  }, "simulator-slices");
28
34
  simulatorManager.state.on(StateEventType.Message, (newMessage) => setMessage(newMessage), "simulator-message");
@@ -1 +1 @@
1
- {"version":3,"file":"SliceSimulator.js","names":[],"sources":["../src/SliceSimulator.tsx"],"sourcesContent":["\"use client\"\n\nimport { SimulatorManager, StateEventType, getDefaultMessage } from \"@prismicio/simulator/kit\"\nimport type { SliceSimulatorProps as BaseSliceSimulatorProps } from \"@prismicio/simulator/kit\"\nimport lzString from \"lz-string\"\nimport { useRouter } from \"next/navigation\"\nimport { useEffect, useState } from \"react\"\nimport type { FC, ReactNode } from \"react\"\n\nimport { getSlices } from \"./getSlices\"\nimport { SliceSimulatorWrapper } from \"./SliceSimulatorWrapper\"\n\nconst STATE_PARAMS_KEY = \"state\"\n\nconst simulatorManager = new SimulatorManager()\n\n/** Parameters provided to the Slice Simulator page. */\nexport type SliceSimulatorParams = {\n\tsearchParams: Promise<{\n\t\tstate?: string\n\t}>\n}\n\nexport type SliceSimulatorProps = BaseSliceSimulatorProps & {\n\tchildren: ReactNode\n\tclassName?: string\n}\n\n/**\n * Simulate slices in isolation. The slice simulator enables live slice development in Slice Machine\n * and live previews in the Page Builder.\n */\nexport const SliceSimulator: FC<SliceSimulatorProps> = ({\n\tchildren,\n\tbackground,\n\tzIndex,\n\tclassName,\n}) => {\n\tconst [message, setMessage] = useState(() => getDefaultMessage())\n\tconst router = useRouter()\n\n\tconst state =\n\t\ttypeof window !== \"undefined\"\n\t\t\t? new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY)\n\t\t\t: undefined\n\tconst hasSlices = getSlices(state).length > 0\n\n\tuseEffect(() => {\n\t\tsimulatorManager.state.on(\n\t\t\tStateEventType.Slices,\n\t\t\t(newSlices) => {\n\t\t\t\tconst url = new URL(window.location.href)\n\t\t\t\turl.searchParams.set(\n\t\t\t\t\tSTATE_PARAMS_KEY,\n\t\t\t\t\tlzString.compressToEncodedURIComponent(JSON.stringify(newSlices)),\n\t\t\t\t)\n\n\t\t\t\twindow.history.replaceState(null, \"\", url)\n\t\t\t\t// Wait until the next tick to prevent URL state race conditions.\n\t\t\t\tsetTimeout(() => router.refresh(), 0)\n\t\t\t},\n\t\t\t\"simulator-slices\",\n\t\t)\n\t\tsimulatorManager.state.on(\n\t\t\tStateEventType.Message,\n\t\t\t(newMessage) => setMessage(newMessage),\n\t\t\t\"simulator-message\",\n\t\t)\n\n\t\tsimulatorManager.init()\n\n\t\treturn () => {\n\t\t\tsimulatorManager.state.off(StateEventType.Slices, \"simulator-slices\")\n\n\t\t\tsimulatorManager.state.off(StateEventType.Message, \"simulator-message\")\n\t\t}\n\t}, [router])\n\n\treturn (\n\t\t<SliceSimulatorWrapper\n\t\t\tmessage={message}\n\t\t\thasSlices={hasSlices}\n\t\t\tbackground={background}\n\t\t\tzIndex={zIndex}\n\t\t\tclassName={className}\n\t\t>\n\t\t\t{children}\n\t\t</SliceSimulatorWrapper>\n\t)\n}\n"],"mappings":";;;;;;;;;AAYA,MAAM,mBAAmB;AAEzB,MAAM,mBAAmB,IAAI,iBAAiB;;;;;AAkB9C,MAAa,kBAA2C,EACvD,UACA,YACA,QACA,gBACK;CACL,MAAM,CAAC,SAAS,cAAc,eAAe,kBAAkB,CAAC;CAChE,MAAM,SAAS,UAAU;CAEzB,MAAM,QACL,OAAO,WAAW,cACf,IAAI,IAAI,OAAO,SAAS,IAAI,CAAC,CAAC,aAAa,IAAI,gBAAgB,IAC/D,KAAA;CACJ,MAAM,YAAY,UAAU,KAAK,CAAC,CAAC,SAAS;CAE5C,gBAAgB;EACf,iBAAiB,MAAM,GACtB,eAAe,SACd,cAAc;GACd,MAAM,MAAM,IAAI,IAAI,OAAO,SAAS,IAAI;GACxC,IAAI,aAAa,IAChB,kBACA,SAAS,8BAA8B,KAAK,UAAU,SAAS,CAAC,CACjE;GAEA,OAAO,QAAQ,aAAa,MAAM,IAAI,GAAG;GAEzC,iBAAiB,OAAO,QAAQ,GAAG,CAAC;EACrC,GACA,kBACD;EACA,iBAAiB,MAAM,GACtB,eAAe,UACd,eAAe,WAAW,UAAU,GACrC,mBACD;EAEA,iBAAiB,KAAK;EAEtB,aAAa;GACZ,iBAAiB,MAAM,IAAI,eAAe,QAAQ,kBAAkB;GAEpE,iBAAiB,MAAM,IAAI,eAAe,SAAS,mBAAmB;EACvE;CACD,GAAG,CAAC,MAAM,CAAC;CAEX,OACC,oBAAC,uBAAD;EACU;EACE;EACC;EACJ;EACG;EAEV;CACqB,CAAA;AAEzB"}
1
+ {"version":3,"file":"SliceSimulator.js","names":[],"sources":["../src/SliceSimulator.tsx"],"sourcesContent":["\"use client\"\n\nimport { SimulatorManager, StateEventType, getDefaultMessage } from \"@prismicio/simulator/kit\"\nimport type { SliceSimulatorProps as BaseSliceSimulatorProps } from \"@prismicio/simulator/kit\"\nimport lzString from \"lz-string\"\nimport { useRouter } from \"next/navigation\"\nimport { useEffect, useState } from \"react\"\nimport type { FC, ReactNode } from \"react\"\n\nimport { getSlices } from \"./getSlices\"\nimport { SliceSimulatorWrapper } from \"./SliceSimulatorWrapper\"\n\nconst STATE_PARAMS_KEY = \"state\"\n\nconst simulatorManager = new SimulatorManager()\n\n/** Parameters provided to the Slice Simulator page. */\nexport type SliceSimulatorParams = {\n\tsearchParams: Promise<{\n\t\tstate?: string\n\t}>\n}\n\nexport type SliceSimulatorProps = BaseSliceSimulatorProps & {\n\tchildren: ReactNode\n\tclassName?: string\n}\n\n/**\n * Simulate slices in isolation. The slice simulator enables live slice development in Slice Machine\n * and live previews in the Page Builder.\n */\nexport const SliceSimulator: FC<SliceSimulatorProps> = ({\n\tchildren,\n\tbackground,\n\tzIndex,\n\tclassName,\n}) => {\n\tconst [message, setMessage] = useState(() => getDefaultMessage())\n\tconst [trustedState, setTrustedState] = useState<string | null>(null)\n\tconst router = useRouter()\n\n\tconst state =\n\t\ttypeof window !== \"undefined\"\n\t\t\t? new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY)\n\t\t\t: undefined\n\t// Only render state this page received from Slice Machine or the Page\n\t// Builder. The `state` URL parameter on its own can be set by anyone.\n\tconst hasSlices = state != null && state === trustedState && getSlices(state).length > 0\n\n\tuseEffect(() => {\n\t\t// `@prismicio/simulator` accepts messages from any origin in development,\n\t\t// so the URL is as trustworthy as a message there. Trusting it keeps\n\t\t// slices visible when the dev server fully reloads the page. It is set\n\t\t// after hydration so the first render matches the server.\n\t\tif (process.env.NODE_ENV === \"development\") {\n\t\t\t// oxlint-disable-next-line react/set-state-in-effect\n\t\t\tsetTrustedState(new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY))\n\t\t}\n\t}, [])\n\n\tuseEffect(() => {\n\t\tsimulatorManager.state.on(\n\t\t\tStateEventType.Slices,\n\t\t\t(newSlices) => {\n\t\t\t\tconst nextState = lzString.compressToEncodedURIComponent(JSON.stringify(newSlices))\n\t\t\t\tconst url = new URL(window.location.href)\n\t\t\t\turl.searchParams.set(STATE_PARAMS_KEY, nextState)\n\n\t\t\t\twindow.history.replaceState(null, \"\", url)\n\t\t\t\tsetTrustedState(nextState)\n\t\t\t\t// Wait until the next tick to prevent URL state race conditions.\n\t\t\t\tsetTimeout(() => router.refresh(), 0)\n\t\t\t},\n\t\t\t\"simulator-slices\",\n\t\t)\n\t\tsimulatorManager.state.on(\n\t\t\tStateEventType.Message,\n\t\t\t(newMessage) => setMessage(newMessage),\n\t\t\t\"simulator-message\",\n\t\t)\n\n\t\tsimulatorManager.init()\n\n\t\treturn () => {\n\t\t\tsimulatorManager.state.off(StateEventType.Slices, \"simulator-slices\")\n\n\t\t\tsimulatorManager.state.off(StateEventType.Message, \"simulator-message\")\n\t\t}\n\t}, [router])\n\n\treturn (\n\t\t<SliceSimulatorWrapper\n\t\t\tmessage={message}\n\t\t\thasSlices={hasSlices}\n\t\t\tbackground={background}\n\t\t\tzIndex={zIndex}\n\t\t\tclassName={className}\n\t\t>\n\t\t\t{children}\n\t\t</SliceSimulatorWrapper>\n\t)\n}\n"],"mappings":";;;;;;;;;AAYA,MAAM,mBAAmB;AAEzB,MAAM,mBAAmB,IAAI,iBAAiB;;;;;AAkB9C,MAAa,kBAA2C,EACvD,UACA,YACA,QACA,gBACK;CACL,MAAM,CAAC,SAAS,cAAc,eAAe,kBAAkB,CAAC;CAChE,MAAM,CAAC,cAAc,mBAAmB,SAAwB,IAAI;CACpE,MAAM,SAAS,UAAU;CAEzB,MAAM,QACL,OAAO,WAAW,cACf,IAAI,IAAI,OAAO,SAAS,IAAI,CAAC,CAAC,aAAa,IAAI,gBAAgB,IAC/D,KAAA;CAGJ,MAAM,YAAY,SAAS,QAAQ,UAAU,gBAAgB,UAAU,KAAK,CAAC,CAAC,SAAS;CAEvF,gBAAgB;EAKf,IAAI,QAAQ,IAAI,aAAa,eAE5B,gBAAgB,IAAI,IAAI,OAAO,SAAS,IAAI,CAAC,CAAC,aAAa,IAAI,gBAAgB,CAAC;CAElF,GAAG,CAAC,CAAC;CAEL,gBAAgB;EACf,iBAAiB,MAAM,GACtB,eAAe,SACd,cAAc;GACd,MAAM,YAAY,SAAS,8BAA8B,KAAK,UAAU,SAAS,CAAC;GAClF,MAAM,MAAM,IAAI,IAAI,OAAO,SAAS,IAAI;GACxC,IAAI,aAAa,IAAI,kBAAkB,SAAS;GAEhD,OAAO,QAAQ,aAAa,MAAM,IAAI,GAAG;GACzC,gBAAgB,SAAS;GAEzB,iBAAiB,OAAO,QAAQ,GAAG,CAAC;EACrC,GACA,kBACD;EACA,iBAAiB,MAAM,GACtB,eAAe,UACd,eAAe,WAAW,UAAU,GACrC,mBACD;EAEA,iBAAiB,KAAK;EAEtB,aAAa;GACZ,iBAAiB,MAAM,IAAI,eAAe,QAAQ,kBAAkB;GAEpE,iBAAiB,MAAM,IAAI,eAAe,SAAS,mBAAmB;EACvE;CACD,GAAG,CAAC,MAAM,CAAC;CAEX,OACC,oBAAC,uBAAD;EACU;EACE;EACC;EACJ;EACG;EAEV;CACqB,CAAA;AAEzB"}
package/dist/package.cjs CHANGED
@@ -1,5 +1,5 @@
1
1
  //#region package.json
2
- var version = "2.3.3-canary.2d3b06a";
2
+ var version = "2.3.3-canary.6340cef";
3
3
  //#endregion
4
4
  Object.defineProperty(exports, "version", {
5
5
  enumerable: true,
package/dist/package.js CHANGED
@@ -1,5 +1,5 @@
1
1
  //#region package.json
2
- var version = "2.3.3-canary.2d3b06a";
2
+ var version = "2.3.3-canary.6340cef";
3
3
  //#endregion
4
4
  export { version };
5
5
 
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@prismicio/next",
3
- "version": "2.3.3-canary.2d3b06a",
3
+ "version": "2.3.3-canary.6340cef",
4
4
  "description": "Helpers to integrate Prismic into Next.js apps",
5
5
  "keywords": [
6
6
  "next",
@@ -18,6 +18,7 @@
18
18
  "workspaces": [
19
19
  ".",
20
20
  "e2e-projects/*",
21
+ "!e2e-projects/next-14",
21
22
  "!e2e-projects/next-15"
22
23
  ],
23
24
  "files": [
@@ -59,17 +60,17 @@
59
60
  "lz-string": "^1.5.0"
60
61
  },
61
62
  "devDependencies": {
62
- "@playwright/test": "^1.63.0",
63
- "@prismicio/client": "^7.22.1",
64
- "@types/node": "^26.6.4",
63
+ "@playwright/test": "^1.64.0",
64
+ "@prismicio/client": "^7.22.3",
65
+ "@types/node": "^26.6.5",
65
66
  "@types/react": "^19.3.0",
66
- "next": "16.3.8",
67
+ "next": "16.4.0",
67
68
  "oxfmt": "^0.72.0",
68
69
  "oxlint": "^1.87.0",
69
- "playwright": "^1.63.0",
70
+ "playwright": "^1.64.0",
70
71
  "react": "^19.3.0",
71
72
  "react-dom": "^19.3.0",
72
- "tsdown": "^0.23.0",
73
+ "tsdown": "^0.23.1",
73
74
  "typescript": "^7.0.2"
74
75
  },
75
76
  "peerDependencies": {
@@ -37,25 +37,38 @@ export const SliceSimulator: FC<SliceSimulatorProps> = ({
37
37
  className,
38
38
  }) => {
39
39
  const [message, setMessage] = useState(() => getDefaultMessage())
40
+ const [trustedState, setTrustedState] = useState<string | null>(null)
40
41
  const router = useRouter()
41
42
 
42
43
  const state =
43
44
  typeof window !== "undefined"
44
45
  ? new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY)
45
46
  : undefined
46
- const hasSlices = getSlices(state).length > 0
47
+ // Only render state this page received from Slice Machine or the Page
48
+ // Builder. The `state` URL parameter on its own can be set by anyone.
49
+ const hasSlices = state != null && state === trustedState && getSlices(state).length > 0
50
+
51
+ useEffect(() => {
52
+ // `@prismicio/simulator` accepts messages from any origin in development,
53
+ // so the URL is as trustworthy as a message there. Trusting it keeps
54
+ // slices visible when the dev server fully reloads the page. It is set
55
+ // after hydration so the first render matches the server.
56
+ if (process.env.NODE_ENV === "development") {
57
+ // oxlint-disable-next-line react/set-state-in-effect
58
+ setTrustedState(new URL(window.location.href).searchParams.get(STATE_PARAMS_KEY))
59
+ }
60
+ }, [])
47
61
 
48
62
  useEffect(() => {
49
63
  simulatorManager.state.on(
50
64
  StateEventType.Slices,
51
65
  (newSlices) => {
66
+ const nextState = lzString.compressToEncodedURIComponent(JSON.stringify(newSlices))
52
67
  const url = new URL(window.location.href)
53
- url.searchParams.set(
54
- STATE_PARAMS_KEY,
55
- lzString.compressToEncodedURIComponent(JSON.stringify(newSlices)),
56
- )
68
+ url.searchParams.set(STATE_PARAMS_KEY, nextState)
57
69
 
58
70
  window.history.replaceState(null, "", url)
71
+ setTrustedState(nextState)
59
72
  // Wait until the next tick to prevent URL state race conditions.
60
73
  setTimeout(() => router.refresh(), 0)
61
74
  },