@sanity/vercel-protection-bypass 5.0.11 → 5.0.13

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.
@@ -0,0 +1,276 @@
1
+ import { apiVersion, fetchVercelProtectionBypassSecret, tag, vercelProtectionBypassSchemaId, vercelProtectionBypassSchemaType } from "@sanity/preview-url-secret/constants";
2
+ import { Activity, Suspense, use, useActionState, useEffect, useEffectEvent, useState, useTransition } from "react";
3
+ import { useClient } from "sanity";
4
+ import { c } from "react/compiler-runtime";
5
+ import { AddIcon } from "@sanity/icons/Add";
6
+ import { TrashIcon } from "@sanity/icons/Trash";
7
+ import { Box, Button, Card, Dialog, Flex, Heading, Spinner, Stack, Text, TextInput, useToast } from "@sanity/ui";
8
+ import { Fragment, jsx, jsxs } from "react/jsx-runtime";
9
+ async function enableVercelProtectionBypass(client, secret) {
10
+ let patch = client.patch(vercelProtectionBypassSchemaId).set({ secret });
11
+ await client.transaction().createIfNotExists({
12
+ _id: vercelProtectionBypassSchemaId,
13
+ _type: vercelProtectionBypassSchemaType
14
+ }).patch(patch).commit({ tag });
15
+ }
16
+ async function disableVercelProtectionBypass(client) {
17
+ let patch = client.patch(vercelProtectionBypassSchemaId).set({ secret: null });
18
+ await client.transaction().createIfNotExists({
19
+ _id: vercelProtectionBypassSchemaId,
20
+ _type: vercelProtectionBypassSchemaType
21
+ }).patch(patch).commit({ tag });
22
+ }
23
+ function VercelProtectionBypassTool() {
24
+ let $ = c(9), t0;
25
+ $[0] === Symbol.for("react.memo_cache_sentinel") ? (t0 = { apiVersion }, $[0] = t0) : t0 = $[0];
26
+ let client = useClient(t0), t1;
27
+ $[1] === client ? t1 = $[2] : (t1 = async function(lastLiveEventId) {
28
+ let { result, syncTags } = await client.fetch(fetchVercelProtectionBypassSecret, {}, {
29
+ filterResponse: !1,
30
+ lastLiveEventId: typeof lastLiveEventId == "string" ? lastLiveEventId : null,
31
+ tag: "preview-url-secret.fetch-vercel-bypass-protection-secret"
32
+ });
33
+ return {
34
+ secret: result,
35
+ syncTags: syncTags ?? []
36
+ };
37
+ }, $[1] = client, $[2] = t1);
38
+ let fetchSecret = t1, t2;
39
+ $[3] === fetchSecret ? t2 = $[4] : (t2 = () => fetchSecret(null), $[3] = fetchSecret, $[4] = t2);
40
+ let [initialStatePromise] = useState(t2), t3;
41
+ $[5] === Symbol.for("react.memo_cache_sentinel") ? (t3 = /* @__PURE__ */ jsx(Flex, {
42
+ align: "center",
43
+ direction: "column",
44
+ height: "fill",
45
+ justify: "center",
46
+ style: { width: "100%" },
47
+ children: /* @__PURE__ */ jsx(Spinner, {})
48
+ }), $[5] = t3) : t3 = $[5];
49
+ let t4;
50
+ return $[6] !== fetchSecret || $[7] !== initialStatePromise ? (t4 = /* @__PURE__ */ jsx(Suspense, {
51
+ fallback: t3,
52
+ children: /* @__PURE__ */ jsx(Layout, {
53
+ initialStatePromise,
54
+ fetchSecret
55
+ })
56
+ }), $[6] = fetchSecret, $[7] = initialStatePromise, $[8] = t4) : t4 = $[8], t4;
57
+ }
58
+ function Layout(t0) {
59
+ let $ = c(29), { initialStatePromise, fetchSecret } = t0, { push: pushToast } = useToast(), [isDialogOpen, setIsDialogOpen] = useState(!1), t1;
60
+ $[0] === Symbol.for("react.memo_cache_sentinel") ? (t1 = { apiVersion }, $[0] = t1) : t1 = $[0];
61
+ let client = useClient(t1), t2;
62
+ $[1] !== client || $[2] !== fetchSecret || $[3] !== pushToast ? (t2 = async (prevState, formData) => {
63
+ let action = formData.get("action");
64
+ if (typeof action != "string") throw Error("Action is not a string");
65
+ switch (action) {
66
+ case "remove-secret": return disableVercelProtectionBypass(client).then(() => (pushToast({
67
+ status: "warning",
68
+ title: "Protection bypass is now disabled"
69
+ }), {
70
+ ...prevState,
71
+ secret: null
72
+ })).catch((reason_0) => (console.error(reason_0), pushToast({
73
+ status: "error",
74
+ title: "There was an error when trying to disable protection bypass. See the browser console for more information."
75
+ }), prevState));
76
+ case "add-secret": {
77
+ let secret = formData.get("secret");
78
+ if (typeof secret != "string") throw Error("Secret is not a string");
79
+ return enableVercelProtectionBypass(client, secret).then(() => (pushToast({
80
+ status: "success",
81
+ title: "Protection bypass is now enabled"
82
+ }), setIsDialogOpen(!1), {
83
+ ...prevState,
84
+ secret
85
+ })).catch((reason) => (console.error(reason), pushToast({
86
+ status: "error",
87
+ title: "There was an error when trying to enable protection bypass. See the browser console for more information."
88
+ }), prevState));
89
+ }
90
+ case "refresh-secret": return fetchSecret(formData.get("lastLiveEventId"));
91
+ default: throw Error(`Unknown action: ${action}`);
92
+ }
93
+ }, $[1] = client, $[2] = fetchSecret, $[3] = pushToast, $[4] = t2) : t2 = $[4];
94
+ let [formState, formAction, isPending] = useActionState(t2, use(initialStatePromise)), isBackgroundRefetch = useRefetchOnLiveEvent(client, formState, formAction), loading = isPending && !isBackgroundRefetch, enabled = !!formState.secret, t3;
95
+ $[5] === Symbol.for("react.memo_cache_sentinel") ? (t3 = {
96
+ height: "100%",
97
+ alignItems: "center",
98
+ justifyContent: "center",
99
+ flexDirection: "column"
100
+ }, $[5] = t3) : t3 = $[5];
101
+ let t4;
102
+ $[6] === Symbol.for("react.memo_cache_sentinel") ? (t4 = { maxWidth: 640 }, $[6] = t4) : t4 = $[6];
103
+ let t5, t6;
104
+ $[7] === Symbol.for("react.memo_cache_sentinel") ? (t5 = {
105
+ justifyItems: "flex-start",
106
+ textWrap: "pretty"
107
+ }, t6 = /* @__PURE__ */ jsx(Heading, { children: "Vercel Protection Bypass" }), $[7] = t5, $[8] = t6) : (t5 = $[7], t6 = $[8]);
108
+ let t7;
109
+ $[9] !== enabled || $[10] !== loading ? (t7 = /* @__PURE__ */ jsx(Box, {
110
+ as: "form",
111
+ action: formAction,
112
+ sizing: "border",
113
+ display: "flex",
114
+ style: t3,
115
+ children: /* @__PURE__ */ jsx(Stack, {
116
+ gap: 5,
117
+ children: /* @__PURE__ */ jsx(Card, {
118
+ padding: 4,
119
+ style: t4,
120
+ children: /* @__PURE__ */ jsxs(Stack, {
121
+ gap: 4,
122
+ style: t5,
123
+ children: [t6, enabled ? /* @__PURE__ */ jsxs(Fragment, { children: [
124
+ /* @__PURE__ */ jsx(Box, { children: /* @__PURE__ */ jsxs(Text, {
125
+ style: { textWrap: "pretty" },
126
+ children: [
127
+ "Sanity Presentation is setup to use",
128
+ " ",
129
+ /* @__PURE__ */ jsx("a", {
130
+ href: "https://vercel.com/docs/security/deployment-protection/methods-to-bypass-deployment-protection/protection-bypass-automation",
131
+ target: "_blank",
132
+ rel: "noreferrer",
133
+ children: "protection bypass for automation"
134
+ }),
135
+ " ",
136
+ "in order to display protected deployments in its preview iframe for the current Sanity dataset."
137
+ ]
138
+ }) }),
139
+ /* @__PURE__ */ jsx(Box, { children: /* @__PURE__ */ jsx(Text, { children: "You can turn off automatic protection bypass at any time by clicking the button below." }) }),
140
+ /* @__PURE__ */ jsx(Button, {
141
+ mode: "ghost",
142
+ tone: "critical",
143
+ icon: /* @__PURE__ */ jsx(TrashIcon, {}),
144
+ loading,
145
+ type: "submit",
146
+ name: "action",
147
+ value: "remove-secret",
148
+ text: "Remove secret"
149
+ }),
150
+ /* @__PURE__ */ jsx(Text, { children: "Protection bypass remains enabled if this plugin is removed from your Sanity config." })
151
+ ] }) : /* @__PURE__ */ jsxs(Fragment, { children: [
152
+ /* @__PURE__ */ jsx(Box, { children: /* @__PURE__ */ jsxs(Text, {
153
+ style: { textWrap: "pretty" },
154
+ children: [
155
+ "Follow the instructions on",
156
+ " ",
157
+ /* @__PURE__ */ jsx("a", {
158
+ href: "https://vercel.com/docs/security/deployment-protection/methods-to-bypass-deployment-protection/protection-bypass-automation",
159
+ target: "_blank",
160
+ rel: "noreferrer",
161
+ children: "how to enable protection bypass for automation"
162
+ }),
163
+ "."
164
+ ]
165
+ }) }),
166
+ /* @__PURE__ */ jsx(Box, { children: /* @__PURE__ */ jsx(Text, { children: "This will setup a secret that Vercel exposes as an environment variable called VERCEL_AUTOMATION_BYPASS_SECRET, its value is the secret you need." }) }),
167
+ /* @__PURE__ */ jsx(Button, {
168
+ mode: "ghost",
169
+ icon: /* @__PURE__ */ jsx(AddIcon, {}),
170
+ onClick: () => {
171
+ setIsDialogOpen(!0);
172
+ },
173
+ text: "Add secret"
174
+ }),
175
+ /* @__PURE__ */ jsx(Text, { children: "If you're using Sanity Presentation Tool with multiple protected deployments ensure that they have the same secret set, as this tool will set a secret that is shared in your dataset with all instances of Presentation Tool." })
176
+ ] })]
177
+ })
178
+ })
179
+ })
180
+ }), $[9] = enabled, $[10] = loading, $[11] = t7) : t7 = $[11];
181
+ let t8 = isDialogOpen ? "visible" : "hidden", t9;
182
+ $[12] === Symbol.for("react.memo_cache_sentinel") ? (t9 = () => setIsDialogOpen(!1), $[12] = t9) : t9 = $[12];
183
+ let t10, t11;
184
+ $[13] === Symbol.for("react.memo_cache_sentinel") ? (t10 = /* @__PURE__ */ jsx(Text, {
185
+ as: "label",
186
+ weight: "semibold",
187
+ size: 1,
188
+ children: "Add bypass secret"
189
+ }), t11 = /* @__PURE__ */ jsx(Text, {
190
+ muted: !0,
191
+ size: 1,
192
+ children: "Make sure it's the same secret the Vercel deployment is using that's loaded in the preview iframe."
193
+ }), $[13] = t10, $[14] = t11) : (t10 = $[13], t11 = $[14]);
194
+ let t12;
195
+ $[15] === loading ? t12 = $[16] : (t12 = /* @__PURE__ */ jsxs(Stack, {
196
+ gap: 2,
197
+ children: [
198
+ t10,
199
+ t11,
200
+ /* @__PURE__ */ jsx(TextInput, {
201
+ name: "secret",
202
+ onFocus: _temp,
203
+ onBlur: _temp2,
204
+ minLength: 32,
205
+ maxLength: 32,
206
+ autoComplete: "off",
207
+ autoCapitalize: "off",
208
+ autoCorrect: "off",
209
+ spellCheck: "false",
210
+ disabled: loading
211
+ })
212
+ ]
213
+ }), $[15] = loading, $[16] = t12);
214
+ let t13 = loading ? "Saving…" : "Save", t14;
215
+ $[17] !== loading || $[18] !== t13 ? (t14 = /* @__PURE__ */ jsx(Button, {
216
+ type: "submit",
217
+ loading,
218
+ text: t13,
219
+ tone: "positive",
220
+ name: "action",
221
+ value: "add-secret"
222
+ }), $[17] = loading, $[18] = t13, $[19] = t14) : t14 = $[19];
223
+ let t15;
224
+ $[20] !== t12 || $[21] !== t14 ? (t15 = /* @__PURE__ */ jsx(Dialog, {
225
+ animate: !0,
226
+ id: "add-secret-dialog",
227
+ onClickOutside: t9,
228
+ children: /* @__PURE__ */ jsx(Card, {
229
+ as: "form",
230
+ action: formAction,
231
+ padding: 3,
232
+ children: /* @__PURE__ */ jsxs(Stack, {
233
+ gap: 3,
234
+ children: [t12, t14]
235
+ })
236
+ })
237
+ }), $[20] = t12, $[21] = t14, $[22] = t15) : t15 = $[22];
238
+ let t16;
239
+ $[23] !== t15 || $[24] !== t8 ? (t16 = /* @__PURE__ */ jsx(Activity, {
240
+ mode: t8,
241
+ children: t15
242
+ }), $[23] = t15, $[24] = t8, $[25] = t16) : t16 = $[25];
243
+ let t17;
244
+ return $[26] !== t16 || $[27] !== t7 ? (t17 = /* @__PURE__ */ jsxs(Fragment, { children: [t7, t16] }), $[26] = t16, $[27] = t7, $[28] = t17) : t17 = $[28], t17;
245
+ }
246
+ function _temp2(event_0) {
247
+ event_0.currentTarget.setCustomValidity(event_0.currentTarget.value.length == 32 ? "" : "Secret must be 32 characters long"), event_0.currentTarget.required = !0;
248
+ }
249
+ function _temp(event) {
250
+ event.currentTarget.setCustomValidity("");
251
+ }
252
+ function useRefetchOnLiveEvent(client, formState, action) {
253
+ let $ = c(8), [isBackgroundRefetch, startTransition] = useTransition(), t0;
254
+ $[0] !== action || $[1] !== formState ? (t0 = (event) => {
255
+ if (event.type === "message" && event.tags.some((tag) => formState.syncTags.includes(tag))) {
256
+ let formData = new FormData();
257
+ formData.set("action", "refresh-secret"), formData.set("lastLiveEventId", event.id), startTransition(() => action(formData));
258
+ }
259
+ }, $[0] = action, $[1] = formState, $[2] = t0) : t0 = $[2];
260
+ let handleLiveEvent = useEffectEvent(t0), t1;
261
+ $[3] !== client.live || $[4] !== handleLiveEvent ? (t1 = () => {
262
+ let subscription = client.live.events().subscribe({
263
+ next: handleLiveEvent,
264
+ error: _temp3
265
+ });
266
+ return () => subscription.unsubscribe();
267
+ }, $[3] = client.live, $[4] = handleLiveEvent, $[5] = t1) : t1 = $[5];
268
+ let t2;
269
+ return $[6] === client ? t2 = $[7] : (t2 = [client], $[6] = client, $[7] = t2), useEffect(t1, t2), isBackgroundRefetch;
270
+ }
271
+ function _temp3(reason) {
272
+ return console.error(reason);
273
+ }
274
+ export { VercelProtectionBypassTool as default };
275
+
276
+ //# sourceMappingURL=VercelProtectionBypassTool.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"VercelProtectionBypassTool.js","names":["SyncTag","LiveEvent","AddIcon","TrashIcon","apiVersion","vercelProtectionBypassSchemaId","_id","vercelProtectionBypassSchemaType","_type","tag","fetchVercelProtectionBypassSecret","Box","Button","Card","Dialog","Flex","Heading","Spinner","Stack","Text","TextInput","useToast","Activity","Suspense","use","useActionState","useEffect","useEffectEvent","useState","useTransition","useClient","SanityClient","enableVercelProtectionBypass","client","secret","Promise","patch","set","transaction","createIfNotExists","commit","disableVercelProtectionBypass","VercelProtectionBypassTool","$","_c","t0","Symbol","for","t1","fetchSecret","lastLiveEventId","result","syncTags","fetch","filterResponse","t2","initialStatePromise","t3","width","t4","FormAction","FormName","FormState","Layout","push","pushToast","isDialogOpen","setIsDialogOpen","prevState","formData","action","get","Error","then","status","title","catch","reason_0","console","error","reason","action_0","formState","formAction","isPending","isBackgroundRefetch","useRefetchOnLiveEvent","loading","enabled","Boolean","height","alignItems","justifyContent","flexDirection","maxWidth","t5","t6","justifyItems","textWrap","t7","t8","t9","t10","t11","t12","_temp","_temp2","t13","t14","t15","t16","t17","event_0","event","currentTarget","setCustomValidity","value","length","required","startTransition","type","tags","some","includes","FormData","id","handleLiveEvent","live","subscription","events","subscribe","next","_temp3","unsubscribe"],"sources":["../src/VercelProtectionBypassTool.tsx"],"sourcesContent":["import type {SyncTag, LiveEvent} from '@sanity/client'\nimport {AddIcon} from '@sanity/icons/Add'\nimport {TrashIcon} from '@sanity/icons/Trash'\nimport {\n apiVersion,\n vercelProtectionBypassSchemaId as _id,\n vercelProtectionBypassSchemaType as _type,\n tag,\n fetchVercelProtectionBypassSecret,\n} from '@sanity/preview-url-secret/constants'\nimport {\n Box,\n Button,\n Card,\n Dialog,\n Flex,\n Heading,\n Spinner,\n Stack,\n Text,\n TextInput,\n useToast,\n} from '@sanity/ui'\nimport {\n Activity,\n Suspense,\n use,\n useActionState,\n useEffect,\n useEffectEvent,\n useState,\n useTransition,\n} from 'react'\nimport {useClient, type SanityClient} from 'sanity'\n\nasync function enableVercelProtectionBypass(client: SanityClient, secret: string): Promise<void> {\n const patch = client.patch(_id).set({secret})\n await client.transaction().createIfNotExists({_id, _type}).patch(patch).commit({tag})\n}\n\nasync function disableVercelProtectionBypass(client: SanityClient): Promise<void> {\n const patch = client.patch(_id).set({secret: null})\n await client.transaction().createIfNotExists({_id, _type}).patch(patch).commit({tag})\n}\n\nexport default function VercelProtectionBypassTool(): React.JSX.Element {\n const client = useClient({apiVersion: apiVersion})\n\n async function fetchSecret(lastLiveEventId: FormDataEntryValue | null): Promise<FormState> {\n const {result, syncTags} = await client.fetch<string | null>(\n fetchVercelProtectionBypassSecret,\n {},\n {\n filterResponse: false,\n lastLiveEventId: typeof lastLiveEventId === 'string' ? lastLiveEventId : null,\n tag: 'preview-url-secret.fetch-vercel-bypass-protection-secret',\n },\n )\n return {secret: result, syncTags: syncTags ?? []}\n }\n const [initialStatePromise] = useState(() => fetchSecret(null))\n\n return (\n <Suspense\n fallback={\n <Flex\n align=\"center\"\n direction=\"column\"\n height=\"fill\"\n justify=\"center\"\n style={{width: '100%'}}\n >\n <Spinner />\n </Flex>\n }\n >\n <Layout initialStatePromise={initialStatePromise} fetchSecret={fetchSecret} />\n </Suspense>\n )\n}\n\ntype FormAction = 'remove-secret' | 'add-secret' | 'refresh-secret'\ntype FormName = 'action' | 'lastLiveEventId' | 'secret'\ntype FormState = {secret: string | null; syncTags: SyncTag[]}\n\nfunction Layout({\n initialStatePromise,\n fetchSecret,\n}: {\n initialStatePromise: Promise<FormState>\n fetchSecret(this: void, lastLiveEventId: FormDataEntryValue | null): Promise<FormState>\n}) {\n const {push: pushToast} = useToast()\n const [isDialogOpen, setIsDialogOpen] = useState(false)\n const client = useClient({apiVersion})\n\n const action = async (prevState: FormState, formData: FormData): Promise<FormState> => {\n const action = formData.get('action' satisfies FormName)\n if (typeof action !== 'string') {\n throw new Error('Action is not a string')\n }\n\n switch (action) {\n case 'remove-secret':\n return disableVercelProtectionBypass(client)\n .then((): FormState => {\n pushToast({\n status: 'warning',\n title: 'Protection bypass is now disabled',\n })\n return {...prevState, secret: null}\n })\n .catch((reason): FormState => {\n console.error(reason)\n pushToast({\n status: 'error',\n title:\n 'There was an error when trying to disable protection bypass. See the browser console for more information.',\n })\n return prevState\n })\n\n case 'add-secret': {\n const secret = formData.get('secret' satisfies FormName)\n if (typeof secret !== 'string') {\n throw new Error('Secret is not a string')\n }\n return enableVercelProtectionBypass(client, secret)\n .then(() => {\n pushToast({\n status: 'success',\n title: 'Protection bypass is now enabled',\n })\n setIsDialogOpen(false)\n return {...prevState, secret}\n })\n .catch((reason) => {\n console.error(reason)\n pushToast({\n status: 'error',\n title:\n 'There was an error when trying to enable protection bypass. See the browser console for more information.',\n })\n return prevState\n })\n }\n case 'refresh-secret':\n return fetchSecret(formData.get('lastLiveEventId' satisfies FormName))\n default:\n throw new Error(`Unknown action: ${action}`)\n }\n }\n\n const [formState, formAction, isPending] = useActionState(action, use(initialStatePromise))\n const isBackgroundRefetch = useRefetchOnLiveEvent(client, formState, formAction)\n\n const loading = isPending && !isBackgroundRefetch\n const enabled = Boolean(formState.secret)\n\n return (\n <>\n <Box\n as=\"form\"\n action={formAction}\n sizing=\"border\"\n display=\"flex\"\n style={{\n height: '100%',\n alignItems: 'center',\n justifyContent: 'center',\n flexDirection: 'column',\n }}\n >\n <Stack gap={5}>\n <Card padding={4} style={{maxWidth: 640}}>\n <Stack gap={4} style={{justifyItems: 'flex-start', textWrap: 'pretty'}}>\n <Heading>Vercel Protection Bypass</Heading>\n {enabled ? (\n <>\n <Box>\n <Text style={{textWrap: 'pretty'}}>\n Sanity Presentation is setup to use{' '}\n <a\n href=\"https://vercel.com/docs/security/deployment-protection/methods-to-bypass-deployment-protection/protection-bypass-automation\"\n target=\"_blank\"\n rel=\"noreferrer\"\n >\n protection bypass for automation\n </a>{' '}\n in order to display protected deployments in its preview iframe for the\n current Sanity dataset.\n </Text>\n </Box>\n <Box>\n <Text>\n You can turn off automatic protection bypass at any time by clicking the\n button below.\n </Text>\n </Box>\n <Button\n mode=\"ghost\"\n tone=\"critical\"\n icon={<TrashIcon />}\n loading={loading}\n type=\"submit\"\n name={'action' satisfies FormName}\n value={'remove-secret' satisfies FormAction}\n text=\"Remove secret\"\n />\n <Text>\n Protection bypass remains enabled if this plugin is removed from your Sanity\n config.\n </Text>\n </>\n ) : (\n <>\n <Box>\n <Text style={{textWrap: 'pretty'}}>\n Follow the instructions on{' '}\n <a\n href=\"https://vercel.com/docs/security/deployment-protection/methods-to-bypass-deployment-protection/protection-bypass-automation\"\n target=\"_blank\"\n rel=\"noreferrer\"\n >\n how to enable protection bypass for automation\n </a>\n .\n </Text>\n </Box>\n <Box>\n <Text>\n This will setup a secret that Vercel exposes as an environment variable called\n VERCEL_AUTOMATION_BYPASS_SECRET, its value is the secret you need.\n </Text>\n </Box>\n <Button\n mode=\"ghost\"\n icon={<AddIcon />}\n onClick={() => {\n setIsDialogOpen(true)\n }}\n text=\"Add secret\"\n />\n <Text>\n If you&apos;re using Sanity Presentation Tool with multiple protected\n deployments ensure that they have the same secret set, as this tool will set a\n secret that is shared in your dataset with all instances of Presentation Tool.\n </Text>\n </>\n )}\n </Stack>\n </Card>\n </Stack>\n </Box>\n\n <Activity mode={isDialogOpen ? 'visible' : 'hidden'}>\n <Dialog animate id=\"add-secret-dialog\" onClickOutside={() => setIsDialogOpen(false)}>\n <Card as=\"form\" action={formAction} padding={3}>\n <Stack gap={3}>\n <Stack gap={2}>\n <Text as=\"label\" weight=\"semibold\" size={1}>\n Add bypass secret\n </Text>\n <Text muted size={1}>\n {`Make sure it's the same secret the Vercel deployment is using that's loaded in the preview iframe.`}\n </Text>\n <TextInput\n name={'secret' satisfies FormName}\n onFocus={(event) => {\n event.currentTarget.setCustomValidity('')\n }}\n onBlur={(event) => {\n event.currentTarget.setCustomValidity(\n event.currentTarget.value.length == 32\n ? ''\n : 'Secret must be 32 characters long',\n )\n event.currentTarget.required = true\n }}\n minLength={32}\n maxLength={32}\n autoComplete=\"off\"\n autoCapitalize=\"off\"\n autoCorrect=\"off\"\n spellCheck=\"false\"\n disabled={loading}\n />\n </Stack>\n <Button\n type=\"submit\"\n loading={loading}\n text={loading ? 'Saving…' : 'Save'}\n tone=\"positive\"\n name={'action' satisfies FormName}\n value={'add-secret' satisfies FormAction}\n />\n </Stack>\n </Card>\n </Dialog>\n </Activity>\n </>\n )\n}\n\ntype isBackgroundRefetch = boolean\nfunction useRefetchOnLiveEvent(\n client: SanityClient,\n formState: FormState,\n action: (formData: FormData) => void,\n): isBackgroundRefetch {\n const [isBackgroundRefetch, startTransition] = useTransition()\n const handleLiveEvent = useEffectEvent((event: LiveEvent) => {\n if (event.type === 'message' && event.tags.some((tag) => formState.syncTags.includes(tag))) {\n const formData = new FormData()\n formData.set('action' satisfies FormName, 'refresh-secret' satisfies FormAction)\n formData.set('lastLiveEventId' satisfies FormName, event.id)\n startTransition(() => action(formData))\n }\n })\n useEffect(() => {\n const subscription = client.live.events().subscribe({\n next: handleLiveEvent,\n error: (reason) => console.error(reason),\n })\n\n return () => subscription.unsubscribe()\n }, [client])\n return isBackgroundRefetch\n}\n"],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","names":[],"sources":["../src/index.ts"],"mappings":";UAYiB,4BAAA;EACf,IAAA;EACA,KAAA;EACA,IAAA,GAAO,KAAA,CAAM,aAAA;AAAA;AAAA,cAkCF,0BAAA,EAA4B,MAAA,CAAO,4BAAA"}
1
+ {"version":3,"file":"index.d.ts","names":[],"sources":["../src/index.ts"],"mappings":";UAYiB,4BAAA;EACf,IAAA;EACA,KAAA;EACA,IAAA,GAAO,KAAA,CAAM,aAAa;AAAA;AAAA,cAkCf,0BAAA,EAA4B,MAAM,CAAC,4BAAA"}
package/dist/index.js CHANGED
@@ -3,57 +3,45 @@ import { CloseCircleIcon } from "@sanity/icons/CloseCircle";
3
3
  import { LockIcon } from "@sanity/icons/Lock";
