mirror of
https://github.com/coaidev/coai.git
synced 2025-05-23 23:10:13 +09:00
update context length settings and admin pages
This commit is contained in:
parent
e79c29e24a
commit
7e7798d213
@ -7,7 +7,7 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
func UsingWebSegment(instance *conversation.Conversation) []globals.Message {
|
func UsingWebSegment(instance *conversation.Conversation) []globals.Message {
|
||||||
segment := conversation.CopyMessage(instance.GetMessageSegment(12))
|
segment := conversation.CopyMessage(instance.GetChatMessage())
|
||||||
|
|
||||||
if instance.IsEnableWeb() {
|
if instance.IsEnableWeb() {
|
||||||
segment = ChatWithWeb(func(message []globals.Message, token int) (string, error) {
|
segment = ChatWithWeb(func(message []globals.Message, token int) (string, error) {
|
||||||
|
@ -4,6 +4,7 @@ import { getMemory } from "@/utils/memory.ts";
|
|||||||
export const endpoint = `${ws_api}/chat`;
|
export const endpoint = `${ws_api}/chat`;
|
||||||
|
|
||||||
export type StreamMessage = {
|
export type StreamMessage = {
|
||||||
|
conversation?: number;
|
||||||
keyword?: string;
|
keyword?: string;
|
||||||
quota?: number;
|
quota?: number;
|
||||||
message: string;
|
message: string;
|
||||||
@ -97,6 +98,9 @@ export class Connection {
|
|||||||
}
|
}
|
||||||
|
|
||||||
protected triggerCallback(message: StreamMessage): void {
|
protected triggerCallback(message: StreamMessage): void {
|
||||||
|
if (this.id === -1 && message.conversation) {
|
||||||
|
this.setId(message.conversation);
|
||||||
|
}
|
||||||
this.callback && this.callback(message);
|
this.callback && this.callback(message);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
import { useDispatch, useSelector } from "react-redux";
|
import { useDispatch, useSelector } from "react-redux";
|
||||||
import { closeMenu, selectMenu } from "@/store/menu.ts";
|
import { closeMenu, selectMenu } from "@/store/menu.ts";
|
||||||
import React, { useMemo } from "react";
|
import React, { useMemo } from "react";
|
||||||
import { LayoutDashboard, Radio, Settings, Users } from "lucide-react";
|
import {CandlestickChart, LayoutDashboard, Radio, Settings, Users} from "lucide-react";
|
||||||
import router from "@/router.tsx";
|
import router from "@/router.tsx";
|
||||||
import { useLocation } from "react-router-dom";
|
import { useLocation } from "react-router-dom";
|
||||||
import { useTranslation } from "react-i18next";
|
import { useTranslation } from "react-i18next";
|
||||||
@ -53,9 +53,14 @@ function MenuBar() {
|
|||||||
path={"/broadcast"}
|
path={"/broadcast"}
|
||||||
/>
|
/>
|
||||||
<MenuItem
|
<MenuItem
|
||||||
title={t("admin.settings")}
|
title={t("admin.channel")}
|
||||||
icon={<Settings />}
|
icon={<Settings />}
|
||||||
path={"/settings"}
|
path={"/channel"}
|
||||||
|
/>
|
||||||
|
<MenuItem
|
||||||
|
title={t("admin.prize")}
|
||||||
|
icon={<CandlestickChart />}
|
||||||
|
path={"/prize"}
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
@ -92,7 +92,7 @@ function OperationMenu({ id }: OperationMenuProps) {
|
|||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
<DropdownMenu>
|
<DropdownMenu>
|
||||||
<DropdownMenuTrigger>
|
<DropdownMenuTrigger asChild>
|
||||||
<Button variant={`outline`} size={`icon`}>
|
<Button variant={`outline`} size={`icon`}>
|
||||||
<MoreHorizontal className={`h-4 w-4`} />
|
<MoreHorizontal className={`h-4 w-4`} />
|
||||||
</Button>
|
</Button>
|
||||||
|
@ -34,6 +34,7 @@ import {
|
|||||||
SelectValue,
|
SelectValue,
|
||||||
} from "@/components/ui/select.tsx";
|
} from "@/components/ui/select.tsx";
|
||||||
import { langs, setLanguage } from "@/i18n.ts";
|
import { langs, setLanguage } from "@/i18n.ts";
|
||||||
|
import {cn} from "@/components/ui/lib/utils.ts";
|
||||||
|
|
||||||
function SettingsDialog() {
|
function SettingsDialog() {
|
||||||
const { t, i18n } = useTranslation();
|
const { t, i18n } = useTranslation();
|
||||||
@ -140,7 +141,7 @@ function SettingsDialog() {
|
|||||||
<div className={`name`}>{t("settings.history")}</div>
|
<div className={`name`}>{t("settings.history")}</div>
|
||||||
<div className={`grow`} />
|
<div className={`grow`} />
|
||||||
<NumberInput
|
<NumberInput
|
||||||
className={`value`}
|
className={cn(`value`, history === 0 && `text-red-500`)}
|
||||||
value={history}
|
value={history}
|
||||||
acceptNaN={false}
|
acceptNaN={false}
|
||||||
min={0}
|
min={0}
|
||||||
|
@ -127,9 +127,9 @@ const resources = {
|
|||||||
go: "前往实名认证",
|
go: "前往实名认证",
|
||||||
cert: "实名认证礼包",
|
cert: "实名认证礼包",
|
||||||
"cert-desc": "实名认证后可获得 50 点数 (价值 5 元)",
|
"cert-desc": "实名认证后可获得 50 点数 (价值 5 元)",
|
||||||
teen: "未成年人福利",
|
teen: "学生福利",
|
||||||
"teen-desc":
|
"teen-desc":
|
||||||
"实名认证后未成年人(18 周岁及以下)可额外获得 150 点数 (价值 15 元),并且获得每天 100 次免费使用 Claude 100k 模型额度",
|
"实名认证后未成年人(18 周岁及以下)可额外获得 150 点数 (价值 15 元)",
|
||||||
close: "关闭",
|
close: "关闭",
|
||||||
state: {
|
state: {
|
||||||
true: "已领取",
|
true: "已领取",
|
||||||
@ -308,7 +308,8 @@ const resources = {
|
|||||||
dashboard: "仪表盘",
|
dashboard: "仪表盘",
|
||||||
users: "用户管理",
|
users: "用户管理",
|
||||||
broadcast: "公告管理",
|
broadcast: "公告管理",
|
||||||
settings: "设置",
|
channel: "渠道设置",
|
||||||
|
prize: "价格设定",
|
||||||
"billing-today": "今日入账",
|
"billing-today": "今日入账",
|
||||||
"billing-month": "本月入账",
|
"billing-month": "本月入账",
|
||||||
"subscription-users": "订阅用户",
|
"subscription-users": "订阅用户",
|
||||||
@ -491,9 +492,9 @@ const resources = {
|
|||||||
cert: "Certification Package",
|
cert: "Certification Package",
|
||||||
"cert-desc":
|
"cert-desc":
|
||||||
"After real-name certification, you can get 50 points (worth 5 CNY)",
|
"After real-name certification, you can get 50 points (worth 5 CNY)",
|
||||||
teen: "Teenager Package",
|
teen: "Student Package",
|
||||||
"teen-desc":
|
"teen-desc":
|
||||||
"After real-name certification, teenagers (18 years old and below) can get an additional 150 points (worth 15 CNY) and 100 times of free use of Claude 100k model per day",
|
"After real-name certification, teenagers (18 years old and under) can get an additional 150 points (worth 15 CNY)",
|
||||||
close: "Close",
|
close: "Close",
|
||||||
state: {
|
state: {
|
||||||
true: "Received",
|
true: "Received",
|
||||||
@ -681,7 +682,8 @@ const resources = {
|
|||||||
dashboard: "Dashboard",
|
dashboard: "Dashboard",
|
||||||
users: "User Management",
|
users: "User Management",
|
||||||
broadcast: "Broadcast Management",
|
broadcast: "Broadcast Management",
|
||||||
settings: "Settings",
|
channel: "Channel Settings",
|
||||||
|
prize: "Price Settings",
|
||||||
"billing-today": "Billing Today",
|
"billing-today": "Billing Today",
|
||||||
"billing-month": "Billing Month",
|
"billing-month": "Billing Month",
|
||||||
"subscription-users": "Subscription Users",
|
"subscription-users": "Subscription Users",
|
||||||
@ -870,7 +872,7 @@ const resources = {
|
|||||||
"После сертификации подлинности вы можете получить 100 очков (стоимостью 5 CNY)",
|
"После сертификации подлинности вы можете получить 100 очков (стоимостью 5 CNY)",
|
||||||
teen: "Подростковый пакет",
|
teen: "Подростковый пакет",
|
||||||
"teen-desc":
|
"teen-desc":
|
||||||
"После сертификации подлинности подростки (до 18 лет) могут получить дополнительно 150 очков (стоимостью 15 CNY) и 100 раз бесплатно использовать модель Claude 100k в день",
|
"После сертификации подлинности подростки (до 18 лет) могут получить дополнительно 150 очков (стоимостью 15 CNY)",
|
||||||
close: "Закрыть",
|
close: "Закрыть",
|
||||||
state: {
|
state: {
|
||||||
true: "Получено",
|
true: "Получено",
|
||||||
@ -1057,7 +1059,8 @@ const resources = {
|
|||||||
dashboard: "Панель управления",
|
dashboard: "Панель управления",
|
||||||
users: "Управление пользователями",
|
users: "Управление пользователями",
|
||||||
broadcast: "Управление объявлениями",
|
broadcast: "Управление объявлениями",
|
||||||
settings: "Настройки",
|
channel: "Настройки канала",
|
||||||
|
prize: "Настройки цен",
|
||||||
"billing-today": "Сегодняшний доход",
|
"billing-today": "Сегодняшний доход",
|
||||||
"billing-month": "Доход за месяц",
|
"billing-month": "Доход за месяц",
|
||||||
"subscription-users": "Подписчики",
|
"subscription-users": "Подписчики",
|
||||||
|
@ -10,7 +10,8 @@ const Article = lazy(() => import("@/routes/Article.tsx"));
|
|||||||
|
|
||||||
const Admin = lazy(() => import("@/routes/Admin.tsx"));
|
const Admin = lazy(() => import("@/routes/Admin.tsx"));
|
||||||
const Dashboard = lazy(() => import("@/routes/admin/DashBoard.tsx"));
|
const Dashboard = lazy(() => import("@/routes/admin/DashBoard.tsx"));
|
||||||
const Settings = lazy(() => import("@/routes/admin/Settings.tsx"));
|
const Channel = lazy(() => import("@/routes/admin/Channel.tsx"));
|
||||||
|
const Prize = lazy(() => import("@/routes/admin/Prize.tsx"));
|
||||||
const Users = lazy(() => import("@/routes/admin/Users.tsx"));
|
const Users = lazy(() => import("@/routes/admin/Users.tsx"));
|
||||||
const Broadcast = lazy(() => import("@/routes/admin/Broadcast.tsx"));
|
const Broadcast = lazy(() => import("@/routes/admin/Broadcast.tsx"));
|
||||||
|
|
||||||
@ -85,11 +86,20 @@ const router = createBrowserRouter([
|
|||||||
),
|
),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
id: "admin-settings",
|
id: "admin-channel",
|
||||||
path: "settings",
|
path: "channel",
|
||||||
element: (
|
element: (
|
||||||
<Suspense>
|
<Suspense>
|
||||||
<Settings />
|
<Channel />
|
||||||
|
</Suspense>
|
||||||
|
),
|
||||||
|
},
|
||||||
|
{
|
||||||
|
id: "admin-prize",
|
||||||
|
path: "prize",
|
||||||
|
element: (
|
||||||
|
<Suspense>
|
||||||
|
<Prize />
|
||||||
</Suspense>
|
</Suspense>
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
|
5
app/src/routes/admin/Channel.tsx
Normal file
5
app/src/routes/admin/Channel.tsx
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
function Channel() {
|
||||||
|
return <></>;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default Channel;
|
5
app/src/routes/admin/Prize.tsx
Normal file
5
app/src/routes/admin/Prize.tsx
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
function Prize() {
|
||||||
|
return <></>;
|
||||||
|
}
|
||||||
|
|
||||||
|
export default Prize;
|
@ -1,5 +0,0 @@
|
|||||||
function Settings() {
|
|
||||||
return <></>;
|
|
||||||
}
|
|
||||||
|
|
||||||
export default Settings;
|
|
@ -9,11 +9,12 @@ type Message struct {
|
|||||||
}
|
}
|
||||||
|
|
||||||
type ChatSegmentResponse struct {
|
type ChatSegmentResponse struct {
|
||||||
Quota float32 `json:"quota"`
|
Conversation int64 `json:"conversation"`
|
||||||
Keyword string `json:"keyword"`
|
Quota float32 `json:"quota"`
|
||||||
Message string `json:"message"`
|
Keyword string `json:"keyword"`
|
||||||
End bool `json:"end"`
|
Message string `json:"message"`
|
||||||
Plan bool `json:"plan"`
|
End bool `json:"end"`
|
||||||
|
Plan bool `json:"plan"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type GenerationSegmentResponse struct {
|
type GenerationSegmentResponse struct {
|
||||||
|
@ -63,6 +63,9 @@ func ChatHandler(conn *Connection, user *auth.User, instance *conversation.Conve
|
|||||||
db := conn.GetDB()
|
db := conn.GetDB()
|
||||||
cache := conn.GetCache()
|
cache := conn.GetCache()
|
||||||
check, plan := auth.CanEnableModelWithSubscription(db, cache, user, model)
|
check, plan := auth.CanEnableModelWithSubscription(db, cache, user, model)
|
||||||
|
conn.Send(globals.ChatSegmentResponse{
|
||||||
|
Conversation: instance.GetId(),
|
||||||
|
})
|
||||||
|
|
||||||
if !check {
|
if !check {
|
||||||
conn.Send(globals.ChatSegmentResponse{
|
conn.Send(globals.ChatSegmentResponse{
|
||||||
|
@ -10,17 +10,18 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
const defaultConversationName = "new chat"
|
const defaultConversationName = "new chat"
|
||||||
|
const defaultConversationContext = 8
|
||||||
|
|
||||||
type Conversation struct {
|
type Conversation struct {
|
||||||
Auth bool `json:"auth"`
|
Auth bool `json:"auth"`
|
||||||
UserID int64 `json:"user_id"`
|
UserID int64 `json:"user_id"`
|
||||||
Id int64 `json:"id"`
|
Id int64 `json:"id"`
|
||||||
Name string `json:"name"`
|
Name string `json:"name"`
|
||||||
Message []globals.Message `json:"message"`
|
Message []globals.Message `json:"message"`
|
||||||
Model string `json:"model"`
|
Model string `json:"model"`
|
||||||
EnableWeb bool `json:"enable_web"`
|
EnableWeb bool `json:"enable_web"`
|
||||||
Shared bool `json:"shared"`
|
Shared bool `json:"shared"`
|
||||||
IgnoreContext bool `json:"ignore_context"`
|
Context int `json:"context"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type FormMessage struct {
|
type FormMessage struct {
|
||||||
@ -29,17 +30,18 @@ type FormMessage struct {
|
|||||||
Web bool `json:"web"`
|
Web bool `json:"web"`
|
||||||
Model string `json:"model"`
|
Model string `json:"model"`
|
||||||
IgnoreContext bool `json:"ignore_context"`
|
IgnoreContext bool `json:"ignore_context"`
|
||||||
|
Context int `json:"context"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func NewAnonymousConversation() *Conversation {
|
func NewAnonymousConversation() *Conversation {
|
||||||
return &Conversation{
|
return &Conversation{
|
||||||
Auth: false,
|
Auth: false,
|
||||||
UserID: -1,
|
UserID: -1,
|
||||||
Id: -1,
|
Id: -1,
|
||||||
Name: defaultConversationName,
|
Name: defaultConversationName,
|
||||||
Message: []globals.Message{},
|
Message: []globals.Message{},
|
||||||
Model: globals.GPT3Turbo,
|
Model: globals.GPT3Turbo,
|
||||||
IgnoreContext: false,
|
Context: defaultConversationContext,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -89,8 +91,8 @@ func (c *Conversation) IsEnableWeb() bool {
|
|||||||
return c.EnableWeb
|
return c.EnableWeb
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *Conversation) IsIgnoreContext() bool {
|
func (c *Conversation) GetContextLength() int {
|
||||||
return c.IgnoreContext
|
return c.Context
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *Conversation) SetModel(model string) {
|
func (c *Conversation) SetModel(model string) {
|
||||||
@ -104,8 +106,8 @@ func (c *Conversation) SetEnableWeb(enable bool) {
|
|||||||
c.EnableWeb = enable
|
c.EnableWeb = enable
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *Conversation) SetIgnoreContext(ignore bool) {
|
func (c *Conversation) SetContextLength(context int) {
|
||||||
c.IgnoreContext = ignore
|
c.Context = context
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *Conversation) GetName() string {
|
func (c *Conversation) GetName() string {
|
||||||
@ -142,20 +144,16 @@ func (c *Conversation) GetMessageLength() int {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (c *Conversation) GetMessageSegment(length int) []globals.Message {
|
func (c *Conversation) GetMessageSegment(length int) []globals.Message {
|
||||||
if c.IsIgnoreContext() {
|
|
||||||
if len(c.Message) >= 1 {
|
|
||||||
// get latest message
|
|
||||||
return []globals.Message{c.Message[len(c.Message)-1]}
|
|
||||||
}
|
|
||||||
// empty
|
|
||||||
return []globals.Message{}
|
|
||||||
}
|
|
||||||
if length > len(c.Message) {
|
if length > len(c.Message) {
|
||||||
return c.Message
|
return c.Message
|
||||||
}
|
}
|
||||||
return c.Message[len(c.Message)-length:]
|
return c.Message[len(c.Message)-length:]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (c *Conversation) GetChatMessage() []globals.Message {
|
||||||
|
return c.GetMessageSegment(c.GetContextLength())
|
||||||
|
}
|
||||||
|
|
||||||
func CopyMessage(message []globals.Message) []globals.Message {
|
func CopyMessage(message []globals.Message) []globals.Message {
|
||||||
return utils.DeepCopy[[]globals.Message](message) // deep copy
|
return utils.DeepCopy[[]globals.Message](message) // deep copy
|
||||||
}
|
}
|
||||||
@ -224,7 +222,14 @@ func (c *Conversation) AddMessageFromByte(data []byte) (string, error) {
|
|||||||
c.AddMessageFromUser(form.Message)
|
c.AddMessageFromUser(form.Message)
|
||||||
c.SetModel(form.Model)
|
c.SetModel(form.Model)
|
||||||
c.SetEnableWeb(form.Web)
|
c.SetEnableWeb(form.Web)
|
||||||
c.SetIgnoreContext(form.IgnoreContext)
|
|
||||||
|
if form.IgnoreContext {
|
||||||
|
form.Context = 1
|
||||||
|
} else if form.Context <= 0 {
|
||||||
|
form.Context = defaultConversationContext
|
||||||
|
}
|
||||||
|
|
||||||
|
c.SetContextLength(form.Context)
|
||||||
return form.Message, nil
|
return form.Message, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -236,7 +241,13 @@ func (c *Conversation) AddMessageFromForm(form *FormMessage) error {
|
|||||||
c.AddMessageFromUser(form.Message)
|
c.AddMessageFromUser(form.Message)
|
||||||
c.SetModel(form.Model)
|
c.SetModel(form.Model)
|
||||||
c.SetEnableWeb(form.Web)
|
c.SetEnableWeb(form.Web)
|
||||||
c.SetIgnoreContext(form.IgnoreContext)
|
if form.IgnoreContext {
|
||||||
|
form.Context = 1
|
||||||
|
} else if form.Context <= 0 {
|
||||||
|
form.Context = defaultConversationContext
|
||||||
|
}
|
||||||
|
|
||||||
|
c.SetContextLength(form.Context)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user