mirror of
https://github.com/hanzo-apps/dataroom.git
synced 2026-10-30 14:47:36 +00:00
445 lines
9.4 KiB
TypeScript
445 lines
9.4 KiB
TypeScript
import { useRouter } from "next/router";
|
|
|
|
import { useMemo } from "react";
|
|
|
|
import { useTeam } from "@/context/team-context";
|
|
import { Dataroom, DataroomDocument, DataroomFolder } from "@prisma/client";
|
|
import { toast } from "sonner";
|
|
import useSWR from "swr";
|
|
|
|
import { LinkWithViews } from "@/lib/types";
|
|
import { fetcher } from "@/lib/utils";
|
|
import { sortByIndexThenName } from "@/lib/utils/sort-items-by-index-name";
|
|
|
|
export type DataroomFolderWithCount = DataroomFolder & {
|
|
_count: {
|
|
documents: number;
|
|
childFolders: number;
|
|
};
|
|
};
|
|
|
|
export function useDataroom() {
|
|
const router = useRouter();
|
|
|
|
const { id } = router.query as {
|
|
id: string;
|
|
};
|
|
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
// Only make the API call if we're on a dataroom page
|
|
const isDataroomPage = router.pathname.startsWith("/datarooms");
|
|
const shouldFetch = teamId && id && isDataroomPage;
|
|
|
|
const { data: dataroom, error } = useSWR<
|
|
Dataroom & {
|
|
_count?: { viewerGroups: number; permissionGroups: number };
|
|
tags?: {
|
|
tag: {
|
|
id: string;
|
|
name: string;
|
|
color: string;
|
|
description: string | null;
|
|
};
|
|
}[];
|
|
}
|
|
>(shouldFetch ? `/api/teams/${teamId}/datarooms/${id}` : null, fetcher, {
|
|
dedupingInterval: 10000,
|
|
onError: (err) => {
|
|
if (err.status === 404) {
|
|
toast.error("Dataroom not found", {
|
|
description:
|
|
"The dataroom you're looking for doesn't exist or has been moved.",
|
|
});
|
|
router.replace("/datarooms");
|
|
}
|
|
},
|
|
});
|
|
|
|
return {
|
|
dataroom,
|
|
loading: !error && !dataroom,
|
|
error,
|
|
};
|
|
}
|
|
|
|
export function useDataroomLinks() {
|
|
const router = useRouter();
|
|
|
|
const { id } = router.query as {
|
|
id: string;
|
|
};
|
|
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data: links, error } = useSWR<LinkWithViews[]>(
|
|
teamId && id && `/api/teams/${teamId}/datarooms/${id}/links`,
|
|
fetcher,
|
|
{ dedupingInterval: 10000 },
|
|
);
|
|
|
|
return {
|
|
links,
|
|
loading: !error && !links,
|
|
error,
|
|
};
|
|
}
|
|
|
|
export function useDataroomItems({
|
|
root,
|
|
name,
|
|
}: {
|
|
root?: boolean;
|
|
name?: string[];
|
|
}) {
|
|
const router = useRouter();
|
|
const { id } = router.query as {
|
|
id: string;
|
|
};
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data: folderData, error: folderError } = useSWR<
|
|
DataroomFolderWithCount[]
|
|
>(
|
|
teamId &&
|
|
id &&
|
|
`/api/teams/${teamId}/datarooms/${id}/folders${root ? "?root=true" : name ? `/${name.join("/")}` : ""}`,
|
|
fetcher,
|
|
{
|
|
revalidateOnFocus: false,
|
|
dedupingInterval: 30000,
|
|
},
|
|
);
|
|
|
|
const { data: documentData, error: documentError } = useSWR<
|
|
DataroomFolderDocument[]
|
|
>(
|
|
teamId &&
|
|
id &&
|
|
`/api/teams/${teamId}/datarooms/${id}${name ? `/folders/documents/${name.join("/")}` : "/documents"}`,
|
|
|
|
fetcher,
|
|
{
|
|
revalidateOnFocus: false,
|
|
dedupingInterval: 30000,
|
|
},
|
|
);
|
|
|
|
const isLoading =
|
|
!folderData && !documentData && !folderError && !documentError;
|
|
const error = folderError || documentError;
|
|
|
|
const combinedItems = useMemo(() => {
|
|
if (!folderData && !documentData) return [];
|
|
|
|
const allItems = [
|
|
...(folderData || []).map((folder) => ({
|
|
...folder,
|
|
itemType: "folder",
|
|
})),
|
|
...(documentData || []).map((doc) => ({ ...doc, itemType: "document" })),
|
|
];
|
|
return sortByIndexThenName(allItems);
|
|
}, [folderData, documentData]);
|
|
|
|
return {
|
|
items: combinedItems as (
|
|
| (DataroomFolderWithCount & { itemType: "folder" })
|
|
| (DataroomFolderDocument & { itemType: "document" })
|
|
)[],
|
|
folderCount: folderData?.length || 0,
|
|
documentCount: documentData?.length || 0,
|
|
isLoading,
|
|
error,
|
|
};
|
|
}
|
|
|
|
export function useDataroomDocuments() {
|
|
const router = useRouter();
|
|
|
|
const { id } = router.query as {
|
|
id: string;
|
|
};
|
|
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data: documents, error } = useSWR<DataroomFolderDocument[]>(
|
|
teamId && id && `/api/teams/${teamId}/datarooms/${id}/documents`,
|
|
fetcher,
|
|
{
|
|
revalidateOnFocus: false,
|
|
dedupingInterval: 30000,
|
|
},
|
|
);
|
|
|
|
return {
|
|
documents,
|
|
loading: !documents && !error,
|
|
error,
|
|
};
|
|
}
|
|
|
|
export function useDataroomFolders({
|
|
root,
|
|
name,
|
|
}: {
|
|
root?: boolean;
|
|
name?: string[];
|
|
}) {
|
|
const router = useRouter();
|
|
|
|
const { id } = router.query as {
|
|
id: string;
|
|
};
|
|
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data: folders, error } = useSWR<DataroomFolderWithCount[]>(
|
|
teamId &&
|
|
id &&
|
|
`/api/teams/${teamId}/datarooms/${id}/folders${root ? "?root=true" : name ? `/${name.join("/")}` : ""}`,
|
|
fetcher,
|
|
{
|
|
revalidateOnFocus: false,
|
|
dedupingInterval: 30000,
|
|
},
|
|
);
|
|
|
|
return {
|
|
folders,
|
|
loading: !folders && !error,
|
|
error,
|
|
};
|
|
}
|
|
|
|
export type DataroomFolderWithDocuments = DataroomFolder & {
|
|
childFolders: DataroomFolderWithDocuments[];
|
|
documents: {
|
|
orderIndex: number | null;
|
|
id: string;
|
|
folderId: string;
|
|
hierarchicalIndex: string | null;
|
|
document: {
|
|
id: string;
|
|
name: string;
|
|
type: string;
|
|
};
|
|
}[];
|
|
};
|
|
|
|
export function useDataroomFoldersTree({
|
|
dataroomId,
|
|
include_documents,
|
|
}: {
|
|
dataroomId: string;
|
|
include_documents?: boolean;
|
|
}) {
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data: folders, error } = useSWR<DataroomFolderWithDocuments[]>(
|
|
teamId &&
|
|
`/api/teams/${teamId}/datarooms/${dataroomId}/folders${include_documents ? "?include_documents=true" : ""}`,
|
|
fetcher,
|
|
{
|
|
revalidateOnFocus: false,
|
|
dedupingInterval: 30000,
|
|
},
|
|
);
|
|
|
|
return {
|
|
folders,
|
|
loading: !folders && !error,
|
|
error,
|
|
};
|
|
}
|
|
|
|
export function useDataroomFolderWithParents({
|
|
name,
|
|
dataroomId,
|
|
}: {
|
|
name: string[];
|
|
dataroomId: string;
|
|
}) {
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data: folders, error } = useSWR<{ name: string; path: string }[]>(
|
|
teamId &&
|
|
name &&
|
|
!!name.length &&
|
|
`/api/teams/${teamId}/datarooms/${dataroomId}/folders/parents/${name.join("/")}`,
|
|
fetcher,
|
|
{
|
|
revalidateOnFocus: false,
|
|
dedupingInterval: 30000,
|
|
},
|
|
);
|
|
|
|
return {
|
|
folders,
|
|
loading: !folders && !error,
|
|
error,
|
|
};
|
|
}
|
|
|
|
export type DataroomFolderDocument = DataroomDocument & {
|
|
document: {
|
|
id: string;
|
|
name: string;
|
|
type: string;
|
|
versions?: { id: string; hasPages: boolean }[];
|
|
isExternalUpload?: boolean;
|
|
_count: {
|
|
views: number;
|
|
versions: number;
|
|
};
|
|
};
|
|
};
|
|
|
|
export function useDataroomFolderDocuments({ name }: { name: string[] }) {
|
|
const router = useRouter();
|
|
|
|
const { id } = router.query as {
|
|
id: string;
|
|
};
|
|
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data: documents, error } = useSWR<DataroomFolderDocument[]>(
|
|
teamId &&
|
|
id &&
|
|
name &&
|
|
`/api/teams/${teamId}/datarooms/${id}/folders/documents/${name.join("/")}`,
|
|
fetcher,
|
|
{
|
|
revalidateOnFocus: false,
|
|
dedupingInterval: 30000,
|
|
},
|
|
);
|
|
|
|
return {
|
|
documents,
|
|
loading: !documents && !error,
|
|
error,
|
|
};
|
|
}
|
|
|
|
export function useDataroomViewers({ dataroomId }: { dataroomId: string }) {
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data: viewers, error } = useSWR<any[]>(
|
|
teamId &&
|
|
dataroomId &&
|
|
`/api/teams/${teamId}/datarooms/${dataroomId}/viewers`,
|
|
fetcher,
|
|
{
|
|
dedupingInterval: 10000,
|
|
},
|
|
);
|
|
|
|
return {
|
|
viewers,
|
|
loading: !error && !viewers,
|
|
error,
|
|
};
|
|
}
|
|
|
|
type DataroomVisitsResponse = {
|
|
views: any[];
|
|
hiddenFromPause: number;
|
|
};
|
|
|
|
export function useDataroomVisits({
|
|
dataroomId,
|
|
groupId,
|
|
}: {
|
|
dataroomId: string;
|
|
groupId?: string;
|
|
}) {
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data, error } = useSWR<DataroomVisitsResponse>(
|
|
teamId &&
|
|
dataroomId &&
|
|
`/api/teams/${teamId}/datarooms/${dataroomId}${groupId ? `/groups/${groupId}` : ""}/views`,
|
|
fetcher,
|
|
{
|
|
dedupingInterval: 10000,
|
|
},
|
|
);
|
|
|
|
return {
|
|
views: data?.views,
|
|
hiddenFromPause: data?.hiddenFromPause ?? 0,
|
|
loading: !error && !data,
|
|
error,
|
|
};
|
|
}
|
|
|
|
type DataroomDocumentViewHistory = {
|
|
id: string;
|
|
downloadedAt: string;
|
|
viewedAt: string;
|
|
downloadType?: "SINGLE" | "BULK" | "FOLDER";
|
|
downloadMetadata?: {
|
|
folderName?: string;
|
|
folderPath?: string;
|
|
dataroomName?: string;
|
|
documentCount?: number;
|
|
documents?: {
|
|
id: string;
|
|
name: string;
|
|
}[];
|
|
};
|
|
document: {
|
|
id: string;
|
|
name: string;
|
|
};
|
|
};
|
|
|
|
type DataroomDocumentUploadViewHistory = {
|
|
uploadedAt: string;
|
|
documentId: string;
|
|
originalFilename: string;
|
|
};
|
|
|
|
export function useDataroomVisitHistory({
|
|
viewId,
|
|
dataroomId,
|
|
}: {
|
|
viewId: string;
|
|
dataroomId: string;
|
|
}) {
|
|
const teamInfo = useTeam();
|
|
const teamId = teamInfo?.currentTeam?.id;
|
|
|
|
const { data, error } = useSWR<{
|
|
documentViews: DataroomDocumentViewHistory[];
|
|
uploadedDocumentViews: DataroomDocumentUploadViewHistory[];
|
|
}>(
|
|
teamId &&
|
|
dataroomId &&
|
|
`/api/teams/${teamId}/datarooms/${dataroomId}/views/${viewId}/history`,
|
|
fetcher,
|
|
{
|
|
dedupingInterval: 10000,
|
|
},
|
|
);
|
|
|
|
return {
|
|
documentViews: data?.documentViews,
|
|
uploadedDocumentViews: data?.uploadedDocumentViews,
|
|
loading: !error && !data,
|
|
error,
|
|
};
|
|
}
|