import { useState, useRef } from "react";
import { useSelector, useDispatch } from "react-redux";
import {
PiRobot,
PiBrain,
PiGraduationCap,
PiCode,
PiFlask,
PiBook,
PiStar,
PiRocket,
PiLightning,
PiSparkle,
PiGlobe,
PiHeart,
PiShield,
PiWrench,
PiMagnifyingGlass,
PiChartLine,
PiPenNib,
PiMusicNotes,
PiCamera,
PiGameController,
PiPencil,
} from "react-icons/pi";
import {
FiSearch,
FiX,
FiUpload,
FiFileText,
FiTrash2,
FiGlobe,
FiLock,
FiCheck,
FiArrowLeft,
} from "react-icons/fi";
import { cancelCreateSpace } from "../../store/slices/appSlice";
import { dmService } from "../../services/dm.service";
import { usernameColors } from "../../constants/usernameColors";
const agentIcons = [
{ id: "robot", icon: PiRobot, label: "Robot" },
{ id: "brain", icon: PiBrain, label: "Trí tuệ" },
{ id: "graduation", icon: PiGraduationCap, label: "Học tập" },
{ id: "code", icon: PiCode, label: "Lập trình" },
{ id: "flask", icon: PiFlask, label: "Thí nghiệm" },
{ id: "book", icon: PiBook, label: "Sách" },
{ id: "star", icon: PiStar, label: "Ngôi sao" },
{ id: "rocket", icon: PiRocket, label: "Tên lửa" },
{ id: "lightning", icon: PiLightning, label: "Tia sét" },
{ id: "sparkle", icon: PiSparkle, label: "Lấp lánh" },
{ id: "globe", icon: PiGlobe, label: "Thế giới" },
{ id: "heart", icon: PiHeart, label: "Yêu thích" },
{ id: "shield", icon: PiShield, label: "Bảo vệ" },
{ id: "wrench", icon: PiWrench, label: "Công cụ" },
{ id: "search", icon: PiMagnifyingGlass, label: "Tìm kiếm" },
{ id: "chart", icon: PiChartLine, label: "Phân tích" },
{ id: "pen", icon: PiPenNib, label: "Sáng tạo" },
{ id: "music", icon: PiMusicNotes, label: "Âm nhạc" },
{ id: "camera", icon: PiCamera, label: "Hình ảnh" },
{ id: "game", icon: PiGameController, label: "Game" },
{ id: "pencil", icon: PiPencil, label: "Viết lách" },
];
const availableTools = [
{ id: "web_search", label: "Tìm kiếm web", desc: "Tìm kiếm thông tin trên internet" },
{ id: "calculator", label: "Máy tính", desc: "Thực hiện phép tính toán học" },
{ id: "code_interpreter", label: "Chạy code", desc: "Thực thi và kiểm tra code" },
{ id: "image_gen", label: "Tạo ảnh", desc: "Tạo hình ảnh từ mô tả" },
{ id: "pdf_reader", label: "Đọc PDF", desc: "Trích xuất nội dung từ file PDF" },
{ id: "translator", label: "Dịch thuật", desc: "Dịch ngôn ngữ đa ngôn ngữ" },
];
function CreateAgent({ editMode = false, initialData = null, onCancel }) {
const dispatch = useDispatch();
const { isDark } = useSelector((state) => state.theme);
const fileInputRef = useRef(null);
const [agentName, setAgentName] = useState(initialData?.name || "");
const [agentDescription, setAgentDescription] = useState(initialData?.description || "");
const [agentIcon, setAgentIcon] = useState(initialData?.icon || agentIcons[0].id);
const [agentColor, setAgentColor] = useState(initialData?.color || usernameColors[0].value);
const [systemPrompt, setSystemPrompt] = useState(initialData?.systemPrompt || "");
const [selectedTools, setSelectedTools] = useState(initialData?.tools || []);
const [toolSearchQuery, setToolSearchQuery] = useState("");
const [uploadedFiles, setUploadedFiles] = useState([]);
const [visibility, setVisibility] = useState(initialData?.visibility || "public");
// Members state (giống tạo space)
const [members, setMembers] = useState([]);
const [memberSearchQuery, setMemberSearchQuery] = useState("");
const [searchResults, setSearchResults] = useState([]);
const [isSearching, setIsSearching] = useState(false);
const handleMemberSearch = async (query) => {
setMemberSearchQuery(query);
if (!query.trim()) {
setSearchResults([]);
setIsSearching(false);
return;
}
};
const handleMemberSearchKeyDown = async (e) => {
if (e.key === "Enter") {
e.preventDefault();
const query = memberSearchQuery.trim();
if (!query) {
setSearchResults([]);
return;
}
setIsSearching(true);
try {
const { data } = await dmService.searchUsers(query);
const users = (data.users || []).map((user) => ({
id: user.id,
name: user.display_name || user.email || "Unknown",
avatar: user.avatar_url || null,
email: user.email || "",
}));
setSearchResults(users);
} catch {
setSearchResults([]);
} finally {
setIsSearching(false);
}
}
};
const addMember = (user) => {
if (!members.some((m) => m.id === user.id)) {
setMembers([...members, user]);
}
};
const removeMember = (userId) => {
setMembers((prev) => prev.filter((m) => m.id !== userId));
};
const toggleTool = (toolId) => {
setSelectedTools((prev) =>
prev.includes(toolId)
? prev.filter((id) => id !== toolId)
: [...prev, toolId]
);
};
const filteredTools = availableTools.filter(
(tool) =>
tool.label.toLowerCase().includes(toolSearchQuery.toLowerCase()) ||
tool.desc.toLowerCase().includes(toolSearchQuery.toLowerCase())
);
const handleFileUpload = (e) => {
const files = Array.from(e.target.files);
const newFiles = files.map((file) => ({
id: `${file.name}-${Date.now()}`,
name: file.name,
size: file.size,
type: file.type,
}));
setUploadedFiles((prev) => [...prev, ...newFiles]);
e.target.value = "";
};
const removeFile = (fileId) => {
setUploadedFiles((prev) => prev.filter((f) => f.id !== fileId));
};
const formatFileSize = (bytes) => {
if (bytes < 1024) return `${bytes} B`;
if (bytes < 1024 * 1024) return `${(bytes / 1024).toFixed(1)} KB`;
return `${(bytes / (1024 * 1024)).toFixed(1)} MB`;
};
const handleSubmit = () => {
if (agentName.trim()) {
const agentData = {
id: editMode && initialData ? initialData.id : agentName
.toLowerCase()
.replace(/\s+/g, "-")
.replace(/[^a-z0-9-]/g, ""),
name: agentName.trim(),
description: agentDescription.trim(),
icon: agentIcon,
color: agentColor.trim(),
systemPrompt: systemPrompt.trim(),
tools: selectedTools,
files: uploadedFiles.map((f) => f.name),
visibility,
members: members.map((m) => m.id),
};
console.log(editMode ? "Updating agent:" : "Creating agent:", agentData);
if (editMode && onCancel) {
onCancel();
} else {
dispatch(cancelCreateSpace());
}
}
};
const selectedIconData = agentIcons.find((s) => s.id === agentIcon);
const SelectedIcon = selectedIconData?.icon || PiRobot;
const selectedColorHex = usernameColors.find((c) => c.value === agentColor)?.hex || usernameColors[0].hex;
return (
{editMode && (
)}
{editMode ? "Chỉnh sửa Agent" : "Tạo Agent mới"}
{editMode ? "Cập nhật thông tin agent" : "Tạo trợ lý AI tùy chỉnh"}
{/* Icon Selection */}
Chọn icon
{agentIcons.map(({ id, icon: Icon }) => (
))}
{/* Color Selection */}
Chọn màu
{usernameColors.map((color) => (
))}
{agentColor && (
Màu hiện tại:{" "}
c.value === agentColor)?.hex || agentColor,
fontWeight: "600",
}}
>
{usernameColors.find((c) => c.value === agentColor)?.name || agentColor}
)}
{/* Agent Name */}
Tên Agent
setAgentName(e.target.value)}
placeholder="VD: Trợ lý Toán học, Code Reviewer..."
className="w-full px-3 py-2 rounded-md text-sm border outline-none"
style={{
background: "var(--input-bg)",
borderColor: "var(--input-border)",
color: "var(--input-text)",
}}
onFocus={(e) =>
(e.currentTarget.style.borderColor = "var(--primary)")
}
onBlur={(e) =>
(e.currentTarget.style.borderColor = "var(--input-border)")
}
/>
{/* Description */}
Mô tả
{/* System Prompt */}
System Prompt (tùy chọn)
{/* Tools Selection */}
Công cụ (Tools)
{/* Tool search */}
setToolSearchQuery(e.target.value)}
placeholder="Tìm công cụ..."
className="w-full pl-9 pr-3 py-2 rounded-md text-sm border outline-none"
style={{
background: "var(--input-bg)",
borderColor: "var(--input-border)",
color: "var(--input-text)",
}}
onFocus={(e) =>
(e.currentTarget.style.borderColor = "var(--primary)")
}
onBlur={(e) =>
(e.currentTarget.style.borderColor = "var(--input-border)")
}
/>
{filteredTools.map((tool) => {
const isSelected = selectedTools.includes(tool.id);
return (
);
})}
{filteredTools.length === 0 && (
Không tìm thấy công cụ nào
)}
{/* PDF Upload */}
Tài liệu kiến thức (PDF)
fileInputRef.current?.click()}
onMouseEnter={(e) => {
e.currentTarget.style.borderColor = "var(--primary)";
}}
onMouseLeave={(e) => {
e.currentTarget.style.borderColor = "var(--input-border)";
}}
>
Nhấn để tải lên PDF
Hoặc kéo thả file vào đây
{uploadedFiles.length > 0 && (
{uploadedFiles.map((file) => (
{file.name}
{formatFileSize(file.size)}
))}
)}
{/* Visibility */}
Quyền truy cập
{/* Members - chỉ hiện khi chọn Private */}
{visibility === "private" && (
Thêm người dùng
{isSearching ? (
) : (
)}
handleMemberSearch(e.target.value)}
onKeyDown={handleMemberSearchKeyDown}
placeholder="Nhập tên và nhấn Enter để tìm..."
className="w-full pl-9 pr-3 py-2 rounded-md text-sm border outline-none"
style={{
background: "var(--input-bg)",
borderColor: "var(--input-border)",
color: "var(--input-text)",
}}
onFocus={(e) =>
(e.currentTarget.style.borderColor = "var(--primary)")
}
onBlur={(e) =>
(e.currentTarget.style.borderColor = "var(--input-border)")
}
/>
{members.length > 0 && (
Đã chọn ({members.length})
{members.map((member) => (
{member.name?.charAt(0)?.toUpperCase() || "?"}
{member.name}
))}
)}
{searchResults.length > 0 && (
Kết quả tìm kiếm
{searchResults.map((user) => {
const isSelected = members.some((m) => m.id === user.id);
return (
);
})}
)}
)}
{/* Preview */}
{agentName && (
Xem trước
{agentName}
{agentDescription && (
{agentDescription.length > 60
? agentDescription.slice(0, 60) + "..."
: agentDescription}
)}
)}
);
}
export default CreateAgent;