@sanity/sdk-react 2.17.0 → 2.19.0

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/index.d.ts CHANGED
@@ -18,6 +18,7 @@ import { DocumentEvent } from "@sanity/sdk";
18
18
  import { DocumentHandle as DocumentHandle_2 } from "@sanity/sdk";
19
19
  import { DocumentOptions } from "@sanity/sdk";
20
20
  import { DocumentPermissionsResult } from "@sanity/sdk";
21
+ import { DocumentPresence } from "@sanity/sdk";
21
22
  import { DocumentResource } from "@sanity/sdk";
22
23
  import { DocumentTypeHandle as DocumentTypeHandle_2 } from "@sanity/sdk";
23
24
  import { FallbackProps } from "react-error-boundary";
@@ -31,7 +32,9 @@ import { Organization } from "@sanity/sdk";
31
32
  import { OrganizationOptions } from "@sanity/sdk";
32
33
  import { Organizations } from "@sanity/sdk";
33
34
  import { OrganizationsOptions } from "@sanity/sdk";
35
+ import { Path } from "@sanity/types";
34
36
  import { PathChangeMessage } from "@sanity/message-protocol";
37
+ import { PresenceSelection } from "@sanity/sdk";
35
38
  import { PreviewValue } from "@sanity/sdk";
36
39
  import { Project } from "@sanity/sdk";
37
40
  import { ProjectHandle } from "@sanity/sdk";
