From c227be5d24f2bf368fbd83f2e149c0676725968a Mon Sep 17 00:00:00 2001 From: Andrew Chou Date: Mon, 1 Dec 2025 10:56:23 -0500 Subject: [PATCH 1/3] feat!: remove useDocumentCreatedBy hook --- docs/API.md | 27 ------------------------- src/hooks/projects.ts | 36 --------------------------------- src/index.ts | 1 - src/lib/react-query/projects.ts | 23 --------------------- 4 files changed, 87 deletions(-) diff --git a/docs/API.md b/docs/API.md index 24d1706..243b466 100644 --- a/docs/API.md +++ b/docs/API.md @@ -13,7 +13,6 @@ - [useManyMembers](#usemanymembers) - [useIconUrl](#useiconurl) - [useAttachmentUrl](#useattachmenturl) -- [useDocumentCreatedBy](#usedocumentcreatedby) - [useOwnRoleInProject](#useownroleinproject) - [useAddServerPeer](#useaddserverpeer) - [useRemoveServerPeer](#useremoveserverpeer) @@ -361,32 +360,6 @@ function VideoExample() { ``` -### useDocumentCreatedBy - -Retrieve the device ID that created a document. - -| Function | Type | -| ---------- | ---------- | -| `useDocumentCreatedBy` | `({ projectId, originalVersionId, }: { projectId: string; originalVersionId: string; }) => { data: string; error: Error or null; isRefetching: boolean; }` | - -Parameters: - -* `opts.projectId`: Project public ID -* `opts.originalVersionId`: Version ID of document - - -Examples: - -```tsx -function BasicExample() { - const { data } = useDocumentCreatedBy({ - projectId: '...', - originalVersionId: '...', - }) -} -``` - - ### useOwnRoleInProject Get the role for the current device in a specified project. diff --git a/src/hooks/projects.ts b/src/hooks/projects.ts index 20c5204..bc86a0a 100644 --- a/src/hooks/projects.ts +++ b/src/hooks/projects.ts @@ -21,7 +21,6 @@ import { createBlobMutationOptions, createProjectMutationOptions, disconnectSyncServersMutationOptions, - documentCreatedByQueryOptions, exportGeoJSONMutationOptions, exportZipFileMutationOptions, getMembersQueryKey, @@ -345,41 +344,6 @@ function useMediaServerOrigin({ projectApi }: { projectApi: MapeoProjectApi }) { return { data, error, isRefetching } } -// TODO: Eventually remove in favor of this information being provided by the backend when retrieving documents -/** - * Retrieve the device ID that created a document. - * - * @param opts.projectId Project public ID - * @param opts.originalVersionId Version ID of document - * - * @example - * ```tsx - * function BasicExample() { - * const { data } = useDocumentCreatedBy({ - * projectId: '...', - * originalVersionId: '...', - * }) - * } - * ``` - * - * @deprecated Use `createdBy` field from document read hooks. - */ -export function useDocumentCreatedBy({ - projectId, - originalVersionId, -}: { - projectId: string - originalVersionId: string -}) { - const { data: projectApi } = useSingleProject({ projectId }) - - const { data, error, isRefetching } = useSuspenseQuery( - documentCreatedByQueryOptions({ projectApi, projectId, originalVersionId }), - ) - - return { data, error, isRefetching } -} - /** * Get the role for the current device in a specified project. * This is a more convenient alternative to using the `useOwnDeviceInfo` and `useManyMembers` hooks. diff --git a/src/index.ts b/src/index.ts index d73eeb0..54b12e4 100644 --- a/src/index.ts +++ b/src/index.ts @@ -32,7 +32,6 @@ export { useCreateProject, useDataSyncProgress, useDisconnectSyncServers, - useDocumentCreatedBy, useIconUrl, useImportProjectCategories, useImportProjectConfig, diff --git a/src/lib/react-query/projects.ts b/src/lib/react-query/projects.ts index 1281045..47ac921 100644 --- a/src/lib/react-query/projects.ts +++ b/src/lib/react-query/projects.ts @@ -179,29 +179,6 @@ export function projectOwnRoleQueryOptions({ }) } -export function documentCreatedByQueryOptions({ - projectApi, - projectId, - originalVersionId, -}: { - projectApi: MapeoProjectApi - projectId: string - originalVersionId: string -}) { - return queryOptions({ - ...baseQueryOptions(), - queryKey: getDocumentCreatedByQueryKey({ - projectId, - originalVersionId, - }), - queryFn: async () => { - return projectApi.$originalVersionIdToDeviceId(originalVersionId) - }, - staleTime: 'static', - gcTime: Infinity, - }) -} - // Used as a placeholder so that we can read the server port from the $blobs.getUrl() method const FAKE_BLOB_ID: BlobApi.BlobId = { type: 'photo', From be52551a9f97ac5ead46bb2f99cbd12509469b72 Mon Sep 17 00:00:00 2001 From: Andrew Chou Date: Mon, 1 Dec 2025 11:01:57 -0500 Subject: [PATCH 2/3] remove unused query key factory --- src/lib/react-query/projects.ts | 16 ---------------- 1 file changed, 16 deletions(-) diff --git a/src/lib/react-query/projects.ts b/src/lib/react-query/projects.ts index 47ac921..8b3a341 100644 --- a/src/lib/react-query/projects.ts +++ b/src/lib/react-query/projects.ts @@ -53,22 +53,6 @@ export function getMemberByIdQueryKey({ return [ROOT_QUERY_KEY, 'projects', projectId, 'members', deviceId] as const } -export function getDocumentCreatedByQueryKey({ - projectId, - originalVersionId, -}: { - projectId: string - originalVersionId: string -}) { - return [ - ROOT_QUERY_KEY, - 'projects', - projectId, - 'document_created_by', - originalVersionId, - ] as const -} - /** * We call this within a project hook, because that's the only place the API is * exposed right now, but it is the same for all projects, so no need for From 834af76d3acd681a7b54932a80f1224e16c91b26 Mon Sep 17 00:00:00 2001 From: Andrew Chou Date: Mon, 1 Dec 2025 11:28:10 -0500 Subject: [PATCH 3/3] chore!: rename document-related exports to use "docs" in naming --- docs/API.md | 258 +++++++++++++----- src/hooks/{documents.ts => docs.ts} | 40 +-- src/index.ts | 12 +- src/lib/react-query/{documents.ts => docs.ts} | 54 ++-- src/lib/types.ts | 14 +- 5 files changed, 251 insertions(+), 127 deletions(-) rename src/hooks/{documents.ts => docs.ts} (88%) rename src/lib/react-query/{documents.ts => docs.ts} (77%) diff --git a/docs/API.md b/docs/API.md index 243b466..3ca690e 100644 --- a/docs/API.md +++ b/docs/API.md @@ -18,8 +18,12 @@ - [useRemoveServerPeer](#useremoveserverpeer) - [useCreateProject](#usecreateproject) - [useLeaveProject](#useleaveproject) +- [useImportProjectCategories](#useimportprojectcategories) - [useImportProjectConfig](#useimportprojectconfig) - [useUpdateProjectSettings](#useupdateprojectsettings) +- [useChangeMemberRole](#usechangememberrole) +- [useRemoveMember](#useremovemember) +- [useProjectOwnRoleChangeListener](#useprojectownrolechangelistener) - [useCreateBlob](#usecreateblob) - [useSyncState](#usesyncstate) - [useDataSyncProgress](#usedatasyncprogress) @@ -33,10 +37,10 @@ - [useSingleDocByDocId](#usesingledocbydocid) - [useSingleDocByVersionId](#usesingledocbyversionid) - [useManyDocs](#usemanydocs) -- [useCreateDocument](#usecreatedocument) -- [useUpdateDocument](#useupdatedocument) -- [useDeleteDocument](#usedeletedocument) -- [useSetUpInvitesListeners](#usesetupinviteslisteners) +- [useCreateDoc](#usecreatedoc) +- [useUpdateDoc](#useupdatedoc) +- [useDeleteDoc](#usedeletedoc) +- [usePresetsSelection](#usepresetsselection) - [useManyInvites](#usemanyinvites) - [useSingleInvite](#usesingleinvite) - [useAcceptInvite](#useacceptinvite) @@ -51,7 +55,7 @@ Create a context provider that holds a CoMapeo API client instance. | Function | Type | | ---------- | ---------- | -| `ClientApiProvider` | `({ children, clientApi, }: { children: ReactNode; clientApi: MapeoClientApi; }) => Element` | +| `ClientApiProvider` | `({ children, clientApi, }: { children: ReactNode; clientApi: any; }) => Element` | Parameters: @@ -66,7 +70,11 @@ set up, it will throw an error. | Function | Type | | ---------- | ---------- | -| `useClientApi` | `() => MapeoClientApi` | +| `useClientApi` | `() => any` | + +Returns: + +Client API instance Examples: @@ -94,7 +102,7 @@ Retrieve info about the current device. | Function | Type | | ---------- | ---------- | -| `useOwnDeviceInfo` | `() => { data: { deviceId: string; deviceType: "UNRECOGNIZED" or "device_type_unspecified" or "mobile" or "tablet" or "desktop" or "selfHostedServer"; } and Partial; error: Error or null; isRefetching: boolean; }` | +| `useOwnDeviceInfo` | `() => { data: any; error: Error or null; isRefetching: boolean; }` | Examples: @@ -111,7 +119,7 @@ Retrieve whether the current device is an archive device or not. | Function | Type | | ---------- | ---------- | -| `useIsArchiveDevice` | `() => { data: boolean; error: Error or null; isRefetching: boolean; }` | +| `useIsArchiveDevice` | `() => { data: any; error: Error or null; isRefetching: boolean; }` | Examples: @@ -128,7 +136,7 @@ Update the device info for the current device. | Function | Type | | ---------- | ---------- | -| `useSetOwnDeviceInfo` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | +| `useSetOwnDeviceInfo` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | ### useSetIsArchiveDevice @@ -136,7 +144,7 @@ Set or unset the current device as an archive device. | Function | Type | | ---------- | ---------- | -| `useSetIsArchiveDevice` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useSetIsArchiveDevice` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | ### useProjectSettings @@ -144,7 +152,7 @@ Retrieve the project settings for a project. | Function | Type | | ---------- | ---------- | -| `useProjectSettings` | `({ projectId }: { projectId: string; }) => { data: EditableProjectSettings; error: Error or null; isRefetching: boolean; }` | +| `useProjectSettings` | `({ projectId }: { projectId: string; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -170,7 +178,7 @@ This is mostly used internally by the other hooks and should only be used if cer | Function | Type | | ---------- | ---------- | -| `useSingleProject` | `({ projectId }: { projectId: string; }) => { data: ClientApi; error: Error or null; isRefetching: boolean; }` | +| `useSingleProject` | `({ projectId }: { projectId: string; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -192,7 +200,7 @@ Retrieve project information for each project that exists. | Function | Type | | ---------- | ---------- | -| `useManyProjects` | `() => { data: (Pick<{ schemaName: "projectSettings"; name?: string or undefined; defaultPresets?: { point: string[]; area: string[]; vertex: string[]; line: string[]; relation: string[]; } or undefined; configMetadata?: { ...; } or undefined; }, "name"> and { ...; })[]; error: Error or null; isRefetching: boolean; }` | +| `useManyProjects` | `() => { data: any; error: Error or null; isRefetching: boolean; }` | Examples: @@ -211,7 +219,7 @@ Retrieve a single member of a project. | Function | Type | | ---------- | ---------- | -| `useSingleMember` | `({ projectId, deviceId, }: { projectId: string; deviceId: string; }) => { data: MemberInfo; error: Error or null; isRefetching: boolean; }` | +| `useSingleMember` | `({ projectId, deviceId, }: { projectId: string; deviceId: string; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -236,7 +244,7 @@ Retrieve all members of a project. | Function | Type | | ---------- | ---------- | -| `useManyMembers` | `({ projectId }: { projectId: string; }) => { data: MemberInfo[]; error: Error or null; isRefetching: boolean; }` | +| `useManyMembers` | `({ projectId }: { projectId: string; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -367,7 +375,7 @@ This is a more convenient alternative to using the `useOwnDeviceInfo` and `useMa | Function | Type | | ---------- | ---------- | -| `useOwnRoleInProject` | `({ projectId }: { projectId: string; }) => { data: Role<"a12a6702b93bd7ff" or "f7c150f5a3a9a855" or "012fd2d431c0bf60" or "9e6d29263cba36c9" or "8ced989b1904606b" or "a24eaca65ab5d5d0" or "08e4251e36f6e7ed">; error: Error or null; isRefetching: boolean; }` | +| `useOwnRoleInProject` | `({ projectId }: { projectId: string; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -389,13 +397,13 @@ function BasicExample() { | Function | Type | | ---------- | ---------- | -| `useAddServerPeer` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | +| `useAddServerPeer` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | ### useRemoveServerPeer | Function | Type | | ---------- | ---------- | -| `useRemoveServerPeer` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | +| `useRemoveServerPeer` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | ### useCreateProject @@ -403,7 +411,7 @@ Create a new project. | Function | Type | | ---------- | ---------- | -| `useCreateProject` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | +| `useCreateProject` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | ### useLeaveProject @@ -411,7 +419,20 @@ Leave an existing project. | Function | Type | | ---------- | ---------- | -| `useLeaveProject` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useLeaveProject` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | + +### useImportProjectCategories + +Update the categories of a project using an external file. + +| Function | Type | +| ---------- | ---------- | +| `useImportProjectCategories` | `({ projectId, }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | + +Parameters: + +* `opts.projectId`: Public ID of the project to apply changes to. + ### useImportProjectConfig @@ -419,7 +440,7 @@ Update the configuration of a project using an external file. | Function | Type | | ---------- | ---------- | -| `useImportProjectConfig` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useImportProjectConfig` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | Parameters: @@ -432,20 +453,108 @@ Update the settings of a project. | Function | Type | | ---------- | ---------- | -| `useUpdateProjectSettings` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; muta...` | +| `useUpdateProjectSettings` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction, unknown>; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | Parameters: * `opts.projectId`: Public ID of the project to apply changes to. +### useChangeMemberRole + +Change a project member's role. + +| Function | Type | +| ---------- | ---------- | +| `useChangeMemberRole` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | + +Parameters: + +* `opts.projectId`: Project public ID + + +Examples: + +```tsx +function BasicExample() { + const { mutate } = useChangeMemberRole({ projectId: '...' }) + // Use one of: COORDINATOR_ROLE_ID, MEMBER_ROLE_ID, BLOCKED_ROLE_ID + mutate({ deviceId: '...', roleId: COORDINATOR_ROLE_ID }) +} +``` + + +### useRemoveMember + +Remove a member from a project, providing an optional reason for removal. + +Do NOT use this for removing your own device from a project. Use `useLeaveProject` instead. + +| Function | Type | +| ---------- | ---------- | +| `useRemoveMember` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | + +Parameters: + +* `opts.projectId`: Project public ID + + +Examples: + +```tsx +function BasicExample() { + const { mutate } = useRemoveMember({ projectId: '...' }) + mutate({ + deviceId: '...', + // Optional + reason: '...', + }) +} +``` + + +### useProjectOwnRoleChangeListener + +Set up listener for changes to your own role in a project. +It is necessary to use this if you want the project role-related read hooks to update +based on role change events that are received in the background. + +| Function | Type | +| ---------- | ---------- | +| `useProjectOwnRoleChangeListener` | `({ projectId, listener, }: { projectId: string; listener?: ((event: RoleChangeEvent) => void) or undefined; }) => void` | + +Parameters: + +* `opts.listener`: Optional listener to invoke when role changes + + +Examples: + +```tsx +function SomeComponent({ projectId }: { projectId: string }) { + useProjectOwnRoleChangeListener({ projectId }) +} +``` +```tsx +function ComponentWithListener({ projectId }: { projectId: string }) { + useProjectOwnRoleChangeListener({ + projectId, + listener: (event) => { + // Handle role change, e.g., navigate to default project + console.log('New role:', event.role) + } + }) +} +``` + + ### useCreateBlob Create a blob for a project. | Function | Type | | ---------- | ---------- | -| `useCreateBlob` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction<{ driveId: string; name: string; type: "photo" or "audio" or "video"; hash: string; }, Error, { original: string; preview?: string or undefined; thumbnail?: string or undefined; metadata: Metadata; }, unknown>; mutateAsync: UseMutateAsy...` | +| `useCreateBlob` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | Parameters: @@ -462,7 +571,7 @@ additional listeners across the IPC channel. | Function | Type | | ---------- | ---------- | -| `useSyncState` | `({ projectId, }: { projectId: string; }) => State or null` | +| `useSyncState` | `({ projectId, }: { projectId: string; }) => any` | Parameters: @@ -492,35 +601,39 @@ Provides the progress of data sync for sync-enabled connected peers | ---------- | ---------- | | `useDataSyncProgress` | `({ projectId, }: { projectId: string; }) => number or null` | +Returns: + +`null` if no sync state events have been received. Otherwise returns a value between 0 and 1 (inclusive) + ### useStartSync | Function | Type | | ---------- | ---------- | -| `useStartSync` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | +| `useStartSync` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | ### useStopSync | Function | Type | | ---------- | ---------- | -| `useStopSync` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useStopSync` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | ### useConnectSyncServers | Function | Type | | ---------- | ---------- | -| `useConnectSyncServers` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useConnectSyncServers` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | ### useDisconnectSyncServers | Function | Type | | ---------- | ---------- | -| `useDisconnectSyncServers` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useDisconnectSyncServers` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | ### useSetAutostopDataSyncTimeout | Function | Type | | ---------- | ---------- | -| `useSetAutostopDataSyncTimeout` | `({ projectId, }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useSetAutostopDataSyncTimeout` | `({ projectId, }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | ### useExportGeoJSON @@ -528,7 +641,7 @@ Creates a GeoJson file with all the observations and/or tracks in the project. | Function | Type | | ---------- | ---------- | -| `useExportGeoJSON` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error...` | +| `useExportGeoJSON` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; ...` | Parameters: @@ -541,7 +654,7 @@ Creates a zip file containing a GeoJson file with all the observations and/or tr | Function | Type | | ---------- | ---------- | -| `useExportZipFile` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>...` | +| `useExportZipFile` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; r...` | Parameters: @@ -556,7 +669,7 @@ Triggers the closest error boundary if the document cannot be found | Function | Type | | ---------- | ---------- | -| `useSingleDocByDocId` | `({ projectId, docType, docId, lang, }: { projectId: string; docType: D; docId: string; lang?: string or undefined; }) => ReadHookResult({ projectId, docType, docId, lang, }: { projectId: string; docType: D; docId: string; lang?: string or undefined; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -589,7 +702,7 @@ Triggers the closest error boundary if the document cannot be found. | Function | Type | | ---------- | ---------- | -| `useSingleDocByVersionId` | `({ projectId, docType, versionId, lang, }: { projectId: string; docType: D; versionId: string; lang?: string or undefined; }) => ReadHookResult({ projectId, docType, versionId, lang, }: { projectId: string; docType: D; versionId: string; lang?: string or undefined; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -622,7 +735,7 @@ Retrieve all documents of a specific `docType`. | Function | Type | | ---------- | ---------- | -| `useManyDocs` | `({ projectId, docType, includeDeleted, lang, }: { projectId: string; docType: D; includeDeleted?: boolean or undefined; lang?: string or undefined; }) => ReadHookResult<(Extract<{ schemaName: "deviceInfo"; name: string; deviceType: "UNRECOGNIZED" or ... 4 more ... or "selfHostedServer"; ...` | +| `useManyDocs` | `({ projectId, docType, includeDeleted, lang, }: { projectId: string; docType: D; includeDeleted?: boolean or undefined; lang?: string or undefined; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -660,13 +773,13 @@ function useAllPresets(opts) { ``` -### useCreateDocument +### useCreateDoc Create a document for a project. | Function | Type | | ---------- | ---------- | -| `useCreateDocument` | `({ docType, projectId, }: { docType: D; projectId: string; }) => { error: Error; mutate: UseMutateFunction and { forks: string[]; }, Error, { ...; }, unknown>; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | +| `useCreateDoc` | `({ docType, projectId, }: { docType: D; projectId: string; }) => { error: Error; mutate: UseMutateFunction and DerivedDocFields, Error, { ...; }, unknown>; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | Parameters: @@ -674,13 +787,13 @@ Parameters: * `opts.projectId`: Public ID of project to create document for. -### useUpdateDocument +### useUpdateDoc Update a document within a project. | Function | Type | | ---------- | ---------- | -| `useUpdateDocument` | `({ docType, projectId, }: { docType: D; projectId: string; }) => { error: Error; mutate: UseMutateFunction and { forks: string[]; }, Error, { ...; }, unknown>; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | +| `useUpdateDoc` | `({ docType, projectId, }: { docType: D; projectId: string; }) => { error: Error; mutate: UseMutateFunction and DerivedDocFields, Error, { ...; }, unknown>; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | Parameters: @@ -688,13 +801,13 @@ Parameters: * `opts.projectId`: Public ID of project document belongs to. -### useDeleteDocument +### useDeleteDoc Delete a document within a project. | Function | Type | | ---------- | ---------- | -| `useDeleteDocument` | `({ docType, projectId, }: { docType: D; projectId: string; }) => { error: Error; mutate: UseMutateFunction and { forks: string[]; }, Error, { ...; }, unknown>; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | +| `useDeleteDoc` | `({ docType, projectId, }: { docType: D; projectId: string; }) => { error: Error; mutate: UseMutateFunction and DerivedDocFields, Error, { ...; }, unknown>; mutateAsync: UseMutateAsyncFunction<...>; reset: () => void; status: "error"; } or { ...; }` | Parameters: @@ -702,24 +815,41 @@ Parameters: * `opts.projectId`: Public ID of project document belongs to. -### useSetUpInvitesListeners +### usePresetsSelection + +Retrieve presets for category selection, ordered by project settings. -Set up listeners for received and updated invites. -It is necessary to use this if you want the invites-related read hooks to update -based on invites that are received or changed in the background. +Returns presets in the order defined by `projectSettings.defaultPresets` for the +specified data type. Falls back to alphabetical order (by preset name) if no defaults are configured. | Function | Type | | ---------- | ---------- | -| `useSetUpInvitesListeners` | `() => void` | +| `usePresetsSelection` | `({ projectId, dataType, lang, }: { projectId: string; dataType: "track" or "observation"; lang?: string or undefined; }) => { schemaName: "preset"; name: string; geometry: ("point" or "vertex" or "line" or "area" or "relation")[]; ... 13 more ...; deleted: boolean; }[]` | + +Parameters: + +* `opts.projectId`: Project public ID +* `opts.dataType`: Type of data being created ('observation' or 'track') +* `opts.lang`: Language to translate presets into + Examples: ```tsx -function App() { - // Use this somewhere near the root of the application - useSetUpInvitesListeners() +function ObservationCategoryChooser() { + const presets = usePresetsSelection({ + projectId: '...', + dataType: 'observation', + }) +} +``` - return +```tsx +function TrackCategoryChooser() { + const presets = usePresetsSelection({ + projectId: '...', + dataType: 'track', + }) } ``` @@ -730,7 +860,7 @@ Get all invites that the device has received. | Function | Type | | ---------- | ---------- | -| `useManyInvites` | `() => { data: Invite[]; error: Error or null; isRefetching: boolean; }` | +| `useManyInvites` | `() => { data: any; error: Error or null; isRefetching: boolean; }` | Examples: @@ -747,7 +877,7 @@ Get a single invite based on its ID. | Function | Type | | ---------- | ---------- | -| `useSingleInvite` | `({ inviteId }: { inviteId: string; }) => { data: Invite; error: Error or null; isRefetching: boolean; }` | +| `useSingleInvite` | `({ inviteId }: { inviteId: string; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -769,7 +899,7 @@ Accept an invite that has been received. | Function | Type | | ---------- | ---------- | -| `useAcceptInvite` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useAcceptInvite` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | ### useRejectInvite @@ -777,7 +907,7 @@ Reject an invite that has been received. | Function | Type | | ---------- | ---------- | -| `useRejectInvite` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useRejectInvite` | `() => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | ### useSendInvite @@ -785,7 +915,7 @@ Send an invite for a project. | Function | Type | | ---------- | ---------- | -| `useSendInvite` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction<"ACCEPT" or "REJECT" or "ALREADY", Error, { deviceId: string; roleDescription?: string or undefined; roleId: "f7c150f5a3a9a855" or "012fd2d431c0bf60" or "9e6d29263cba36c9"; roleName?: string or undefined; }, unknown>; mutateAsync: UseMuta...` | +| `useSendInvite` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction<...>; reset:...` | Parameters: @@ -798,7 +928,7 @@ Request a cancellation of an invite sent to another device. | Function | Type | | ---------- | ---------- | -| `useRequestCancelInvite` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | +| `useRequestCancelInvite` | `({ projectId }: { projectId: string; }) => { error: Error; mutate: UseMutateFunction; mutateAsync: UseMutateAsyncFunction; reset: () => void; status: "error"; } or { ...; }` | Parameters: @@ -814,7 +944,7 @@ due to hidden internal details by consuming components (e.g. map component from | Function | Type | | ---------- | ---------- | -| `useMapStyleUrl` | `({ refreshToken, }?: { refreshToken?: string or undefined; }) => { data: string; error: Error or null; isRefetching: boolean; }` | +| `useMapStyleUrl` | `({ refreshToken, }?: { refreshToken?: string or undefined; }) => { data: any; error: Error or null; isRefetching: boolean; }` | Parameters: @@ -850,31 +980,31 @@ function ExampleWithRefreshToken() { | Constant | Type | | ---------- | ---------- | -| `ClientApiContext` | `Context` | +| `ClientApiContext` | `Context` | ## Types -- [WriteableDocumentType](#writeabledocumenttype) +- [WriteableDocType](#writeabledoctype) - [WriteableValue](#writeablevalue) -- [WriteableDocument](#writeabledocument) +- [WriteableDoc](#writeabledoc) -### WriteableDocumentType +### WriteableDocType | Type | Type | | ---------- | ---------- | -| `WriteableDocumentType` | `Extract< MapeoDoc['schemaName'], 'field' or 'observation' or 'preset' or 'track' or 'remoteDetectionAlert' >` | +| `WriteableDocType` | `Extract< ComapeoDoc['schemaName'], 'field' or 'observation' or 'preset' or 'track' or 'remoteDetectionAlert' >` | ### WriteableValue | Type | Type | | ---------- | ---------- | -| `WriteableValue` | `Extract< MapeoValue, { schemaName: D } >` | +| `WriteableValue` | `Extract< ComapeoValue, { schemaName: D } >` | -### WriteableDocument +### WriteableDoc | Type | Type | | ---------- | ---------- | -| `WriteableDocument` | `Extract< MapeoDoc, { schemaName: D } >` | +| `WriteableDoc` | `Extract< ComapeoValue, { schemaName: D } >` | diff --git a/src/hooks/documents.ts b/src/hooks/docs.ts similarity index 88% rename from src/hooks/documents.ts rename to src/hooks/docs.ts index c632ee7..8f59413 100644 --- a/src/hooks/documents.ts +++ b/src/hooks/docs.ts @@ -10,14 +10,14 @@ import { useMemo } from 'react' import { getPresetsSelection } from '../lib/presets.js' import { - createDocumentMutationOptions, - deleteDocumentMutationOptions, - documentByDocumentIdQueryOptions, - documentByVersionIdQueryOptions, - documentsQueryOptions, - updateDocumentMutationOptions, -} from '../lib/react-query/documents.js' -import type { WriteableDocumentType } from '../lib/types.js' + createDocMutationOptions, + deleteDocMutationOptions, + docByDocIdQueryOptions, + docByVersionIdQueryOptions, + docsQueryOptions, + updateDocMutationOptions, +} from '../lib/react-query/docs.js' +import type { WriteableDocType } from '../lib/types.js' import { useProjectSettings, useSingleProject } from './projects.js' /** @@ -43,7 +43,7 @@ import { useProjectSettings, useSingleProject } from './projects.js' * } * ``` */ -export function useSingleDocByDocId({ +export function useSingleDocByDocId({ projectId, docType, docId, @@ -57,7 +57,7 @@ export function useSingleDocByDocId({ const { data: projectApi } = useSingleProject({ projectId }) const { data, error, isRefetching } = useSuspenseQuery( - documentByDocumentIdQueryOptions({ + docByDocIdQueryOptions({ projectApi, projectId, docType, @@ -96,7 +96,7 @@ export function useSingleDocByDocId({ * } * ``` */ -export function useSingleDocByVersionId({ +export function useSingleDocByVersionId({ projectId, docType, versionId, @@ -110,7 +110,7 @@ export function useSingleDocByVersionId({ const { data: projectApi } = useSingleProject({ projectId }) const { data, error, isRefetching } = useSuspenseQuery( - documentByVersionIdQueryOptions({ + docByVersionIdQueryOptions({ projectApi, projectId, docType, @@ -160,7 +160,7 @@ export function useSingleDocByVersionId({ * } * ``` */ -export function useManyDocs({ +export function useManyDocs({ projectId, docType, includeDeleted, @@ -174,7 +174,7 @@ export function useManyDocs({ const { data: projectApi } = useSingleProject({ projectId }) const { data, error, isRefetching } = useSuspenseQuery( - documentsQueryOptions({ + docsQueryOptions({ projectApi, projectId, docType, @@ -196,7 +196,7 @@ export function useManyDocs({ * @param opts.docType Document type to create. * @param opts.projectId Public ID of project to create document for. */ -export function useCreateDocument({ +export function useCreateDoc({ docType, projectId, }: { @@ -207,7 +207,7 @@ export function useCreateDocument({ const { data: projectApi } = useSingleProject({ projectId }) const { error, mutate, mutateAsync, reset, status } = useMutation( - createDocumentMutationOptions({ + createDocMutationOptions({ docType, projectApi, projectId, @@ -226,7 +226,7 @@ export function useCreateDocument({ * @param opts.docType Document type to update. * @param opts.projectId Public ID of project document belongs to. */ -export function useUpdateDocument({ +export function useUpdateDoc({ docType, projectId, }: { @@ -237,7 +237,7 @@ export function useUpdateDocument({ const { data: projectApi } = useSingleProject({ projectId }) const { error, mutate, mutateAsync, reset, status } = useMutation( - updateDocumentMutationOptions({ + updateDocMutationOptions({ docType, projectApi, projectId, @@ -256,7 +256,7 @@ export function useUpdateDocument({ * @param opts.docType Document type to delete. * @param opts.projectId Public ID of project document belongs to. */ -export function useDeleteDocument({ +export function useDeleteDoc({ docType, projectId, }: { @@ -267,7 +267,7 @@ export function useDeleteDocument({ const { data: projectApi } = useSingleProject({ projectId }) const { error, mutate, mutateAsync, reset, status } = useMutation( - deleteDocumentMutationOptions({ + deleteDocMutationOptions({ docType, projectApi, projectId, diff --git a/src/index.ts b/src/index.ts index 54b12e4..a8a3bd8 100644 --- a/src/index.ts +++ b/src/index.ts @@ -7,14 +7,14 @@ export { useSetOwnDeviceInfo, } from './hooks/client.js' export { - useCreateDocument, - useDeleteDocument, + useCreateDoc, + useDeleteDoc, useManyDocs, usePresetsSelection, useSingleDocByDocId, useSingleDocByVersionId, - useUpdateDocument, -} from './hooks/documents.js' + useUpdateDoc, +} from './hooks/docs.js' export { useAcceptInvite, useManyInvites, @@ -56,7 +56,7 @@ export { } from './hooks/projects.js' export { type SyncState } from './lib/sync.js' export { - type WriteableDocument, - type WriteableDocumentType, + type WriteableDoc, + type WriteableDocType, type WriteableValue, } from './lib/types.js' diff --git a/src/lib/react-query/documents.ts b/src/lib/react-query/docs.ts similarity index 77% rename from src/lib/react-query/documents.ts rename to src/lib/react-query/docs.ts index 1d49cc5..8b287a1 100644 --- a/src/lib/react-query/documents.ts +++ b/src/lib/react-query/docs.ts @@ -11,8 +11,8 @@ import { } from '@tanstack/react-query' import type { - WriteableDocument, - WriteableDocumentType, + WriteableDoc, + WriteableDocType, WriteableValue, } from '../types.js' import { @@ -21,7 +21,7 @@ import { ROOT_QUERY_KEY, } from './shared.js' -export function getDocumentsQueryKey({ +export function getDocsQueryKey({ projectId, docType, }: { @@ -31,7 +31,7 @@ export function getDocumentsQueryKey({ return [ROOT_QUERY_KEY, 'projects', projectId, docType] as const } -export function getManyDocumentsQueryKey({ +export function getManyDocsQueryKey({ projectId, docType, includeDeleted, @@ -51,7 +51,7 @@ export function getManyDocumentsQueryKey({ ] as const } -export function getDocumentByDocIdQueryKey({ +export function getDocByDocIdQueryKey({ projectId, docType, docId, @@ -72,9 +72,7 @@ export function getDocumentByDocIdQueryKey({ ] as const } -export function getDocumentByVersionIdQueryKey< - D extends WriteableDocumentType, ->({ +export function getDocByVersionIdQueryKey({ projectId, docType, versionId, @@ -95,7 +93,7 @@ export function getDocumentByVersionIdQueryKey< ] as const } -export function documentsQueryOptions({ +export function docsQueryOptions({ projectApi, projectId, docType, @@ -110,7 +108,7 @@ export function documentsQueryOptions({ }) { return queryOptions({ ...baseQueryOptions(), - queryKey: getManyDocumentsQueryKey({ + queryKey: getManyDocsQueryKey({ projectId, docType, includeDeleted, @@ -125,9 +123,7 @@ export function documentsQueryOptions({ }) } -export function documentByDocumentIdQueryOptions< - D extends WriteableDocumentType, ->({ +export function docByDocIdQueryOptions({ projectApi, projectId, docType, @@ -142,7 +138,7 @@ export function documentByDocumentIdQueryOptions< }) { return queryOptions({ ...baseQueryOptions(), - queryKey: getDocumentByDocIdQueryKey({ + queryKey: getDocByDocIdQueryKey({ projectId, docType, docId, @@ -158,9 +154,7 @@ export function documentByDocumentIdQueryOptions< }) } -export function documentByVersionIdQueryOptions< - D extends WriteableDocumentType, ->({ +export function docByVersionIdQueryOptions({ projectApi, projectId, docType, @@ -175,7 +169,7 @@ export function documentByVersionIdQueryOptions< }) { return queryOptions({ ...baseQueryOptions(), - queryKey: getDocumentByVersionIdQueryKey({ + queryKey: getDocByVersionIdQueryKey({ projectId, docType, versionId, @@ -187,9 +181,9 @@ export function documentByVersionIdQueryOptions< }) } -export function createDocumentMutationOptions< - D extends WriteableDocumentType, - Result = WriteableDocument & DerivedDocFields, +export function createDocMutationOptions< + D extends WriteableDocType, + Result = WriteableDoc & DerivedDocFields, >({ docType, projectApi, @@ -212,7 +206,7 @@ export function createDocumentMutationOptions< }, onSuccess: () => { queryClient.invalidateQueries({ - queryKey: getDocumentsQueryKey({ + queryKey: getDocsQueryKey({ projectId, docType, }), @@ -225,9 +219,9 @@ export function createDocumentMutationOptions< > } -export function updateDocumentMutationOptions< - D extends WriteableDocumentType, - Result = WriteableDocument & DerivedDocFields, +export function updateDocMutationOptions< + D extends WriteableDocType, + Result = WriteableDoc & DerivedDocFields, >({ docType, projectApi, @@ -247,7 +241,7 @@ export function updateDocumentMutationOptions< }, onSuccess: () => { queryClient.invalidateQueries({ - queryKey: getDocumentsQueryKey({ + queryKey: getDocsQueryKey({ projectId, docType, }), @@ -260,9 +254,9 @@ export function updateDocumentMutationOptions< > } -export function deleteDocumentMutationOptions< - D extends WriteableDocumentType, - Result = WriteableDocument & DerivedDocFields, +export function deleteDocMutationOptions< + D extends WriteableDocType, + Result = WriteableDoc & DerivedDocFields, >({ docType, projectApi, @@ -282,7 +276,7 @@ export function deleteDocumentMutationOptions< }, onSuccess: () => { queryClient.invalidateQueries({ - queryKey: getDocumentsQueryKey({ + queryKey: getDocsQueryKey({ projectId, docType, }), diff --git a/src/lib/types.ts b/src/lib/types.ts index 9b2446a..9108605 100644 --- a/src/lib/types.ts +++ b/src/lib/types.ts @@ -1,17 +1,17 @@ -import type { MapeoDoc, MapeoValue } from '@comapeo/schema' with { +import type { ComapeoDoc, ComapeoValue } from '@comapeo/schema' with { 'resolution-mode': 'import', } -export type WriteableDocumentType = Extract< - MapeoDoc['schemaName'], +export type WriteableDocType = Extract< + ComapeoDoc['schemaName'], 'field' | 'observation' | 'preset' | 'track' | 'remoteDetectionAlert' > -export type WriteableValue = Extract< - MapeoValue, +export type WriteableValue = Extract< + ComapeoValue, { schemaName: D } > -export type WriteableDocument = Extract< - MapeoDoc, +export type WriteableDoc = Extract< + ComapeoValue, { schemaName: D } >