Fix shared chats

This commit is contained in:
Weves
2024-07-04 11:21:15 -07:00
committed by Chris Weaver
parent 0b384c5b34
commit de4d8e9a65
10 changed files with 94 additions and 54 deletions

View File

@@ -6,18 +6,28 @@ import { ErrorCallout } from "@/components/ErrorCallout";
import { DocumentSet, SlackBotConfig } from "@/lib/types"; import { DocumentSet, SlackBotConfig } from "@/lib/types";
import { Text } from "@tremor/react"; import { Text } from "@tremor/react";
import { BackButton } from "@/components/BackButton"; import { BackButton } from "@/components/BackButton";
import { Persona } from "../../assistants/interfaces";
import { InstantSSRAutoRefresh } from "@/components/SSRAutoRefresh"; import { InstantSSRAutoRefresh } from "@/components/SSRAutoRefresh";
import {
FetchAssistantsResponse,
fetchAssistantsSS,
} from "@/lib/assistants/fetchAssistantsSS";
async function Page({ params }: { params: { id: string } }) { async function Page({ params }: { params: { id: string } }) {
const tasks = [ const tasks = [
fetchSS("/manage/admin/slack-bot/config"), fetchSS("/manage/admin/slack-bot/config"),
fetchSS("/manage/document-set"), fetchSS("/manage/document-set"),
fetchSS("/persona"), fetchAssistantsSS(),
]; ];
const [slackBotsResponse, documentSetsResponse, personasResponse] = const [
await Promise.all(tasks); slackBotsResponse,
documentSetsResponse,
[assistants, assistantsFetchError],
] = (await Promise.all(tasks)) as [
Response,
Response,
FetchAssistantsResponse,
];
if (!slackBotsResponse.ok) { if (!slackBotsResponse.ok) {
return ( return (
@@ -51,15 +61,14 @@ async function Page({ params }: { params: { id: string } }) {
} }
const documentSets = (await documentSetsResponse.json()) as DocumentSet[]; const documentSets = (await documentSetsResponse.json()) as DocumentSet[];
if (!personasResponse.ok) { if (assistantsFetchError) {
return ( return (
<ErrorCallout <ErrorCallout
errorTitle="Something went wrong :(" errorTitle="Something went wrong :("
errorMsg={`Failed to fetch personas - ${await personasResponse.text()}`} errorMsg={`Failed to fetch personas - ${assistantsFetchError}`}
/> />
); );
} }
const personas = (await personasResponse.json()) as Persona[];
return ( return (
<div className="container mx-auto"> <div className="container mx-auto">
@@ -78,7 +87,7 @@ async function Page({ params }: { params: { id: string } }) {
<SlackBotCreationForm <SlackBotCreationForm
documentSets={documentSets} documentSets={documentSets}
personas={personas} personas={assistants}
existingSlackBotConfig={slackBotConfig} existingSlackBotConfig={slackBotConfig}
/> />
</div> </div>

View File

@@ -6,11 +6,15 @@ import { ErrorCallout } from "@/components/ErrorCallout";
import { DocumentSet } from "@/lib/types"; import { DocumentSet } from "@/lib/types";
import { BackButton } from "@/components/BackButton"; import { BackButton } from "@/components/BackButton";
import { Text } from "@tremor/react"; import { Text } from "@tremor/react";
import { Persona } from "../../assistants/interfaces"; import {
FetchAssistantsResponse,
fetchAssistantsSS,
} from "@/lib/assistants/fetchAssistantsSS";
async function Page() { async function Page() {
const tasks = [fetchSS("/manage/document-set"), fetchSS("/persona")]; const tasks = [fetchSS("/manage/document-set"), fetchAssistantsSS()];
const [documentSetsResponse, personasResponse] = await Promise.all(tasks); const [documentSetsResponse, [assistants, assistantsFetchError]] =
(await Promise.all(tasks)) as [Response, FetchAssistantsResponse];
if (!documentSetsResponse.ok) { if (!documentSetsResponse.ok) {
return ( return (
@@ -22,15 +26,14 @@ async function Page() {
} }
const documentSets = (await documentSetsResponse.json()) as DocumentSet[]; const documentSets = (await documentSetsResponse.json()) as DocumentSet[];
if (!personasResponse.ok) { if (assistantsFetchError) {
return ( return (
<ErrorCallout <ErrorCallout
errorTitle="Something went wrong :(" errorTitle="Something went wrong :("
errorMsg={`Failed to fetch personas - ${await personasResponse.text()}`} errorMsg={`Failed to fetch assistants - ${assistantsFetchError}`}
/> />
); );
} }
const personas = (await personasResponse.json()) as Persona[];
return ( return (
<div className="container mx-auto"> <div className="container mx-auto">
@@ -45,7 +48,7 @@ async function Page() {
DanswerBot behaves in the specified channels. DanswerBot behaves in the specified channels.
</Text> </Text>
<SlackBotCreationForm documentSets={documentSets} personas={personas} /> <SlackBotCreationForm documentSets={documentSets} personas={assistants} />
</div> </div>
); );
} }

View File

@@ -26,7 +26,7 @@ export default async function GalleryPage({
chatSessions, chatSessions,
availableSources, availableSources,
documentSets, documentSets,
personas, assistants,
tags, tags,
llmProviders, llmProviders,
folders, folders,
@@ -46,7 +46,7 @@ export default async function GalleryPage({
chatSessions, chatSessions,
availableSources, availableSources,
availableDocumentSets: documentSets, availableDocumentSets: documentSets,
availablePersonas: personas, availablePersonas: assistants,
availableTags: tags, availableTags: tags,
llmProviders, llmProviders,
folders, folders,
@@ -71,7 +71,7 @@ export default async function GalleryPage({
</div> </div>
<div className="mt-4"> <div className="mt-4">
<AssistantsGallery assistants={personas} user={user} /> <AssistantsGallery assistants={assistants} user={user} />
</div> </div>
</div> </div>
</div> </div>

View File

@@ -27,7 +27,7 @@ export default async function GalleryPage({
chatSessions, chatSessions,
availableSources, availableSources,
documentSets, documentSets,
personas, assistants,
tags, tags,
llmProviders, llmProviders,
folders, folders,
@@ -47,7 +47,7 @@ export default async function GalleryPage({
chatSessions, chatSessions,
availableSources, availableSources,
availableDocumentSets: documentSets, availableDocumentSets: documentSets,
availablePersonas: personas, availablePersonas: assistants,
availableTags: tags, availableTags: tags,
llmProviders, llmProviders,
folders, folders,
@@ -72,7 +72,7 @@ export default async function GalleryPage({
</div> </div>
<div className="mt-4"> <div className="mt-4">
<AssistantsList user={user} assistants={personas} /> <AssistantsList user={user} assistants={assistants} />
</div> </div>
</div> </div>
</div> </div>

View File

@@ -27,7 +27,7 @@ export default async function Page({
ccPairs, ccPairs,
availableSources, availableSources,
documentSets, documentSets,
personas, assistants,
tags, tags,
llmProviders, llmProviders,
folders, folders,
@@ -54,7 +54,7 @@ export default async function Page({
chatSessions, chatSessions,
availableSources, availableSources,
availableDocumentSets: documentSets, availableDocumentSets: documentSets,
availablePersonas: personas, availablePersonas: assistants,
availableTags: tags, availableTags: tags,
llmProviders, llmProviders,
folders, folders,

View File

@@ -10,7 +10,7 @@ import {
import { AIMessage, HumanMessage } from "../../message/Messages"; import { AIMessage, HumanMessage } from "../../message/Messages";
import { Button, Callout, Divider } from "@tremor/react"; import { Button, Callout, Divider } from "@tremor/react";
import { useRouter } from "next/navigation"; import { useRouter } from "next/navigation";
import { useChatContext } from "@/components/context/ChatContext"; import { Persona } from "@/app/admin/assistants/interfaces";
function BackToDanswerButton() { function BackToDanswerButton() {
const router = useRouter(); const router = useRouter();
@@ -28,10 +28,11 @@ function BackToDanswerButton() {
export function SharedChatDisplay({ export function SharedChatDisplay({
chatSession, chatSession,
availableAssistants,
}: { }: {
chatSession: BackendChatSession | null; chatSession: BackendChatSession | null;
availableAssistants: Persona[];
}) { }) {
let { availablePersonas } = useChatContext();
if (!chatSession) { if (!chatSession) {
return ( return (
<div className="min-h-full w-full"> <div className="min-h-full w-full">
@@ -46,7 +47,7 @@ export function SharedChatDisplay({
); );
} }
const currentPersona = availablePersonas.find( const currentPersona = availableAssistants.find(
(persona) => persona.id === chatSession.persona_id (persona) => persona.id === chatSession.persona_id
); );

View File

@@ -9,6 +9,8 @@ import { redirect } from "next/navigation";
import { BackendChatSession } from "../../interfaces"; import { BackendChatSession } from "../../interfaces";
import { Header } from "@/components/header/Header"; import { Header } from "@/components/header/Header";
import { SharedChatDisplay } from "./SharedChatDisplay"; import { SharedChatDisplay } from "./SharedChatDisplay";
import { Persona } from "@/app/admin/assistants/interfaces";
import { fetchAssistantsSS } from "@/lib/assistants/fetchAssistantsSS";
async function getSharedChat(chatId: string) { async function getSharedChat(chatId: string) {
const response = await fetchSS( const response = await fetchSS(
@@ -25,12 +27,14 @@ export default async function Page({ params }: { params: { chatId: string } }) {
getAuthTypeMetadataSS(), getAuthTypeMetadataSS(),
getCurrentUserSS(), getCurrentUserSS(),
getSharedChat(params.chatId), getSharedChat(params.chatId),
fetchAssistantsSS(),
]; ];
// catch cases where the backend is completely unreachable here // catch cases where the backend is completely unreachable here
// without try / catch, will just raise an exception and the page // without try / catch, will just raise an exception and the page
// will not render // will not render
let results: (User | AuthTypeMetadata | null)[] = [null, null, null]; let results: (User | AuthTypeMetadata | [Persona[], string | null] | null)[] =
[null, null, null];
try { try {
results = await Promise.all(tasks); results = await Promise.all(tasks);
} catch (e) { } catch (e) {
@@ -39,6 +43,7 @@ export default async function Page({ params }: { params: { chatId: string } }) {
const authTypeMetadata = results[0] as AuthTypeMetadata | null; const authTypeMetadata = results[0] as AuthTypeMetadata | null;
const user = results[1] as User | null; const user = results[1] as User | null;
const chatSession = results[2] as BackendChatSession | null; const chatSession = results[2] as BackendChatSession | null;
const [availableAssistants, _] = results[3] as [Persona[], string | null];
const authDisabled = authTypeMetadata?.authType === "disabled"; const authDisabled = authTypeMetadata?.authType === "disabled";
if (!authDisabled && !user) { if (!authDisabled && !user) {
@@ -56,7 +61,10 @@ export default async function Page({ params }: { params: { chatId: string } }) {
</div> </div>
<div className="flex relative bg-background text-default overflow-hidden pt-16 h-screen"> <div className="flex relative bg-background text-default overflow-hidden pt-16 h-screen">
<SharedChatDisplay chatSession={chatSession} /> <SharedChatDisplay
chatSession={chatSession}
availableAssistants={availableAssistants}
/>
</div> </div>
</div> </div>
); );

View File

@@ -24,6 +24,10 @@ import { FullEmbeddingModelResponse } from "../admin/models/embedding/embeddingM
import { NoSourcesModal } from "@/components/initialSetup/search/NoSourcesModal"; import { NoSourcesModal } from "@/components/initialSetup/search/NoSourcesModal";
import { NoCompleteSourcesModal } from "@/components/initialSetup/search/NoCompleteSourceModal"; import { NoCompleteSourcesModal } from "@/components/initialSetup/search/NoCompleteSourceModal";
import { ChatPopup } from "../chat/ChatPopup"; import { ChatPopup } from "../chat/ChatPopup";
import {
FetchAssistantsResponse,
fetchAssistantsSS,
} from "@/lib/assistants/fetchAssistantsSS";
export default async function Home() { export default async function Home() {
// Disable caching so we always get the up to date connector / document set / persona info // Disable caching so we always get the up to date connector / document set / persona info
@@ -36,7 +40,7 @@ export default async function Home() {
getCurrentUserSS(), getCurrentUserSS(),
fetchSS("/manage/indexing-status"), fetchSS("/manage/indexing-status"),
fetchSS("/manage/document-set"), fetchSS("/manage/document-set"),
fetchSS("/persona"), fetchAssistantsSS(),
fetchSS("/query/valid-tags"), fetchSS("/query/valid-tags"),
fetchSS("/secondary-index/get-embedding-models"), fetchSS("/secondary-index/get-embedding-models"),
]; ];
@@ -49,6 +53,7 @@ export default async function Home() {
| Response | Response
| AuthTypeMetadata | AuthTypeMetadata
| FullEmbeddingModelResponse | FullEmbeddingModelResponse
| FetchAssistantsResponse
| null | null
)[] = [null, null, null, null, null, null]; )[] = [null, null, null, null, null, null];
try { try {
@@ -60,7 +65,8 @@ export default async function Home() {
const user = results[1] as User | null; const user = results[1] as User | null;
const ccPairsResponse = results[2] as Response | null; const ccPairsResponse = results[2] as Response | null;
const documentSetsResponse = results[3] as Response | null; const documentSetsResponse = results[3] as Response | null;
const personaResponse = results[4] as Response | null; const [initialAssistantsList, assistantsFetchError] =
results[4] as FetchAssistantsResponse;
const tagsResponse = results[5] as Response | null; const tagsResponse = results[5] as Response | null;
const embeddingModelResponse = results[6] as Response | null; const embeddingModelResponse = results[6] as Response | null;
@@ -89,19 +95,17 @@ export default async function Home() {
); );
} }
let personas: Persona[] = []; let assistants: Persona[] = initialAssistantsList;
if (assistantsFetchError) {
if (personaResponse?.ok) { console.log(`Failed to fetch assistants - ${assistantsFetchError}`);
personas = await personaResponse.json();
} else { } else {
console.log(`Failed to fetch personas - ${personaResponse?.status}`); // remove those marked as hidden by an admin
assistants = assistants.filter((assistant) => assistant.is_visible);
// hide personas with no retrieval
assistants = assistants.filter((assistant) => assistant.num_chunks !== 0);
// sort them in priority order
assistants.sort(personaComparator);
} }
// remove those marked as hidden by an admin
personas = personas.filter((persona) => persona.is_visible);
// hide personas with no retrieval
personas = personas.filter((persona) => persona.num_chunks !== 0);
// sort them in priority order
personas.sort(personaComparator);
let tags: Tag[] = []; let tags: Tag[] = [];
if (tagsResponse?.ok) { if (tagsResponse?.ok) {
@@ -176,7 +180,7 @@ export default async function Home() {
<SearchSection <SearchSection
ccPairs={ccPairs} ccPairs={ccPairs}
documentSets={documentSets} documentSets={documentSets}
personas={personas} personas={assistants}
tags={tags} tags={tags}
defaultSearchType={searchTypeDefault} defaultSearchType={searchTypeDefault}
/> />

View File

@@ -0,0 +1,12 @@
import { Persona } from "@/app/admin/assistants/interfaces";
import { fetchSS } from "../utilsSS";
export type FetchAssistantsResponse = [Persona[], string | null];
export async function fetchAssistantsSS(): Promise<FetchAssistantsResponse> {
const response = await fetchSS("/persona");
if (response.ok) {
return [(await response.json()) as Persona[], null];
}
return [[], (await response.json()).detail || "Unknown Error"];
}

View File

@@ -22,6 +22,7 @@ import { personaComparator } from "@/app/admin/assistants/lib";
import { cookies } from "next/headers"; import { cookies } from "next/headers";
import { DOCUMENT_SIDEBAR_WIDTH_COOKIE_NAME } from "@/components/resizable/contants"; import { DOCUMENT_SIDEBAR_WIDTH_COOKIE_NAME } from "@/components/resizable/contants";
import { hasCompletedWelcomeFlowSS } from "@/components/initialSetup/welcome/WelcomeModalWrapper"; import { hasCompletedWelcomeFlowSS } from "@/components/initialSetup/welcome/WelcomeModalWrapper";
import { fetchAssistantsSS } from "../assistants/fetchAssistantsSS";
interface FetchChatDataResult { interface FetchChatDataResult {
user: User | null; user: User | null;
@@ -29,7 +30,7 @@ interface FetchChatDataResult {
ccPairs: CCPairBasicInfo[]; ccPairs: CCPairBasicInfo[];
availableSources: ValidSources[]; availableSources: ValidSources[];
documentSets: DocumentSet[]; documentSets: DocumentSet[];
personas: Persona[]; assistants: Persona[];
tags: Tag[]; tags: Tag[];
llmProviders: LLMProviderDescriptor[]; llmProviders: LLMProviderDescriptor[];
folders: Folder[]; folders: Folder[];
@@ -48,7 +49,7 @@ export async function fetchChatData(searchParams: {
getCurrentUserSS(), getCurrentUserSS(),
fetchSS("/manage/indexing-status"), fetchSS("/manage/indexing-status"),
fetchSS("/manage/document-set"), fetchSS("/manage/document-set"),
fetchSS("/persona?include_default=true"), fetchAssistantsSS(),
fetchSS("/chat/get-user-chat-sessions"), fetchSS("/chat/get-user-chat-sessions"),
fetchSS("/query/valid-tags"), fetchSS("/query/valid-tags"),
fetchLLMProvidersSS(), fetchLLMProvidersSS(),
@@ -62,6 +63,7 @@ export async function fetchChatData(searchParams: {
| FullEmbeddingModelResponse | FullEmbeddingModelResponse
| Settings | Settings
| LLMProviderDescriptor[] | LLMProviderDescriptor[]
| [Persona[], string | null]
| null | null
)[] = [null, null, null, null, null, null, null, null, null, null]; )[] = [null, null, null, null, null, null, null, null, null, null];
try { try {
@@ -74,7 +76,10 @@ export async function fetchChatData(searchParams: {
const user = results[1] as User | null; const user = results[1] as User | null;
const ccPairsResponse = results[2] as Response | null; const ccPairsResponse = results[2] as Response | null;
const documentSetsResponse = results[3] as Response | null; const documentSetsResponse = results[3] as Response | null;
const personasResponse = results[4] as Response | null; const [rawAssistantsList, assistantsFetchError] = results[4] as [
Persona[],
string | null,
];
const chatSessionsResponse = results[5] as Response | null; const chatSessionsResponse = results[5] as Response | null;
const tagsResponse = results[6] as Response | null; const tagsResponse = results[6] as Response | null;
const llmProviders = (results[7] || []) as LLMProviderDescriptor[]; const llmProviders = (results[7] || []) as LLMProviderDescriptor[];
@@ -122,17 +127,15 @@ export async function fetchChatData(searchParams: {
); );
} }
let personas: Persona[] = []; let assistants = rawAssistantsList;
if (personasResponse?.ok) { if (assistantsFetchError) {
personas = await personasResponse.json(); console.log(`Failed to fetch assistants - ${assistantsFetchError}`);
} else {
console.log(`Failed to fetch personas - ${personasResponse?.status}`);
} }
// remove those marked as hidden by an admin // remove those marked as hidden by an admin
personas = personas.filter((persona) => persona.is_visible); assistants = assistants.filter((assistant) => assistant.is_visible);
// sort them in priority order // sort them in priority order
personas.sort(personaComparator); assistants.sort(personaComparator);
let tags: Tag[] = []; let tags: Tag[] = [];
if (tagsResponse?.ok) { if (tagsResponse?.ok) {
@@ -168,7 +171,7 @@ export async function fetchChatData(searchParams: {
// if no connectors are setup, only show personas that are pure // if no connectors are setup, only show personas that are pure
// passthrough and don't do any retrieval // passthrough and don't do any retrieval
if (!hasAnyConnectors) { if (!hasAnyConnectors) {
personas = personas.filter((persona) => persona.num_chunks === 0); assistants = assistants.filter((assistant) => assistant.num_chunks === 0);
} }
let folders: Folder[] = []; let folders: Folder[] = [];
@@ -189,7 +192,7 @@ export async function fetchChatData(searchParams: {
ccPairs, ccPairs,
availableSources, availableSources,
documentSets, documentSets,
personas, assistants,
tags, tags,
llmProviders, llmProviders,
folders, folders,