mirror of
https://github.com/lobehub/lobehub.git
synced 2026-03-27 13:29:15 +07:00
🐛 fix: global memory setting & tool enabled logic (#12610)
* fix: global enable user memories * fix: memory tool enabled logic
This commit is contained in:
@@ -164,10 +164,10 @@
|
||||
"memory.effort.low.title": "Low",
|
||||
"memory.effort.medium.title": "Medium",
|
||||
"memory.effort.title": "Aggressiveness",
|
||||
"memory.off.desc": "Disable memory for this conversation.",
|
||||
"memory.off.title": "Disable Memory",
|
||||
"memory.on.desc": "Remember preferences and info from conversations.",
|
||||
"memory.on.title": "Enable Memory",
|
||||
"memory.off.desc": "AI will not search, create, or update memories in this conversation.",
|
||||
"memory.off.title": "Disable Memory Tool",
|
||||
"memory.on.desc": "Allow AI to actively search and manage your memories during conversation.",
|
||||
"memory.on.title": "Enable Memory Tool",
|
||||
"memory.title": "Memory",
|
||||
"mention.title": "Mention Members",
|
||||
"messageAction.collapse": "Collapse Message",
|
||||
|
||||
@@ -164,10 +164,10 @@
|
||||
"memory.effort.low.title": "低",
|
||||
"memory.effort.medium.title": "中",
|
||||
"memory.effort.title": "积极性",
|
||||
"memory.off.desc": "禁用此对话的记忆功能。",
|
||||
"memory.off.title": "关闭记忆",
|
||||
"memory.on.desc": "从对话中记住偏好和信息。",
|
||||
"memory.on.title": "启用记忆",
|
||||
"memory.off.desc": "AI 将不会在此对话中搜索、创建或更新记忆。",
|
||||
"memory.off.title": "关闭记忆工具",
|
||||
"memory.on.desc": "允许 AI 在对话中主动搜索和管理你的记忆。",
|
||||
"memory.on.title": "启用记忆工具",
|
||||
"memory.title": "记忆",
|
||||
"mention.title": "提及成员",
|
||||
"messageAction.collapse": "收起消息",
|
||||
|
||||
@@ -27,6 +27,7 @@ export const defaultToolIds = [
|
||||
SkillStoreManifest.identifier,
|
||||
WebBrowsingManifest.identifier,
|
||||
KnowledgeBaseManifest.identifier,
|
||||
MemoryManifest.identifier,
|
||||
];
|
||||
|
||||
export const builtinTools: LobeBuiltinTool[] = [
|
||||
|
||||
@@ -60,7 +60,9 @@ interface ToggleOption {
|
||||
const ToggleItem = memo<ToggleOption>(({ value, description, icon, label }) => {
|
||||
const agentId = useAgentId();
|
||||
const { updateAgentChatConfig } = useUpdateAgentConfig();
|
||||
const isEnabled = useAgentStore((s) => chatConfigByIdSelectors.isMemoryEnabledById(agentId)(s));
|
||||
const isEnabled = useAgentStore((s) =>
|
||||
chatConfigByIdSelectors.isMemoryToolEnabledById(agentId)(s),
|
||||
);
|
||||
|
||||
const isActive = value === 'on' ? isEnabled : !isEnabled;
|
||||
|
||||
@@ -90,8 +92,8 @@ const Controls = memo(() => {
|
||||
const agentId = useAgentId();
|
||||
const { updateAgentChatConfig } = useUpdateAgentConfig();
|
||||
const [isEnabled, effort] = useAgentStore((s) => [
|
||||
chatConfigByIdSelectors.isMemoryEnabledById(agentId)(s),
|
||||
chatConfigByIdSelectors.getMemoryEffortById(agentId)(s),
|
||||
chatConfigByIdSelectors.isMemoryToolEnabledById(agentId)(s),
|
||||
chatConfigByIdSelectors.getMemoryToolEffortById(agentId)(s),
|
||||
]);
|
||||
|
||||
const toggleOptions: ToggleOption[] = [
|
||||
|
||||
@@ -18,7 +18,7 @@ const Memory = memo(() => {
|
||||
const { updateAgentChatConfig } = useUpdateAgentConfig();
|
||||
const [isLoading, isEnabled] = useAgentStore((s) => [
|
||||
agentByIdSelectors.isAgentConfigLoadingById(agentId)(s),
|
||||
chatConfigByIdSelectors.isMemoryEnabledById(agentId)(s),
|
||||
chatConfigByIdSelectors.isMemoryToolEnabledById(agentId)(s),
|
||||
]);
|
||||
const isMobile = useIsMobile();
|
||||
|
||||
|
||||
@@ -2,6 +2,7 @@
|
||||
* Tools Engineering - Unified tools processing using ToolsEngine
|
||||
*/
|
||||
import { KnowledgeBaseManifest } from '@lobechat/builtin-tool-knowledge-base';
|
||||
import { MemoryManifest } from '@lobechat/builtin-tool-memory';
|
||||
import { WebBrowsingManifest } from '@lobechat/builtin-tool-web-browsing';
|
||||
import { defaultToolIds } from '@lobechat/builtin-tools';
|
||||
import { isDesktop } from '@lobechat/const';
|
||||
@@ -11,7 +12,7 @@ import { type ChatCompletionTool, type WorkingModel } from '@lobechat/types';
|
||||
import { type LobeChatPluginManifest } from '@lobehub/chat-plugin-sdk';
|
||||
|
||||
import { getAgentStoreState } from '@/store/agent';
|
||||
import { agentSelectors } from '@/store/agent/selectors';
|
||||
import { agentChatConfigSelectors, agentSelectors } from '@/store/agent/selectors';
|
||||
import { getToolStoreState } from '@/store/tool';
|
||||
import {
|
||||
klavisStoreSelectors,
|
||||
@@ -116,6 +117,11 @@ export const createAgentToolsEngine = (workingModel: WorkingModel) =>
|
||||
return agentSelectors.hasEnabledKnowledgeBases(agentState);
|
||||
}
|
||||
|
||||
// For MemoryManifest, check per-agent memory tool toggle
|
||||
if (pluginId === MemoryManifest.identifier) {
|
||||
return agentChatConfigSelectors.isMemoryToolEnabled(getAgentStoreState());
|
||||
}
|
||||
|
||||
// For all other plugins, enable by default
|
||||
return true;
|
||||
},
|
||||
|
||||
@@ -265,10 +265,10 @@ export default {
|
||||
'memory.effort.low.title': 'Low',
|
||||
'memory.effort.medium.title': 'Medium',
|
||||
'memory.effort.title': 'Aggressiveness',
|
||||
'memory.off.desc': 'Disable memory for this conversation.',
|
||||
'memory.off.title': 'Disable Memory',
|
||||
'memory.on.desc': 'Remember preferences and info from conversations.',
|
||||
'memory.on.title': 'Enable Memory',
|
||||
'memory.off.desc': 'AI will not search, create, or update memories in this conversation.',
|
||||
'memory.off.title': 'Disable Memory Tool',
|
||||
'memory.on.desc': 'Allow AI to actively search and manage your memories during conversation.',
|
||||
'memory.on.title': 'Enable Memory Tool',
|
||||
'memory.title': 'Memory',
|
||||
'search.grounding.searchQueries': 'Search Keywords',
|
||||
'search.grounding.title': 'Found {{count}} results',
|
||||
|
||||
@@ -142,9 +142,7 @@ class ChatService {
|
||||
|
||||
// =================== 1.1 process user memories =================== //
|
||||
|
||||
const globalMemoryEnabled = settingsSelectors.memoryEnabled(getUserStoreState());
|
||||
const agentMemoryEnabled = chatConfig.memory?.enabled ?? false;
|
||||
const enableUserMemories = globalMemoryEnabled && agentMemoryEnabled;
|
||||
const enableUserMemories = settingsSelectors.memoryEnabled(getUserStoreState());
|
||||
const userMemorySettings = settingsSelectors.currentMemorySettings(getUserStoreState());
|
||||
const effectiveMemoryEffort =
|
||||
chatConfig.memory?.effort ?? userMemorySettings.effort ?? 'medium';
|
||||
|
||||
@@ -249,7 +249,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe('getMemoryConfigById', () => {
|
||||
describe('getMemoryToolConfigById', () => {
|
||||
it('should return memory config for specified agent', () => {
|
||||
const state = createState({
|
||||
agentMap: {
|
||||
@@ -261,7 +261,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.getMemoryConfigById('agent-1')(state)).toEqual({
|
||||
expect(chatConfigByIdSelectors.getMemoryToolConfigById('agent-1')(state)).toEqual({
|
||||
effort: 'high',
|
||||
enabled: true,
|
||||
toolPermission: 'read-write',
|
||||
@@ -273,7 +273,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
agentMap: { 'agent-1': {} },
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.getMemoryConfigById('agent-1')(state)).toBeUndefined();
|
||||
expect(chatConfigByIdSelectors.getMemoryToolConfigById('agent-1')(state)).toBeUndefined();
|
||||
});
|
||||
|
||||
it('should return undefined for non-existent agent', () => {
|
||||
@@ -281,11 +281,13 @@ describe('chatConfigByIdSelectors', () => {
|
||||
agentMap: {},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.getMemoryConfigById('non-existent')(state)).toBeUndefined();
|
||||
expect(
|
||||
chatConfigByIdSelectors.getMemoryToolConfigById('non-existent')(state),
|
||||
).toBeUndefined();
|
||||
});
|
||||
});
|
||||
|
||||
describe('isMemoryEnabledById', () => {
|
||||
describe('isMemoryToolEnabledById', () => {
|
||||
it('should return true when memory is enabled', () => {
|
||||
const state = createState({
|
||||
agentMap: {
|
||||
@@ -293,7 +295,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.isMemoryEnabledById('agent-1')(state)).toBe(true);
|
||||
expect(chatConfigByIdSelectors.isMemoryToolEnabledById('agent-1')(state)).toBe(true);
|
||||
});
|
||||
|
||||
it('should return false when memory is explicitly disabled', () => {
|
||||
@@ -303,7 +305,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.isMemoryEnabledById('agent-1')(state)).toBe(false);
|
||||
expect(chatConfigByIdSelectors.isMemoryToolEnabledById('agent-1')(state)).toBe(false);
|
||||
});
|
||||
|
||||
it('should return false when memory config is not set (default)', () => {
|
||||
@@ -311,7 +313,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
agentMap: { 'agent-1': {} },
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.isMemoryEnabledById('agent-1')(state)).toBe(false);
|
||||
expect(chatConfigByIdSelectors.isMemoryToolEnabledById('agent-1')(state)).toBe(false);
|
||||
});
|
||||
|
||||
it('should return false when memory exists but enabled is not set', () => {
|
||||
@@ -321,7 +323,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.isMemoryEnabledById('agent-1')(state)).toBe(false);
|
||||
expect(chatConfigByIdSelectors.isMemoryToolEnabledById('agent-1')(state)).toBe(false);
|
||||
});
|
||||
|
||||
it('should return false for non-existent agent', () => {
|
||||
@@ -329,7 +331,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
agentMap: {},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.isMemoryEnabledById('non-existent')(state)).toBe(false);
|
||||
expect(chatConfigByIdSelectors.isMemoryToolEnabledById('non-existent')(state)).toBe(false);
|
||||
});
|
||||
|
||||
it('should work with different agents independently', () => {
|
||||
@@ -341,13 +343,13 @@ describe('chatConfigByIdSelectors', () => {
|
||||
},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.isMemoryEnabledById('agent-1')(state)).toBe(true);
|
||||
expect(chatConfigByIdSelectors.isMemoryEnabledById('agent-2')(state)).toBe(false);
|
||||
expect(chatConfigByIdSelectors.isMemoryEnabledById('agent-3')(state)).toBe(false);
|
||||
expect(chatConfigByIdSelectors.isMemoryToolEnabledById('agent-1')(state)).toBe(true);
|
||||
expect(chatConfigByIdSelectors.isMemoryToolEnabledById('agent-2')(state)).toBe(false);
|
||||
expect(chatConfigByIdSelectors.isMemoryToolEnabledById('agent-3')(state)).toBe(false);
|
||||
});
|
||||
});
|
||||
|
||||
describe('getMemoryEffortById', () => {
|
||||
describe('getMemoryToolEffortById', () => {
|
||||
it('should return effort level for specified agent', () => {
|
||||
const state = createState({
|
||||
agentMap: {
|
||||
@@ -355,7 +357,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.getMemoryEffortById('agent-1')(state)).toBe('high');
|
||||
expect(chatConfigByIdSelectors.getMemoryToolEffortById('agent-1')(state)).toBe('high');
|
||||
});
|
||||
|
||||
it('should return "medium" as default when effort is not set', () => {
|
||||
@@ -365,7 +367,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.getMemoryEffortById('agent-1')(state)).toBe('medium');
|
||||
expect(chatConfigByIdSelectors.getMemoryToolEffortById('agent-1')(state)).toBe('medium');
|
||||
});
|
||||
|
||||
it('should return "medium" when memory config is not set', () => {
|
||||
@@ -373,7 +375,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
agentMap: { 'agent-1': {} },
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.getMemoryEffortById('agent-1')(state)).toBe('medium');
|
||||
expect(chatConfigByIdSelectors.getMemoryToolEffortById('agent-1')(state)).toBe('medium');
|
||||
});
|
||||
|
||||
it('should return "medium" for non-existent agent', () => {
|
||||
@@ -381,7 +383,7 @@ describe('chatConfigByIdSelectors', () => {
|
||||
agentMap: {},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.getMemoryEffortById('non-existent')(state)).toBe('medium');
|
||||
expect(chatConfigByIdSelectors.getMemoryToolEffortById('non-existent')(state)).toBe('medium');
|
||||
});
|
||||
|
||||
it('should return each effort level correctly', () => {
|
||||
@@ -393,9 +395,9 @@ describe('chatConfigByIdSelectors', () => {
|
||||
},
|
||||
});
|
||||
|
||||
expect(chatConfigByIdSelectors.getMemoryEffortById('agent-low')(state)).toBe('low');
|
||||
expect(chatConfigByIdSelectors.getMemoryEffortById('agent-medium')(state)).toBe('medium');
|
||||
expect(chatConfigByIdSelectors.getMemoryEffortById('agent-high')(state)).toBe('high');
|
||||
expect(chatConfigByIdSelectors.getMemoryToolEffortById('agent-low')(state)).toBe('low');
|
||||
expect(chatConfigByIdSelectors.getMemoryToolEffortById('agent-medium')(state)).toBe('medium');
|
||||
expect(chatConfigByIdSelectors.getMemoryToolEffortById('agent-high')(state)).toBe('high');
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -54,24 +54,24 @@ const getUseModelBuiltinSearchById = (agentId: string) => (s: AgentStoreState) =
|
||||
const getSearchFCModelById = (agentId: string) => (s: AgentStoreState) =>
|
||||
getChatConfigById(agentId)(s).searchFCModel || DEFAULT_AGENT_SEARCH_FC_MODEL;
|
||||
|
||||
const getMemoryConfigById = (agentId: string) => (s: AgentStoreState) =>
|
||||
const getMemoryToolConfigById = (agentId: string) => (s: AgentStoreState) =>
|
||||
getChatConfigById(agentId)(s).memory;
|
||||
|
||||
const isMemoryEnabledById = (agentId: string) => (s: AgentStoreState) =>
|
||||
const isMemoryToolEnabledById = (agentId: string) => (s: AgentStoreState) =>
|
||||
getChatConfigById(agentId)(s).memory?.enabled ?? false;
|
||||
|
||||
const getMemoryEffortById = (agentId: string) => (s: AgentStoreState) =>
|
||||
const getMemoryToolEffortById = (agentId: string) => (s: AgentStoreState) =>
|
||||
getChatConfigById(agentId)(s).memory?.effort ?? 'medium';
|
||||
|
||||
export const chatConfigByIdSelectors = {
|
||||
getChatConfigById,
|
||||
getEnableHistoryCountById,
|
||||
getHistoryCountById,
|
||||
getMemoryConfigById,
|
||||
getMemoryEffortById,
|
||||
getMemoryToolConfigById,
|
||||
getMemoryToolEffortById,
|
||||
getSearchFCModelById,
|
||||
getSearchModeById,
|
||||
getUseModelBuiltinSearchById,
|
||||
isEnableSearchById,
|
||||
isMemoryEnabledById,
|
||||
isMemoryToolEnabledById,
|
||||
};
|
||||
|
||||
@@ -27,6 +27,9 @@ const enableHistoryCount = (s: AgentStoreState) =>
|
||||
const historyCount = (s: AgentStoreState): number =>
|
||||
chatConfigByIdSelectors.getHistoryCountById(s.activeAgentId || '')(s);
|
||||
|
||||
const isMemoryToolEnabled = (s: AgentStoreState) =>
|
||||
chatConfigByIdSelectors.isMemoryToolEnabledById(s.activeAgentId || '')(s);
|
||||
|
||||
const enableHistoryDivider =
|
||||
(historyLength: number, currentIndex: number) => (s: AgentStoreState) => {
|
||||
const config = currentChatConfig(s);
|
||||
@@ -45,6 +48,7 @@ export const agentChatConfigSelectors = {
|
||||
enableHistoryDivider,
|
||||
historyCount,
|
||||
isAgentEnableSearch,
|
||||
isMemoryToolEnabled,
|
||||
searchFCModel,
|
||||
useModelBuiltinSearch,
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user