Skip to content

Commit 41d3b23

Browse files
committed
feat: frontend changes
1 parent 6480c25 commit 41d3b23

File tree

6 files changed

+204
-335
lines changed

6 files changed

+204
-335
lines changed

chat/bun.lock

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,6 @@
1515
"lucide-react": "^0.511.0",
1616
"next": "15.4.7",
1717
"next-themes": "^0.4.6",
18-
"path-browserify": "^1.0.1",
1918
"react": "^19.0.0",
2019
"react-dom": "^19.0.0",
2120
"react-dropzone": "^14.3.8",

chat/package.json

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,6 @@
1111
"lucide-react": "^0.511.0",
1212
"next": "15.4.7",
1313
"next-themes": "^0.4.6",
14-
"path-browserify": "^1.0.1",
1514
"react": "^19.0.0",
1615
"react-dom": "^19.0.0",
1716
"react-dropzone": "^14.3.8",

chat/src/components/chat-provider.tsx

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -42,12 +42,17 @@ type MessageType = "user" | "raw";
4242

4343
export type ServerStatus = "stable" | "running" | "offline" | "unknown";
4444

45+
export interface FileUploadResponse {
46+
ok: boolean;
47+
filePath?: string;
48+
}
49+
4550
interface ChatContextValue {
4651
messages: (Message | DraftMessage)[];
4752
loading: boolean;
4853
serverStatus: ServerStatus;
4954
sendMessage: (message: string, type?: MessageType) => void;
50-
uploadFiles: (formData: FormData) => Promise<boolean>;
55+
uploadFiles: (formData: FormData) => Promise<FileUploadResponse>;
5156
}
5257

5358
const ChatContext = createContext<ChatContextValue | undefined>(undefined);
@@ -270,16 +275,16 @@ export function ChatProvider({ children }: PropsWithChildren) {
270275
};
271276

272277
// Upload files to workspace
273-
const uploadFiles = async (formData: FormData): Promise<boolean> => {
274-
let success = true;
278+
const uploadFiles = async (formData: FormData): Promise<FileUploadResponse> => {
279+
let result: FileUploadResponse = {ok: true};
275280
try{
276281
const response = await fetch(`${agentAPIUrl}/upload`, {
277282
method: 'POST',
278283
body: formData,
279284
});
280285

281286
if (!response.ok) {
282-
success = false;
287+
result.ok = false;
283288
const errorData = await response.json();
284289
console.error("Failed to send message:", errorData);
285290
const detail = errorData.detail;
@@ -293,10 +298,12 @@ export function ChatProvider({ children }: PropsWithChildren) {
293298
toast.error(`Failed to upload files`, {
294299
description: fullDetail,
295300
});
301+
} else {
302+
result = (await response.json()) as FileUploadResponse;
296303
}
297304
// eslint-disable-next-line @typescript-eslint/no-explicit-any
298305
} catch (error: any) {
299-
success = false;
306+
result.ok = false;
300307
console.error("Error uploading files:", error);
301308
const detail = error.detail;
302309
const messages =
@@ -311,10 +318,9 @@ export function ChatProvider({ children }: PropsWithChildren) {
311318
description: fullDetail,
312319
});
313320
}
314-
return success;
321+
return result;
315322
}
316323

317-
318324
return (
319325
<ChatContext.Provider
320326
value={{

chat/src/components/drag-drop.tsx

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
import React from "react";
2+
import { useDropzone } from "react-dropzone";
3+
4+
export interface DragDropProps {
5+
onFilesAdded: (files: File[]) => void;
6+
disabled?: boolean;
7+
children: React.ReactNode;
8+
className?: string;
9+
}
10+
11+
export function DragDrop({ onFilesAdded, disabled = false, children, className = "" }: DragDropProps) {
12+
const { getRootProps, getInputProps, isDragActive } = useDropzone({
13+
noClick: true,
14+
disabled,
15+
onDropAccepted: (files: File[]) => {
16+
onFilesAdded(files);
17+
},
18+
multiple: true,
19+
});
20+
21+
return (
22+
<div
23+
{...getRootProps()}
24+
className={`relative ${className} ${
25+
isDragActive && !disabled ? 'border-primary border-2 border-dashed rounded-lg text-center transition-colors' : ''
26+
}`}
27+
>
28+
<input {...getInputProps()} />
29+
{isDragActive && !disabled && (
30+
<div className="absolute inset-0 flex items-center justify-center bg-primary/20z-10">
31+
<p className="text-sm text-primary font-medium">Drop the files here</p>
32+
</div>
33+
)}
34+
{children}
35+
</div>
36+
);
37+
}

0 commit comments

Comments
 (0)