mirror of
https://github.com/danswer-ai/danswer.git
synced 2025-06-12 09:00:53 +02:00
Updated modals for clarity (#2529)
* udpated modals for clarity * fix build
This commit is contained in:
parent
18c62a0c24
commit
ba64543dd7
@ -24,50 +24,21 @@ export function _CompletedWelcomeFlowDummyComponent() {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
function UsageTypeSection({
|
|
||||||
title,
|
|
||||||
description,
|
|
||||||
callToAction,
|
|
||||||
onClick,
|
|
||||||
}: {
|
|
||||||
title: string;
|
|
||||||
description: string | JSX.Element;
|
|
||||||
callToAction: string;
|
|
||||||
onClick: () => void;
|
|
||||||
}) {
|
|
||||||
return (
|
|
||||||
<div>
|
|
||||||
<Text className="font-bold">{title}</Text>
|
|
||||||
<div className="text-base mt-1 mb-3">{description}</div>
|
|
||||||
<div
|
|
||||||
onClick={(e) => {
|
|
||||||
e.preventDefault();
|
|
||||||
onClick();
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
<div className="text-link font-medium cursor-pointer select-none">
|
|
||||||
{callToAction}
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
export function _WelcomeModal({ user }: { user: User | null }) {
|
export function _WelcomeModal({ user }: { user: User | null }) {
|
||||||
const router = useRouter();
|
const router = useRouter();
|
||||||
const [selectedFlow, setSelectedFlow] = useState<null | "search" | "chat">(
|
const [selectedFlow, setSelectedFlow] = useState<null | "search" | "chat">(
|
||||||
null
|
null
|
||||||
);
|
);
|
||||||
const [isHidden, setIsHidden] = useState(false);
|
const [canBegin, setCanBegin] = useState(false);
|
||||||
const [apiKeyVerified, setApiKeyVerified] = useState<boolean>(false);
|
const [apiKeyVerified, setApiKeyVerified] = useState<boolean>(false);
|
||||||
const [providerOptions, setProviderOptions] = useState<
|
const [providerOptions, setProviderOptions] = useState<
|
||||||
WellKnownLLMProviderDescriptor[]
|
WellKnownLLMProviderDescriptor[]
|
||||||
>([]);
|
>([]);
|
||||||
const { refreshProviderInfo } = useProviderStatus();
|
const { refreshProviderInfo } = useProviderStatus();
|
||||||
|
|
||||||
const clientSetWelcomeFlowComplete = async () => {
|
const clientSetWelcomeFlowComplete = async () => {
|
||||||
setWelcomeFlowComplete();
|
setWelcomeFlowComplete();
|
||||||
refreshProviderInfo();
|
refreshProviderInfo();
|
||||||
|
router.refresh();
|
||||||
};
|
};
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
@ -81,193 +52,35 @@ export function _WelcomeModal({ user }: { user: User | null }) {
|
|||||||
fetchProviderInfo();
|
fetchProviderInfo();
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
if (isHidden) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
let title;
|
|
||||||
let body;
|
|
||||||
switch (selectedFlow) {
|
|
||||||
case "search":
|
|
||||||
title = undefined;
|
|
||||||
body = (
|
|
||||||
<div className="max-h-[85vh] overflow-y-auto px-4 pb-4">
|
|
||||||
<BackButton behaviorOverride={() => setSelectedFlow(null)} />
|
|
||||||
<div className="mt-3">
|
|
||||||
<Text className="font-bold flex">
|
|
||||||
{apiKeyVerified && (
|
|
||||||
<FiCheckCircle className="my-auto mr-2 text-success" />
|
|
||||||
)}
|
|
||||||
Step 1: Setup an LLM
|
|
||||||
</Text>
|
|
||||||
<div>
|
|
||||||
{apiKeyVerified ? (
|
|
||||||
<Text className="mt-2">
|
|
||||||
LLM setup complete!
|
|
||||||
<br /> <br />
|
|
||||||
If you want to change the key later, you'll be able to
|
|
||||||
easily to do so in the Admin Panel.
|
|
||||||
</Text>
|
|
||||||
) : (
|
|
||||||
<ApiKeyForm
|
|
||||||
onSuccess={() => setApiKeyVerified(true)}
|
|
||||||
providerOptions={providerOptions}
|
|
||||||
/>
|
|
||||||
)}
|
|
||||||
</div>
|
|
||||||
<Text className="font-bold mt-6 mb-2">
|
|
||||||
Step 2: Connect Data Sources
|
|
||||||
</Text>
|
|
||||||
<div>
|
|
||||||
<Text>
|
|
||||||
Connectors are the way that Danswer gets data from your
|
|
||||||
organization's various data sources. Once setup, we'll
|
|
||||||
automatically sync data from your apps and docs into Danswer, so
|
|
||||||
you can search through all of them in one place.
|
|
||||||
</Text>
|
|
||||||
|
|
||||||
<div className="flex mt-3">
|
|
||||||
<Link
|
|
||||||
href="/admin/add-connector"
|
|
||||||
onClick={(e) => {
|
|
||||||
e.preventDefault();
|
|
||||||
clientSetWelcomeFlowComplete();
|
|
||||||
router.push("/admin/add-connector");
|
|
||||||
}}
|
|
||||||
className="w-fit mx-auto"
|
|
||||||
>
|
|
||||||
<Button size="xs" icon={FiShare2} disabled={!apiKeyVerified}>
|
|
||||||
Setup your first connector!
|
|
||||||
</Button>
|
|
||||||
</Link>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
break;
|
|
||||||
case "chat":
|
|
||||||
title = undefined;
|
|
||||||
body = (
|
|
||||||
<div className="mt-3 max-h-[85vh] overflow-y-auto px-4 pb-4">
|
|
||||||
<BackButton behaviorOverride={() => setSelectedFlow(null)} />
|
|
||||||
|
|
||||||
<div className="mt-3">
|
|
||||||
<Text className="font-bold flex">
|
|
||||||
{apiKeyVerified && (
|
|
||||||
<FiCheckCircle className="my-auto mr-2 text-success" />
|
|
||||||
)}
|
|
||||||
Step 1: Setup an LLM
|
|
||||||
</Text>
|
|
||||||
<div>
|
|
||||||
{apiKeyVerified ? (
|
|
||||||
<Text className="mt-2">
|
|
||||||
LLM setup complete!
|
|
||||||
<br /> <br />
|
|
||||||
If you want to change the key later or choose a different LLM,
|
|
||||||
you'll be able to easily to do so in the Admin Panel.
|
|
||||||
</Text>
|
|
||||||
) : (
|
|
||||||
<div>
|
|
||||||
<ApiKeyForm
|
|
||||||
onSuccess={() => setApiKeyVerified(true)}
|
|
||||||
providerOptions={providerOptions}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
)}
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<Text className="font-bold mt-6 mb-2 flex">
|
|
||||||
Step 2: Start Chatting!
|
|
||||||
</Text>
|
|
||||||
|
|
||||||
<Text>
|
|
||||||
Click the button below to start chatting with the LLM setup above!
|
|
||||||
Don't worry, if you do decide later on you want to connect
|
|
||||||
your organization's knowledge, you can always do that in the{" "}
|
|
||||||
<Link
|
|
||||||
className="text-link"
|
|
||||||
href="/admin/add-connector"
|
|
||||||
onClick={(e) => {
|
|
||||||
e.preventDefault();
|
|
||||||
router.push("/admin/add-connector");
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
Admin Panel
|
|
||||||
</Link>
|
|
||||||
.
|
|
||||||
</Text>
|
|
||||||
|
|
||||||
<div className="flex mt-3">
|
|
||||||
<Link
|
|
||||||
href="/chat"
|
|
||||||
onClick={(e) => {
|
|
||||||
e.preventDefault();
|
|
||||||
clientSetWelcomeFlowComplete();
|
|
||||||
router.push("/chat");
|
|
||||||
setIsHidden(true);
|
|
||||||
}}
|
|
||||||
className="w-fit mx-auto"
|
|
||||||
>
|
|
||||||
<Button size="xs" icon={FiShare2} disabled={!apiKeyVerified}>
|
|
||||||
Start chatting!
|
|
||||||
</Button>
|
|
||||||
</Link>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
title = "🎉 Welcome to Danswer";
|
|
||||||
body = (
|
|
||||||
<>
|
|
||||||
<div>
|
|
||||||
<Text>How are you planning on using Danswer?</Text>
|
|
||||||
</div>
|
|
||||||
<Divider />
|
|
||||||
<UsageTypeSection
|
|
||||||
title="Search / Chat with Knowledge"
|
|
||||||
description={
|
|
||||||
<Text>
|
|
||||||
If you're looking to search through, chat with, or ask
|
|
||||||
direct questions of your organization's knowledge, then
|
|
||||||
this is the option for you!
|
|
||||||
</Text>
|
|
||||||
}
|
|
||||||
callToAction="Get Started"
|
|
||||||
onClick={() => setSelectedFlow("search")}
|
|
||||||
/>
|
|
||||||
<Divider />
|
|
||||||
<UsageTypeSection
|
|
||||||
title="Secure ChatGPT"
|
|
||||||
description={
|
|
||||||
<Text>
|
|
||||||
If you're looking for a pure ChatGPT-like experience, then
|
|
||||||
this is the option for you!
|
|
||||||
</Text>
|
|
||||||
}
|
|
||||||
callToAction="Get Started"
|
|
||||||
onClick={() => {
|
|
||||||
setSelectedFlow("chat");
|
|
||||||
}}
|
|
||||||
/>
|
|
||||||
|
|
||||||
{/* TODO: add a Slack option here */}
|
|
||||||
{/* <Divider />
|
|
||||||
<UsageTypeSection
|
|
||||||
title="AI-powered Slack Assistant"
|
|
||||||
description="If you're looking to setup a bot to auto-answer questions in Slack"
|
|
||||||
callToAction="Connect your company knowledge!"
|
|
||||||
link="/admin/add-connector"
|
|
||||||
/> */}
|
|
||||||
</>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Modal title={title} className="max-w-4xl">
|
<Modal title={"Welcome to Danswer!"} width="w-full max-w-3xl">
|
||||||
<div className="text-base">{body}</div>
|
<div>
|
||||||
|
<Text className="mb-4">
|
||||||
|
Danswer brings all your company's knowledge to your fingertips,
|
||||||
|
ready to be accessed instantly.
|
||||||
|
</Text>
|
||||||
|
<Text className="mb-4">
|
||||||
|
To get started, we need to set up an API key for the Language Model
|
||||||
|
(LLM) provider. This key allows Danswer to interact with the AI model,
|
||||||
|
enabling intelligent responses to your queries.
|
||||||
|
</Text>
|
||||||
|
|
||||||
|
<div className="max-h-[900px] overflow-y-scroll">
|
||||||
|
<ApiKeyForm
|
||||||
|
hidePopup
|
||||||
|
onSuccess={() => {
|
||||||
|
router.refresh();
|
||||||
|
refreshProviderInfo();
|
||||||
|
setCanBegin(true);
|
||||||
|
}}
|
||||||
|
providerOptions={providerOptions}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<Divider />
|
||||||
|
<Button disabled={!canBegin} onClick={clientSetWelcomeFlowComplete}>
|
||||||
|
Get Started
|
||||||
|
</Button>
|
||||||
|
</div>
|
||||||
</Modal>
|
</Modal>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -8,9 +8,11 @@ import { CustomLLMProviderUpdateForm } from "@/app/admin/configuration/llm/Custo
|
|||||||
export const ApiKeyForm = ({
|
export const ApiKeyForm = ({
|
||||||
onSuccess,
|
onSuccess,
|
||||||
providerOptions,
|
providerOptions,
|
||||||
|
hidePopup,
|
||||||
}: {
|
}: {
|
||||||
onSuccess: () => void;
|
onSuccess: () => void;
|
||||||
providerOptions: WellKnownLLMProviderDescriptor[];
|
providerOptions: WellKnownLLMProviderDescriptor[];
|
||||||
|
hidePopup?: boolean;
|
||||||
}) => {
|
}) => {
|
||||||
const [popup, setPopup] = useState<{
|
const [popup, setPopup] = useState<{
|
||||||
message: string;
|
message: string;
|
||||||
@ -33,7 +35,10 @@ export const ApiKeyForm = ({
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<div>
|
<div>
|
||||||
{popup && <Popup message={popup.message} type={popup.type} />}
|
{!hidePopup && popup && (
|
||||||
|
<Popup message={popup.message} type={popup.type} />
|
||||||
|
)}
|
||||||
|
|
||||||
<TabGroup
|
<TabGroup
|
||||||
index={providerNameToIndexMap.get(providerName) || 0}
|
index={providerNameToIndexMap.get(providerName) || 0}
|
||||||
onIndexChange={(index) =>
|
onIndexChange={(index) =>
|
||||||
|
@ -21,10 +21,10 @@ export const ApiKeyModal = ({ hide }: { hide: () => void }) => {
|
|||||||
return (
|
return (
|
||||||
<Modal
|
<Modal
|
||||||
title="Set an API Key!"
|
title="Set an API Key!"
|
||||||
className="max-w-3xl"
|
width="max-w-3xl w-full"
|
||||||
onOutsideClick={() => hide()}
|
onOutsideClick={() => hide()}
|
||||||
>
|
>
|
||||||
<div className="max-h-[75vh] overflow-y-auto flex flex-col px-4">
|
<div className="max-h-[75vh] overflow-y-auto flex flex-col">
|
||||||
<div>
|
<div>
|
||||||
<div className="mb-5 text-sm">
|
<div className="mb-5 text-sm">
|
||||||
Please provide an API Key below in order to start using
|
Please provide an API Key below in order to start using
|
||||||
|
Loading…
x
Reference in New Issue
Block a user