Skip to content

Commit 6b5da01

Browse files
committed
updates based on feedback
1 parent b7c72f4 commit 6b5da01

File tree

9 files changed

+358
-274
lines changed

9 files changed

+358
-274
lines changed

apps/dashboard/src/@/components/chat/CustomChatButton.tsx

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
import { MessageCircleIcon, XIcon } from "lucide-react";
44
import { useCallback, useRef, useState } from "react";
55
import { createThirdwebClient } from "thirdweb";
6+
import type { Team } from "@/api/team";
67
import { Button } from "@/components/ui/button";
78
import { NEXT_PUBLIC_DASHBOARD_CLIENT_ID } from "@/constants/public-envs";
89
import { cn } from "@/lib/utils";
@@ -21,7 +22,7 @@ export function CustomChatButton(props: {
2122
label: string;
2223
examplePrompts: string[];
2324
authToken: string | undefined;
24-
teamId: string | undefined;
25+
team: Team; // changed from teamId
2526
clientId: string | undefined;
2627
requireLogin?: boolean;
2728
}) {
@@ -82,7 +83,7 @@ export function CustomChatButton(props: {
8283
}))}
8384
networks={props.networks}
8485
requireLogin={props.requireLogin}
85-
teamId={props.teamId}
86+
team={props.team} // pass full team object
8687
/>
8788
)}
8889
</div>

apps/dashboard/src/@/components/chat/CustomChatContent.tsx

Lines changed: 18 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import { usePathname } from "next/navigation";
55
import { useCallback, useState } from "react";
66
import type { ThirdwebClient } from "thirdweb";
77
import { useActiveWalletConnectionStatus } from "thirdweb/react";
8+
import type { Team } from "@/api/team";
89
import { Button } from "@/components/ui/button";
910
import { NebulaIcon } from "@/icons/NebulaIcon";
1011
import { ChatBar } from "./ChatBar";
@@ -14,7 +15,7 @@ import type { ExamplePrompt, NebulaContext } from "./types";
1415

