这是indexloc提供的服务,不要输入任何密码
Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -31,11 +31,13 @@
"react-tag-input-component": "^2.0.2",
"react-toastify": "^9.1.3",
"react-tooltip": "^5.25.2",
"react-i18next": "13.0.3",
"recharts": "^2.12.5",
"recharts-to-png": "^2.3.1",
"text-case": "^1.0.9",
"truncate": "^3.0.0",
"uuid": "^9.0.0"
"uuid": "^9.0.0",
"i18next": "23.4.2"
},
"devDependencies": {
"@esbuild-plugins/node-globals-polyfill": "^0.1.1",
Expand Down
23 changes: 23 additions & 0 deletions frontend/public/locales/en/settings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
{
"title":"Instance Settings",
"WorkspaceChat": "Workspace Chat",
"Appearance": {
"menu-title":"Appearance",
"page-title":"Appearance"
},
"APIKeys": "API Keys",
"LLMPreference": "LLM Preference",
"TranscriptionModel": "Transcription Model",
"EmbedderPreferences": "Embedding Preferences",
"VectorDatabase": "Vector Database",
"EmbeddedChat": "Embedded Chat",
"EmbeddedChatHistory": "Embedded Chat History",
"Security": {
"menu-title": "Security",
"page-title": "Multi-User Mode",
"Enable_Multi-User_Mode": "Enable Multi-User Mode",
"PasswordProtection": "Password Protection"
},
"EventLogs": "Event Logs",
"PrivacyData": "Privacy & Data"
}
23 changes: 23 additions & 0 deletions frontend/public/locales/zh/settings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
{
"title":"设置",
"WorkspaceChat": "对话工作区",
"Appearance": {
"menu-title":"外观",
"page-title":"外观设置"
},
"APIKeys": "API 密钥",
"LLMPreference": "LLM 首选项",
"TranscriptionModel": "Transcription 模型",
"EmbedderPreferences": "Embedder 首选项",
"VectorDatabase": "向量数据库",
"EmbeddedChat": "嵌入式对话",
"EmbeddedChatHistory": "嵌入式对话历史",
"Security": {
"menu-title": "用户与安全",
"page-title": "多用户模式",
"Enable_Multi-User_Mode": "启用多用户模式",
"PasswordProtection": "密码保护"
},
"EventLogs": "事件日志",
"PrivacyData": "隐私与数据"
}
1 change: 1 addition & 0 deletions frontend/src/App.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ const EmbedChats = lazy(() => import("@/pages/GeneralSettings/EmbedChats"));
const PrivacyAndData = lazy(
() => import("@/pages/GeneralSettings/PrivacyAndData")
);
import "./utils/locale/i18n"

export default function App() {
return (
Expand Down
33 changes: 18 additions & 15 deletions frontend/src/components/SettingsSidebar/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ import { USER_BACKGROUND_COLOR } from "@/utils/constants";
import { isMobile } from "react-device-detect";
import Footer from "../Footer";
import { Link } from "react-router-dom";
import { useTranslation } from "react-i18next";

export default function SettingsSidebar() {
const { logo } = useLogo();
Expand All @@ -35,6 +36,8 @@ export default function SettingsSidebar() {
const [showSidebar, setShowSidebar] = useState(false);
const [showBgOverlay, setShowBgOverlay] = useState(false);

const { t } = useTranslation(["settings"]);

useEffect(() => {
function handleBg() {
if (showSidebar) {
Expand Down Expand Up @@ -143,12 +146,12 @@ export default function SettingsSidebar() {
>
<div className="w-full h-full flex flex-col overflow-x-hidden items-between min-w-[235px]">
<div className="text-white text-opacity-60 text-sm font-medium uppercase mt-[4px] mb-0 ml-2">
Instance Settings
{t("title")}
</div>
<div className="relative h-full flex flex-col w-full justify-between pt-[10px] overflow-y-scroll no-scroll">
<div className="h-auto sidebar-items">
<div className="flex flex-col gap-y-2 h-full pb-8 overflow-y-scroll no-scroll">
<SidebarOptions user={user} />
<SidebarOptions user={user} t={t} />
</div>
</div>
<div className="mb-2">
Expand Down Expand Up @@ -218,7 +221,7 @@ const Option = ({
);
};

const SidebarOptions = ({ user = null }) => (
const SidebarOptions = ({ user = null,t=null }) => (
<>
<Option
href={paths.settings.system()}
Expand Down Expand Up @@ -250,39 +253,39 @@ const SidebarOptions = ({ user = null }) => (
/>
<Option
href={paths.settings.chats()}
btnText="Workspace Chat"
btnText={t("WorkspaceChat")}
icon={<ChatCenteredText className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
allowedRole={["admin", "manager"]}
/>
<Option
href={paths.settings.appearance()}
btnText="Appearance"
btnText={t("Appearance.menu-title")}
icon={<Eye className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
allowedRole={["admin", "manager"]}
/>
<Option
href={paths.settings.apiKeys()}
btnText="API Keys"
btnText={t("APIKeys")}
icon={<Key className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
allowedRole={["admin"]}
/>
<Option
href={paths.settings.llmPreference()}
btnText="LLM Preference"
btnText={t("LLMPreference")}
icon={<ChatText className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
allowedRole={["admin"]}
/>
<Option
href={paths.settings.transcriptionPreference()}
btnText="Transcription Model"
btnText={t("TranscriptionModel")}
icon={<ClosedCaptioning className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
Expand All @@ -291,7 +294,7 @@ const SidebarOptions = ({ user = null }) => (
<Option
href={paths.settings.embedder.modelPreference()}
childLinks={[paths.settings.embedder.chunkingPreference()]}
btnText="Embedder Preferences"
btnText={t("EmbedderPreferences")}
icon={<FileCode className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
Expand All @@ -311,7 +314,7 @@ const SidebarOptions = ({ user = null }) => (
/>
<Option
href={paths.settings.vectorDatabase()}
btnText="Vector Database"
btnText={t("VectorDatabase")}
icon={<Database className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
Expand All @@ -320,7 +323,7 @@ const SidebarOptions = ({ user = null }) => (
<Option
href={paths.settings.embedSetup()}
childLinks={[paths.settings.embedChats()]}
btnText="Embedded Chat"
btnText={t("EmbeddedChat")}
icon={<CodeBlock className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
Expand All @@ -329,7 +332,7 @@ const SidebarOptions = ({ user = null }) => (
<>
<Option
href={paths.settings.embedChats()}
btnText="Embedded Chat History"
btnText={t("EmbeddedChatHistory")}
icon={<Barcode className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
Expand All @@ -340,7 +343,7 @@ const SidebarOptions = ({ user = null }) => (
/>
<Option
href={paths.settings.security()}
btnText="Security"
btnText={t("Security.menu-title")}
icon={<Lock className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
Expand All @@ -349,15 +352,15 @@ const SidebarOptions = ({ user = null }) => (
/>
<Option
href={paths.settings.logs()}
btnText="Event Logs"
btnText={t("EventLogs")}
icon={<Notepad className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
allowedRole={["admin"]}
/>
<Option
href={paths.settings.privacy()}
btnText="Privacy & Data"
btnText={t("PrivacyData")}
icon={<EyeSlash className="h-5 w-5 flex-shrink-0" />}
user={user}
flex={true}
Expand Down
34 changes: 34 additions & 0 deletions frontend/src/pages/GeneralSettings/Appearance/Language/index.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
import { useState } from "react";
import { useTranslation } from "react-i18next";

export default function Language() {
const { i18n } = useTranslation();
const [language, setLanguage] = useState('en');

const handleLanguageChange = (event) => {
setLanguage(event.target.value);
console.log("Selected language: " + event.target.value);
i18n.changeLanguage(event.target.value);
};

return (
<div className="mt-6 mb-8">

<div className="flex flex-col gap-y-1">
<h2 className="text-base leading-6 font-bold text-white">
Select Language
</h2>
<p className="text-xs leading-[18px] font-base text-white/60">
Select your display language.
</p>
</div>
<div>
<select value={language} onChange={handleLanguageChange}>
<option value="en">English</option>
<option value="zh">中文</option>
</select>
</div>

</div>
);
}
8 changes: 6 additions & 2 deletions frontend/src/pages/GeneralSettings/Appearance/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,13 @@ import Sidebar from "@/components/SettingsSidebar";
import { isMobile } from "react-device-detect";
import FooterCustomization from "./FooterCustomization";
import SupportEmail from "./SupportEmail";
import Language from "./Language";
import CustomLogo from "./CustomLogo";
import CustomMessages from "./CustomMessages";
import { useTranslation } from "react-i18next";

export default function Appearance() {
const { t } = useTranslation(["settings"]);
return (
<div className="w-screen h-screen overflow-hidden bg-sidebar flex">
<Sidebar />
Expand All @@ -17,13 +20,14 @@ export default function Appearance() {
<div className="w-full flex flex-col gap-y-1 pb-6 border-white border-b-2 border-opacity-10">
<div className="items-center">
<p className="text-lg leading-6 font-bold text-white">
Appearance
{t("Appearance.page-title")}
</p>
</div>
<p className="text-xs leading-[18px] font-base text-white text-opacity-60">
Customize the appearance settings of your platform.
</p>
</div>
</div>
<Language />
<CustomLogo />
<CustomMessages />
<FooterCustomization />
Expand Down
4 changes: 3 additions & 1 deletion frontend/src/pages/GeneralSettings/Chats/index.jsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import showToast from "@/utils/toast";
import System from "@/models/system";
import { CaretDown, Download } from "@phosphor-icons/react";
import { saveAs } from "file-saver";
import { useTranslation } from "react-i18next";

const exportOptions = {
csv: {
Expand Down Expand Up @@ -46,6 +47,7 @@ const exportOptions = {
};

export default function WorkspaceChats() {
const { t } = useTranslation(["settings"]);
const [showMenu, setShowMenu] = useState(false);
const menuRef = useRef();
const openMenuButton = useRef();
Expand Down Expand Up @@ -94,7 +96,7 @@ export default function WorkspaceChats() {
<div className="w-full flex flex-col gap-y-1 pb-6 border-white border-b-2 border-opacity-10">
<div className="flex gap-x-4 items-center">
<p className="text-lg leading-6 font-bold text-white">
Workspace Chats
{t("WorkspaceChat")}
</p>
<div className="relative">
<button
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ import { CaretUpDown, MagnifyingGlass, X } from "@phosphor-icons/react";
import { useModal } from "@/hooks/useModal";
import ModalWrapper from "@/components/ModalWrapper";
import CTAButton from "@/components/lib/CTAButton";
import { useTranslation } from "react-i18next";

const EMBEDDERS = [
{
Expand Down Expand Up @@ -94,6 +95,8 @@ export default function GeneralEmbeddingPreference() {
const searchInputRef = useRef(null);
const { isOpen, openModal, closeModal } = useModal();

const { t } = useTranslation(["main"]);

function embedderModelChanged(formEl) {
try {
const newModel = new FormData(formEl).get("EmbeddingModelPref") ?? null;
Expand Down Expand Up @@ -204,7 +207,7 @@ export default function GeneralEmbeddingPreference() {
<div className="w-full flex flex-col gap-y-1 pb-6 border-white border-b-2 border-opacity-10">
<div className="flex gap-x-4 items-center">
<p className="text-lg leading-6 font-bold text-white">
Embedding Preference
{t("EmbedderPreferences")}
</p>
</div>
<p className="text-xs leading-[18px] font-base text-white text-opacity-60">
Expand Down
Loading