fix: number of context incorrect (#2653)

* fix: number of context incorrect

* feat: 优化上下文数显示样式

* fix: 上下文数显示不正确

修复无限上下文情况下,当前上下文数显示不正确的问题

* fix: slider display incorrect

* fix: Update infinity display style
This commit is contained in:
George·Dong 2025-03-08 20:49:24 +08:00 committed by kangfenmao
parent 3312befe11
commit 85bf4498c0
11 changed files with 60 additions and 19 deletions

View File

@ -86,7 +86,7 @@
"input.clear.content": "Do you want to clear all messages of the current topic?",
"input.clear.title": "Clear all messages?",
"input.collapse": "Collapse",
"input.context_count.tip": "Context Count",
"input.context_count.tip": "Context / Max Context",
"input.estimated_tokens.tip": "Estimated tokens",
"input.expand": "Expand",
"input.file_not_supported": "Model does not support this file type",

View File

@ -86,7 +86,7 @@
"input.clear.content": "現在のトピックのすべてのメッセージをクリアしますか?",
"input.clear.title": "すべてのメッセージをクリアしますか?",
"input.collapse": "折りたたむ",
"input.context_count.tip": "コンテキスト数",
"input.context_count.tip": "コンテキスト数 / 最大コンテキスト数",
"input.estimated_tokens.tip": "推定トークン数",
"input.expand": "展開",
"input.file_not_supported": "モデルはこのファイルタイプをサポートしません",

View File

@ -86,7 +86,7 @@
"input.clear.content": "Хотите очистить все сообщения текущего топика?",
"input.clear.title": "Очистить все сообщения?",
"input.collapse": "Свернуть",
"input.context_count.tip": "Количество контекстов",
"input.context_count.tip": "Контекст / Макс. контекст",
"input.estimated_tokens.tip": "Затраты токенов",
"input.expand": "Развернуть",
"input.file_not_supported": "Модель не поддерживает этот тип файла",

View File

@ -86,7 +86,7 @@
"input.clear.content": "确定要清除当前会话所有消息吗?",
"input.clear.title": "清空消息",
"input.collapse": "收起",
"input.context_count.tip": "上下文数",
"input.context_count.tip": "上下文数 / 最大上下文数",
"input.estimated_tokens.tip": "预估 token 数",
"input.expand": "展开",
"input.file_not_supported": "模型不支持此文件类型",

View File

@ -86,7 +86,7 @@
"input.clear.content": "您想要清除目前話題的所有訊息嗎?",
"input.clear.title": "清除所有訊息?",
"input.collapse": "折疊",
"input.context_count.tip": "上下文數",
"input.context_count.tip": "上下文數 / 最大上下文數",
"input.estimated_tokens.tip": "預估 Token 數",
"input.expand": "展開",
"input.file_not_supported": "模型不支援此檔案類型",

View File

@ -75,7 +75,7 @@ const Inputbar: FC<Props> = ({ assistant: _assistant, setActiveTopic }) => {
} = useSettings()
const [expended, setExpend] = useState(false)
const [estimateTokenCount, setEstimateTokenCount] = useState(0)
const [contextCount, setContextCount] = useState(0)
const [contextCount, setContextCount] = useState({ current: 0, max: 0 })
const generating = useAppSelector((state) => state.runtime.generating)
const textareaRef = useRef<TextAreaRef>(null)
const [files, setFiles] = useState<FileType[]>(_files)
@ -503,7 +503,7 @@ const Inputbar: FC<Props> = ({ assistant: _assistant, setActiveTopic }) => {
}),
EventEmitter.on(EVENT_NAMES.ESTIMATED_TOKEN_COUNT, ({ tokensCount, contextCount }) => {
_setEstimateTokenCount(tokensCount)
setContextCount(contextCount)
setContextCount({ current: contextCount.current, max: contextCount.max }) // 现在contextCount是一个对象而不是单个数值
}),
EventEmitter.on(EVENT_NAMES.ADD_NEW_TOPIC, addNewTopic),
EventEmitter.on(EVENT_NAMES.QUOTE_TEXT, (quotedText: string) => {

View File

@ -9,7 +9,7 @@ import styled from 'styled-components'
type Props = {
estimateTokenCount: number
inputTokenCount: number
contextCount: number
contextCount: { current: number; max: number }
ToolbarButton: any
} & React.HTMLAttributes<HTMLDivElement>
@ -21,12 +21,30 @@ const TokenCount: FC<Props> = ({ estimateTokenCount, inputTokenCount, contextCou
return null
}
const formatMaxCount = (max: number) => {
if (max == 20) {
return (
<span
style={{
fontSize: '16px',
position: 'relative',
top: '1px'
}}>
</span>
)
}
return max.toString()
}
const PopoverContent = () => {
return (
<VStack w="150px" background="100%">
<VStack w="185px" background="100%">
<HStack justifyContent="space-between" w="100%">
<Text>{t('chat.input.context_count.tip')}</Text>
<Text>{contextCount}</Text>
<Text>
{contextCount.current} / {contextCount.max == 20 ? '∞' : contextCount.max}
</Text>
</HStack>
<Divider style={{ margin: '5px 0' }} />
<HStack justifyContent="space-between" w="100%">
@ -40,7 +58,7 @@ const TokenCount: FC<Props> = ({ estimateTokenCount, inputTokenCount, contextCou
return (
<Container>
<Popover content={PopoverContent}>
<MenuOutlined /> {contextCount}
<MenuOutlined /> {contextCount.current} / {formatMaxCount(contextCount.max)}
<Divider type="vertical" style={{ marginTop: 0, marginLeft: 5, marginRight: 5 }} />
<ArrowUpOutlined />
{inputTokenCount} / {estimateTokenCount}
@ -66,7 +84,7 @@ const Container = styled.div`
font-size: 10px;
margin-right: 3px;
}
@media (max-width: 600px) {
@media (max-width: 700px) {
display: none;
}
`

View File

@ -133,6 +133,11 @@ const SettingsTab: FC<Props> = (props) => {
setReasoningEffort(assistant?.settings?.reasoning_effort)
}, [assistant])
const formatSliderTooltip = (value?: number) => {
if (value === undefined) return ''
return value === 20 ? '∞' : value.toString()
}
return (
<Container className="settings-tab">
<SettingGroup style={{ marginTop: 10 }}>
@ -176,6 +181,7 @@ const SettingsTab: FC<Props> = (props) => {
onChangeComplete={onContextCountChange}
value={typeof contextCount === 'number' ? contextCount : 0}
step={1}
tooltip={{ formatter: formatSliderTooltip }}
/>
</Col>
</Row>

View File

@ -184,6 +184,11 @@ const AssistantModelSettings: FC<Props> = ({ assistant, updateAssistant, updateA
return () => updateAssistantSettings({ customParameters: customParametersRef.current })
}, [])
const formatSliderTooltip = (value?: number) => {
if (value === undefined) return ''
return value === 20 ? '∞' : value.toString()
}
return (
<Container>
<Row align="middle" style={{ marginBottom: 10 }}>
@ -298,6 +303,7 @@ const AssistantModelSettings: FC<Props> = ({ assistant, updateAssistant, updateA
value={typeof contextCount === 'number' ? contextCount : 0}
marks={{ 0: '0', 5: '5', 10: '10', 15: '15', 20: t('chat.settings.max') }}
step={1}
tooltip={{ formatter: formatSliderTooltip }}
/>
</Col>
<Col span={4}>

View File

@ -68,16 +68,26 @@ export function filterUsefulMessages(messages: Message[]): Message[] {
}
export function getContextCount(assistant: Assistant, messages: Message[]) {
const contextCount = assistant?.settings?.contextCount ?? DEFAULT_CONTEXTCOUNT
const _messages = takeRight(messages, contextCount)
const clearIndex = _messages.findLastIndex((message) => message.type === 'clear')
const messagesCount = _messages.length
const rawContextCount = assistant?.settings?.contextCount ?? DEFAULT_CONTEXTCOUNT
// 使用与 getAssistantSettings 相同的逻辑处理无限上下文
const maxContextCount = rawContextCount === 20 ? 100000 : rawContextCount
// 在无限模式下,设置一个合理的高上限而不是处理所有消息
const _messages = rawContextCount === 20 ? takeRight(messages, 1000) : takeRight(messages, maxContextCount)
const clearIndex = _messages.findLastIndex((message) => message.type === 'clear')
let currentContextCount = 0
if (clearIndex === -1) {
return contextCount
currentContextCount = _messages.length
} else {
currentContextCount = _messages.length - (clearIndex + 1)
}
return messagesCount - (clearIndex + 1)
return {
current: currentContextCount,
max: rawContextCount
}
}
export function deleteMessageFiles(message: Message) {

View File

@ -95,7 +95,8 @@ export async function estimateMessagesUsage({
export async function estimateHistoryTokens(assistant: Assistant, msgs: Message[]) {
const { contextCount } = getAssistantSettings(assistant)
const messages = filterMessages(filterContextMessages(takeRight(msgs, contextCount)))
const maxContextCount = contextCount
const messages = filterMessages(filterContextMessages(takeRight(msgs, maxContextCount)))
// 有 usage 数据的消息,快速计算总数
const uasageTokens = messages