1516
export default function CustomChatContent(props: {
1617
authToken: string | undefined;
17-
teamId: string | undefined;
18+
team: Team;
1819
clientId: string | undefined;
1920
client: ThirdwebClient;
2021
examplePrompts: ExamplePrompt[];
@@ -31,14 +32,14 @@ export default function CustomChatContent(props: {
3132
client={props.client}
3233
clientId={props.clientId}
3334
examplePrompts={props.examplePrompts}
34-
teamId={props.teamId}
35+
team={props.team}
3536
/>
3637
);
3738
}
3839

3940
function CustomChatContentLoggedIn(props: {
4041
authToken: string;
41-
teamId: string | undefined;
42+
team: Team;
4243
clientId: string | undefined;
4344
client: ThirdwebClient;
4445
examplePrompts: ExamplePrompt[];
@@ -55,6 +56,10 @@ function CustomChatContentLoggedIn(props: {
5556
const [enableAutoScroll, setEnableAutoScroll] = useState(false);
5657
const connectionStatus = useActiveWalletConnectionStatus();
5758

59+
// Support form state
60+
const [showSupportForm, setShowSupportForm] = useState(false);
61+
const [productLabel, setProductLabel] = useState("");
62+
5863
const handleSendMessage = useCallback(
5964
async (userMessage: UserMessage) => {
6065
const abortController = new AbortController();
@@ -96,7 +101,7 @@ function CustomChatContentLoggedIn(props: {
96101
headers: {
97102
Authorization: `Bearer ${props.authToken}`,
98103
"Content-Type": "application/json",
99-
...(props.teamId ? { "x-team-id": props.teamId } : {}),
104+
...(props.team.id ? { "x-team-id": props.team.id } : {}),
100105
...(props.clientId ? { "x-client-id": props.clientId } : {}),
101106
},
102107
method: "POST",
@@ -132,7 +137,7 @@ function CustomChatContentLoggedIn(props: {
132137
setEnableAutoScroll(false);
133138
}
134139
},
135-
[props.authToken, props.clientId, props.teamId, sessionId],
140+
[props.authToken, props.clientId, props.team.id, sessionId],
136141
);
137142

138143
const handleFeedback = useCallback(
@@ -165,7 +170,7 @@ function CustomChatContentLoggedIn(props: {
165170
headers: {
166171
Authorization: `Bearer ${props.authToken}`,
167172
"Content-Type": "application/json",
168-
...(props.teamId ? { "x-team-id": props.teamId } : {}),
173+
...(props.team.id ? { "x-team-id": props.team.id } : {}),
169174
},
170175
method: "POST",
171176
});
@@ -188,7 +193,7 @@ function CustomChatContentLoggedIn(props: {
188193
// Consider implementing retry logic here
189194
}
190195
},
191-
[sessionId, props.authToken, props.teamId, messages],
196+
[sessionId, props.authToken, props.team.id, messages],
192197
);
193198

194199
const showEmptyState = !userHasSubmittedMessage && messages.length === 0;
@@ -212,8 +217,14 @@ function CustomChatContentLoggedIn(props: {
212217
sessionId={sessionId}
213218
setEnableAutoScroll={setEnableAutoScroll}
214219
useSmallText
220+
showSupportForm={showSupportForm}
221+
setShowSupportForm={setShowSupportForm}
222+
productLabel={productLabel}
223+
setProductLabel={setProductLabel}
224+
team={props.team}
215225
/>
216226
)}
227+
{/* Removed floating support case button and form */}
217228
<ChatBar
218229
abortChatStream={() => {
219230
chatAbortController?.abort();

apps/dashboard/src/@/components/chat/CustomChats.tsx

Lines changed: 74 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,18 @@
11
import {
22
AlertCircleIcon,
3+
ArrowRightIcon,
34
MessageCircleIcon,
45
ThumbsDownIcon,
56
ThumbsUpIcon,
67
} from "lucide-react";
78
import { useEffect, useRef, useState } from "react";
89
import type { ThirdwebClient } from "thirdweb";
10+
import type { Team } from "@/api/team";
911
import { MarkdownRenderer } from "@/components/blocks/markdown-renderer";
12+
import { Button } from "@/components/ui/button";
1013
import { ScrollShadow } from "@/components/ui/ScrollShadow/ScrollShadow";
1114
import { cn } from "@/lib/utils";
15+
import { SupportTicketForm } from "../../../app/(app)/team/[team_slug]/(team)/~/support/_components/SupportTicketForm";
1216
import { Reasoning } from "./Reasoning";
1317

1418
// Define local types
@@ -47,10 +51,18 @@ export function CustomChats(props: {
4751
useSmallText?: boolean;
4852
sendMessage: (message: UserMessage) => void;
4953
onFeedback?: (messageIndex: number, feedback: 1 | -1) => void;
54+
// New props for support form
55+
showSupportForm: boolean;
56+
setShowSupportForm: (v: boolean) => void;
57+
productLabel: string;
58+
setProductLabel: (v: string) => void;
59+
team: Team;
5060
}) {
5161
const { messages, setEnableAutoScroll, enableAutoScroll } = props;
5262
const scrollAnchorRef = useRef<HTMLDivElement>(null);
5363
const chatContainerRef = useRef<HTMLDivElement>(null);
64+
// Add state to track if a support ticket was created
65+
const [supportTicketCreated, setSupportTicketCreated] = useState(false);
5466

5567
// auto scroll to bottom when messages change
5668
// eslint-disable-next-line no-restricted-syntax
@@ -123,6 +135,68 @@ export function CustomChats(props: {
123135
sendMessage={props.sendMessage}
124136
sessionId={props.sessionId}
125137
/>
138+
{/* Support Case Button/Form in last assistant message */}
139+
{message.type === "assistant" &&
140+
index === props.messages.length - 1 && (
141+
<>
142+
{/* Only show button/form if ticket not created */}
143+
{!props.showSupportForm && !supportTicketCreated && (
144+
<div className="mt-3 pt-3 border-t border-[#333333]">
145+
<Button
146+
onClick={() => props.setShowSupportForm(true)}
147+
size="sm"
148+
className="bg-[#2663EB] hover:bg-[#2663EB]/80 text-white transition-opacity"
149+
>
150+
Create Support Case
151+
<ArrowRightIcon className="w-4 h-4 ml-2" />
152+
</Button>
153+
</div>
154+
)}
155+
{/* Show form if open and ticket not created */}
156+
{props.showSupportForm && !supportTicketCreated && (
157+
<div className="mt-4 pt-4 border-t border-[#333333]">
158+
<SupportTicketForm
159+
team={props.team}
160+
productLabel={props.productLabel}
161+
setProductLabel={props.setProductLabel}
162+
conversationId={props.sessionId}
163+
onSuccess={() => {
164+
props.setShowSupportForm(false);
165+
props.setProductLabel("");
166+
setSupportTicketCreated(true);
167+
}}
168+
/>
169+
</div>
170+
)}
171+
{/* Show success message if ticket created */}
172+
{supportTicketCreated && (
173+
<div className="mt-4 pt-4 border-t border-[#333333]">
174+
<div className="rounded-xl border bg-card px-4 py-2 text-green-500 leading-normal">
175+
Your support ticket has been created! Our team
176+
will get back to you soon.
177+
</div>
178+
<div className="mt-3 flex justify-end">
179+
<a
180+
href={
181+
props.team?.slug
182+
? `/team/${props.team.slug}/~/support`
183+
: "/support"
184+
}
185+
target="_blank"
186+
rel="noopener noreferrer"
187+
>
188+
<Button
189+
size="sm"
190+
className="bg-[#2663EB] hover:bg-[#2663EB]/80 text-white transition-opacity"
191+
>
192+
Go to Support Portal
193+
</Button>
194+
</a>
195+
</div>
196+
</div>
197+
)}
198+
</>
199+
)}
126200
</div>
127201
);
128202
})}

apps/dashboard/src/app/(app)/(dashboard)/support/page.tsx

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ export default async function SupportPage() {
7171
]);
7272

7373
const teams = await getTeams();
74-
const teamId = teams?.[0]?.id ?? undefined;
74+
const team = teams?.[0];
7575

7676
return (
7777
<main className="flex flex-col gap-12 pb-12">
@@ -92,17 +92,19 @@ export default async function SupportPage() {
9292
team.
9393
</p>
9494
<div className="mt-6 flex w-full flex-col items-center gap-3">
95-
<CustomChatButton
96-
authToken={authToken || undefined}
97-
clientId={undefined}
98-
examplePrompts={siwaExamplePrompts}
99-
isFloating={false}
100-
isLoggedIn={!!accountAddress}
101-
label="Ask AI for support"
102-
networks="all"
103-
pageType="support"
104-
teamId={teamId}
105-
/>
95+
{team && (
96+
<CustomChatButton
97+
authToken={authToken || undefined}
98+
clientId={undefined}
99+
examplePrompts={siwaExamplePrompts}
100+
isFloating={false}
101+
isLoggedIn={!!accountAddress}
102+
label="Ask AI for support"
103+
networks="all"
104+
pageType="support"
105+
team={team}
106+
/>
107+
)}
106108

107109
<Link
108110
className="text-muted-foreground text-sm hover:underline"

apps/dashboard/src/app/(app)/components/Header/SecondaryNav/SecondaryNav.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ export function SecondaryNavLinks() {
4646

4747
<Link
4848
className="text-muted-foreground text-sm hover:text-foreground"
49-
href="/support"
49+
href="/team/~/~/support"
5050
rel="noopener noreferrer"
5151
target="_blank"
5252
>

apps/dashboard/src/app/(app)/team/[team_slug]/(team)/layout.tsx

Lines changed: 15 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -103,19 +103,21 @@ export default async function TeamLayout(props: {
103103
>
104104
{props.children}
105105
</TeamSidebarLayout>
106-
<div className="fixed right-6 bottom-6 z-50">
107-
<CustomChatButton
108-
authToken={authToken}
109-
clientId={undefined}
110-
examplePrompts={siwaExamplePrompts}
111-
isFloating={true}
112-
isLoggedIn={true}
113-
label="Ask AI Assistant"
114-
networks="all"
115-
pageType="support"
116-
teamId={team.id}
117-
/>
118-
</div>
106+
{team && (
107+
<div className="fixed right-6 bottom-6 z-50">
108+
<CustomChatButton
109+
authToken={authToken}
110+
clientId={undefined}
111+
examplePrompts={siwaExamplePrompts}
112+
isFloating={true}
113+
isLoggedIn={true}
114+
label="Get Help"
115+
networks="all"
116+
pageType="support"
117+
team={team}
118+
/>
119+
</div>
120+
)}
119121
</div>
120122
</SidebarProvider>
121123
);

0 commit comments

Comments
 (0)