@@ -153,10 +156,7 @@ export declare interface AuthBoundaryProps {
153
156
  * @public
154
157
  */
155
158
  export declare type ComlinkStatus =
156
- | "idle"
157
- | "handshaking"
158
- | "connected"
159
- | "disconnected";
159
+ "idle" | "handshaking" | "connected" | "disconnected";
160
160
 
161
161
  /**
162
162
  * This provider is used to provide the Comlink token refresh feature.
@@ -327,11 +327,7 @@ export declare interface FrameConnection<TFrameMessage extends FrameMessage> {
327
327
  }
328
328
 
329
329
  declare type IgnoredKey =
330
- | "_id"
331
- | "_type"
332
- | "_rev"
333
- | "_createdAt"
334
- | "_updatedAt";
330
+ "_id" | "_type" | "_rev" | "_createdAt" | "_updatedAt";
335
331
 
336
332
  /**
337
333
  * @alpha
@@ -3066,9 +3062,7 @@ export declare function useManageFavorite({
3066
3062
  declare interface UseManageFavoriteProps extends DocumentHandle_2 {
3067
3063
  resourceId?: string;
3068
3064
  resourceType:
3069
- | StudioResource["type"]
3070
- | MediaResource["type"]
3071
- | CanvasResource["type"];
3065
+ StudioResource["type"] | MediaResource["type"] | CanvasResource["type"];
3072
3066
  /**
3073
3067
  * The name of the schema collection this document belongs to.
3074
3068
  * Typically is the name of the workspace when used in the context of a studio.
@@ -3312,13 +3306,80 @@ export declare function usePerspective(
3312
3306
  ): string | string[];
3313
3307
 
3314
3308
  /**
3315
- * A hook for subscribing to presence information for the current project or Canvas.
3309
+ * Every participant in the current project and dataset, or Canvas.
3310
+ *
3311
+ * Reading presence never announces anything. Call `useReportPresence` to make the
3312
+ * current user visible to others, including to the Studio, which shares the same
3313
+ * presence room.
3314
+ *
3315
+ * This returns everyone in the whole resource and leaves the filtering to you.
3316
+ * Prefer `usePresenceForDocument` when you care about one document: it scopes and
3317
+ * flattens the result for rendering. Note that participants are counted by session,
3318
+ * so one person in two tabs appears twice.
3319
+ *
3320
+ * Presence is scoped to a single project and dataset. It is not a list of everyone
3321
+ * signed in to your organization.
3322
+ *
3316
3323
  * @public
3317
3324
  */
3318
3325
  export declare function usePresence(options?: ResourceHandle): {
3319
3326
  locations: UserPresence[];
3320
3327
  };
3321
3328
 
3329
+ /**
3330
+ * Who else is in a document, flattened to one entry per participant per location
3331
+ * so it can be rendered straight against a field.
3332
+ *
3333
+ * Reading presence never announces anything. Use `useReportPresence` to make the
3334
+ * current user visible to others.
3335
+ *
3336
+ * Prefer this over `usePresence` when you care about one document: `usePresence`
3337
+ * returns every participant in the whole project and dataset, leaving the filtering
3338
+ * to you.
3339
+ *
3340
+ * Resolves the document through its perspective exactly as `useReportPresence` does,
3341
+ * so reads match writes. Participants are counted by session, so one person in two
3342
+ * tabs appears twice.
3343
+ *
3344
+ * @example Avatars on a document
3345
+ * ```tsx
3346
+ * const {presence} = usePresenceForDocument({documentId, documentType})
3347
+ * return presence.map((p) => <Avatar key={p.sessionId} user={p.user} />)
3348
+ * ```
3349
+ *
3350
+ * @example Avatars on a single field
3351
+ * ```tsx
3352
+ * const {presence} = usePresenceForDocument({
3353
+ * documentId,
3354
+ * documentType,
3355
+ * path: ['title'],
3356
+ * excludeVersions: true,
3357
+ * })
3358
+ * ```
3359
+ *
3360
+ * @beta
3361
+ */
3362
+ export declare function usePresenceForDocument(
3363
+ options: UsePresenceForDocumentOptions,
3364
+ ): {
3365
+ presence: DocumentPresence[];
3366
+ };
3367
+
3368
+ /** @beta */
3369
+ export declare interface UsePresenceForDocumentOptions extends DocumentHandle {
3370
+ /**
3371
+ * Narrows to participants at or below this field path, which is what a field
3372
+ * indicator wants. Omit it for everyone in the document.
3373
+ */
3374
+ path?: Path;
3375
+ /**
3376
+ * By default a draft, its published version, and any release versions count as
3377
+ * the same document, which is what document lists want. Set this to compare ids
3378
+ * exactly, so that a draft and a release version do not bleed into each other.
3379
+ */
3380
+ excludeVersions?: boolean;
3381
+ }
3382
+
3322
3383
  /**
3323
3384
  * Returns metadata for a given project.
3324
3385
  *
@@ -3567,9 +3628,7 @@ export declare function useRecordDocumentHistoryEvent({
3567
3628
  */
3568
3629
  declare interface UseRecordDocumentHistoryEventProps extends DocumentHandle_2 {
3569
3630
  resourceType:
3570
- | StudioResource["type"]
3571
- | MediaResource["type"]
3572
- | CanvasResource["type"];
3631
+ StudioResource["type"] | MediaResource["type"] | CanvasResource["type"];
3573
3632
  resourceId?: string;
3574
3633
  /**
3575
3634
  * The name of the schema collection this document belongs to.
@@ -3578,6 +3637,74 @@ declare interface UseRecordDocumentHistoryEventProps extends DocumentHandle_2 {
3578
3637
  schemaName?: string;
3579
3638
  }
3580
3639
 
3640
+ /**
3641
+ * Announces that the current user is in a document, so that other clients in the
3642
+ * same project and dataset can show them.
3643
+ *
3644
+ * Writing presence is opt-in. Reading it with `usePresenceForDocument` or
3645
+ * `usePresence` never announces anything, and this hook is the only thing that
3646
+ * makes an app visible to others. That includes the Studio, which shares the same
3647
+ * presence room and will show these users in its navbar and field indicators.
3648
+ *
3649
+ * Announcements are throttled, collapsed over a short window, and then repeated
3650
+ * every 30 seconds while the user is idle. That repeat is what tells peers the
3651
+ * session is still alive, so the intended usage is to mount this hook for as long
3652
+ * as the user is in the document. On unmount the location is cleared, leaving the
3653
+ * user present in the app but not in any particular document.
3654
+ *
3655
+ * The perspective decides which specific document is reported: the draft under
3656
+ * `drafts`, the published document under `published`, a version under a release.
3657
+ * It is taken from `ResourceProvider` unless you pass one on the handle. That
3658
+ * matters for interoperability, because the Studio's field indicators compare the
3659
+ * exact id its form is on, so a mismatch shows your user at document level while
3660
+ * never lighting up a field.
3661
+ *
3662
+ * Presence is scoped to a single project and dataset. It is not a list of everyone
3663
+ * signed in to your organization.
3664
+ *
3665
+ * @example Document-level presence
3666
+ * ```tsx
3667
+ * function DocumentEditor({documentId, documentType}: DocumentHandle) {
3668
+ * useReportPresence({documentId, documentType})
3669
+ * return <Editor />
3670
+ * }
3671
+ * ```
3672
+ *
3673
+ * @example Presence in a release version
3674
+ * ```tsx
3675
+ * // The document id stays plain; the perspective selects the version.
3676
+ * useReportPresence({documentId, documentType, perspective: {releaseName: 'autumn'}})
3677
+ * ```
3678
+ *
3679
+ * @example Field-level presence
3680
+ * ```tsx
3681
+ * function TitleField({documentId, documentType}: DocumentHandle) {
3682
+ * const [focused, setFocused] = useState(false)
3683
+ * useReportPresence({documentId, documentType, path: focused ? ['title'] : undefined})
3684
+ * return <input onFocus={() => setFocused(true)} onBlur={() => setFocused(false)} />
3685
+ * }
3686
+ * ```
3687
+ *
3688
+ * @beta
3689
+ */
3690
+ export declare function useReportPresence(
3691
+ options: UseReportPresenceOptions,
3692
+ ): void;
3693
+
3694
+ /** @beta */
3695
+ export declare interface UseReportPresenceOptions extends DocumentHandle {
3696
+ /**
3697
+ * The focused field path. Omit it for document-level presence. Keyed and numeric
3698
+ * segments are supported, so array items and Portable Text spans can be
3699
+ * addressed.
3700
+ */
3701
+ path?: Path;
3702
+ /** The Portable Text caret, when the focused field is a Portable Text field. */
3703
+ selection?: PresenceSelection;
3704
+ /** Overrides the throttle interval. Mainly useful in tests. */
3705
+ throttleMs?: number;
3706
+ }
3707
+
3581
3708
  /**
3582
3709
  * Returns the currently active `DocumentResource` for the nearest resource context.
3583
3710
  *
package/dist/index.js CHANGED
@@ -1,7 +1,7 @@
1
1
  import { jsx, jsxs, Fragment } from "react/jsx-runtime";
2
2
  import { c } from "react-compiler-runtime";
3
3
  import { ClientError, CorsOriginError } from "@sanity/client";
4
- import { getAuthState, getNodeState, getIsInDashboardState, isStudioConfig, setAuthToken, AuthStateType, getLoginUrlState, observeOrganizationVerificationState, handleAuthCallback, logout, isProjectUserNotFoundClientError, getClientErrorApiDescription, getClientErrorApiBody, isImportError, getCorsErrorProjectId, getDashboardOrganizationId, getClientState, isDatasetResource, createSanityInstance, agentGenerate, agentPatch, agentPrompt, agentTransform, agentTranslate, getTokenState, getCurrentUserState, getOrCreateController, getOrCreateChannel, releaseChannel, isMediaLibraryResource, isCanvasResource, getFavoritesState, resolveFavoritesState, resolveDatasets, getDatasetsState, applyDocumentActions, createDocument, resolveDocument, getDocumentState, subscribeDocumentEvents, getPermissionsState, getDocumentSyncStatus, editDocument, getQueryKey, parseQueryKey, getQueryState, resolveQuery, createGroqSearchFilter, resolveOrganization, getOrganizationState, resolveOrganizations, getOrganizationsState, getPresence, getProjectionState, resolveProjection, transformProjectionToPreview, PREVIEW_PROJECTION, resolveProject, getProjectState, resolveProjects, getProjectsState, getActiveReleasesState, getAllReleasesState, getPerspectiveState, getUsersKey, parseUsersKey, getUsersState, resolveUsers, loadMoreUsers } from "@sanity/sdk";
4
+ import { getAuthState, getNodeState, getIsInDashboardState, isStudioConfig, setAuthToken, AuthStateType, getLoginUrlState, observeOrganizationVerificationState, handleAuthCallback, logout, isProjectUserNotFoundClientError, getClientErrorApiDescription, getClientErrorApiBody, isImportError, getCorsErrorProjectId, getDashboardOrganizationId, getClientState, isDatasetResource, createSanityInstance, agentGenerate, agentPatch, agentPrompt, agentTransform, agentTranslate, getTokenState, getCurrentUserState, getOrCreateController, getOrCreateChannel, releaseChannel, isMediaLibraryResource, isCanvasResource, getFavoritesState, resolveFavoritesState, resolveDatasets, getDatasetsState, applyDocumentActions, createDocument, resolveDocument, getDocumentState, subscribeDocumentEvents, getPermissionsState, getDocumentSyncStatus, editDocument, getQueryKey, parseQueryKey, getQueryState, resolveQuery, createGroqSearchFilter, resolveOrganization, getOrganizationState, resolveOrganizations, getOrganizationsState, getPresence, getDocumentPresence, reportPresence, getProjectionState, resolveProjection, PREVIEW_PROJECTION, transformProjectionToPreview, resolveProject, getProjectState, resolveProjects, getProjectsState, getActiveReleasesState, getAllReleasesState, getPerspectiveState, getUsersKey, parseUsersKey, getUsersState, resolveUsers, loadMoreUsers } from "@sanity/sdk";
5
5
  export * from "@sanity/sdk";
6
6
  import { createContext, useContext, useSyncExternalStore, useRef, useEffect, useState, Suspense, use, StrictMode, useCallback, useMemo, useInsertionEffect, useTransition } from "react";
7
7
  import { getErrorMessage, ErrorBoundary } from "react-error-boundary";
@@ -1307,48 +1307,39 @@ function useRecordDocumentHistoryEvent(t0) {
1307
1307
  }, $[8] = recordEvent, $[9] = t3) : t3 = $[9], t3;
1308
1308
  }
1309
1309
  function resolveAppTitle(resource) {
1310
- return resource.manifest?.title ?? resource.activeDeployment?.manifest?.title ?? resource.title;
1310
+ return resource.manifest?.title || resource.activeDeployment?.manifest?.title || resource.title;
1311
1311
  }
1312
1312
  function useWindowTitle(viewTitle) {
1313
- const $ = c(8), [appTitle, setAppTitle] = useState(null);
1314
- let t0;
1315
- $[0] === /* @__PURE__ */ Symbol.for("react.memo_cache_sentinel") ? (t0 = {
1313
+ const [appTitle, setAppTitle] = useState(null), {
1314
+ fetch
1315
+ } = useWindowConnection({
1316
1316
  name: SDK_NODE_NAME,
1317
1317
  connectTo: SDK_CHANNEL_NAME
1318
- }, $[0] = t0) : t0 = $[0];
1319
- const {
1320
- fetch
1321
- } = useWindowConnection(t0);
1322
- let t1, t2;
1323
- $[1] !== fetch ? (t1 = () => {
1324
- if (!fetch)
1325
- return;
1318
+ });
1319
+ useEffect(() => {
1320
+ if (!fetch) return;
1326
1321
  const controller = new AbortController();
1327
- return (async function(signal) {
1322
+ async function fetchAppTitle(signal) {
1328
1323
  try {
1329
1324
  const data = await fetch("dashboard/v1/context", void 0, {
1330
1325
  signal
1331
- }), title = resolveAppTitle(data.context.resource);
1326
+ }), title = resolveAppTitle(data.context.resource) || document.title;
1332
1327
  title && setAppTitle(title);
1333
- } catch (t32) {
1334
- const err = t32;
1335
- if (err instanceof Error && err.name === "AbortError")
1336
- return;
1328
+ } catch (err) {
1329
+ if (err instanceof Error && err.name === "AbortError") return;
1337
1330
  console.error("Failed to fetch app title from dashboard context:", err);
1338
1331
  }
1339
- })(controller.signal), () => {
1332
+ }
1333
+ return fetchAppTitle(controller.signal), () => {
1340
1334
  controller.abort();
1341
1335
  };
1342
- }, t2 = [fetch], $[1] = fetch, $[2] = t1, $[3] = t2) : (t1 = $[2], t2 = $[3]), useEffect(t1, t2);
1343
- let t3, t4;
1344
- $[4] !== appTitle || $[5] !== viewTitle ? (t3 = () => {
1345
- if (!appTitle)
1346
- return;
1336
+ }, [fetch]), useEffect(() => {
1337
+ if (!appTitle) return;
1347
1338
  const previous = document.title;
1348
1339
  return document.title = viewTitle ? `${viewTitle} | ${appTitle}` : appTitle, () => {
1349
1340
  document.title = previous;
1350
1341
  };
1351
- }, t4 = [viewTitle, appTitle], $[4] = appTitle, $[5] = viewTitle, $[6] = t3, $[7] = t4) : (t3 = $[6], t4 = $[7]), useEffect(t3, t4);
1342
+ }, [viewTitle, appTitle]);
1352
1343
  }