4
4
  import { vercelProtectionBypassSchemaType } from "@sanity/preview-url-secret/constants";
5
5
  import { lazy } from "react";
6
- import { defineType, definePlugin } from "sanity";
6
+ import { definePlugin, defineType } from "sanity";
7
7
  const id = "vercel-protection-bypass", defaultTitle = "Vercel Protection Bypass", schema = defineType({
8
- type: "document",
9
- icon: LockIcon,
10
- name: vercelProtectionBypassSchemaType,
11
- title: defaultTitle,
12
- readOnly: !0,
13
- fields: [{
14
- type: "string",
15
- name: "secret",
16
- title: "Secret"
17
- }],
18
- preview: {
19
- select: {
20
- secret: "secret"
21
- },
22
- prepare(data) {
23
- const enabled = data.secret !== null;
24
- return {
25
- title: enabled ? "Enabled" : "Disabled",
26
- subtitle: defaultTitle,
27
- media: enabled ? CheckmarkCircleIcon : CloseCircleIcon
28
- };
29
- }
30
- }
31
- }), VercelProtectionBypassTool = lazy(() => import("./_chunks-es/VercelProtectionBypassTool.js")), vercelProtectionBypassTool = definePlugin((options) => {
32
- const {
33
- name = "vercel-protection-bypass",
34
- title = "Vercel Protection Bypass",
35
- icon = LockIcon,
36
- ...config
37
- } = options || {};
38
- return {
39
- name: `@sanity/preview-url-secret/${id}`,
40
- tools: [{
41
- name,
42
- title,
43
- icon,
44
- component: VercelProtectionBypassTool,
45
- options: config,
46
- __internalApplicationType: `sanity/${id}`
47
- }],
48
- document: {
49
- actions: (prev, context) => context.schemaType !== vercelProtectionBypassSchemaType ? prev : []
50
- },
51
- schema: {
52
- types: [schema]
53
- }
54
- };
8
+ type: "document",
9
+ icon: LockIcon,
10
+ name: vercelProtectionBypassSchemaType,
11
+ title: defaultTitle,
12
+ readOnly: !0,
13
+ fields: [{
14
+ type: "string",
15
+ name: "secret",
16
+ title: "Secret"
17
+ }],
18
+ preview: {
19
+ select: { secret: "secret" },
20
+ prepare(data) {
21
+ let enabled = data.secret !== null;
22
+ return {
23
+ title: enabled ? "Enabled" : "Disabled",
24
+ subtitle: defaultTitle,
25
+ media: enabled ? CheckmarkCircleIcon : CloseCircleIcon
26
+ };
27
+ }
28
+ }
29
+ }), VercelProtectionBypassTool = lazy(() => import("./VercelProtectionBypassTool.js")), vercelProtectionBypassTool = definePlugin((options) => {
30
+ let { name = "vercel-protection-bypass", title = "Vercel Protection Bypass", icon = LockIcon, ...config } = options || {};
31
+ return {
32
+ name: `@sanity/preview-url-secret/${id}`,
33
+ tools: [{
34
+ name,
35
+ title,
36
+ icon,
37
+ component: VercelProtectionBypassTool,
38
+ options: config,
39
+ __internalApplicationType: `sanity/${id}`
40
+ }],
41
+ document: { actions: (prev, context) => context.schemaType === vercelProtectionBypassSchemaType ? [] : prev },
42
+ schema: { types: [schema] }
43
+ };
55
44
  });