1353
1344
  function useResolvedProjectId(options) {
1354
1345
  const $ = c(6);
@@ -1807,6 +1798,137 @@ function usePresence(t0) {
1807
1798
  locations: t6
1808
1799
  }, $[12] = t6, $[13] = t7) : t7 = $[13], t7;
1809
1800
  }
1801
+ function usePresenceForDocument(options) {
1802
+ const $ = c(23);
1803
+ let excludeVersions, handle, path;
1804
+ $[0] !== options ? ({
1805
+ path,
1806
+ excludeVersions,
1807
+ ...handle
1808
+ } = options, $[0] = options, $[1] = excludeVersions, $[2] = handle, $[3] = path) : (excludeVersions = $[1], handle = $[2], path = $[3]);
1809
+ const normalizedOptions = useNormalizedResourceOptions(handle);
1810
+ if (normalizedOptions.resource && isMediaLibraryResource(normalizedOptions.resource))
1811
+ throw new Error("usePresenceForDocument() does not support media library resources. Presence tracking requires a canvas or dataset resource.");
1812
+ const sanityInstance = useSanityInstance();
1813
+ trackHookUsage(sanityInstance, "usePresenceForDocument");
1814
+ const {
1815
+ resource,
1816
+ perspective
1817
+ } = normalizedOptions, {
1818
+ documentId,
1819
+ liveEdit
1820
+ } = options;
1821
+ let t0;
1822
+ $[4] !== path ? (t0 = JSON.stringify(path ?? null), $[4] = path, $[5] = t0) : t0 = $[5];
1823
+ const pathKey = t0;
1824
+ let t1;
1825
+ $[6] !== documentId || $[7] !== excludeVersions || $[8] !== liveEdit || $[9] !== pathKey || $[10] !== perspective || $[11] !== resource || $[12] !== sanityInstance ? (t1 = getDocumentPresence(sanityInstance, {
1826
+ ...resource ? {
1827
+ resource
1828
+ } : {},
1829
+ documentId,
1830
+ ...perspective ? {
1831
+ perspective
1832
+ } : {},
1833
+ ...liveEdit ? {
1834
+ liveEdit
1835
+ } : {},
1836
+ ...pathKey === "null" ? {} : {
1837
+ path: JSON.parse(pathKey)
1838
+ },
1839
+ ...excludeVersions === void 0 ? {} : {
1840
+ excludeVersions
1841
+ }
1842
+ }), $[6] = documentId, $[7] = excludeVersions, $[8] = liveEdit, $[9] = pathKey, $[10] = perspective, $[11] = resource, $[12] = sanityInstance, $[13] = t1) : t1 = $[13];
1843
+ const source = t1;
1844
+ let t2;
1845
+ $[14] !== source ? (t2 = (callback) => source.subscribe(callback), $[14] = source, $[15] = t2) : t2 = $[15];
1846
+ const subscribe = t2;
1847
+ let t3, t4;
1848
+ $[16] !== source ? (t3 = () => source.getCurrent(), t4 = () => source.getCurrent(), $[16] = source, $[17] = t3, $[18] = t4) : (t3 = $[17], t4 = $[18]);
1849
+ const presence = useSyncExternalStore(subscribe, t3, t4);
1850
+ let t5;
1851
+ $[19] !== presence ? (t5 = presence || [], $[19] = presence, $[20] = t5) : t5 = $[20];
1852
+ let t6;
1853
+ return $[21] !== t5 ? (t6 = {
1854
+ presence: t5
1855
+ }, $[21] = t5, $[22] = t6) : t6 = $[22], t6;
1856
+ }
1857
+ const FOCUS_THROTTLE_MS = 1e3, SELECTION_THROTTLE_MS = 250;
1858
+ function useReportPresence(options) {
1859
+ const $ = c(37);
1860
+ let handle, path, selection, throttleMs;
1861
+ $[0] !== options ? ({
1862
+ path,
1863
+ selection,
1864
+ throttleMs,
1865
+ ...handle
1866
+ } = options, $[0] = options, $[1] = handle, $[2] = path, $[3] = selection, $[4] = throttleMs) : (handle = $[1], path = $[2], selection = $[3], throttleMs = $[4]);
1867
+ const normalizedOptions = useNormalizedResourceOptions(handle);
1868
+ if (normalizedOptions.resource && isMediaLibraryResource(normalizedOptions.resource))
1869
+ throw new Error("useReportPresence() does not support media library resources. Presence tracking requires a canvas or dataset resource.");
1870
+ const sanityInstance = useSanityInstance();
1871
+ trackHookUsage(sanityInstance, "useReportPresence");
1872
+ const {
1873
+ resource,
1874
+ perspective
1875
+ } = normalizedOptions, {
1876
+ documentId,
1877
+ liveEdit
1878
+ } = options, interval = throttleMs ?? (selection ? SELECTION_THROTTLE_MS : FOCUS_THROTTLE_MS);
1879
+ let t0;
1880
+ $[5] !== documentId || $[6] !== liveEdit || $[7] !== path || $[8] !== perspective || $[9] !== selection ? (t0 = JSON.stringify([documentId, path ?? [], selection ?? null, perspective ?? null, liveEdit]), $[5] = documentId, $[6] = liveEdit, $[7] = path, $[8] = perspective, $[9] = selection, $[10] = t0) : t0 = $[10];
1881
+ const locationKey = t0;
1882
+ let t1;
1883
+ $[11] !== locationKey ? (t1 = JSON.parse(locationKey), $[11] = locationKey, $[12] = t1) : t1 = $[12];
1884
+ const [id, parsedPath, parsedSelection, parsedPerspective, parsedLiveEdit] = t1;
1885
+ let t2;
1886
+ $[13] !== parsedPerspective ? (t2 = parsedPerspective ? {
1887
+ perspective: parsedPerspective
1888
+ } : {}, $[13] = parsedPerspective, $[14] = t2) : t2 = $[14];
1889
+ let t3;
1890
+ $[15] !== parsedLiveEdit ? (t3 = parsedLiveEdit ? {
1891
+ liveEdit: parsedLiveEdit
1892
+ } : {}, $[15] = parsedLiveEdit, $[16] = t3) : t3 = $[16];
1893
+ let t4;
1894
+ $[17] !== parsedPath ? (t4 = parsedPath.length > 0 ? {
1895
+ path: parsedPath
1896
+ } : {}, $[17] = parsedPath, $[18] = t4) : t4 = $[18];
1897
+ let t5;
1898
+ $[19] !== parsedSelection ? (t5 = parsedSelection ? {
1899
+ selection: parsedSelection
1900
+ } : {}, $[19] = parsedSelection, $[20] = t5) : t5 = $[20];
1901
+ let t6;
1902
+ $[21] !== id || $[22] !== t2 || $[23] !== t3 || $[24] !== t4 || $[25] !== t5 ? (t6 = {
1903
+ documentId: id,
1904
+ ...t2,
1905
+ ...t3,
1906
+ ...t4,
1907
+ ...t5
1908
+ }, $[21] = id, $[22] = t2, $[23] = t3, $[24] = t4, $[25] = t5, $[26] = t6) : t6 = $[26];
1909
+ const location2 = t6, lastSentAt = useRef(0), pending = useRef(void 0);
1910
+ let t7, t8;
1911
+ $[27] !== interval || $[28] !== location2 || $[29] !== resource || $[30] !== sanityInstance ? (t7 = () => {
1912
+ const send = () => {
1913
+ lastSentAt.current = Date.now(), reportPresence(sanityInstance, {
1914
+ ...resource ? {
1915
+ resource
1916
+ } : {},
1917
+ locations: [location2]
1918
+ });
1919
+ }, elapsed = Date.now() - lastSentAt.current;
1920
+ return elapsed >= interval ? send() : (clearTimeout(pending.current), pending.current = setTimeout(send, interval - elapsed)), () => clearTimeout(pending.current);
1921
+ }, t8 = [location2, interval, sanityInstance, resource], $[27] = interval, $[28] = location2, $[29] = resource, $[30] = sanityInstance, $[31] = t7, $[32] = t8) : (t7 = $[31], t8 = $[32]), useEffect(t7, t8);
1922
+ let t10, t9;
1923
+ $[33] !== resource || $[34] !== sanityInstance ? (t9 = () => () => {
1924
+ reportPresence(sanityInstance, {
1925
+ ...resource ? {
1926
+ resource
1927
+ } : {},
1928
+ locations: []
1929
+ });
1930
+ }, t10 = [sanityInstance, resource], $[33] = resource, $[34] = sanityInstance, $[35] = t10, $[36] = t9) : (t10 = $[35], t9 = $[36]), useEffect(t9, t10);
1931
+ }
1810
1932
  function useDocumentProjection(t0) {
1811
1933
  const $ = c(13);
1812
1934
  let docHandle, projection, ref;
@@ -2024,7 +2146,7 @@ function useUsers(options) {
2024
2146
  loadMore
2025
2147
  }, $[20] = data, $[21] = hasMore, $[22] = isPending, $[23] = loadMore, $[24] = t8) : t8 = $[24], t8;
2026
2148
  }
2027
- var version = "2.17.0";
2149
+ var version = "2.19.0";
2028
2150
  function getEnv(key) {
2029
2151
  if (typeof import.meta < "u" && import.meta.env)
2030
2152
  return import.meta.env[key];
@@ -2082,10 +2204,12 @@ export {
2082
2204
  usePaginatedDocuments,
2083
2205
  usePerspective,
2084
2206
  usePresence,
2207
+ usePresenceForDocument,
2085
2208
  useProject,
2086
2209
  useProjects,
2087
2210
  useQuery,
2088
2211
  useRecordDocumentHistoryEvent,
2212
+ useReportPresence,
2089
2213
  useResource,
2090
2214
  useSanityInstance,
2091
2215
  useStudioWorkspacesByProjectIdDataset,