56
- export {
57
- vercelProtectionBypassTool
58
- };
59
- //# sourceMappingURL=index.js.map
45
+ export { vercelProtectionBypassTool };
46
+
47
+ //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sources":["../src/index.ts"],"sourcesContent":["import {CheckmarkCircleIcon} from '@sanity/icons/CheckmarkCircle'\nimport {CloseCircleIcon} from '@sanity/icons/CloseCircle'\nimport {LockIcon} from '@sanity/icons/Lock'\nimport {\n vercelProtectionBypassSchemaId as _id,\n vercelProtectionBypassSchemaType as type,\n} from '@sanity/preview-url-secret/constants'\nimport {lazy} from 'react'\nimport {definePlugin, defineType, type Plugin} from 'sanity'\n\nconst id = 'vercel-protection-bypass'\n\nexport interface VercelProtectionBypassConfig {\n name?: string\n title?: string\n icon?: React.ComponentType\n}\n\nconst defaultTitle = 'Vercel Protection Bypass'\nconst schema = defineType({\n type: 'document',\n icon: LockIcon,\n name: type,\n title: defaultTitle,\n readOnly: true,\n fields: [\n {\n type: 'string',\n name: 'secret',\n title: 'Secret',\n },\n ],\n preview: {\n select: {\n secret: 'secret',\n },\n prepare(data) {\n const enabled = data.secret !== null\n return {\n title: enabled ? 'Enabled' : 'Disabled',\n subtitle: defaultTitle,\n media: enabled ? CheckmarkCircleIcon : CloseCircleIcon,\n }\n },\n },\n})\n\nconst VercelProtectionBypassTool = lazy(() => import('./VercelProtectionBypassTool'))\n\nexport const vercelProtectionBypassTool: Plugin<VercelProtectionBypassConfig | void> = definePlugin(\n (options) => {\n const {\n name = 'vercel-protection-bypass',\n title = 'Vercel Protection Bypass',\n icon = LockIcon,\n ...config\n } = options || {}\n return {\n name: `@sanity/preview-url-secret/${id}`,\n tools: [\n {\n name,\n title,\n icon: icon,\n component: VercelProtectionBypassTool,\n options: config,\n __internalApplicationType: `sanity/${id}`,\n },\n ],\n document: {\n actions: (prev, context) => {\n if (context.schemaType !== type) {\n return prev\n }\n return []\n },\n },\n schema: {types: [schema]},\n }\n },\n)\n"],"names":["id","defaultTitle","schema","defineType","type","icon","LockIcon","name","title","readOnly","fields","preview","select","secret","prepare","data","enabled","subtitle","media","CheckmarkCircleIcon","CloseCircleIcon","VercelProtectionBypassTool","lazy","vercelProtectionBypassTool","definePlugin","options","config","tools","component","__internalApplicationType","document","actions","prev","context","schemaType","types"],"mappings":";;;;;;AAUA,MAAMA,KAAK,4BAQLC,eAAe,4BACfC,SAASC,WAAW;AAAA,EACxBC,MAAM;AAAA,EACNC,MAAMC;AAAAA,EACNC,MAAMH;AAAAA,EACNI,OAAOP;AAAAA,EACPQ,UAAU;AAAA,EACVC,QAAQ,CACN;AAAA,IACEN,MAAM;AAAA,IACNG,MAAM;AAAA,IACNC,OAAO;AAAA,EAAA,CACR;AAAA,EAEHG,SAAS;AAAA,IACPC,QAAQ;AAAA,MACNC,QAAQ;AAAA,IAAA;AAAA,IAEVC,QAAQC,MAAM;AACZ,YAAMC,UAAUD,KAAKF,WAAW;AAChC,aAAO;AAAA,QACLL,OAAOQ,UAAU,YAAY;AAAA,QAC7BC,UAAUhB;AAAAA,QACViB,OAAOF,UAAUG,sBAAsBC;AAAAA,MAAAA;AAAAA,IAE3C;AAAA,EAAA;AAEJ,CAAC,GAEKC,6BAA6BC,KAAK,MAAM,OAAO,4CAA8B,CAAC,GAEvEC,6BAA0EC,aACpFC,CAAAA,YAAY;AACX,QAAM;AAAA,IACJlB,OAAO;AAAA,IACPC,QAAQ;AAAA,IACRH,OAAOC;AAAAA,IACP,GAAGoB;AAAAA,EAAAA,IACDD,WAAW,CAAA;AACf,SAAO;AAAA,IACLlB,MAAM,8BAA8BP,EAAE;AAAA,IACtC2B,OAAO,CACL;AAAA,MACEpB;AAAAA,MACAC;AAAAA,MACAH;AAAAA,MACAuB,WAAWP;AAAAA,MACXI,SAASC;AAAAA,MACTG,2BAA2B,UAAU7B,EAAE;AAAA,IAAA,CACxC;AAAA,IAEH8B,UAAU;AAAA,MACRC,SAASA,CAACC,MAAMC,YACVA,QAAQC,eAAe9B,mCAClB4B,OAEF,CAAA;AAAA,IAAA;AAAA,IAGX9B,QAAQ;AAAA,MAACiC,OAAO,CAACjC,MAAM;AAAA,IAAA;AAAA,EAAC;AAE5B,CACF;"}
1
+ {"version":3,"file":"index.js","names":["CheckmarkCircleIcon","CloseCircleIcon","LockIcon","vercelProtectionBypassSchemaId","_id","vercelProtectionBypassSchemaType","type","lazy","definePlugin","defineType","Plugin","id","VercelProtectionBypassConfig","name","title","icon","React","ComponentType","defaultTitle","schema","readOnly","fields","preview","select","secret","prepare","data","enabled","subtitle","media","VercelProtectionBypassTool","vercelProtectionBypassTool","options","config","tools","component","__internalApplicationType","document","actions","prev","context","schemaType","types"],"sources":["../src/index.ts"],"sourcesContent":["import {CheckmarkCircleIcon} from '@sanity/icons/CheckmarkCircle'\nimport {CloseCircleIcon} from '@sanity/icons/CloseCircle'\nimport {LockIcon} from '@sanity/icons/Lock'\nimport {\n vercelProtectionBypassSchemaId as _id,\n vercelProtectionBypassSchemaType as type,\n} from '@sanity/preview-url-secret/constants'\nimport {lazy} from 'react'\nimport {definePlugin, defineType, type Plugin} from 'sanity'\n\nconst id = 'vercel-protection-bypass'\n\nexport interface VercelProtectionBypassConfig {\n name?: string\n title?: string\n icon?: React.ComponentType\n}\n\nconst defaultTitle = 'Vercel Protection Bypass'\nconst schema = defineType({\n type: 'document',\n icon: LockIcon,\n name: type,\n title: defaultTitle,\n readOnly: true,\n fields: [\n {\n type: 'string',\n name: 'secret',\n title: 'Secret',\n },\n ],\n preview: {\n select: {\n secret: 'secret',\n },\n prepare(data) {\n const enabled = data.secret !== null\n return {\n title: enabled ? 'Enabled' : 'Disabled',\n subtitle: defaultTitle,\n media: enabled ? CheckmarkCircleIcon : CloseCircleIcon,\n }\n },\n },\n})\n\nconst VercelProtectionBypassTool = lazy(() => import('./VercelProtectionBypassTool'))\n\nexport const vercelProtectionBypassTool: Plugin<VercelProtectionBypassConfig | void> = definePlugin(\n (options) => {\n const {\n name = 'vercel-protection-bypass',\n title = 'Vercel Protection Bypass',\n icon = LockIcon,\n ...config\n } = options || {}\n return {\n name: `@sanity/preview-url-secret/${id}`,\n tools: [\n {\n name,\n title,\n icon: icon,\n component: VercelProtectionBypassTool,\n options: config,\n __internalApplicationType: `sanity/${id}`,\n },\n ],\n document: {\n actions: (prev, context) => {\n if (context.schemaType !== type) {\n return prev\n }\n return []\n },\n },\n schema: {types: [schema]},\n }\n },\n)\n"],"mappings":";;;;;;AAUA,MAAMW,KAAK,4BAQLO,eAAe,4BACfC,SAASV,WAAW;CACxBH,MAAM;CACNS,MAAMb;CACNW,MAAMP;CACNQ,OAAOI;CACPE,UAAU;CACVC,QAAQ,CACN;EACEf,MAAM;EACNO,MAAM;EACNC,OAAO;CACT,CAAC;CAEHQ,SAAS;EACPC,QAAQ,EACNC,QAAQ,SACV;EACAC,QAAQC,MAAM;GACZ,IAAMC,UAAUD,KAAKF,WAAW;GAChC,OAAO;IACLV,OAAOa,UAAU,YAAY;IAC7BC,UAAUV;IACVW,OAAOF,UAAU3B,sBAAsBC;GACzC;EACF;CACF;AACF,CAAC,GAEK6B,6BAA6BvB,WAAW,OAAO,kCAA+B,GAEvEwB,6BAA0EvB,cACpFwB,YAAY;CACX,IAAM,EACJnB,OAAO,4BACPC,QAAQ,4BACRC,OAAOb,UACP,GAAG+B,WACDD,WAAW,CAAC;CAChB,OAAO;EACLnB,MAAM,8BAA8BF;EACpCuB,OAAO,CACL;GACErB;GACAC;GACMC;GACNoB,WAAWL;GACXE,SAASC;GACTG,2BAA2B,UAAUzB;EACvC,CAAC;EAEH0B,UAAU,EACRC,UAAUC,MAAMC,YACVA,QAAQC,eAAenC,mCAGpB,CAAA,IAFEiC,KAIb;EACApB,QAAQ,EAACuB,OAAO,CAACvB,MAAM,EAAC;CAC1B;AACF,CACF"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sanity/vercel-protection-bypass",
3
- "version": "5.0.11",
3
+ "version": "5.0.13",
4
4
  "keywords": [
5
5
  "sanity",
6
6
  "sanity-plugin",
@@ -28,21 +28,21 @@
28
28
  "./package.json": "./package.json"
29
29
  },
30
30
  "dependencies": {
31
- "@sanity/icons": "^4.1.0",
31
+ "@sanity/icons": "^5.0.0",
32
32
  "@sanity/preview-url-secret": "^4.0.7",
33
33
  "@sanity/ui": "^3.3.0"
34
34
  },
35
35
  "devDependencies": {
36
36
  "@sanity/client": "^7.23.0",
37
- "@sanity/pkg-utils": "^10.8.2",
37
+ "@sanity/tsconfig": "^2.2.0",
38
+ "@sanity/tsdown-config": "^0.11.0",
38
39
  "@types/node": "^24.13.2",
39
40
  "@types/react": "^19.2.17",
40
41
  "babel-plugin-react-compiler": "^1.0.0",
41
42
  "react": "^19.2.7",
42
43
  "sanity": "^6.3.0",
43
44
  "styled-components": "^6.4.3",
44
- "@repo/package.config": "0.0.0",
45
- "@repo/tsconfig": "0.0.0"
45
+ "tsdown": "^0.22.3"
46
46
  },
47
47
  "peerDependencies": {
48
48
  "react": "^19.2",
@@ -52,6 +52,6 @@
52
52
  "node": ">=20.19 <22 || >=22.12"
53
53
  },
54
54
  "scripts": {
55
- "build": "pkg build --strict --check --clean"
55
+ "build": "tsdown"
56
56
  }
57
57
  }
@@ -1,223 +0,0 @@
1
- import { jsx, jsxs, Fragment } from "react/jsx-runtime";
2
- import { c } from "react/compiler-runtime";
3
- import { AddIcon } from "@sanity/icons/Add";
4
- import { TrashIcon } from "@sanity/icons/Trash";
5
- import { apiVersion, fetchVercelProtectionBypassSecret, vercelProtectionBypassSchemaId, vercelProtectionBypassSchemaType, tag } from "@sanity/preview-url-secret/constants";
6
- import { Flex, Spinner, useToast, Heading, Box, Stack, Card, Text, Button, TextInput, Dialog } from "@sanity/ui";
7
- import { useState, Suspense, useActionState, use, useTransition, useEffectEvent, useEffect, Activity } from "react";
8
- import { useClient } from "sanity";
9
- async function enableVercelProtectionBypass(client, secret) {
10
- const patch = client.patch(vercelProtectionBypassSchemaId).set({
11
- secret
12
- });
13
- await client.transaction().createIfNotExists({
14
- _id: vercelProtectionBypassSchemaId,
15
- _type: vercelProtectionBypassSchemaType
16
- }).patch(patch).commit({
17
- tag
18
- });
19
- }
20
- async function disableVercelProtectionBypass(client) {
21
- const patch = client.patch(vercelProtectionBypassSchemaId).set({
22
- secret: null
23
- });
24
- await client.transaction().createIfNotExists({
25
- _id: vercelProtectionBypassSchemaId,
26
- _type: vercelProtectionBypassSchemaType
27
- }).patch(patch).commit({
28
- tag
29
- });
30
- }
31
- function VercelProtectionBypassTool() {
32
- const $ = c(9);
33
- let t0;
34
- $[0] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (t0 = {
35
- apiVersion
36
- }, $[0] = t0) : t0 = $[0];
37
- const client = useClient(t0);
38
- let t1;
39
- $[1] !== client ? (t1 = async function(lastLiveEventId) {
40
- const {
41
- result,
42
- syncTags
43
- } = await client.fetch(fetchVercelProtectionBypassSecret, {}, {
44
- filterResponse: !1,
45
- lastLiveEventId: typeof lastLiveEventId == "string" ? lastLiveEventId : null,
46
- tag: "preview-url-secret.fetch-vercel-bypass-protection-secret"
47
- });
48
- return {
49
- secret: result,
50
- syncTags: syncTags ?? []
51
- };
52
- }, $[1] = client, $[2] = t1) : t1 = $[2];
53
- const fetchSecret = t1;
54
- let t2;
55
- $[3] !== fetchSecret ? (t2 = () => fetchSecret(null), $[3] = fetchSecret, $[4] = t2) : t2 = $[4];
56
- const [initialStatePromise] = useState(t2);
57
- let t3;
58
- $[5] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (t3 = /* @__PURE__ */ jsx(Flex, { align: "center", direction: "column", height: "fill", justify: "center", style: {
59
- width: "100%"
60
- }, children: /* @__PURE__ */ jsx(Spinner, {}) }), $[5] = t3) : t3 = $[5];
61
- let t4;
62
- return $[6] !== fetchSecret || $[7] !== initialStatePromise ? (t4 = /* @__PURE__ */ jsx(Suspense, { fallback: t3, children: /* @__PURE__ */ jsx(Layout, { initialStatePromise, fetchSecret }) }), $[6] = fetchSecret, $[7] = initialStatePromise, $[8] = t4) : t4 = $[8], t4;
63
- }
64
- function Layout(t0) {
65
- const $ = c(29), {
66
- initialStatePromise,
67
- fetchSecret
68
- } = t0, {
69
- push: pushToast
70
- } = useToast(), [isDialogOpen, setIsDialogOpen] = useState(!1);
71
- let t1;
72
- $[0] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (t1 = {
73
- apiVersion
74
- }, $[0] = t1) : t1 = $[0];
75
- const client = useClient(t1);
76
- let t2;
77
- $[1] !== client || $[2] !== fetchSecret || $[3] !== pushToast ? (t2 = async (prevState, formData) => {
78
- const action = formData.get("action");
79
- if (typeof action != "string")
80
- throw new Error("Action is not a string");
81
- switch (action) {
82
- case "remove-secret":
83
- return disableVercelProtectionBypass(client).then(() => (pushToast({
84
- status: "warning",
85
- title: "Protection bypass is now disabled"
86
- }), {
87
- ...prevState,
88
- secret: null
89
- })).catch((reason_0) => (console.error(reason_0), pushToast({
90
- status: "error",
91
- title: "There was an error when trying to disable protection bypass. See the browser console for more information."
92
- }), prevState));
93
- case "add-secret": {
94
- const secret = formData.get("secret");
95
- if (typeof secret != "string")
96
- throw new Error("Secret is not a string");
97
- return enableVercelProtectionBypass(client, secret).then(() => (pushToast({
98
- status: "success",
99
- title: "Protection bypass is now enabled"
100
- }), setIsDialogOpen(!1), {
101
- ...prevState,
102
- secret
103
- })).catch((reason) => (console.error(reason), pushToast({
104
- status: "error",
105
- title: "There was an error when trying to enable protection bypass. See the browser console for more information."
106
- }), prevState));
107
- }
108
- case "refresh-secret":
109
- return fetchSecret(formData.get("lastLiveEventId"));
110
- default:
111
- throw new Error(`Unknown action: ${action}`);
112
- }
113
- }, $[1] = client, $[2] = fetchSecret, $[3] = pushToast, $[4] = t2) : t2 = $[4];
114
- const action_0 = t2, [formState, formAction, isPending] = useActionState(action_0, use(initialStatePromise)), isBackgroundRefetch = useRefetchOnLiveEvent(client, formState, formAction), loading = isPending && !isBackgroundRefetch, enabled = !!formState.secret;
115
- let t3;
116
- $[5] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (t3 = {
117
- height: "100%",
118
- alignItems: "center",
119
- justifyContent: "center",
120
- flexDirection: "column"
121
- }, $[5] = t3) : t3 = $[5];
122
- let t4;
123
- $[6] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (t4 = {
124
- maxWidth: 640
125
- }, $[6] = t4) : t4 = $[6];
126
- let t5, t6;
127
- $[7] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (t5 = {
128
- justifyItems: "flex-start",
129
- textWrap: "pretty"
130
- }, t6 = /* @__PURE__ */ jsx(Heading, { children: "Vercel Protection Bypass" }), $[7] = t5, $[8] = t6) : (t5 = $[7], t6 = $[8]);
131
- let t7;
132
- $[9] !== enabled || $[10] !== loading ? (t7 = /* @__PURE__ */ jsx(Box, { as: "form", action: formAction, sizing: "border", display: "flex", style: t3, children: /* @__PURE__ */ jsx(Stack, { gap: 5, children: /* @__PURE__ */ jsx(Card, { padding: 4, style: t4, children: /* @__PURE__ */ jsxs(Stack, { gap: 4, style: t5, children: [
133
- t6,
134
- enabled ? /* @__PURE__ */ jsxs(Fragment, { children: [
135
- /* @__PURE__ */ jsx(Box, { children: /* @__PURE__ */ jsxs(Text, { style: {
136
- textWrap: "pretty"
137
- }, children: [
138
- "Sanity Presentation is setup to use",
139
- " ",
140
- /* @__PURE__ */ jsx("a", { href: "https://vercel.com/docs/security/deployment-protection/methods-to-bypass-deployment-protection/protection-bypass-automation", target: "_blank", rel: "noreferrer", children: "protection bypass for automation" }),
141
- " ",
142
- "in order to display protected deployments in its preview iframe for the current Sanity dataset."
143
- ] }) }),
144
- /* @__PURE__ */ jsx(Box, { children: /* @__PURE__ */ jsx(Text, { children: "You can turn off automatic protection bypass at any time by clicking the button below." }) }),
145
- /* @__PURE__ */ jsx(Button, { mode: "ghost", tone: "critical", icon: /* @__PURE__ */ jsx(TrashIcon, {}), loading, type: "submit", name: "action", value: "remove-secret", text: "Remove secret" }),
146
- /* @__PURE__ */ jsx(Text, { children: "Protection bypass remains enabled if this plugin is removed from your Sanity config." })
147
- ] }) : /* @__PURE__ */ jsxs(Fragment, { children: [
148
- /* @__PURE__ */ jsx(Box, { children: /* @__PURE__ */ jsxs(Text, { style: {
149
- textWrap: "pretty"
150
- }, children: [
151
- "Follow the instructions on",
152
- " ",
153
- /* @__PURE__ */ jsx("a", { href: "https://vercel.com/docs/security/deployment-protection/methods-to-bypass-deployment-protection/protection-bypass-automation", target: "_blank", rel: "noreferrer", children: "how to enable protection bypass for automation" }),
154
- "."
155
- ] }) }),
156
- /* @__PURE__ */ jsx(Box, { children: /* @__PURE__ */ jsx(Text, { children: "This will setup a secret that Vercel exposes as an environment variable called VERCEL_AUTOMATION_BYPASS_SECRET, its value is the secret you need." }) }),
157
- /* @__PURE__ */ jsx(Button, { mode: "ghost", icon: /* @__PURE__ */ jsx(AddIcon, {}), onClick: () => {
158
- setIsDialogOpen(!0);
159
- }, text: "Add secret" }),
160
- /* @__PURE__ */ jsx(Text, { children: "If you're using Sanity Presentation Tool with multiple protected deployments ensure that they have the same secret set, as this tool will set a secret that is shared in your dataset with all instances of Presentation Tool." })
161
- ] })
162
- ] }) }) }) }), $[9] = enabled, $[10] = loading, $[11] = t7) : t7 = $[11];
163
- const t8 = isDialogOpen ? "visible" : "hidden";
164
- let t9;
165
- $[12] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (t9 = () => setIsDialogOpen(!1), $[12] = t9) : t9 = $[12];
166
- let t10, t11;
167
- $[13] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (t10 = /* @__PURE__ */ jsx(Text, { as: "label", weight: "semibold", size: 1, children: "Add bypass secret" }), t11 = /* @__PURE__ */ jsx(Text, { muted: !0, size: 1, children: "Make sure it's the same secret the Vercel deployment is using that's loaded in the preview iframe." }), $[13] = t10, $[14] = t11) : (t10 = $[13], t11 = $[14]);
168
- let t12;
169
- $[15] !== loading ? (t12 = /* @__PURE__ */ jsxs(Stack, { gap: 2, children: [
170
- t10,
171
- t11,
172
- /* @__PURE__ */ jsx(TextInput, { name: "secret", onFocus: _temp, onBlur: _temp2, minLength: 32, maxLength: 32, autoComplete: "off", autoCapitalize: "off", autoCorrect: "off", spellCheck: "false", disabled: loading })
173
- ] }), $[15] = loading, $[16] = t12) : t12 = $[16];
174
- const t13 = loading ? "Saving\u2026" : "Save";
175
- let t14;
176
- $[17] !== loading || $[18] !== t13 ? (t14 = /* @__PURE__ */ jsx(Button, { type: "submit", loading, text: t13, tone: "positive", name: "action", value: "add-secret" }), $[17] = loading, $[18] = t13, $[19] = t14) : t14 = $[19];
177
- let t15;
178
- $[20] !== t12 || $[21] !== t14 ? (t15 = /* @__PURE__ */ jsx(Dialog, { animate: !0, id: "add-secret-dialog", onClickOutside: t9, children: /* @__PURE__ */ jsx(Card, { as: "form", action: formAction, padding: 3, children: /* @__PURE__ */ jsxs(Stack, { gap: 3, children: [
179
- t12,
180
- t14
181
- ] }) }) }), $[20] = t12, $[21] = t14, $[22] = t15) : t15 = $[22];
182
- let t16;
183
- $[23] !== t15 || $[24] !== t8 ? (t16 = /* @__PURE__ */ jsx(Activity, { mode: t8, children: t15 }), $[23] = t15, $[24] = t8, $[25] = t16) : t16 = $[25];
184
- let t17;
185
- return $[26] !== t16 || $[27] !== t7 ? (t17 = /* @__PURE__ */ jsxs(Fragment, { children: [
186
- t7,
187
- t16
188
- ] }), $[26] = t16, $[27] = t7, $[28] = t17) : t17 = $[28], t17;
189
- }
190
- function _temp2(event_0) {
191
- event_0.currentTarget.setCustomValidity(event_0.currentTarget.value.length == 32 ? "" : "Secret must be 32 characters long"), event_0.currentTarget.required = !0;
192
- }
193
- function _temp(event) {
194
- event.currentTarget.setCustomValidity("");
195
- }
196
- function useRefetchOnLiveEvent(client, formState, action) {
197
- const $ = c(8), [isBackgroundRefetch, startTransition] = useTransition();
198
- let t0;
199
- $[0] !== action || $[1] !== formState ? (t0 = (event) => {
200
- if (event.type === "message" && event.tags.some((tag2) => formState.syncTags.includes(tag2))) {
201
- const formData = new FormData();
202
- formData.set("action", "refresh-secret"), formData.set("lastLiveEventId", event.id), startTransition(() => action(formData));
203
- }
204
- }, $[0] = action, $[1] = formState, $[2] = t0) : t0 = $[2];
205
- const handleLiveEvent = useEffectEvent(t0);
206
- let t1;
207
- $[3] !== client.live || $[4] !== handleLiveEvent ? (t1 = () => {
208
- const subscription = client.live.events().subscribe({
209
- next: handleLiveEvent,
210
- error: _temp3
211
- });
212
- return () => subscription.unsubscribe();
213
- }, $[3] = client.live, $[4] = handleLiveEvent, $[5] = t1) : t1 = $[5];
214
- let t2;
215
- return $[6] !== client ? (t2 = [client], $[6] = client, $[7] = t2) : t2 = $[7], useEffect(t1, t2), isBackgroundRefetch;
216
- }
217
- function _temp3(reason) {
218
- return console.error(reason);
219
- }
220
- export {
221
- VercelProtectionBypassTool as default
222
- };
223
- //# sourceMappingURL=VercelProtectionBypassTool.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"VercelProtectionBypassTool.js","sources":["../../src/VercelProtectionBypassTool.tsx"],"sourcesContent":["import type {SyncTag, LiveEvent} from '@sanity/client'\nimport {AddIcon} from '@sanity/icons/Add'\nimport {TrashIcon} from '@sanity/icons/Trash'\nimport {\n apiVersion,\n vercelProtectionBypassSchemaId as _id,\n vercelProtectionBypassSchemaType as _type,\n tag,\n fetchVercelProtectionBypassSecret,\n} from '@sanity/preview-url-secret/constants'\nimport {\n Box,\n Button,\n Card,\n Dialog,\n Flex,\n Heading,\n Spinner,\n Stack,\n Text,\n TextInput,\n useToast,\n} from '@sanity/ui'\nimport {\n Activity,\n Suspense,\n use,\n useActionState,\n useEffect,\n useEffectEvent,\n useState,\n useTransition,\n} from 'react'\nimport {useClient, type SanityClient} from 'sanity'\n\nasync function enableVercelProtectionBypass(client: SanityClient, secret: string): Promise<void> {\n const patch = client.patch(_id).set({secret})\n await client.transaction().createIfNotExists({_id, _type}).patch(patch).commit({tag})\n}\n\nasync function disableVercelProtectionBypass(client: SanityClient): Promise<void> {\n const patch = client.patch(_id).set({secret: null})\n await client.transaction().createIfNotExists({_id, _type}).patch(patch).commit({tag})\n}\n\nexport default function VercelProtectionBypassTool(): React.JSX.Element {\n const client = useClient({apiVersion: apiVersion})\n\n async function fetchSecret(lastLiveEventId: FormDataEntryValue | null): Promise<FormState> {\n const {result, syncTags} = await client.fetch<string | null>(\n fetchVercelProtectionBypassSecret,\n {},\n {\n filterResponse: false,\n lastLiveEventId: typeof lastLiveEventId === 'string' ? lastLiveEventId : null,\n tag: 'preview-url-secret.fetch-vercel-bypass-protection-secret',\n },\n )\n return {secret: result, syncTags: syncTags ?? []}\n }\n const [initialStatePromise] = useState(() => fetchSecret(null))\n\n return (\n <Suspense\n fallback={\n <Flex\n align=\"center\"\n direction=\"column\"\n height=\"fill\"\n justify=\"center\"\n style={{width: '100%'}}\n >\n <Spinner />\n </Flex>\n }\n >\n <Layout initialStatePromise={initialStatePromise} fetchSecret={fetchSecret} />\n </Suspense>\n )\n}\n\ntype FormAction = 'remove-secret' | 'add-secret' | 'refresh-secret'\ntype FormName = 'action' | 'lastLiveEventId' | 'secret'\ntype FormState = {secret: string | null; syncTags: SyncTag[]}\n\nfunction Layout({\n initialStatePromise,\n fetchSecret,\n}: {\n initialStatePromise: Promise<FormState>\n fetchSecret(this: void, lastLiveEventId: FormDataEntryValue | null): Promise<FormState>\n}) {\n const {push: pushToast} = useToast()\n const [isDialogOpen, setIsDialogOpen] = useState(false)\n const client = useClient({apiVersion})\n\n const action = async (prevState: FormState, formData: FormData): Promise<FormState> => {\n const action = formData.get('action' satisfies FormName)\n if (typeof action !== 'string') {\n throw new Error('Action is not a string')\n }\n\n switch (action) {\n case 'remove-secret':\n return disableVercelProtectionBypass(client)\n .then((): FormState => {\n pushToast({\n status: 'warning',\n title: 'Protection bypass is now disabled',\n })\n return {...prevState, secret: null}\n })\n .catch((reason): FormState => {\n console.error(reason)\n pushToast({\n status: 'error',\n title:\n 'There was an error when trying to disable protection bypass. See the browser console for more information.',\n })\n return prevState\n })\n\n case 'add-secret': {\n const secret = formData.get('secret' satisfies FormName)\n if (typeof secret !== 'string') {\n throw new Error('Secret is not a string')\n }\n return enableVercelProtectionBypass(client, secret)\n .then(() => {\n pushToast({\n status: 'success',\n title: 'Protection bypass is now enabled',\n })\n setIsDialogOpen(false)\n return {...prevState, secret}\n })\n .catch((reason) => {\n console.error(reason)\n pushToast({\n status: 'error',\n title:\n 'There was an error when trying to enable protection bypass. See the browser console for more information.',\n })\n return prevState\n })\n }\n case 'refresh-secret':\n return fetchSecret(formData.get('lastLiveEventId' satisfies FormName))\n default:\n throw new Error(`Unknown action: ${action}`)\n }\n }\n\n const [formState, formAction, isPending] = useActionState(action, use(initialStatePromise))\n const isBackgroundRefetch = useRefetchOnLiveEvent(client, formState, formAction)\n\n const loading = isPending && !isBackgroundRefetch\n const enabled = Boolean(formState.secret)\n\n return (\n <>\n <Box\n as=\"form\"\n action={formAction}\n sizing=\"border\"\n display=\"flex\"\n style={{\n height: '100%',\n alignItems: 'center',\n justifyContent: 'center',\n flexDirection: 'column',\n }}\n >\n <Stack gap={5}>\n <Card padding={4} style={{maxWidth: 640}}>\n <Stack gap={4} style={{justifyItems: 'flex-start', textWrap: 'pretty'}}>\n <Heading>Vercel Protection Bypass</Heading>\n {enabled ? (\n <>\n <Box>\n <Text style={{textWrap: 'pretty'}}>\n Sanity Presentation is setup to use{' '}\n <a\n href=\"https://vercel.com/docs/security/deployment-protection/methods-to-bypass-deployment-protection/protection-bypass-automation\"\n target=\"_blank\"\n rel=\"noreferrer\"\n >\n protection bypass for automation\n </a>{' '}\n in order to display protected deployments in its preview iframe for the\n current Sanity dataset.\n </Text>\n </Box>\n <Box>\n <Text>\n You can turn off automatic protection bypass at any time by clicking the\n button below.\n </Text>\n </Box>\n <Button\n mode=\"ghost\"\n tone=\"critical\"\n icon={<TrashIcon />}\n loading={loading}\n type=\"submit\"\n name={'action' satisfies FormName}\n value={'remove-secret' satisfies FormAction}\n text=\"Remove secret\"\n />\n <Text>\n Protection bypass remains enabled if this plugin is removed from your Sanity\n config.\n </Text>\n </>\n ) : (\n <>\n <Box>\n <Text style={{textWrap: 'pretty'}}>\n Follow the instructions on{' '}\n <a\n href=\"https://vercel.com/docs/security/deployment-protection/methods-to-bypass-deployment-protection/protection-bypass-automation\"\n target=\"_blank\"\n rel=\"noreferrer\"\n >\n how to enable protection bypass for automation\n </a>\n .\n </Text>\n </Box>\n <Box>\n <Text>\n This will setup a secret that Vercel exposes as an environment variable called\n VERCEL_AUTOMATION_BYPASS_SECRET, its value is the secret you need.\n </Text>\n </Box>\n <Button\n mode=\"ghost\"\n icon={<AddIcon />}\n onClick={() => {\n setIsDialogOpen(true)\n }}\n text=\"Add secret\"\n />\n <Text>\n If you&apos;re using Sanity Presentation Tool with multiple protected\n deployments ensure that they have the same secret set, as this tool will set a\n secret that is shared in your dataset with all instances of Presentation Tool.\n </Text>\n </>\n )}\n </Stack>\n </Card>\n </Stack>\n </Box>\n\n <Activity mode={isDialogOpen ? 'visible' : 'hidden'}>\n <Dialog animate id=\"add-secret-dialog\" onClickOutside={() => setIsDialogOpen(false)}>\n <Card as=\"form\" action={formAction} padding={3}>\n <Stack gap={3}>\n <Stack gap={2}>\n <Text as=\"label\" weight=\"semibold\" size={1}>\n Add bypass secret\n </Text>\n <Text muted size={1}>\n {`Make sure it's the same secret the Vercel deployment is using that's loaded in the preview iframe.`}\n </Text>\n <TextInput\n name={'secret' satisfies FormName}\n onFocus={(event) => {\n event.currentTarget.setCustomValidity('')\n }}\n onBlur={(event) => {\n event.currentTarget.setCustomValidity(\n event.currentTarget.value.length == 32\n ? ''\n : 'Secret must be 32 characters long',\n )\n event.currentTarget.required = true\n }}\n minLength={32}\n maxLength={32}\n autoComplete=\"off\"\n autoCapitalize=\"off\"\n autoCorrect=\"off\"\n spellCheck=\"false\"\n disabled={loading}\n />\n </Stack>\n <Button\n type=\"submit\"\n loading={loading}\n text={loading ? 'Saving…' : 'Save'}\n tone=\"positive\"\n name={'action' satisfies FormName}\n value={'add-secret' satisfies FormAction}\n />\n </Stack>\n </Card>\n </Dialog>\n </Activity>\n </>\n )\n}\n\ntype isBackgroundRefetch = boolean\nfunction useRefetchOnLiveEvent(\n client: SanityClient,\n formState: FormState,\n action: (formData: FormData) => void,\n): isBackgroundRefetch {\n const [isBackgroundRefetch, startTransition] = useTransition()\n const handleLiveEvent = useEffectEvent((event: LiveEvent) => {\n if (event.type === 'message' && event.tags.some((tag) => formState.syncTags.includes(tag))) {\n const formData = new FormData()\n formData.set('action' satisfies FormName, 'refresh-secret' satisfies FormAction)\n formData.set('lastLiveEventId' satisfies FormName, event.id)\n startTransition(() => action(formData))\n }\n })\n useEffect(() => {\n const subscription = client.live.events().subscribe({\n next: handleLiveEvent,\n error: (reason) => console.error(reason),\n })\n\n return () => subscription.unsubscribe()\n }, [client])\n return isBackgroundRefetch\n}\n"],"names":["enableVercelProtectionBypass","client","secret","patch","_id","set","transaction","createIfNotExists","_type","commit","tag","disableVercelProtectionBypass","VercelProtectionBypassTool","$","_c","t0","for","apiVersion","useClient","t1","lastLiveEventId","result","syncTags","fetch","fetchVercelProtectionBypassSecret","filterResponse","fetchSecret","t2","initialStatePromise","useState","t3","width","t4","Layout","push","pushToast","useToast","isDialogOpen","setIsDialogOpen","prevState","formData","action","get","Error","then","status","title","catch","reason_0","console","error","reason","action_0","formState","formAction","isPending","useActionState","use","isBackgroundRefetch","useRefetchOnLiveEvent","loading","enabled","Boolean","height","alignItems","justifyContent","flexDirection","maxWidth","t5","t6","justifyItems","textWrap","t7","t8","t9","t10","t11","t12","_temp","_temp2","t13","t14","t15","t16","t17","event_0","event","currentTarget","setCustomValidity","value","length","required","startTransition","useTransition","type","tags","some","includes","FormData","id","handleLiveEvent","useEffectEvent","live","subscription","events","subscribe","next","_temp3","unsubscribe","useEffect"],"mappings":"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"}