a2a-memory 0.11.5 → 0.12.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +7 -19
- package/README.md +1 -1
- package/dist/a2a/client.js +1 -252
- package/dist/a2a/discovery.js +1 -115
- package/dist/a2a/index.js +1 -8
- package/dist/a2a/types.js +1 -42
- package/dist/adapters/anthropic.js +1 -117
- package/dist/chunking/chunker.js +1 -163
- package/dist/claude/sync.d.ts +8 -2
- package/dist/claude/sync.js +1 -298
- package/dist/cli/commands/add.js +1 -80
- package/dist/cli/commands/claude-sync.d.ts +3 -3
- package/dist/cli/commands/claude-sync.js +1 -70
- package/dist/cli/commands/cleanup.js +1 -83
- package/dist/cli/commands/config.js +1 -79
- package/dist/cli/commands/edit.js +1 -69
- package/dist/cli/commands/embed.js +1 -92
- package/dist/cli/commands/extract.js +1 -103
- package/dist/cli/commands/health.js +1 -105
- package/dist/cli/commands/list.js +1 -46
- package/dist/cli/commands/migrate-chunks.js +1 -205
- package/dist/cli/commands/migrate-file-refs.js +1 -183
- package/dist/cli/commands/proficiency.js +1 -146
- package/dist/cli/commands/rm.js +1 -64
- package/dist/cli/commands/search.js +1 -90
- package/dist/cli/commands/setup-wizard.js +1 -387
- package/dist/cli/commands/setup.js +1 -170
- package/dist/cli/commands/skill.js +1 -151
- package/dist/cli/commands/status.js +1 -70
- package/dist/cli/commands/sync.js +1 -202
- package/dist/cli/commands/team.js +1 -142
- package/dist/cli/index.js +1 -87
- package/dist/config/manager.js +1 -372
- package/dist/db/database.d.ts +36 -0
- package/dist/db/database.js +1 -1400
- package/dist/embedding/e5-provider.js +1 -147
- package/dist/embedding/index.js +1 -34
- package/dist/embedding/local-provider.js +1 -157
- package/dist/embedding/openai-provider.js +1 -92
- package/dist/embedding/quantization.js +1 -89
- package/dist/extraction/dedup-manager.js +1 -161
- package/dist/extraction/emotion-filter.js +1 -33
- package/dist/extraction/extractor.d.ts +0 -3
- package/dist/extraction/extractor.js +1 -648
- package/dist/extraction/file-reference.js +1 -77
- package/dist/extraction/filter.js +1 -86
- package/dist/extraction/scorer.js +1 -142
- package/dist/extraction/similarity.js +1 -85
- package/dist/hooks/client-factory.js +1 -44
- package/dist/hooks/post-tool-use.js +1 -518
- package/dist/hooks/pre-compact.js +1 -209
- package/dist/hooks/session-end.js +1 -633
- package/dist/hooks/session-start.js +1 -549
- package/dist/hooks/shared.js +1 -110
- package/dist/hooks/stop.d.ts +21 -0
- package/dist/hooks/stop.js +1 -0
- package/dist/hooks/user-prompt-submit.js +1 -316
- package/dist/i18n/index.js +1 -2
- package/dist/i18n/messages.js +1 -150
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -43
- package/dist/lifecycle/cleanup-scheduler.js +1 -137
- package/dist/lifecycle/cleanup.d.ts +1 -0
- package/dist/lifecycle/cleanup.js +1 -116
- package/dist/lifecycle/consolidation.d.ts +22 -0
- package/dist/lifecycle/consolidation.js +1 -0
- package/dist/lifecycle/index.d.ts +2 -0
- package/dist/lifecycle/index.js +1 -13
- package/dist/lifecycle/injection-flush.d.ts +24 -0
- package/dist/lifecycle/injection-flush.js +1 -0
- package/dist/lifecycle/quality-scorer.d.ts +5 -6
- package/dist/lifecycle/quality-scorer.js +1 -46
- package/dist/lifecycle/tiering.js +1 -246
- package/dist/llm/client.js +1 -226
- package/dist/llm/index.js +1 -5
- package/dist/proficiency/actr-engine.js +1 -106
- package/dist/proficiency/detection.js +1 -77
- package/dist/proficiency/index.js +1 -9
- package/dist/proficiency/tracker.js +1 -173
- package/dist/proficiency/types.js +1 -8
- package/dist/providers/adapters.js +1 -140
- package/dist/providers/detector.js +1 -57
- package/dist/search/adaptive-router.js +1 -93
- package/dist/search/index.js +1 -9
- package/dist/search/ranker.js +1 -171
- package/dist/search/reranker.js +1 -155
- package/dist/session/parser.js +1 -130
- package/dist/skill/evaluator.js +1 -509
- package/dist/skill/index.js +1 -7
- package/dist/skill/types.js +1 -7
- package/dist/sync/client.d.ts +7 -0
- package/dist/sync/client.js +1 -597
- package/dist/sync/encryption.js +1 -203
- package/dist/sync/index.js +1 -12
- package/dist/sync/queue.js +1 -214
- package/dist/sync/scheduler.js +1 -140
- package/dist/sync/synchronizer.js +1 -241
- package/dist/sync/team-synchronizer.js +1 -204
- package/dist/sync/vector-clock.js +1 -70
- package/dist/types/index.d.ts +13 -1
- package/dist/types/index.js +1 -132
- package/dist/utils/keychain.js +1 -170
- package/dist/utils/logger.js +1 -128
- package/package.json +15 -10
- package/dist/a2a/client.d.ts.map +0 -1
- package/dist/a2a/client.js.map +0 -1
- package/dist/a2a/discovery.d.ts.map +0 -1
- package/dist/a2a/discovery.js.map +0 -1
- package/dist/a2a/index.d.ts.map +0 -1
- package/dist/a2a/index.js.map +0 -1
- package/dist/a2a/types.d.ts.map +0 -1
- package/dist/a2a/types.js.map +0 -1
- package/dist/adapters/anthropic.d.ts.map +0 -1
- package/dist/adapters/anthropic.js.map +0 -1
- package/dist/chunking/chunker.d.ts.map +0 -1
- package/dist/chunking/chunker.js.map +0 -1
- package/dist/claude/sync.d.ts.map +0 -1
- package/dist/claude/sync.js.map +0 -1
- package/dist/cli/commands/add.d.ts.map +0 -1
- package/dist/cli/commands/add.js.map +0 -1
- package/dist/cli/commands/claude-sync.d.ts.map +0 -1
- package/dist/cli/commands/claude-sync.js.map +0 -1
- package/dist/cli/commands/cleanup.d.ts.map +0 -1
- package/dist/cli/commands/cleanup.js.map +0 -1
- package/dist/cli/commands/config.d.ts.map +0 -1
- package/dist/cli/commands/config.js.map +0 -1
- package/dist/cli/commands/edit.d.ts.map +0 -1
- package/dist/cli/commands/edit.js.map +0 -1
- package/dist/cli/commands/embed.d.ts.map +0 -1
- package/dist/cli/commands/embed.js.map +0 -1
- package/dist/cli/commands/extract.d.ts.map +0 -1
- package/dist/cli/commands/extract.js.map +0 -1
- package/dist/cli/commands/health.d.ts.map +0 -1
- package/dist/cli/commands/health.js.map +0 -1
- package/dist/cli/commands/list.d.ts.map +0 -1
- package/dist/cli/commands/list.js.map +0 -1
- package/dist/cli/commands/migrate-chunks.d.ts.map +0 -1
- package/dist/cli/commands/migrate-chunks.js.map +0 -1
- package/dist/cli/commands/migrate-file-refs.d.ts.map +0 -1
- package/dist/cli/commands/migrate-file-refs.js.map +0 -1
- package/dist/cli/commands/proficiency.d.ts.map +0 -1
- package/dist/cli/commands/proficiency.js.map +0 -1
- package/dist/cli/commands/rm.d.ts.map +0 -1
- package/dist/cli/commands/rm.js.map +0 -1
- package/dist/cli/commands/search.d.ts.map +0 -1
- package/dist/cli/commands/search.js.map +0 -1
- package/dist/cli/commands/setup-wizard.d.ts.map +0 -1
- package/dist/cli/commands/setup-wizard.js.map +0 -1
- package/dist/cli/commands/setup.d.ts.map +0 -1
- package/dist/cli/commands/setup.js.map +0 -1
- package/dist/cli/commands/skill.d.ts.map +0 -1
- package/dist/cli/commands/skill.js.map +0 -1
- package/dist/cli/commands/status.d.ts.map +0 -1
- package/dist/cli/commands/status.js.map +0 -1
- package/dist/cli/commands/sync.d.ts.map +0 -1
- package/dist/cli/commands/sync.js.map +0 -1
- package/dist/cli/commands/team.d.ts.map +0 -1
- package/dist/cli/commands/team.js.map +0 -1
- package/dist/cli/index.d.ts.map +0 -1
- package/dist/cli/index.js.map +0 -1
- package/dist/config/manager.d.ts.map +0 -1
- package/dist/config/manager.js.map +0 -1
- package/dist/db/database.d.ts.map +0 -1
- package/dist/db/database.js.map +0 -1
- package/dist/embedding/e5-provider.d.ts.map +0 -1
- package/dist/embedding/e5-provider.js.map +0 -1
- package/dist/embedding/index.d.ts.map +0 -1
- package/dist/embedding/index.js.map +0 -1
- package/dist/embedding/local-provider.d.ts.map +0 -1
- package/dist/embedding/local-provider.js.map +0 -1
- package/dist/embedding/openai-provider.d.ts.map +0 -1
- package/dist/embedding/openai-provider.js.map +0 -1
- package/dist/embedding/quantization.d.ts.map +0 -1
- package/dist/embedding/quantization.js.map +0 -1
- package/dist/extraction/dedup-manager.d.ts.map +0 -1
- package/dist/extraction/dedup-manager.js.map +0 -1
- package/dist/extraction/emotion-filter.d.ts.map +0 -1
- package/dist/extraction/emotion-filter.js.map +0 -1
- package/dist/extraction/extractor.d.ts.map +0 -1
- package/dist/extraction/extractor.js.map +0 -1
- package/dist/extraction/file-reference.d.ts.map +0 -1
- package/dist/extraction/file-reference.js.map +0 -1
- package/dist/extraction/filter.d.ts.map +0 -1
- package/dist/extraction/filter.js.map +0 -1
- package/dist/extraction/scorer.d.ts.map +0 -1
- package/dist/extraction/scorer.js.map +0 -1
- package/dist/extraction/similarity.d.ts.map +0 -1
- package/dist/extraction/similarity.js.map +0 -1
- package/dist/hooks/client-factory.d.ts.map +0 -1
- package/dist/hooks/client-factory.js.map +0 -1
- package/dist/hooks/post-tool-use.d.ts.map +0 -1
- package/dist/hooks/post-tool-use.js.map +0 -1
- package/dist/hooks/pre-compact.d.ts.map +0 -1
- package/dist/hooks/pre-compact.js.map +0 -1
- package/dist/hooks/session-end.d.ts.map +0 -1
- package/dist/hooks/session-end.js.map +0 -1
- package/dist/hooks/session-start.d.ts.map +0 -1
- package/dist/hooks/session-start.js.map +0 -1
- package/dist/hooks/shared.d.ts.map +0 -1
- package/dist/hooks/shared.js.map +0 -1
- package/dist/hooks/user-prompt-submit.d.ts.map +0 -1
- package/dist/hooks/user-prompt-submit.js.map +0 -1
- package/dist/i18n/index.d.ts.map +0 -1
- package/dist/i18n/index.js.map +0 -1
- package/dist/i18n/messages.d.ts.map +0 -1
- package/dist/i18n/messages.js.map +0 -1
- package/dist/index.d.ts.map +0 -1
- package/dist/index.js.map +0 -1
- package/dist/lifecycle/cleanup-scheduler.d.ts.map +0 -1
- package/dist/lifecycle/cleanup-scheduler.js.map +0 -1
- package/dist/lifecycle/cleanup.d.ts.map +0 -1
- package/dist/lifecycle/cleanup.js.map +0 -1
- package/dist/lifecycle/index.d.ts.map +0 -1
- package/dist/lifecycle/index.js.map +0 -1
- package/dist/lifecycle/quality-scorer.d.ts.map +0 -1
- package/dist/lifecycle/quality-scorer.js.map +0 -1
- package/dist/lifecycle/tiering.d.ts.map +0 -1
- package/dist/lifecycle/tiering.js.map +0 -1
- package/dist/llm/client.d.ts.map +0 -1
- package/dist/llm/client.js.map +0 -1
- package/dist/llm/index.d.ts.map +0 -1
- package/dist/llm/index.js.map +0 -1
- package/dist/proficiency/actr-engine.d.ts.map +0 -1
- package/dist/proficiency/actr-engine.js.map +0 -1
- package/dist/proficiency/detection.d.ts.map +0 -1
- package/dist/proficiency/detection.js.map +0 -1
- package/dist/proficiency/index.d.ts.map +0 -1
- package/dist/proficiency/index.js.map +0 -1
- package/dist/proficiency/tracker.d.ts.map +0 -1
- package/dist/proficiency/tracker.js.map +0 -1
- package/dist/proficiency/types.d.ts.map +0 -1
- package/dist/proficiency/types.js.map +0 -1
- package/dist/providers/adapters.d.ts.map +0 -1
- package/dist/providers/adapters.js.map +0 -1
- package/dist/providers/detector.d.ts.map +0 -1
- package/dist/providers/detector.js.map +0 -1
- package/dist/search/adaptive-router.d.ts.map +0 -1
- package/dist/search/adaptive-router.js.map +0 -1
- package/dist/search/index.d.ts.map +0 -1
- package/dist/search/index.js.map +0 -1
- package/dist/search/ranker.d.ts.map +0 -1
- package/dist/search/ranker.js.map +0 -1
- package/dist/search/reranker.d.ts.map +0 -1
- package/dist/search/reranker.js.map +0 -1
- package/dist/session/parser.d.ts.map +0 -1
- package/dist/session/parser.js.map +0 -1
- package/dist/skill/evaluator.d.ts.map +0 -1
- package/dist/skill/evaluator.js.map +0 -1
- package/dist/skill/index.d.ts.map +0 -1
- package/dist/skill/index.js.map +0 -1
- package/dist/skill/types.d.ts.map +0 -1
- package/dist/skill/types.js.map +0 -1
- package/dist/sync/client.d.ts.map +0 -1
- package/dist/sync/client.js.map +0 -1
- package/dist/sync/encryption.d.ts.map +0 -1
- package/dist/sync/encryption.js.map +0 -1
- package/dist/sync/index.d.ts.map +0 -1
- package/dist/sync/index.js.map +0 -1
- package/dist/sync/queue.d.ts.map +0 -1
- package/dist/sync/queue.js.map +0 -1
- package/dist/sync/scheduler.d.ts.map +0 -1
- package/dist/sync/scheduler.js.map +0 -1
- package/dist/sync/synchronizer.d.ts.map +0 -1
- package/dist/sync/synchronizer.js.map +0 -1
- package/dist/sync/team-synchronizer.d.ts.map +0 -1
- package/dist/sync/team-synchronizer.js.map +0 -1
- package/dist/sync/vector-clock.d.ts.map +0 -1
- package/dist/sync/vector-clock.js.map +0 -1
- package/dist/types/index.d.ts.map +0 -1
- package/dist/types/index.js.map +0 -1
- package/dist/utils/keychain.d.ts.map +0 -1
- package/dist/utils/keychain.js.map +0 -1
- package/dist/utils/logger.d.ts.map +0 -1
- package/dist/utils/logger.js.map +0 -1
|
@@ -1,648 +1 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Memory Extractor
|
|
3
|
-
*
|
|
4
|
-
* 세션 메시지에서 의미 있는 메모리를 추출합니다.
|
|
5
|
-
* 카테고리: error_solution, code_pattern, decision, context, convention
|
|
6
|
-
*/
|
|
7
|
-
import { filterSensitiveInfo } from './filter.js';
|
|
8
|
-
import { deduplicateByContent } from './similarity.js';
|
|
9
|
-
const STRONG_DECISION_KEYWORDS = [
|
|
10
|
-
'chose', 'decided', 'opted for', 'instead of', 'rather than',
|
|
11
|
-
'선택했', '결정했', '대신',
|
|
12
|
-
];
|
|
13
|
-
const WEAK_DECISION_KEYWORDS = [
|
|
14
|
-
'approach', 'strategy', 'decision', '방식', '접근', '전략',
|
|
15
|
-
'선택', '결정',
|
|
16
|
-
];
|
|
17
|
-
const CONVENTION_KEYWORDS = [
|
|
18
|
-
'선호', '항상', '무조건', '습관', '규칙',
|
|
19
|
-
'prefer', 'always', 'never', 'convention', 'rule',
|
|
20
|
-
'style', 'pattern',
|
|
21
|
-
];
|
|
22
|
-
const ERROR_INDICATORS = [
|
|
23
|
-
'error', 'Error', 'ERROR',
|
|
24
|
-
'exception', 'Exception',
|
|
25
|
-
'failed', 'Failed', 'FAILED',
|
|
26
|
-
'traceback', 'Traceback',
|
|
27
|
-
'stack trace',
|
|
28
|
-
'에러', '오류', '실패',
|
|
29
|
-
];
|
|
30
|
-
/**
|
|
31
|
-
* 노이즈 콘텐츠 패턴 — 메모리로 저장하면 안 되는 시스템 메시지
|
|
32
|
-
*/
|
|
33
|
-
const NOISE_PATTERNS = [
|
|
34
|
-
/This session is being continued from a previous conversation/,
|
|
35
|
-
/Base directory for this skill:/,
|
|
36
|
-
/Tool use was interrupted/,
|
|
37
|
-
/<system-reminder>/,
|
|
38
|
-
/pre-push hook/i,
|
|
39
|
-
/A plan file exists from plan mode at:/,
|
|
40
|
-
/Running backend tests/,
|
|
41
|
-
/The following skills? (?:are|were) (?:available|invoked)/,
|
|
42
|
-
/Called the (?:Read|Write|Edit|Glob|Grep|Bash) tool with the following input/,
|
|
43
|
-
/Result of calling the \w+ tool/,
|
|
44
|
-
// Fix 7: Additional noise patterns for low-value tool output memories
|
|
45
|
-
/^Tool: (?:Edit|Read|Write|Glob|Grep|Bash)\b/,
|
|
46
|
-
/^Tool use was rejected/,
|
|
47
|
-
/^File (?:created|updated|written) successfully/,
|
|
48
|
-
/^No files found$/,
|
|
49
|
-
/^The file .+ has been (?:updated|created) successfully/,
|
|
50
|
-
// Sprint 1-1: Additional patterns for tool call logs missed by Fix 7
|
|
51
|
-
/^Tool: (?:Edit|Read|Write|Glob|Grep|Bash|MCP)/i,
|
|
52
|
-
/^(?:Called|Result of calling) the \w+ tool/i,
|
|
53
|
-
/^File (?:created|modified|deleted):/i,
|
|
54
|
-
/^\d+ (?:file|files) (?:found|matched|updated|deleted)/i,
|
|
55
|
-
/^(?:Read|Edit|Write|Glob|Grep|Bash) tool/i,
|
|
56
|
-
/^Searching for /i,
|
|
57
|
-
/^Found \d+ (?:result|results|match|matches)/i,
|
|
58
|
-
// Production fix: File path metadata noise (48% of memories were these patterns)
|
|
59
|
-
/^File: \//,
|
|
60
|
-
/^\{"filePath"/,
|
|
61
|
-
/^\{"file_path"/,
|
|
62
|
-
/\/var\/folders\//,
|
|
63
|
-
/\/tmp\//,
|
|
64
|
-
];
|
|
65
|
-
/**
|
|
66
|
-
* 노이즈 메모리 제목 패턴 — 추출된 메모리 제목이 이 패턴과 일치하면 저장 금지
|
|
67
|
-
* content에서 파생된 제목 또는 content 자체의 첫 줄이 여기에 해당하면 필터링
|
|
68
|
-
*/
|
|
69
|
-
const NOISE_TITLE_PATTERNS = [
|
|
70
|
-
/^Tool: /i,
|
|
71
|
-
/^File (?:created|updated|deleted|modified)/i,
|
|
72
|
-
/^(?:Read|Edit|Write|Glob|Grep|Bash) /i,
|
|
73
|
-
/^Result of /i,
|
|
74
|
-
// Note: [Error] is intentionally excluded — it's a valid error_solution format generated by extractErrorSolutions()
|
|
75
|
-
/^\[(?:Tool|System)\]/i,
|
|
76
|
-
/^(?:Called|Calling) the \w+ tool/i,
|
|
77
|
-
];
|
|
78
|
-
/**
|
|
79
|
-
* 메시지가 노이즈인지 판별
|
|
80
|
-
*/
|
|
81
|
-
export function isNoiseMessage(text) {
|
|
82
|
-
return NOISE_PATTERNS.some((pattern) => pattern.test(text));
|
|
83
|
-
}
|
|
84
|
-
/**
|
|
85
|
-
* 세션 메시지에서 메모리 추출
|
|
86
|
-
*/
|
|
87
|
-
export function extractMemories(messages, projectPath) {
|
|
88
|
-
const startTime = Date.now();
|
|
89
|
-
const memories = [];
|
|
90
|
-
let filteredSensitive = 0;
|
|
91
|
-
// 0. 노이즈 메시지 필터링
|
|
92
|
-
const cleanMessages = messages.filter((msg) => {
|
|
93
|
-
const text = getFullText(msg);
|
|
94
|
-
return !isNoiseMessage(text);
|
|
95
|
-
});
|
|
96
|
-
// 1. error_solution 추출
|
|
97
|
-
const errorSolutions = extractErrorSolutions(cleanMessages, projectPath);
|
|
98
|
-
memories.push(...errorSolutions);
|
|
99
|
-
// 2. code_pattern 추출
|
|
100
|
-
const codePatterns = extractCodePatterns(cleanMessages, projectPath);
|
|
101
|
-
memories.push(...codePatterns);
|
|
102
|
-
// 3. decision 추출
|
|
103
|
-
const decisions = extractDecisions(cleanMessages, projectPath);
|
|
104
|
-
memories.push(...decisions);
|
|
105
|
-
// 4. context 추출
|
|
106
|
-
const contexts = extractContexts(cleanMessages, projectPath);
|
|
107
|
-
memories.push(...contexts);
|
|
108
|
-
// 5. convention 추출
|
|
109
|
-
const conventions = extractConventions(cleanMessages, projectPath);
|
|
110
|
-
memories.push(...conventions);
|
|
111
|
-
// 6. learning 추출 (Issue 5 Fix)
|
|
112
|
-
const learnings = extractLearnings(cleanMessages, projectPath);
|
|
113
|
-
memories.push(...learnings);
|
|
114
|
-
// 민감 정보 필터링
|
|
115
|
-
for (let i = 0; i < memories.length; i++) {
|
|
116
|
-
const result = filterSensitiveInfo(memories[i].content);
|
|
117
|
-
if (result.matchCount > 0) {
|
|
118
|
-
memories[i] = { ...memories[i], content: result.filtered };
|
|
119
|
-
filteredSensitive += result.matchCount;
|
|
120
|
-
}
|
|
121
|
-
}
|
|
122
|
-
// Fix 7: Filter out very short content (< 50 chars) — too low value to store
|
|
123
|
-
const meaningful = memories.filter((m) => m.content.length >= 50);
|
|
124
|
-
// Sprint 1-1: Filter by noise title patterns — reject if first line matches tool/file log patterns
|
|
125
|
-
const titleFiltered = meaningful.filter((m) => {
|
|
126
|
-
const firstLine = m.content.split('\n')[0].trim();
|
|
127
|
-
return !NOISE_TITLE_PATTERNS.some((pattern) => pattern.test(firstLine));
|
|
128
|
-
});
|
|
129
|
-
// 중복 제거 (동일 콘텐츠)
|
|
130
|
-
const unique = deduplicateMemories(titleFiltered);
|
|
131
|
-
const sessionInfo = {
|
|
132
|
-
sessionId: cleanMessages[0]?.uuid?.split('-')[0] ?? 'unknown',
|
|
133
|
-
projectPath,
|
|
134
|
-
filePath: '',
|
|
135
|
-
messageCount: cleanMessages.length,
|
|
136
|
-
startTime: cleanMessages[0]?.timestamp,
|
|
137
|
-
endTime: cleanMessages[cleanMessages.length - 1]?.timestamp,
|
|
138
|
-
sizeBytes: 0,
|
|
139
|
-
modifiedAt: Date.now(),
|
|
140
|
-
};
|
|
141
|
-
return {
|
|
142
|
-
memories: unique,
|
|
143
|
-
sessionInfo,
|
|
144
|
-
stats: {
|
|
145
|
-
totalMessages: messages.length,
|
|
146
|
-
extractedPatterns: unique.length,
|
|
147
|
-
filteredSensitive,
|
|
148
|
-
processingTimeMs: Date.now() - startTime,
|
|
149
|
-
},
|
|
150
|
-
};
|
|
151
|
-
}
|
|
152
|
-
/**
|
|
153
|
-
* 에러 → 해결 쌍 추출
|
|
154
|
-
*/
|
|
155
|
-
function extractErrorSolutions(messages, projectPath) {
|
|
156
|
-
const results = [];
|
|
157
|
-
for (let i = 0; i < messages.length; i++) {
|
|
158
|
-
const msg = messages[i];
|
|
159
|
-
const text = getFullText(msg);
|
|
160
|
-
// Issue 3 Fix: Check if error indicator is in natural language context
|
|
161
|
-
const hasError = ERROR_INDICATORS.some((ind) => text.includes(ind));
|
|
162
|
-
if (!hasError)
|
|
163
|
-
continue;
|
|
164
|
-
// Skip if message is mostly code (>50% lines are indented or code keywords)
|
|
165
|
-
const lines = text.split('\n');
|
|
166
|
-
const codeLines = lines.filter((line) => {
|
|
167
|
-
const trimmed = line.trim();
|
|
168
|
-
return line.startsWith(' ') || line.startsWith('\t') ||
|
|
169
|
-
trimmed.startsWith('import ') || trimmed.startsWith('function ') ||
|
|
170
|
-
trimmed.startsWith('class ') || trimmed.startsWith('const ') ||
|
|
171
|
-
trimmed.startsWith('let ') || trimmed.startsWith('var ') ||
|
|
172
|
-
trimmed.startsWith('def ') || trimmed.startsWith('if ') ||
|
|
173
|
-
trimmed.startsWith('for ') || trimmed.startsWith('return ');
|
|
174
|
-
}).length;
|
|
175
|
-
if (lines.length > 0 && (codeLines / lines.length) > 0.5)
|
|
176
|
-
continue;
|
|
177
|
-
// Error message should be at least 20 chars (filter single-word matches)
|
|
178
|
-
const errorContext = text.split('\n').find((line) => ERROR_INDICATORS.some((ind) => line.includes(ind)));
|
|
179
|
-
if (!errorContext || errorContext.trim().length < 20)
|
|
180
|
-
continue;
|
|
181
|
-
// 다음 assistant 메시지에서 해결 과정 찾기
|
|
182
|
-
for (let j = i + 1; j < Math.min(i + 5, messages.length); j++) {
|
|
183
|
-
const next = messages[j];
|
|
184
|
-
if (next.type !== 'assistant')
|
|
185
|
-
continue;
|
|
186
|
-
const nextText = getFullText(next);
|
|
187
|
-
const hasToolUse = Array.isArray(next.message.content) &&
|
|
188
|
-
next.message.content.some((b) => b.type === 'tool_use');
|
|
189
|
-
if (hasToolUse || nextText.length > 50) {
|
|
190
|
-
const errorSnippet = text.slice(0, 300);
|
|
191
|
-
const solutionSnippet = nextText.slice(0, 500);
|
|
192
|
-
// Verify solution relevance
|
|
193
|
-
if (!hasToolUse && !verifySolutionRelevance(errorSnippet, solutionSnippet)) {
|
|
194
|
-
continue;
|
|
195
|
-
}
|
|
196
|
-
results.push({
|
|
197
|
-
content: `[Error] ${errorSnippet}\n\n[Solution] ${solutionSnippet}`,
|
|
198
|
-
category: 'error_solution',
|
|
199
|
-
tier: 'episodic',
|
|
200
|
-
tags: extractTags(text, 'error'),
|
|
201
|
-
projectPath,
|
|
202
|
-
});
|
|
203
|
-
break;
|
|
204
|
-
}
|
|
205
|
-
}
|
|
206
|
-
}
|
|
207
|
-
return results;
|
|
208
|
-
}
|
|
209
|
-
/**
|
|
210
|
-
* Error-Solution 페어링 관련성 검증
|
|
211
|
-
*/
|
|
212
|
-
function verifySolutionRelevance(errorText, solutionText) {
|
|
213
|
-
const errorWords = new Set(errorText.toLowerCase().split(/\W+/).filter((w) => w.length > 3));
|
|
214
|
-
const solutionWords = new Set(solutionText.toLowerCase().split(/\W+/).filter((w) => w.length > 3));
|
|
215
|
-
const shared = [...errorWords].filter((w) => solutionWords.has(w));
|
|
216
|
-
// 공유 키워드 2개 이상 필요
|
|
217
|
-
if (shared.length < 2)
|
|
218
|
-
return false;
|
|
219
|
-
// 순수 에러 메시지(스택 트레이스만)면 솔루션 아님
|
|
220
|
-
if (isPureErrorMessage(solutionText))
|
|
221
|
-
return false;
|
|
222
|
-
return true;
|
|
223
|
-
}
|
|
224
|
-
/**
|
|
225
|
-
* 순수 에러 메시지인지 판별 (솔루션 키워드 없이 스택 트레이스만 포함)
|
|
226
|
-
*/
|
|
227
|
-
function isPureErrorMessage(text) {
|
|
228
|
-
const lines = text.split('\n').filter((l) => l.trim());
|
|
229
|
-
if (lines.length === 0)
|
|
230
|
-
return true;
|
|
231
|
-
// 스택 트레이스 패턴
|
|
232
|
-
const stackTraceLines = lines.filter((l) => /^\s*(at |File |Traceback| File "| raise |>>> )/.test(l));
|
|
233
|
-
// 전체 줄의 70% 이상이 스택 트레이스면 순수 에러
|
|
234
|
-
if (stackTraceLines.length / lines.length > 0.7)
|
|
235
|
-
return true;
|
|
236
|
-
// 솔루션 키워드가 하나라도 있으면 에러가 아님
|
|
237
|
-
const SOLUTION_INDICATORS = [
|
|
238
|
-
'fix', 'solve', 'resolve', 'try', 'use', 'change', 'update', 'install',
|
|
239
|
-
'instead', 'should', 'need to', 'make sure', 'ensure',
|
|
240
|
-
'해결', '수정', '변경', '설치', '시도', '사용',
|
|
241
|
-
];
|
|
242
|
-
const lowerText = text.toLowerCase();
|
|
243
|
-
return !SOLUTION_INDICATORS.some((kw) => lowerText.includes(kw));
|
|
244
|
-
}
|
|
245
|
-
/**
|
|
246
|
-
* 반복 사용 도구 패턴 + 파일 수정 패턴 추출
|
|
247
|
-
*/
|
|
248
|
-
function extractCodePatterns(messages, projectPath) {
|
|
249
|
-
const toolCounts = new Map();
|
|
250
|
-
// Issue 1 Fix: Exclude trivial tools from pattern extraction
|
|
251
|
-
const trivialTools = ['Read', 'Glob', 'Grep', 'WebFetch', 'WebSearch'];
|
|
252
|
-
// 파일 수정 패턴 추적
|
|
253
|
-
const fileModifications = new Map(); // 확장자별 수정 횟수
|
|
254
|
-
const dirModifications = new Map(); // 디렉토리별 수정 횟수
|
|
255
|
-
for (const msg of messages) {
|
|
256
|
-
if (!Array.isArray(msg.message.content))
|
|
257
|
-
continue;
|
|
258
|
-
for (const block of msg.message.content) {
|
|
259
|
-
if (block.type !== 'tool_use' || !block.name)
|
|
260
|
-
continue;
|
|
261
|
-
// 파일 수정 패턴 추적 (Write/Edit)
|
|
262
|
-
if ((block.name === 'Write' || block.name === 'Edit') && block.input) {
|
|
263
|
-
const filePath = block.input.file_path;
|
|
264
|
-
if (filePath) {
|
|
265
|
-
const lastDot = filePath.lastIndexOf('.');
|
|
266
|
-
const ext = lastDot >= 0 ? filePath.slice(lastDot) : '';
|
|
267
|
-
const parts = filePath.split('/');
|
|
268
|
-
const dir = parts.slice(-3, -1).join('/');
|
|
269
|
-
if (ext)
|
|
270
|
-
fileModifications.set(ext, (fileModifications.get(ext) || 0) + 1);
|
|
271
|
-
if (dir)
|
|
272
|
-
dirModifications.set(dir, (dirModifications.get(dir) || 0) + 1);
|
|
273
|
-
}
|
|
274
|
-
}
|
|
275
|
-
// Skip trivial tools
|
|
276
|
-
if (trivialTools.includes(block.name))
|
|
277
|
-
continue;
|
|
278
|
-
const entry = toolCounts.get(block.name) ?? { count: 0, samples: [] };
|
|
279
|
-
entry.count++;
|
|
280
|
-
if (entry.samples.length < 3 && block.input) {
|
|
281
|
-
// 키워드 기반 샘플링: 의미있는 부분 우선 추출
|
|
282
|
-
const inputStr = JSON.stringify(block.input);
|
|
283
|
-
if (inputStr.length <= 200) {
|
|
284
|
-
entry.samples.push(inputStr);
|
|
285
|
-
}
|
|
286
|
-
else {
|
|
287
|
-
const keywords = ['error', 'fix', 'solution', 'pattern', 'config', 'import', 'export', 'function', 'class'];
|
|
288
|
-
const lowerInput = inputStr.toLowerCase();
|
|
289
|
-
let bestStart = 0;
|
|
290
|
-
for (const kw of keywords) {
|
|
291
|
-
const idx = lowerInput.indexOf(kw);
|
|
292
|
-
if (idx >= 0) {
|
|
293
|
-
bestStart = Math.max(0, idx - 50);
|
|
294
|
-
break;
|
|
295
|
-
}
|
|
296
|
-
}
|
|
297
|
-
entry.samples.push(inputStr.slice(bestStart, bestStart + 200));
|
|
298
|
-
}
|
|
299
|
-
}
|
|
300
|
-
toolCounts.set(block.name, entry);
|
|
301
|
-
}
|
|
302
|
-
}
|
|
303
|
-
const results = [];
|
|
304
|
-
// 기존: 도구 사용 빈도 패턴
|
|
305
|
-
for (const [toolName, data] of toolCounts) {
|
|
306
|
-
// Issue 1 Fix: Increase threshold from 3 to 5
|
|
307
|
-
if (data.count < 5)
|
|
308
|
-
continue;
|
|
309
|
-
results.push({
|
|
310
|
-
content: `Tool "${toolName}" used ${data.count} times. Samples:\n${data.samples.join('\n')}`,
|
|
311
|
-
category: 'code_pattern',
|
|
312
|
-
tier: 'semantic',
|
|
313
|
-
tags: [toolName, 'pattern', 'tool-usage'],
|
|
314
|
-
projectPath,
|
|
315
|
-
});
|
|
316
|
-
}
|
|
317
|
-
// 신규: 파일 수정 패턴 (3개 이상 수정된 확장자)
|
|
318
|
-
if (fileModifications.size > 0) {
|
|
319
|
-
const topExtensions = [...fileModifications.entries()]
|
|
320
|
-
.filter(([, count]) => count >= 3)
|
|
321
|
-
.sort((a, b) => b[1] - a[1])
|
|
322
|
-
.slice(0, 5);
|
|
323
|
-
if (topExtensions.length > 0) {
|
|
324
|
-
const topDirs = [...dirModifications.entries()]
|
|
325
|
-
.sort((a, b) => b[1] - a[1])
|
|
326
|
-
.slice(0, 3);
|
|
327
|
-
results.push({
|
|
328
|
-
content: `Code modification pattern: ${topExtensions.map(([ext, n]) => `${ext}(${n})`).join(', ')}. ` +
|
|
329
|
-
`Directories: ${topDirs.map(([dir, n]) => `${dir}(${n})`).join(', ')}`,
|
|
330
|
-
category: 'code_pattern',
|
|
331
|
-
tier: 'semantic',
|
|
332
|
-
tags: ['code-pattern', 'file-modification', ...topExtensions.map(([ext]) => ext.replace('.', ''))],
|
|
333
|
-
projectPath,
|
|
334
|
-
});
|
|
335
|
-
}
|
|
336
|
-
}
|
|
337
|
-
return results;
|
|
338
|
-
}
|
|
339
|
-
/**
|
|
340
|
-
* 의사 결정 메시지 추출
|
|
341
|
-
*/
|
|
342
|
-
function extractDecisions(messages, projectPath) {
|
|
343
|
-
const results = [];
|
|
344
|
-
for (const msg of messages) {
|
|
345
|
-
const text = getFullText(msg);
|
|
346
|
-
if (text.length < 50)
|
|
347
|
-
continue; // minimum 50 chars for meaningful decisions
|
|
348
|
-
// Issue 2 Fix: Skip git diffs, changelogs, version patterns
|
|
349
|
-
if (text.startsWith('diff --git') ||
|
|
350
|
-
text.includes('CHANGELOG') ||
|
|
351
|
-
/v\d+\.\d+\.\d+/.test(text)) {
|
|
352
|
-
continue;
|
|
353
|
-
}
|
|
354
|
-
// Remove code blocks and check remaining text for keyword matching
|
|
355
|
-
const textWithoutCode = text.replace(/```[\s\S]*?```/g, '').trim();
|
|
356
|
-
if (!textWithoutCode)
|
|
357
|
-
continue;
|
|
358
|
-
const lowerText = textWithoutCode.toLowerCase();
|
|
359
|
-
// Strong keyword 1개 이상 OR Weak keyword 2개 이상
|
|
360
|
-
const strongCount = STRONG_DECISION_KEYWORDS.filter((kw) => lowerText.includes(kw.toLowerCase())).length;
|
|
361
|
-
const weakCount = WEAK_DECISION_KEYWORDS.filter((kw) => lowerText.includes(kw.toLowerCase())).length;
|
|
362
|
-
if (strongCount < 1 && weakCount < 2)
|
|
363
|
-
continue;
|
|
364
|
-
results.push({
|
|
365
|
-
content: textWithoutCode.slice(0, 800),
|
|
366
|
-
category: 'decision',
|
|
367
|
-
tier: 'semantic',
|
|
368
|
-
tags: extractTags(textWithoutCode, 'decision'),
|
|
369
|
-
projectPath,
|
|
370
|
-
});
|
|
371
|
-
}
|
|
372
|
-
return results;
|
|
373
|
-
}
|
|
374
|
-
const CONTEXT_KEYWORDS = [
|
|
375
|
-
'setup', 'install', 'configure', 'environment', 'initialization',
|
|
376
|
-
'설정', '설치', '환경설정', '초기화',
|
|
377
|
-
];
|
|
378
|
-
const LEARNING_KEYWORDS = [
|
|
379
|
-
'learned', 'TIL', 'realized', 'understood', 'figured out', 'discovery', 'insight',
|
|
380
|
-
'배웠', '깨달', '발견', '알게 됐', '이해했',
|
|
381
|
-
];
|
|
382
|
-
/**
|
|
383
|
-
* 프로젝트 컨텍스트 추출 (첫 human/system 메시지)
|
|
384
|
-
*/
|
|
385
|
-
function extractContexts(messages, projectPath) {
|
|
386
|
-
const results = [];
|
|
387
|
-
for (const msg of messages) {
|
|
388
|
-
if (msg.type !== 'human' && msg.type !== 'system')
|
|
389
|
-
continue;
|
|
390
|
-
// Filter system prompts and CLAUDE.md injections
|
|
391
|
-
if (msg.message.role === 'system')
|
|
392
|
-
continue;
|
|
393
|
-
const text = getFullText(msg);
|
|
394
|
-
if (text.length < 50)
|
|
395
|
-
continue;
|
|
396
|
-
// Filter system-reminder blocks and large CLAUDE.md content
|
|
397
|
-
if (text.includes('<system-reminder>'))
|
|
398
|
-
continue;
|
|
399
|
-
if (text.includes('CLAUDE.md') && text.length > 500)
|
|
400
|
-
continue;
|
|
401
|
-
const lowerText = text.toLowerCase();
|
|
402
|
-
const matchedKeywords = CONTEXT_KEYWORDS.filter((kw) => lowerText.includes(kw.toLowerCase()));
|
|
403
|
-
const msgIndex = messages.indexOf(msg);
|
|
404
|
-
// 조건 강화: (1) 첫 3개 메시지, 또는 (2) context 키워드 2개 이상 동시 포함
|
|
405
|
-
if (msgIndex < 3 || matchedKeywords.length >= 2) {
|
|
406
|
-
results.push({
|
|
407
|
-
content: text.slice(0, 1000),
|
|
408
|
-
category: 'context',
|
|
409
|
-
tier: 'semantic',
|
|
410
|
-
tags: extractTags(text, 'context'),
|
|
411
|
-
projectPath,
|
|
412
|
-
});
|
|
413
|
-
}
|
|
414
|
-
}
|
|
415
|
-
return results;
|
|
416
|
-
}
|
|
417
|
-
/**
|
|
418
|
-
* 사용자 규칙/컨벤션 추출
|
|
419
|
-
*/
|
|
420
|
-
function extractConventions(messages, projectPath) {
|
|
421
|
-
const results = [];
|
|
422
|
-
for (const msg of messages) {
|
|
423
|
-
if (msg.type !== 'human' && msg.type !== 'assistant')
|
|
424
|
-
continue;
|
|
425
|
-
const text = getFullText(msg);
|
|
426
|
-
if (text.length < 20)
|
|
427
|
-
continue;
|
|
428
|
-
// assistant 메시지일 경우 규칙 제안 패턴 필수
|
|
429
|
-
if (msg.type === 'assistant') {
|
|
430
|
-
const hasRuleProposal = /(?:should|must|always|never|recommend|규칙|원칙|필수|금지)/i.test(text);
|
|
431
|
-
if (!hasRuleProposal)
|
|
432
|
-
continue;
|
|
433
|
-
}
|
|
434
|
-
const hasKeyword = CONVENTION_KEYWORDS.some((kw) => text.toLowerCase().includes(kw.toLowerCase()));
|
|
435
|
-
if (!hasKeyword)
|
|
436
|
-
continue;
|
|
437
|
-
results.push({
|
|
438
|
-
content: text.slice(0, 500),
|
|
439
|
-
category: 'convention',
|
|
440
|
-
tier: 'semantic',
|
|
441
|
-
tags: extractTags(text, 'convention'),
|
|
442
|
-
projectPath,
|
|
443
|
-
});
|
|
444
|
-
}
|
|
445
|
-
return results;
|
|
446
|
-
}
|
|
447
|
-
/**
|
|
448
|
-
* Issue 5 Fix: Learning/insight 추출
|
|
449
|
-
*/
|
|
450
|
-
function extractLearnings(messages, projectPath) {
|
|
451
|
-
const results = [];
|
|
452
|
-
for (const msg of messages) {
|
|
453
|
-
// Both human and assistant can express learnings
|
|
454
|
-
if (msg.type !== 'human' && msg.type !== 'assistant')
|
|
455
|
-
continue;
|
|
456
|
-
const text = getFullText(msg);
|
|
457
|
-
if (text.length < 30)
|
|
458
|
-
continue;
|
|
459
|
-
const hasKeyword = LEARNING_KEYWORDS.some((kw) => text.toLowerCase().includes(kw.toLowerCase()));
|
|
460
|
-
if (!hasKeyword)
|
|
461
|
-
continue;
|
|
462
|
-
results.push({
|
|
463
|
-
content: text.slice(0, 800),
|
|
464
|
-
category: 'learning',
|
|
465
|
-
tier: 'episodic', // Fresh learnings start as episodic
|
|
466
|
-
tags: extractTags(text, 'learning'),
|
|
467
|
-
projectPath,
|
|
468
|
-
});
|
|
469
|
-
}
|
|
470
|
-
return results;
|
|
471
|
-
}
|
|
472
|
-
/**
|
|
473
|
-
* 메시지에서 전체 텍스트 추출
|
|
474
|
-
*/
|
|
475
|
-
function getFullText(message) {
|
|
476
|
-
if (typeof message.message.content === 'string') {
|
|
477
|
-
return message.message.content;
|
|
478
|
-
}
|
|
479
|
-
return message.message.content
|
|
480
|
-
.map((block) => {
|
|
481
|
-
if (block.type === 'text' && block.text)
|
|
482
|
-
return block.text;
|
|
483
|
-
if (block.type === 'tool_result' && block.content)
|
|
484
|
-
return block.content;
|
|
485
|
-
return '';
|
|
486
|
-
})
|
|
487
|
-
.filter(Boolean)
|
|
488
|
-
.join('\n');
|
|
489
|
-
}
|
|
490
|
-
const TECH_NAMES = [
|
|
491
|
-
'react', 'vue', 'angular', 'typescript', 'javascript', 'python', 'java',
|
|
492
|
-
'postgresql', 'mysql', 'redis', 'docker', 'kubernetes', 'aws', 'gcp',
|
|
493
|
-
'fastapi', 'express', 'next.js', 'node.js', 'git', 'graphql', 'rest',
|
|
494
|
-
'webpack', 'vite', 'eslint', 'vitest', 'jest', 'playwright', 'sqlite',
|
|
495
|
-
];
|
|
496
|
-
const WORK_TYPES = [
|
|
497
|
-
'deploy', 'debug', 'refactor', 'test', 'review', 'optimize', 'migrate',
|
|
498
|
-
'setup', 'config', 'build', 'release', 'fix', 'implement', 'upgrade',
|
|
499
|
-
];
|
|
500
|
-
// P3-1: 모듈 레벨 Set 상수 — 함수 호출마다 배열 재생성 방지
|
|
501
|
-
const LOW_VALUE_EXTS = new Set(['md', 'txt', 'json', 'yml', 'yaml', 'xml', 'html', 'css']);
|
|
502
|
-
const MEANINGFUL_EXTS = new Set(['py', 'ts', 'tsx', 'js', 'jsx', 'java', 'go', 'rs', 'rb', 'swift', 'kt']);
|
|
503
|
-
/**
|
|
504
|
-
* 텍스트에서 자동 태그 추출
|
|
505
|
-
*/
|
|
506
|
-
function extractTags(text, category) {
|
|
507
|
-
const tags = [category];
|
|
508
|
-
// 파일 경로 추출 (최대 200자로 제한하여 catastrophic backtracking 방지)
|
|
509
|
-
const fileMatch = text.match(/[\w/.-]{1,200}\.\w{1,10}/g);
|
|
510
|
-
if (fileMatch) {
|
|
511
|
-
const extensions = new Set(fileMatch
|
|
512
|
-
.map((f) => f.split('.').pop())
|
|
513
|
-
.filter((ext) => ext.length <= 5 && ext.length > 1)
|
|
514
|
-
.filter((ext) => !/^\d+$/.test(ext))
|
|
515
|
-
.filter((ext) => !LOW_VALUE_EXTS.has(ext.toLowerCase()))
|
|
516
|
-
.filter((ext) => MEANINGFUL_EXTS.has(ext.toLowerCase())));
|
|
517
|
-
tags.push(...[...extensions].slice(0, 2));
|
|
518
|
-
}
|
|
519
|
-
const lowerText = text.toLowerCase();
|
|
520
|
-
// 기술명 자동 감지
|
|
521
|
-
for (const tech of TECH_NAMES) {
|
|
522
|
-
if (lowerText.includes(tech)) {
|
|
523
|
-
tags.push(tech);
|
|
524
|
-
}
|
|
525
|
-
}
|
|
526
|
-
// 작업 유형 자동 감지
|
|
527
|
-
for (const work of WORK_TYPES) {
|
|
528
|
-
if (lowerText.includes(work)) {
|
|
529
|
-
tags.push(work);
|
|
530
|
-
break; // 작업 유형은 1개만
|
|
531
|
-
}
|
|
532
|
-
}
|
|
533
|
-
// 태그 유효성 필터 + 최대 5개 (중복 제거 후)
|
|
534
|
-
return [...new Set(tags)]
|
|
535
|
-
.filter((t) => t.length >= 2 && !/^\d+$/.test(t))
|
|
536
|
-
.map((t) => t.toLowerCase())
|
|
537
|
-
.slice(0, 5);
|
|
538
|
-
}
|
|
539
|
-
/**
|
|
540
|
-
* 중복 메모리 제거 (콘텐츠 유사도 기반)
|
|
541
|
-
*/
|
|
542
|
-
function deduplicateMemories(memories) {
|
|
543
|
-
return deduplicateByContent(memories, 0.7);
|
|
544
|
-
}
|
|
545
|
-
// ============================================================
|
|
546
|
-
// LLM-enhanced extraction (async)
|
|
547
|
-
// ============================================================
|
|
548
|
-
const CLASSIFIABLE_CATEGORIES = [
|
|
549
|
-
'error_solution', 'code_pattern', 'decision', 'convention', 'project_knowledge', 'learning',
|
|
550
|
-
];
|
|
551
|
-
/**
|
|
552
|
-
* LLM 기반 보완 추출 — 패턴 매칭이 부족할 때 LLM으로 추가 메모리 추출
|
|
553
|
-
*/
|
|
554
|
-
async function _llmExtractSupplemental(messages, llmClient, projectPath) {
|
|
555
|
-
// 마지막 20개 메시지 텍스트 수집
|
|
556
|
-
const recentMessages = messages.slice(-20);
|
|
557
|
-
const conversationText = recentMessages
|
|
558
|
-
.map((m) => {
|
|
559
|
-
const role = m.type === 'human' ? 'User' : 'Assistant';
|
|
560
|
-
const text = getFullText(m).slice(0, 500);
|
|
561
|
-
return `[${role}]: ${text}`;
|
|
562
|
-
})
|
|
563
|
-
.filter((t) => t.length > 10)
|
|
564
|
-
.join('\n\n')
|
|
565
|
-
.slice(0, 6000);
|
|
566
|
-
if (!conversationText)
|
|
567
|
-
return [];
|
|
568
|
-
const exampleJson = '[{"category": "...", "content": "...", "tags": ["..."]}]';
|
|
569
|
-
const prompt = `다음 개발 대화에서 나중에 유용할 핵심 지식을 3~5개 추출하세요.\n각각 category(error_solution/code_pattern/decision/project_knowledge/convention), content, tags를 JSON 배열로 반환.\n\n대화:\n${conversationText}\n\nJSON 배열만 반환 (마크다운 코드 블록 없이):\n${exampleJson}`;
|
|
570
|
-
try {
|
|
571
|
-
const response = await llmClient.complete(prompt);
|
|
572
|
-
const cleaned = response.replace(/```(?:json)?\s*\n?([\s\S]*?)\n?```/g, '$1').trim();
|
|
573
|
-
const parsed = JSON.parse(cleaned);
|
|
574
|
-
if (!Array.isArray(parsed))
|
|
575
|
-
return [];
|
|
576
|
-
return parsed
|
|
577
|
-
.filter((item) => item.content &&
|
|
578
|
-
item.content.length >= 50 &&
|
|
579
|
-
CLASSIFIABLE_CATEGORIES.includes(item.category))
|
|
580
|
-
.map((item) => ({
|
|
581
|
-
content: item.content.slice(0, 800),
|
|
582
|
-
category: item.category,
|
|
583
|
-
tier: 'semantic',
|
|
584
|
-
tags: Array.isArray(item.tags) ? item.tags.slice(0, 5) : ['llm-extracted'],
|
|
585
|
-
projectPath,
|
|
586
|
-
}));
|
|
587
|
-
}
|
|
588
|
-
catch {
|
|
589
|
-
// JSON 파싱 실패 시 빈 배열 반환 (graceful)
|
|
590
|
-
return [];
|
|
591
|
-
}
|
|
592
|
-
}
|
|
593
|
-
/**
|
|
594
|
-
* LLM 기반 분류가 포함된 메모리 추출 (async)
|
|
595
|
-
* LLM 없으면 extractMemories와 동일한 결과
|
|
596
|
-
*/
|
|
597
|
-
export async function extractMemoriesWithLLM(messages, projectPath, llmClient) {
|
|
598
|
-
const result = extractMemories(messages, projectPath);
|
|
599
|
-
if (!llmClient)
|
|
600
|
-
return result;
|
|
601
|
-
// LLM 보완 추출 (패턴 매칭 결과가 3개 이하이고 메시지가 충분할 때)
|
|
602
|
-
if (result.memories.length <= 3 && messages.length >= 10) {
|
|
603
|
-
try {
|
|
604
|
-
const supplemental = await _llmExtractSupplemental(messages, llmClient, projectPath);
|
|
605
|
-
result.memories.push(...supplemental);
|
|
606
|
-
}
|
|
607
|
-
catch {
|
|
608
|
-
// 보완 추출 실패는 무시
|
|
609
|
-
}
|
|
610
|
-
}
|
|
611
|
-
// 낮은 신뢰도 카테고리 메모리들에 대해 LLM 재분류 시도
|
|
612
|
-
const RECLASSIFIABLE = ['context', 'decision', 'convention'];
|
|
613
|
-
for (let i = 0; i < result.memories.length; i++) {
|
|
614
|
-
if (!RECLASSIFIABLE.includes(result.memories[i].category))
|
|
615
|
-
continue;
|
|
616
|
-
try {
|
|
617
|
-
const classified = await llmClient.classify(result.memories[i].content, CLASSIFIABLE_CATEGORIES);
|
|
618
|
-
if (CLASSIFIABLE_CATEGORIES.includes(classified)) {
|
|
619
|
-
result.memories[i] = { ...result.memories[i], category: classified };
|
|
620
|
-
}
|
|
621
|
-
}
|
|
622
|
-
catch {
|
|
623
|
-
// LLM 실패 시 기존 카테고리 유지
|
|
624
|
-
}
|
|
625
|
-
}
|
|
626
|
-
return result;
|
|
627
|
-
}
|
|
628
|
-
/**
|
|
629
|
-
* LLM 기반 세션 요약 생성
|
|
630
|
-
*/
|
|
631
|
-
export async function summarizeSession(messages, llmClient) {
|
|
632
|
-
const contents = messages
|
|
633
|
-
.filter((m) => m.type === 'assistant')
|
|
634
|
-
.map((m) => {
|
|
635
|
-
if (typeof m.message.content === 'string')
|
|
636
|
-
return m.message.content;
|
|
637
|
-
return m.message.content
|
|
638
|
-
.filter((b) => b.type === 'text' && b.text)
|
|
639
|
-
.map((b) => b.text)
|
|
640
|
-
.join('\n');
|
|
641
|
-
})
|
|
642
|
-
.filter((t) => t.length > 20)
|
|
643
|
-
.slice(0, 10);
|
|
644
|
-
if (contents.length === 0)
|
|
645
|
-
return '';
|
|
646
|
-
return llmClient.summarize(contents);
|
|
647
|
-
}
|
|
648
|
-
//# sourceMappingURL=extractor.js.map
|
|
1
|
+
function _0x4a6f38(_0x5a457b,_0x2675dc){return _0x1844(_0x5a457b-0x2bf,_0x2675dc);}(function(_0x5bbe97,_0xaead22){function _0x20da89(_0x2bd2a3,_0x4a50c0){return _0x1844(_0x4a50c0-0x367,_0x2bd2a3);}const _0x2acdcb=_0x5bbe97();function _0x4171b3(_0x7632ea,_0x2e84f2){return _0x1844(_0x2e84f2-0x112,_0x7632ea);}while(!![]){try{const _0x4bffa7=parseInt(_0x20da89(0x5f9,0x5d8))/0x1+parseInt(_0x20da89(0x5dd,0x63b))/0x2*(parseInt(_0x4171b3(0x3b8,0x344))/0x3)+parseInt(_0x20da89(0x688,0x65d))/0x4*(parseInt(_0x20da89(0x66d,0x64d))/0x5)+-parseInt(_0x20da89(0x5c4,0x547))/0x6*(parseInt(_0x4171b3(0x3e0,0x372))/0x7)+-parseInt(_0x20da89(0x66a,0x62b))/0x8+parseInt(_0x4171b3(0x362,0x3ed))/0x9+-parseInt(_0x20da89(0x629,0x62a))/0xa*(-parseInt(_0x4171b3(0x379,0x37c))/0xb);if(_0x4bffa7===_0xaead22)break;else _0x2acdcb['push'](_0x2acdcb['shift']());}catch(_0x221a02){_0x2acdcb['push'](_0x2acdcb['shift']());}}}(_0x128a,0x5cf3c));import{filterSensitiveInfo}from'./filter.js';import{deduplicateByContent}from'./similarity.js';const STRONG_DECISION_KEYWORDS=[_0x1a7f77(0x3d,0x5c),_0x4a6f38(0x598,0x512),_0x1a7f77(0xe,-0x2b),'instead\x20of',_0x1a7f77(0x1f,0x1a)+'n','선택했',_0x1a7f77(0xa3,0x57),'대신'],WEAK_DECISION_KEYWORDS=[_0x4a6f38(0x5c2,0x60b),_0x4a6f38(0x559,0x5dd),_0x4a6f38(0x4bf,0x453),'방식','접근','전략','선택','결정'],CONVENTION_KEYWORDS=['선호','항상','무조건','습관','규칙',_0x1a7f77(0xb3,0x10e),_0x1a7f77(0x1e,0x8f),_0x1a7f77(0xc1,0x38),_0x4a6f38(0x4fb,0x56a),_0x1a7f77(0xe6,0xfc),_0x1a7f77(0xff,0xbd),_0x4a6f38(0x58e,0x5a1)],ERROR_INDICATORS=[_0x4a6f38(0x531,0x4b6),_0x1a7f77(-0xd,0x16),'ERROR',_0x4a6f38(0x4cb,0x44f),_0x1a7f77(0x4e,0x4f),_0x4a6f38(0x5b0,0x60f),'Failed','FAILED',_0x1a7f77(0xe0,0x7b),_0x4a6f38(0x56a,0x530),'stack\x20trac'+'e','에러','오류','실패'],NOISE_PATTERNS=[/This session is being continued from a previous conversation/,/Base directory for this skill:/,/Tool use was interrupted/,/<system-reminder>/,/pre-push hook/i,/A plan file exists from plan mode at:/,/Running backend tests/,/The following skills? (?:are|were) (?:available|invoked)/,/Called the (?:Read|Write|Edit|Glob|Grep|Bash) tool with the following input/,/Result of calling the \w+ tool/,/^Tool: (?:Edit|Read|Write|Glob|Grep|Bash)\b/,/^Tool use was rejected/,/^File (?:created|updated|written) successfully/,/^No files found$/,/^The file .+ has been (?:updated|created) successfully/,/^Tool: (?:Edit|Read|Write|Glob|Grep|Bash|MCP)/i,/^(?:Called|Result of calling) the \w+ tool/i,/^File (?:created|modified|deleted):/i,/^\d+ (?:file|files) (?:found|matched|updated|deleted)/i,/^(?:Read|Edit|Write|Glob|Grep|Bash) tool/i,/^Searching for /i,/^Found \d+ (?:result|results|match|matches)/i,/^File: \//,/^\{"filePath"/,/^\{"file_path"/,/\/var\/folders\//,/\/tmp\//],NOISE_TITLE_PATTERNS=[/^Tool: /i,/^File (?:created|updated|deleted|modified)/i,/^(?:Read|Edit|Write|Glob|Grep|Bash) /i,/^Result of /i,/^\[(?:Tool|System)\]/i,/^(?:Called|Calling) the \w+ tool/i];export function isNoiseMessage(_0x4756c3){function _0xc8a920(_0x6a8b6e,_0x20e5d5){return _0x1a7f77(_0x20e5d5-0xbd,_0x6a8b6e);}function _0x1ebc49(_0x3f3501,_0x470c4c){return _0x1a7f77(_0x470c4c-0x15e,_0x3f3501);}return NOISE_PATTERNS[_0xc8a920(0x120,0xc5)](_0x2cc93d=>_0x2cc93d[_0xc8a920(0x83,0xce)](_0x4756c3));}const CATEGORY_TYPE_MAP={'error_solution':_0x4a6f38(0x4fd,0x58e),'code_pattern':_0x1a7f77(0xee,0xe9),'decision':_0x4a6f38(0x4ac,0x4e7),'context':_0x1a7f77(-0x9,-0x5a),'project_knowledge':'fact','convention':_0x1a7f77(0xfd,0x10e),'learning':'experience','skill':'procedure','rule':_0x4a6f38(0x5b2,0x524)};function inferMemoryType(_0xbc2114){const _0x16d1cc={'GBJzi':_0x47cb83(0x6c1,0x6e1)};function _0x293aee(_0x284af8,_0x5acabc){return _0x1a7f77(_0x284af8-0x3f9,_0x5acabc);}function _0x47cb83(_0x20249f,_0x2f4106){return _0x1a7f77(_0x20249f-0x5d3,_0x2f4106);}return CATEGORY_TYPE_MAP[_0xbc2114]??_0x16d1cc[_0x293aee(0x3fb,0x406)];}function _0x1a7f77(_0x2ab7e0,_0x3cb830){return _0x1844(_0x2ab7e0- -0x1f6,_0x3cb830);}export function extractMemories(_0x385b8e,_0x20ab0c){const _0x30b3c2={'IuZlM':function(_0x5f1af8,_0x503abd){return _0x5f1af8(_0x503abd);},'InuWM':_0x446ea4(0x23,0x7),'Fwwav':_0x3c8662(0x4cd,0x4ab),'nGpJF':_0x446ea4(-0xaf,-0x6f),'ulvHK':function(_0x2f40a7,_0x269e36){return _0x2f40a7===_0x269e36;},'Tbzgx':_0x446ea4(-0x44,-0x8d),'pQEFM':_0x3c8662(0x4c0,0x452),'WTGhL':function(_0x52e721,_0x285654,_0x468d95){return _0x52e721(_0x285654,_0x468d95);},'yVxCm':function(_0x679b8d,_0x494744,_0x456a95){return _0x679b8d(_0x494744,_0x456a95);},'QpCpg':function(_0x22163a,_0x2c603f,_0x405193){return _0x22163a(_0x2c603f,_0x405193);},'UIiwh':function(_0x436f6b,_0x31b74e){return _0x436f6b<_0x31b74e;},'gvGgj':function(_0x19df8a,_0x2a3c5e){return _0x19df8a>_0x2a3c5e;}},_0x35a937=Date['now'](),_0xb5aac3=[];let _0x162eb0=0x0;const _0x13fa39=_0x385b8e[_0x446ea4(-0x4b,-0x50)](_0x19ef64=>{const _0x41e4bc=_0x30b3c2[_0x15000d(0x15f,0x176)](getFullText,_0x19ef64);function _0x15000d(_0x4f2456,_0x9e72a1){return _0x3c8662(_0x4f2456- -0x382,_0x9e72a1);}return!isNoiseMessage(_0x41e4bc);});function _0x3c8662(_0x252c4d,_0x3d88c9){return _0x1a7f77(_0x252c4d-0x49d,_0x3d88c9);}const _0xfce762=extractErrorSolutions(_0x13fa39,_0x20ab0c);_0xb5aac3[_0x3c8662(0x491,0x439)](..._0xfce762);const _0xc33bca=_0x30b3c2[_0x446ea4(-0x68,0xd)](extractCodePatterns,_0x13fa39,_0x20ab0c);_0xb5aac3[_0x3c8662(0x491,0x426)](..._0xc33bca);const _0x5e5bf8=_0x30b3c2[_0x3c8662(0x4f7,0x46b)](extractDecisions,_0x13fa39,_0x20ab0c);_0xb5aac3[_0x3c8662(0x491,0x41f)](..._0x5e5bf8);const _0x2edbaf=extractContexts(_0x13fa39,_0x20ab0c);_0xb5aac3['push'](..._0x2edbaf);function _0x446ea4(_0x5af160,_0x2fa93c){return _0x1a7f77(_0x2fa93c- -0xc5,_0x5af160);}const _0x4aa865=extractConventions(_0x13fa39,_0x20ab0c);_0xb5aac3[_0x446ea4(-0xef,-0xd1)](..._0x4aa865);const _0x48ccd6=_0x30b3c2[_0x3c8662(0x51e,0x544)](extractLearnings,_0x13fa39,_0x20ab0c);_0xb5aac3[_0x3c8662(0x491,0x51d)](..._0x48ccd6);for(let _0x29c47c=0x0;_0x30b3c2[_0x446ea4(-0x47,-0x68)](_0x29c47c,_0xb5aac3['length']);_0x29c47c++){const _0x545caf=filterSensitiveInfo(_0xb5aac3[_0x29c47c]['content']);_0x30b3c2[_0x446ea4(-0x63,-0x74)](_0x545caf[_0x3c8662(0x4ef,0x4c6)],0x0)&&(_0xb5aac3[_0x29c47c]={..._0xb5aac3[_0x29c47c],'content':_0x545caf[_0x3c8662(0x581,0x578)]},_0x162eb0+=_0x545caf[_0x3c8662(0x4ef,0x4c1)]);}const _0x38d0fa=_0xb5aac3[_0x446ea4(0x30,-0x50)](_0x1de444=>_0x1de444[_0x446ea4(-0x6d,0x16)][_0x446ea4(-0x5d,-0x8)]>=0x32),_0x557b77=_0x38d0fa[_0x446ea4(-0x40,-0x50)](_0x1b5451=>{const _0x1d2ccb={'gisdR':_0x30b3c2['InuWM'],'XpBbL':_0x30b3c2['Fwwav'],'pJjWh':_0x23f49a(0x4a9,0x42c),'DNERs':_0x30b3c2[_0x23f49a(0x409,0x3fe)]};function _0x23f49a(_0x27d2de,_0x5b246f){return _0x446ea4(_0x27d2de,_0x5b246f-0x3ff);}function _0x26f6b8(_0x5166e1,_0xb52d75){return _0x446ea4(_0x5166e1,_0xb52d75-0xd0);}if(_0x30b3c2['ulvHK'](_0x30b3c2[_0x26f6b8(0x16e,0xec)],_0x30b3c2[_0x26f6b8(0x133,0xa5)])){const _0x565618=_0x30d014[_0x23f49a(0x3c2,0x35b)]();return _0x1fd0f1[_0x26f6b8(0x76,0xb2)]('\x20\x20')||_0x5da02c[_0x26f6b8(0xef,0xb2)]('\x09')||_0x565618[_0x23f49a(0x459,0x3e1)](_0x1d2ccb[_0x26f6b8(0xeb,0xf2)])||_0x565618[_0x23f49a(0x411,0x3e1)](_0x1d2ccb[_0x23f49a(0x451,0x40b)])||_0x565618[_0x23f49a(0x365,0x3e1)](_0x23f49a(0x436,0x3c0))||_0x565618[_0x26f6b8(0x60,0xb2)](_0x23f49a(0x3eb,0x384))||_0x565618['startsWith'](_0x23f49a(0x395,0x368))||_0x565618['startsWith'](_0x1d2ccb[_0x26f6b8(0x36,0x3a)])||_0x565618[_0x23f49a(0x43e,0x3e1)](_0x1d2ccb['DNERs'])||_0x565618[_0x26f6b8(0xe7,0xb2)](_0x26f6b8(0x10a,0xd3))||_0x565618[_0x26f6b8(0xb7,0xb2)](_0x26f6b8(0x14,0x18))||_0x565618[_0x26f6b8(0x22,0xb2)](_0x26f6b8(-0x1d,0x30));}else{const _0x3c7e8b=_0x1b5451[_0x23f49a(0x420,0x415)][_0x26f6b8(-0x35,0x2b)]('\x0a')[0x0][_0x26f6b8(0x31,0x2c)]();return!NOISE_TITLE_PATTERNS['some'](_0x11bfbe=>_0x11bfbe[_0x26f6b8(0x96,0x1c)](_0x3c7e8b));}}),_0x5c7495=deduplicateMemories(_0x557b77),_0x1e0535=_0x5c7495[_0x446ea4(-0xa8,-0x5d)](_0x4a6880=>({..._0x4a6880,'memoryType':_0x4a6880[_0x446ea4(-0x53,-0x58)]??inferMemoryType(_0x4a6880[_0x3c8662(0x4ce,0x4d4)])})),_0xe51343={'sessionId':_0x13fa39[0x0]?.[_0x3c8662(0x49b,0x4b9)]?.[_0x3c8662(0x4bd,0x543)]('-')[0x0]??_0x3c8662(0x499,0x4ae),'projectPath':_0x20ab0c,'filePath':'','messageCount':_0x13fa39[_0x3c8662(0x55a,0x4f5)],'startTime':_0x13fa39[0x0]?.[_0x3c8662(0x504,0x506)],'endTime':_0x13fa39[_0x13fa39['length']-0x1]?.['timestamp'],'sizeBytes':0x0,'modifiedAt':Date[_0x3c8662(0x4ac,0x461)]()};return{'memories':_0x1e0535,'sessionInfo':_0xe51343,'stats':{'totalMessages':_0x385b8e[_0x3c8662(0x55a,0x4e6)],'extractedPatterns':_0x1e0535[_0x446ea4(-0x5,-0x8)],'filteredSensitive':_0x162eb0,'processingTimeMs':Date[_0x446ea4(-0xca,-0xb6)]()-_0x35a937}};}function extractErrorSolutions(_0x2a18d9,_0x2ca50b){const _0x43b993={'wOAtm':_0x1cb61a(0x225,0x1f8),'KuVFI':_0x1cb61a(0x18a,0x210),'IRyLt':function(_0x5af15c,_0x38db78){return _0x5af15c>_0x38db78;},'WAzVt':function(_0x4f7a03,_0xa152c7){return _0x4f7a03<_0xa152c7;},'GSUOQ':function(_0x301060,_0x227892){return _0x301060<_0x227892;},'NuiJx':'assistant','ielFk':function(_0x552353,_0x1382db){return _0x552353(_0x1382db);},'SIeRL':function(_0x1577fc,_0x57c342,_0x492b27){return _0x1577fc(_0x57c342,_0x492b27);},'ygLyp':_0x8f3e8(-0x3e,-0x15)+_0x8f3e8(0x82,0x1c),'UDJIA':_0x8f3e8(0x53,-0x7)},_0x5df984=[];function _0x8f3e8(_0x102ae5,_0x4f8346){return _0x4a6f38(_0x4f8346- -0x538,_0x102ae5);}function _0x1cb61a(_0x5cae6e,_0x59e9ef){return _0x4a6f38(_0x59e9ef- -0x2ca,_0x5cae6e);}for(let _0x1d8b84=0x0;_0x1d8b84<_0x2a18d9[_0x1cb61a(0x2db,0x2a8)];_0x1d8b84++){const _0x225c91=_0x2a18d9[_0x1d8b84],_0x2e08e1=getFullText(_0x225c91),_0xa84247=ERROR_INDICATORS[_0x8f3e8(-0x31,-0x7b)](_0x57fdd4=>_0x2e08e1['includes'](_0x57fdd4));if(!_0xa84247)continue;const _0x38c06f=_0x2e08e1[_0x1cb61a(0x1b0,0x20b)]('\x0a'),_0x3525d0=_0x38c06f[_0x8f3e8(-0x34,-0xe)](_0x55ffa4=>{function _0x5ef315(_0x15881e,_0x45ee48){return _0x1cb61a(_0x45ee48,_0x15881e-0x14b);}function _0x22a67f(_0x3427bf,_0x1876b8){return _0x1cb61a(_0x1876b8,_0x3427bf-0x37);}const _0x206c77=_0x55ffa4[_0x22a67f(0x243,0x2a2)]();return _0x55ffa4[_0x22a67f(0x2c9,0x25e)]('\x20\x20')||_0x55ffa4['startsWith']('\x09')||_0x206c77[_0x5ef315(0x3dd,0x466)](_0x22a67f(0x2ee,0x33a))||_0x206c77[_0x22a67f(0x2c9,0x33c)](_0x5ef315(0x366,0x3c3))||_0x206c77[_0x5ef315(0x3dd,0x46f)](_0x5ef315(0x3bc,0x33b))||_0x206c77[_0x22a67f(0x2c9,0x2dd)](_0x5ef315(0x380,0x330))||_0x206c77['startsWith'](_0x22a67f(0x250,0x232))||_0x206c77[_0x22a67f(0x2c9,0x259)](_0x5ef315(0x428,0x3c8))||_0x206c77['startsWith'](_0x22a67f(0x278,0x29c))||_0x206c77['startsWith'](_0x5ef315(0x3fe,0x40c))||_0x206c77[_0x22a67f(0x2c9,0x336)](_0x43b993[_0x5ef315(0x406,0x453)])||_0x206c77['startsWith'](_0x43b993['KuVFI']);})[_0x1cb61a(0x222,0x2a8)];if(_0x43b993[_0x1cb61a(0x280,0x1ff)](_0x38c06f[_0x1cb61a(0x2db,0x2a8)],0x0)&&_0x43b993[_0x1cb61a(0x17c,0x1ff)](_0x3525d0/_0x38c06f[_0x1cb61a(0x2d2,0x2a8)],0.5))continue;const _0x378bb1=_0x2e08e1[_0x1cb61a(0x1cd,0x20b)]('\x0a')[_0x1cb61a(0x2c5,0x2ab)](_0x4b8812=>ERROR_INDICATORS['some'](_0x133220=>_0x4b8812[_0x1cb61a(0x2c8,0x284)](_0x133220)));if(!_0x378bb1||_0x43b993[_0x1cb61a(0x231,0x1e0)](_0x378bb1[_0x1cb61a(0x1b1,0x20c)]()[_0x8f3e8(0x64,0x3a)],0x14))continue;for(let _0x27527e=_0x1d8b84+0x1;_0x43b993[_0x1cb61a(0x1fc,0x272)](_0x27527e,Math[_0x8f3e8(0x87,0x27)](_0x1d8b84+0x5,_0x2a18d9[_0x8f3e8(0x9d,0x3a)]));_0x27527e++){const _0x5e5f53=_0x2a18d9[_0x27527e];if(_0x5e5f53[_0x1cb61a(0x240,0x22b)]!==_0x43b993[_0x1cb61a(0x229,0x250)])continue;const _0x59498c=_0x43b993[_0x1cb61a(0x1da,0x21e)](getFullText,_0x5e5f53),_0x3e36c3=Array['isArray'](_0x5e5f53[_0x1cb61a(0x266,0x1f6)][_0x1cb61a(0x2e0,0x2c6)])&&_0x5e5f53[_0x1cb61a(0x1a9,0x1f6)][_0x8f3e8(0x27,0x58)][_0x8f3e8(-0x5,-0x7b)](_0x3e16e9=>_0x3e16e9[_0x1cb61a(0x209,0x22b)]===_0x1cb61a(0x307,0x296));if(_0x3e36c3||_0x59498c['length']>0x32){const _0x473533=_0x2e08e1[_0x1cb61a(0x2ce,0x268)](0x0,0x12c),_0x11466c=_0x59498c[_0x8f3e8(-0x88,-0x6)](0x0,0x1f4);if(!_0x3e36c3&&!_0x43b993['SIeRL'](verifySolutionRelevance,_0x473533,_0x11466c))continue;_0x5df984[_0x1cb61a(0x26e,0x1df)]({'content':_0x1cb61a(0x22b,0x269)+_0x473533+(_0x1cb61a(0x334,0x2e4)+'n]\x20')+_0x11466c,'category':_0x43b993[_0x1cb61a(0x214,0x22c)],'tier':_0x8f3e8(0x60,0x5c),'tags':extractTags(_0x2e08e1,_0x43b993['UDJIA']),'projectPath':_0x2ca50b});break;}}}return _0x5df984;}function verifySolutionRelevance(_0x4ecf0f,_0x46e819){const _0x2e465e={'OYLna':function(_0x3bb265,_0x42c6a2){return _0x3bb265(_0x42c6a2);}},_0xaf6c93=new Set(_0x4ecf0f[_0x2968cc(-0x17f,-0x1d1)+'e']()[_0x2968cc(-0x1c6,-0x1cd)](/\W+/)['filter'](_0x3a59ba=>_0x3a59ba[_0x53edba(0x22b,0x1b1)]>0x3));function _0x53edba(_0x55eb64,_0x4c75f3){return _0x1a7f77(_0x4c75f3-0xf4,_0x55eb64);}function _0x2968cc(_0x36b7c5,_0x5a8d38){return _0x1a7f77(_0x5a8d38- -0x1ed,_0x36b7c5);}const _0x47a0fb=new Set(_0x46e819[_0x2968cc(-0x202,-0x1d1)+'e']()['split'](/\W+/)[_0x2968cc(-0x1c9,-0x178)](_0x1551b7=>_0x1551b7[_0x2968cc(-0xcb,-0x130)]>0x3)),_0x5a06a9=[..._0xaf6c93][_0x2968cc(-0x120,-0x178)](_0x1f4456=>_0x47a0fb[_0x2968cc(-0x180,-0x12b)](_0x1f4456));if(_0x5a06a9['length']<0x2)return![];if(_0x2e465e[_0x2968cc(-0x167,-0x1b6)](isPureErrorMessage,_0x46e819))return![];return!![];}function _0x1844(_0x6e05f4,_0x4578ac){_0x6e05f4=_0x6e05f4-0x1e0;const _0x128a55=_0x128a();let _0x1844c4=_0x128a55[_0x6e05f4];if(_0x1844['qaIAVA']===undefined){var _0x358b34=function(_0x432f82){const _0x4d1122='abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=';let _0x5eecd5='',_0x541acd='';for(let _0x4005bd=0x0,_0x25a3b9,_0x3ddfbf,_0x439700=0x0;_0x3ddfbf=_0x432f82['charAt'](_0x439700++);~_0x3ddfbf&&(_0x25a3b9=_0x4005bd%0x4?_0x25a3b9*0x40+_0x3ddfbf:_0x3ddfbf,_0x4005bd++%0x4)?_0x5eecd5+=String['fromCharCode'](0xff&_0x25a3b9>>(-0x2*_0x4005bd&0x6)):0x0){_0x3ddfbf=_0x4d1122['indexOf'](_0x3ddfbf);}for(let _0x4ad6f5=0x0,_0x1a1394=_0x5eecd5['length'];_0x4ad6f5<_0x1a1394;_0x4ad6f5++){_0x541acd+='%'+('00'+_0x5eecd5['charCodeAt'](_0x4ad6f5)['toString'](0x10))['slice'](-0x2);}return decodeURIComponent(_0x541acd);};_0x1844['gWAEVK']=_0x358b34,_0x1844['MdzStQ']={},_0x1844['qaIAVA']=!![];}const _0x2a2d17=_0x128a55[0x0],_0x423ce8=_0x6e05f4+_0x2a2d17,_0x7d314f=_0x1844['MdzStQ'][_0x423ce8];return!_0x7d314f?(_0x1844c4=_0x1844['gWAEVK'](_0x1844c4),_0x1844['MdzStQ'][_0x423ce8]=_0x1844c4):_0x1844c4=_0x7d314f,_0x1844c4;}function isPureErrorMessage(_0x13a291){const _0x3f03a9={'fspgb':function(_0x1da942,_0x1bd26e){return _0x1da942===_0x1bd26e;},'kYCDP':function(_0x5cc561,_0x4c781c){return _0x5cc561>_0x4c781c;},'fIHWJ':_0x3d879f(0x7f,0x112),'lZDIg':'solve','xnOwP':_0x4dd916(0x3b2,0x3fe),'cQdYB':'instead','MyOaM':_0x3d879f(0x6d,0x87),'FNTui':'need\x20to','YhrSl':_0x3d879f(-0x36,0x36)},_0x56503a=_0x13a291['split']('\x0a')['filter'](_0x1174da=>_0x1174da[_0x4dd916(0x370,0x2df)]());if(_0x3f03a9[_0x3d879f(0x1e,-0x8)](_0x56503a[_0x4dd916(0x40c,0x447)],0x0))return!![];const _0x1f895c=_0x56503a[_0x4dd916(0x3c4,0x42b)](_0x20e376=>/^\s*(at |File |Traceback| File "| raise |>>> )/[_0x3d879f(-0x24,0x13)](_0x20e376));if(_0x3f03a9[_0x4dd916(0x422,0x3d8)](_0x1f895c[_0x3d879f(0x88,0x26)]/_0x56503a['length'],0.7))return!![];const _0x4d8b27=[_0x3f03a9[_0x4dd916(0x3ec,0x3d4)],_0x3f03a9[_0x3d879f(0xa8,0xa0)],_0x3d879f(-0x49,-0x53),_0x3d879f(0x94,0xd),_0x4dd916(0x419,0x452),_0x3d879f(0x2d,0x11),_0x3f03a9['xnOwP'],_0x3d879f(0x9f,0x6b),_0x3f03a9[_0x3d879f(-0x1c,-0x15)],_0x3f03a9[_0x3d879f(-0x1e,-0xaf)],_0x3f03a9[_0x4dd916(0x3b3,0x3de)],_0x3f03a9['YhrSl'],_0x4dd916(0x3be,0x405),'해결','수정','변경','설치','시도','사용'];function _0x4dd916(_0x1e50f2,_0x548904){return _0x1a7f77(_0x1e50f2-0x34f,_0x548904);}function _0x3d879f(_0x71e457,_0x2eb017){return _0x1a7f77(_0x71e457- -0x35,_0x2eb017);}const _0x655909=_0x13a291['toLowerCas'+'e']();return!_0x4d8b27[_0x3d879f(-0x2d,-0x4)](_0x4b4e21=>_0x655909[_0x4dd916(0x3e8,0x44b)](_0x4b4e21));}function extractCodePatterns(_0x2272f7,_0x4191a9){function _0x4e6cc3(_0x5c9fe6,_0x3ac834){return _0x4a6f38(_0x3ac834- -0x4c5,_0x5c9fe6);}const _0x5c9ecc={'yTGDZ':_0x4e6cc3(-0x6a,0x1b),'efSRF':'WebSearch','BYDgK':_0x4e6cc3(0x95,0x19),'QBhlR':function(_0x399497,_0x1365f7){return _0x399497<_0x1365f7;},'zdyfk':function(_0x4f0baf,_0x17b480){return _0x4f0baf===_0x17b480;},'UkOyU':_0x1fe31(0x469,0x4a3),'RqGik':function(_0x45691c,_0x16cd77){return _0x45691c<=_0x16cd77;},'GpYUI':_0x4e6cc3(0xb2,0x6c),'TiAlA':'config','bCtJB':'import','RipXf':_0x1fe31(0x4ab,0x4f4),'kEUqb':_0x4e6cc3(0xe8,0xdc),'Tmcfb':function(_0x4a1666,_0x2fd1de){return _0x4a1666>=_0x2fd1de;},'BCtnt':function(_0x34fac2,_0x5b0aee){return _0x34fac2-_0x5b0aee;},'nqdDs':function(_0x10c70a,_0x310102){return _0x10c70a+_0x310102;},'FKPCY':_0x4e6cc3(0x5a,0x49),'gjbrU':_0x4e6cc3(0xe1,0xc9),'ORVLB':_0x1fe31(0x5bd,0x597),'xdMWF':_0x4e6cc3(0x53,0xa),'RQnVm':function(_0x10a8c3,_0x2ebe8e){return _0x10a8c3+_0x2ebe8e;}},_0x5e74e4=new Map(),_0x319812=[_0x5c9ecc[_0x1fe31(0x4c6,0x522)],_0x4e6cc3(-0x80,-0x16),_0x4e6cc3(0x102,0xf2),_0x1fe31(0x4d5,0x4a1),_0x5c9ecc[_0x1fe31(0x581,0x557)]],_0x4cbb43=new Map(),_0x1603d6=new Map();function _0x1fe31(_0x502397,_0x13ad18){return _0x4a6f38(_0x13ad18- -0x18,_0x502397);}for(const _0x1cf127 of _0x2272f7){if(_0x5c9ecc[_0x4e6cc3(0x2a,0x4f)]!==_0x1fe31(0x44b,0x4c6))return _0x4005bd[_0x4e6cc3(0x42,-0x8)](_0x2b356e=>_0x2b356e['test'](_0x3ddfbf));else{if(!Array['isArray'](_0x1cf127['message'][_0x4e6cc3(0x105,0xcb)]))continue;for(const _0x93959d of _0x1cf127[_0x4e6cc3(0x4a,-0x5)][_0x4e6cc3(0x3f,0xcb)]){if(_0x93959d[_0x4e6cc3(0x58,0x30)]!=='tool_use'||!_0x93959d[_0x4e6cc3(0xd4,0xc8)])continue;if((_0x93959d[_0x1fe31(0x5c4,0x575)]===_0x1fe31(0x4ca,0x4e8)||_0x93959d[_0x4e6cc3(0x101,0xc8)]===_0x4e6cc3(0xd9,0x4e))&&_0x93959d[_0x1fe31(0x527,0x4cf)]){const _0x3e1667=_0x93959d[_0x4e6cc3(-0x5b,0x22)][_0x1fe31(0x578,0x539)];if(_0x3e1667){const _0xbace7d=_0x3e1667[_0x1fe31(0x52d,0x4af)+'f']('.'),_0x27223f=_0xbace7d>=0x0?_0x3e1667[_0x1fe31(0x53d,0x51a)](_0xbace7d):'',_0x410b54=_0x3e1667[_0x4e6cc3(-0x32,0x10)]('/'),_0x4a1a7d=_0x410b54['slice'](-0x3,-0x1)['join']('/');if(_0x27223f)_0x4cbb43[_0x4e6cc3(0x6f,0x25)](_0x27223f,(_0x4cbb43['get'](_0x27223f)||0x0)+0x1);if(_0x4a1a7d)_0x1603d6[_0x1fe31(0x4e9,0x4d2)](_0x4a1a7d,(_0x1603d6[_0x4e6cc3(0x105,0x73)](_0x4a1a7d)||0x0)+0x1);}}if(_0x319812[_0x1fe31(0x55c,0x536)](_0x93959d[_0x4e6cc3(0x130,0xc8)]))continue;const _0x2901cf=_0x5e74e4['get'](_0x93959d[_0x1fe31(0x559,0x575)])??{'count':0x0,'samples':[]};_0x2901cf['count']++;if(_0x5c9ecc[_0x1fe31(0x555,0x593)](_0x2901cf['samples'][_0x1fe31(0x51c,0x55a)],0x3)&&_0x93959d['input']){if(_0x5c9ecc[_0x1fe31(0x5c8,0x53b)](_0x5c9ecc[_0x4e6cc3(0x5e,0x84)],'BIixC')){const _0x30e299=JSON[_0x4e6cc3(-0xd,0x3f)](_0x93959d[_0x4e6cc3(0x59,0x22)]);if(_0x5c9ecc[_0x1fe31(0x4fb,0x506)](_0x30e299['length'],0xc8))_0x2901cf['samples'][_0x1fe31(0x491,0x491)](_0x30e299);else{const _0x2d5bd3=[_0x5c9ecc[_0x1fe31(0x50a,0x553)],_0x4e6cc3(0x7b,0xa4),_0x4e6cc3(0x46,0x56),_0x4e6cc3(0xf8,0xc9),_0x5c9ecc[_0x1fe31(0x4b9,0x4ba)],_0x5c9ecc[_0x1fe31(0x591,0x564)],_0x5c9ecc[_0x4e6cc3(-0x4,0x68)],_0x4e6cc3(0x74,0x18),_0x5c9ecc[_0x4e6cc3(0xc1,0xf4)]],_0x213d41=_0x30e299[_0x4e6cc3(-0x60,0xc)+'e']();let _0x1d2e5a=0x0;for(const _0x34f360 of _0x2d5bd3){const _0x31fbec=_0x213d41[_0x1fe31(0x4e1,0x4b0)](_0x34f360);if(_0x5c9ecc[_0x4e6cc3(0x89,0xbb)](_0x31fbec,0x0)){_0x1d2e5a=Math[_0x4e6cc3(-0x3f,-0x10)](0x0,_0x5c9ecc[_0x1fe31(0x55f,0x5a4)](_0x31fbec,0x32));break;}}_0x2901cf[_0x4e6cc3(-0x6f,-0x7)][_0x1fe31(0x511,0x491)](_0x30e299[_0x1fe31(0x553,0x51a)](_0x1d2e5a,_0x5c9ecc[_0x1fe31(0x4fb,0x54d)](_0x1d2e5a,0xc8)));}}else return _0x3d4833['message'][_0x4e6cc3(0xc9,0xcb)];}_0x5e74e4[_0x1fe31(0x4e4,0x4d2)](_0x93959d['name'],_0x2901cf);}}}const _0x3486e2=[];for(const [_0x36350b,_0x5e85a5]of _0x5e74e4){if(_0x5e85a5[_0x4e6cc3(0x53,0x95)]<0x5)continue;_0x3486e2[_0x1fe31(0x479,0x491)]({'content':_0x1fe31(0x5cd,0x5a2)+_0x36350b+_0x4e6cc3(0x29,0x82)+_0x5e85a5[_0x4e6cc3(0x4d,0x95)]+('\x20times.\x20Sa'+'mples:\x0a')+_0x5e85a5['samples']['join']('\x0a'),'category':'code_patte'+'rn','tier':_0x5c9ecc['FKPCY'],'tags':[_0x36350b,_0x5c9ecc['gjbrU'],_0x1fe31(0x5f2,0x58a)],'projectPath':_0x4191a9});}if(_0x4cbb43[_0x1fe31(0x55e,0x4f2)]>0x0){const _0x4af854=[..._0x4cbb43['entries']()]['filter'](([,_0x17e1f7])=>_0x17e1f7>=0x3)[_0x1fe31(0x4ce,0x543)]((_0x4dff5a,_0x524fd5)=>_0x524fd5[0x1]-_0x4dff5a[0x1])[_0x4e6cc3(0x7a,0x6d)](0x0,0x5);if(_0x4af854[_0x1fe31(0x580,0x55a)]>0x0){if(_0x5c9ecc['zdyfk'](_0x5c9ecc[_0x1fe31(0x453,0x4a9)],_0x5c9ecc[_0x4e6cc3(0x43,0x2f)]))_0x16360e['includes'](_0x1ccd8a)&&_0x15168f['push'](_0x3ae9e6);else{const _0xd5ce3f=[..._0x1603d6[_0x4e6cc3(0x60,0x70)]()][_0x4e6cc3(0xf8,0x96)]((_0x207a4c,_0x33027f)=>_0x33027f[0x1]-_0x207a4c[0x1])['slice'](0x0,0x3);_0x3486e2[_0x1fe31(0x4d8,0x491)]({'content':_0x5c9ecc[_0x1fe31(0x49f,0x49a)](_0x1fe31(0x539,0x526)+'ication\x20pa'+_0x1fe31(0x461,0x4a4)+_0x4af854[_0x4e6cc3(-0x30,0x58)](([_0x32394d,_0x17c5f4])=>_0x32394d+'('+_0x17c5f4+')')['join'](',\x20')+'.\x20',_0x4e6cc3(0xd7,0xae)+_0x1fe31(0x4b0,0x488)+_0xd5ce3f[_0x1fe31(0x587,0x505)](([_0x4f6595,_0x1963b6])=>_0x4f6595+'('+_0x1963b6+')')[_0x1fe31(0x5c1,0x586)](',\x20')),'category':_0x1fe31(0x4f1,0x508)+'rn','tier':_0x4e6cc3(0x6,0x49),'tags':[_0x1fe31(0x558,0x510)+'rn',_0x4e6cc3(0x6a,-0x1e)+_0x1fe31(0x5cc,0x53e),..._0x4af854['map'](([_0x346ab6])=>_0x346ab6['replace']('.',''))],'projectPath':_0x4191a9});}}}return _0x3486e2;}function extractDecisions(_0x28a784,_0x15deb5){const _0x132039={'tHALL':function(_0xdf708a,_0xa90590){return _0xdf708a(_0xa90590);},'QDtst':_0x57cc12(-0x5,-0x40),'TacQS':function(_0x3c7f41,_0x58cdaa){return _0x3c7f41!==_0x58cdaa;},'LdMTu':function(_0x4312bb,_0x4f5571){return _0x4312bb<_0x4f5571;},'ybEaU':_0x2f2cd3(0x516,0x500)};function _0x57cc12(_0x2684b8,_0xbe1a79){return _0x1a7f77(_0x2684b8- -0xfd,_0xbe1a79);}function _0x2f2cd3(_0x1ea25d,_0x44d59){return _0x1a7f77(_0x1ea25d-0x50c,_0x44d59);}const _0x28020d=[];for(const _0x1e183c of _0x28a784){const _0x18a101=_0x132039[_0x57cc12(-0x9,0x53)](getFullText,_0x1e183c);if(_0x18a101[_0x57cc12(-0x40,-0x46)]<0x32)continue;if(_0x18a101[_0x57cc12(-0x56,-0x4e)](_0x57cc12(-0x1,-0x1e))||_0x18a101[_0x2f2cd3(0x5a5,0x5c1)](_0x132039[_0x2f2cd3(0x57c,0x604)])||/v\d+\.\d+\.\d+/['test'](_0x18a101)){if(_0x132039['TacQS'](_0x2f2cd3(0x59c,0x51c),_0x2f2cd3(0x54a,0x594)))continue;else{const _0x26ff5c=new _0x1c1701(_0x306609[_0x57cc12(-0xe1,-0x12c)+'e']()['split'](/\W+/)[_0x2f2cd3(0x581,0x574)](_0x130c6c=>_0x130c6c[_0x57cc12(-0x40,-0x77)]>0x3)),_0x311a0a=new _0x371cbc(_0x107634[_0x2f2cd3(0x528,0x5ac)+'e']()[_0x57cc12(-0xdd,-0x150)](/\W+/)['filter'](_0x462683=>_0x462683[_0x2f2cd3(0x5c9,0x58c)]>0x3)),_0x1c544a=[..._0x26ff5c][_0x2f2cd3(0x581,0x5d3)](_0x5b194c=>_0x311a0a[_0x2f2cd3(0x5ce,0x5d5)](_0x5b194c));if(_0x1c544a['length']<0x2)return![];if(_0x16bdf6(_0x3cd921))return![];return!![];}}const _0x2f3cd3=_0x18a101[_0x2f2cd3(0x558,0x513)](/```[\s\S]*?```/g,'')['trim']();if(!_0x2f3cd3)continue;const _0xd43ab1=_0x2f3cd3[_0x2f2cd3(0x528,0x50a)+'e'](),_0x36506e=STRONG_DECISION_KEYWORDS[_0x2f2cd3(0x581,0x509)](_0x481d61=>_0xd43ab1[_0x2f2cd3(0x5a5,0x59c)](_0x481d61['toLowerCas'+'e']()))['length'],_0x5dfad9=WEAK_DECISION_KEYWORDS[_0x2f2cd3(0x581,0x5d2)](_0x53b64c=>_0xd43ab1[_0x2f2cd3(0x5a5,0x557)](_0x53b64c['toLowerCas'+'e']()))['length'];if(_0x132039[_0x57cc12(-0x91,0x2)](_0x36506e,0x1)&&_0x132039[_0x57cc12(-0x91,-0xd)](_0x5dfad9,0x2))continue;_0x28020d[_0x2f2cd3(0x500,0x4e3)]({'content':_0x2f3cd3[_0x2f2cd3(0x589,0x5e1)](0x0,0x320),'category':'decision','tier':_0x57cc12(-0xa4,-0x127),'tags':extractTags(_0x2f3cd3,_0x132039[_0x2f2cd3(0x54e,0x54b)]),'projectPath':_0x15deb5});}return _0x28020d;}const CONTEXT_KEYWORDS=['setup',_0x1a7f77(0xd4,0x48),_0x1a7f77(0x76,0x88),_0x1a7f77(0x88,0x7c)+'t',_0x4a6f38(0x510,0x53b)+_0x4a6f38(0x554,0x55d),'설정','설치','환경설정',_0x1a7f77(0x43,-0x22)],LEARNING_KEYWORDS=[_0x4a6f38(0x54a,0x4c9),_0x4a6f38(0x5b6,0x52d),_0x4a6f38(0x4a5,0x498),_0x1a7f77(0x10a,0xe6),_0x1a7f77(0xc6,0xc6)+'t',_0x4a6f38(0x574,0x585),_0x1a7f77(0x36,0x6a),'배웠','깨달','발견',_0x4a6f38(0x5c0,0x587),'이해했'];function extractContexts(_0x5ed214,_0x38d9ed){const _0x796710={'biJxV':function(_0x4b60f5,_0x172a1c){return _0x4b60f5!==_0x172a1c;},'GhIbs':_0x98b5e6(-0xcd,-0x3e),'sDjQf':function(_0x1a788b,_0x4a759a){return _0x1a788b===_0x4a759a;},'aqgAY':_0x4dd00f(0x343,0x340),'TlvHF':function(_0x6cb3e4,_0x1542a1){return _0x6cb3e4>_0x1542a1;},'NHngt':function(_0x1a590a,_0x430bb6){return _0x1a590a>=_0x430bb6;},'bErxW':_0x98b5e6(0x16,0x37)};function _0x4dd00f(_0x5f26ef,_0x103035){return _0x4a6f38(_0x103035- -0x1d5,_0x5f26ef);}function _0x98b5e6(_0x3fe005,_0x4d073d){return _0x4a6f38(_0x3fe005- -0x5ae,_0x4d073d);}const _0x36a7fb=[];for(const _0x1181b5 of _0x5ed214){if(_0x796710[_0x4dd00f(0x392,0x3d3)](_0x1181b5[_0x98b5e6(-0xb9,-0x3d)],_0x98b5e6(-0xb2,-0x12f))&&_0x1181b5[_0x98b5e6(-0xb9,-0x119)]!==_0x796710['GhIbs'])continue;if(_0x796710['sDjQf'](_0x1181b5[_0x4dd00f(0x2d5,0x2eb)][_0x98b5e6(-0x24,-0xaf)],_0x98b5e6(-0xcd,-0xed)))continue;const _0x4493c9=getFullText(_0x1181b5);if(_0x4493c9[_0x4dd00f(0x3df,0x39d)]<0x32)continue;if(_0x4493c9[_0x4dd00f(0x3ae,0x379)](_0x4dd00f(0x311,0x330)+_0x4dd00f(0x411,0x3a5)))continue;if(_0x4493c9[_0x4dd00f(0x32d,0x379)](_0x796710[_0x98b5e6(-0x22,-0x5a)])&&_0x796710[_0x98b5e6(-0x7a,-0xc4)](_0x4493c9['length'],0x1f4))continue;const _0x11f58c=_0x4493c9[_0x98b5e6(-0xdd,-0x11e)+'e'](),_0x3689b4=CONTEXT_KEYWORDS[_0x98b5e6(-0x84,0x7)](_0x12d508=>_0x11f58c[_0x98b5e6(-0x60,-0xc2)](_0x12d508[_0x98b5e6(-0xdd,-0x138)+'e']())),_0x419744=_0x5ed214[_0x98b5e6(-0xe6,-0xf1)](_0x1181b5);(_0x419744<0x3||_0x796710[_0x98b5e6(-0xcc,-0xd9)](_0x3689b4[_0x98b5e6(-0x3c,-0x86)],0x2))&&_0x36a7fb['push']({'content':_0x4493c9[_0x4dd00f(0x3b9,0x35d)](0x0,0x3e8),'category':_0x796710[_0x98b5e6(-0x75,-0x6b)],'tier':_0x4dd00f(0x3a9,0x339),'tags':extractTags(_0x4493c9,_0x796710[_0x4dd00f(0x364,0x364)]),'projectPath':_0x38d9ed});}return _0x36a7fb;}function extractConventions(_0x235863,_0x289faf){const _0x5702db={'ZQuPU':function(_0x3693c7,_0x1dbf53){return _0x3693c7!==_0x1dbf53;},'MTOpr':_0x6f8563(0x665,0x637),'myuZW':_0x13a4b9(0x3d4,0x445),'ETnwf':_0x13a4b9(0x3e7,0x46f),'kmXqS':function(_0x507bee,_0x51fab5,_0x5d2b3f){return _0x507bee(_0x51fab5,_0x5d2b3f);}};function _0x6f8563(_0x3ed296,_0x1affd1){return _0x1a7f77(_0x1affd1-0x52e,_0x3ed296);}function _0x13a4b9(_0x1494f9,_0x375d80){return _0x1a7f77(_0x1494f9-0x38e,_0x375d80);}const _0x43b98b=[];for(const _0x31da35 of _0x235863){if(_0x31da35[_0x6f8563(0x5de,0x56e)]!=='human'&&_0x5702db[_0x6f8563(0x537,0x569)](_0x31da35[_0x6f8563(0x5d0,0x56e)],_0x5702db[_0x6f8563(0x5d8,0x604)]))continue;const _0x6a81e1=getFullText(_0x31da35);if(_0x6a81e1[_0x6f8563(0x665,0x5eb)]<0x14)continue;if(_0x31da35[_0x13a4b9(0x3ce,0x3ad)]==='assistant'){const _0x5a4290=/(?:should|must|always|never|recommend|규칙|원칙|필수|금지)/i[_0x13a4b9(0x39f,0x3f7)](_0x6a81e1);if(!_0x5a4290)continue;}const _0x4165da=CONVENTION_KEYWORDS['some'](_0x1ba614=>_0x6a81e1[_0x6f8563(0x570,0x54a)+'e']()[_0x13a4b9(0x427,0x3e7)](_0x1ba614[_0x6f8563(0x5b0,0x54a)+'e']()));if(!_0x4165da)continue;_0x43b98b[_0x13a4b9(0x382,0x349)]({'content':_0x6a81e1[_0x13a4b9(0x40b,0x3b5)](0x0,0x1f4),'category':_0x5702db[_0x6f8563(0x5a0,0x5d6)],'tier':_0x5702db[_0x6f8563(0x650,0x5e9)],'tags':_0x5702db['kmXqS'](extractTags,_0x6a81e1,'convention'),'projectPath':_0x289faf});}return _0x43b98b;}function extractLearnings(_0x40886f,_0x1399c1){const _0x1d1fb8={'VBlDt':function(_0x278541,_0x4ad272){return _0x278541!==_0x4ad272;},'knIUv':_0x3710da(-0xc6,-0xfc),'UlmUs':_0x3710da(-0x153,-0xe0),'flHGM':function(_0x121737,_0xb4f23,_0x54d663){return _0x121737(_0xb4f23,_0x54d663);}},_0x41c965=[];function _0x1379e7(_0x39ca5c,_0x5237cb){return _0x4a6f38(_0x5237cb- -0x9f,_0x39ca5c);}function _0x3710da(_0x253406,_0x43b30f){return _0x4a6f38(_0x43b30f- -0x674,_0x253406);}for(const _0x227c59 of _0x40886f){if(_0x1d1fb8[_0x1379e7(0x497,0x40c)](_0x227c59['type'],_0x3710da(-0x1df,-0x178))&&_0x1d1fb8[_0x3710da(-0x186,-0x1c9)](_0x227c59[_0x3710da(-0x184,-0x17f)],_0x3710da(-0x7d,-0xb6)))continue;const _0x4fac57=getFullText(_0x227c59);if(_0x4fac57[_0x1379e7(0x487,0x4d3)]<0x1e)continue;const _0x50f1b3=LEARNING_KEYWORDS[_0x3710da(-0x1fb,-0x1b7)](_0x3c57b4=>_0x4fac57[_0x1379e7(0x45a,0x432)+'e']()[_0x1379e7(0x473,0x4af)](_0x3c57b4[_0x1379e7(0x43d,0x432)+'e']()));if(!_0x50f1b3)continue;_0x41c965['push']({'content':_0x4fac57[_0x1379e7(0x462,0x493)](0x0,0x320),'category':_0x1d1fb8[_0x3710da(-0x19f,-0x172)],'tier':_0x1d1fb8['UlmUs'],'tags':_0x1d1fb8[_0x1379e7(0x4a0,0x4b1)](extractTags,_0x4fac57,_0x1d1fb8['knIUv']),'projectPath':_0x1399c1});}return _0x41c965;}function getFullText(_0x3e48e0){const _0x20181f={'jcwZd':function(_0x29eca1,_0x1c704a){return _0x29eca1===_0x1c704a;},'JjRPT':_0x402678(-0x73,-0x1d)+'t','Dlmym':'string'};if(typeof _0x3e48e0[_0x132a2d(0x2d0,0x2c4)]['content']===_0x20181f[_0x132a2d(0x2eb,0x2c8)])return _0x3e48e0[_0x132a2d(0x2d0,0x31d)]['content'];function _0x402678(_0x316c20,_0x5de842){return _0x4a6f38(_0x5de842- -0x50c,_0x316c20);}function _0x132a2d(_0x50479d,_0x115b2a){return _0x4a6f38(_0x50479d- -0x1f0,_0x115b2a);}return _0x3e48e0[_0x132a2d(0x2d0,0x24d)]['content'][_0x132a2d(0x32d,0x333)](_0x5bcac4=>{if(_0x20181f[_0x338494(0x595,0x59f)](_0x5bcac4[_0xcdc0f8(0x61e,0x64c)],_0x338494(0x542,0x4fe))&&_0x5bcac4[_0xcdc0f8(0x5e3,0x5bc)])return _0x5bcac4[_0x338494(0x542,0x531)];function _0xcdc0f8(_0x2facc2,_0x4cc007){return _0x402678(_0x4cc007,_0x2facc2-0x635);}if(_0x5bcac4[_0xcdc0f8(0x61e,0x68c)]===_0x20181f[_0x338494(0x5d5,0x590)]&&_0x5bcac4[_0xcdc0f8(0x6b9,0x72c)])return _0x5bcac4['content'];function _0x338494(_0x30587d,_0x34c7d8){return _0x402678(_0x34c7d8,_0x30587d-0x594);}return'';})[_0x132a2d(0x33a,0x343)](Boolean)[_0x132a2d(0x3ae,0x385)]('\x0a');}const TECH_NAMES=['react','vue','angular',_0x1a7f77(0x1b,0x5b),'javascript','python',_0x1a7f77(0x7a,0x22),'postgresql',_0x1a7f77(-0xf,-0x2e),'redis','docker','kubernetes',_0x4a6f38(0x56d,0x539),'gcp',_0x4a6f38(0x52c,0x4ae),_0x1a7f77(0xcf,0xef),_0x4a6f38(0x5bb,0x625),_0x4a6f38(0x5bd,0x549),'git',_0x4a6f38(0x59d,0x598),_0x1a7f77(-0x7,0x8a),_0x4a6f38(0x56e,0x51d),_0x1a7f77(0x2a,0x9c),_0x1a7f77(0x27,-0x56),'vitest','jest',_0x1a7f77(0xb7,0x104),_0x1a7f77(0x71,0x10)],WORK_TYPES=[_0x4a6f38(0x563,0x4ff),_0x4a6f38(0x511,0x594),'refactor','test',_0x1a7f77(0x72,0x64),_0x1a7f77(0xa9,0xc9),_0x1a7f77(0xdc,0x77),_0x4a6f38(0x4ee,0x54c),_0x1a7f77(0xb1,0x70),_0x4a6f38(0x4b8,0x4a9),_0x1a7f77(0xac,0xcc),_0x1a7f77(0xb4,0x22),_0x1a7f77(0x10e,0x131),'upgrade'],LOW_VALUE_EXTS=new Set(['md',_0x1a7f77(0x93,0xc1),_0x1a7f77(0x91,0x50),_0x1a7f77(0x24,-0x18),_0x1a7f77(0x45,0x8b),_0x4a6f38(0x4fe,0x574),'html',_0x4a6f38(0x4b0,0x53b)]),MEANINGFUL_EXTS=new Set(['py','ts',_0x4a6f38(0x4e9,0x497),'js','jsx',_0x4a6f38(0x52f,0x523),'go','rs','rb',_0x1a7f77(0xf5,0x179),'kt']);function _0x128a(){const _0x244827=['vwTpEvu','BgvHCM5Lza','BgXTlwv4DhjHyW','64UK7j2mioQWNoUWNcdRJidTMztSL5dSHjW','sMPsufq','Aw5JBhvKzxm','CfffrK0','zMXir00','zMLSzv9WyxrO','zKLiv0O','EMr5zMS','DgLVBG','B3DSzwrNzq','AwnHDgLVBG','C2HVDwXK','6RkW7kcv7zAi','C3rYyxrLz3K','y291BNq','C29YDa','C3rHCNrZv2L0Aa','BxL1wLC','B3b0Aw1PEMu','BwLU','Dg9VBf91C2u','CMvSzwfZzq','ioUWMo2zMcaO66Ei7ygS64UK7jQ0ia','zgvWBg95','BNrLBNqSihrHzW','BNfKrhm','y29UzMLN','C3vTBwfYAxPL','ChjLzMvY','zML4','vhjHy2vIywnR','r3bzvuK','CgXHExDYAwDODa','yxDZ','D2vICgfJAW','zwztuKy','rvrUD2y','Bwf0y2G','BgvUz3rO','rgLYzwn0B3jPzq','zgLZy292zxj5','zMLUza','BMv2zxi','AgfZ','BgvHCM5PBMC','BKDWsKy','BwLUzgvYpG','zMLNDxjLzcbVDq','yKn0sKi','AwyG','Dhj5','DxnL','vg1JzMi','Aw1WB3j0ia','mteYnJyWrMnJsM5x','nty5oteZnKHnrff2wq','zxHWCMvZCW','D09bDg0','whbcyKW','v1rhAeW','A1Ldrfa','Aw5ZDgfSBa','CM9Szq','tvrpChi','yxfNqvK','BMfTzq','Cgf0DgvYBG','66gCioUWMo2zMc4kcUUmGo2zLdO','y29UDgvUDa','BwLNCMf0zq','BfPeswC','mZG1nduYCuL6A3vO','zxbPC29KAwm','DhjHy2vIywnR','vgj6z3G','u3bYu1q','zgvJAwrLza','zMLSDgvYzwq','nty5nZaWBvf4qMT5','CNvSzq','z2LZzfi','z3jHCgHXBa','AM9PBG','Cgf0DgvYBI9Kzq','oIaIlI4UiIWGiG','y2XHC3m','Dg9VBc11C2fNzq','zMfJDa','AxnbCNjHEq','ntKXmJa1tuPxCNL2','y2XHC3nPzNK','DMfYia','yMLkEfy','DeHbteW','C3DPzNq','uujOBfi','ChjVAMvJDf9RBG','q0HbtKDfte9h','cGPBu29SDxrPBW','zef5t1u','zMfPBgvK','zgLMzIaTlwDPDa','ChjVy2vKDxjL','BwvTB3jPzxm','C3r5Bgu','mJbvwKzAAgK','veLm','r3jLCa','w3SIy2f0zwDVCG','A0vvCwi','vg9VBcaI','BMv4Dc5QCW','qKn0BNq','BM9Kzs5QCW','yxnZAxn0yw50','Dw5KzxjZDg9Vza','7jwm6RkmioUqKa','y29TCgXLDgu','yxbWCM9Hy2G','Aw1WBgvTzw50','y29UDgv4Da','nMjRv01ura','CZOG','CMvZB2X2zq','ioUcMoYKKEYxKcdSNkdSMQNTLAaG7zw1','DgfNCW','icjJB250zw50iG','CMvHBgL6zwq','BxLZCwW','zMLSzs1TB2rPzG','rxjYB3i','ChvZAa','v0f6vNq','vKjSrhq','zxbPC29Kzq','y2LZAw9Ul3bYBW','CMvZDa','r2XVyG','y3nZ','Dw5RBM93BG','uLfUvM0','DxvPza','BwfRzsbZDxjL','Bwf4','sfnJD1i','r0jkEMK','yNvPBgq','v2vIrMv0y2G','Dgv4Da','qKLPEem','DhrLCM46ia','C29Tzq','C2fTCgXLCW','zgvJAxnPB24','BwvZC2fNzq','t1jwtei','zM9Yia','B3b0zwqGzM9Y','BM93','CgfYC2u','DgvZDa','BgfZDeLUzgv4tW','Aw5KzxHpzG','svj5thq','Esi6iciUlI4Ila','zxHJzxb0Aw9U','txLpyu0','C3rYAw5N','y1fKwui','tgvTvue','DhLWzxnJCMLWDa','Dg9mB3DLCKnHCW','vgLbBee','ywX3yxLZ','CMf0AgvYihrOyq','C3bSAxq','DhjPBq','DgvK','zw9Quw0','Ew1S','CMv0DxjUia','rgXTEw0','zxnSAw50','zNvUy3rPB24','uvvSBwu','DML0zq','uMvHza','C3LZDgvT','tKHUz3q','Bgv0ia','CePQv2G','zNvUy3rPB24G','y2f0zwDVCNK','Aw5WDxq','AwvSrMS','Dhn4','C2v0','Aw5ZAwDODa','t1LmBMe','quHRC3O','C2v0Dxa','Dg9VBf9Yzxn1Ba','wLf1ufu','m2feuKrzEq','y2HVC2u','D0nNB24','Egrnv0y','DhLWzq','EwDmExa','Ewjfyvu','7lsi6RIW7zMu','sxvABe0','EwfTBa','y29UDMvUDgLVBG','AhvTyw4','zxHWzxjPzw5Jzq','Eg1S','y29UC3qG','v3jPDgu','CMvWBgfJzq','A25jvxy','rxHJzxb0Aw9U','C3rYAw5NAwz5','phn5C3rLBs1Yzq','z3zhz2O','Bwf0y2HdB3vUDa','zNnWz2i','7iUSioYNGoYlNEYDHcaZFJxQSjW','C2L6zq','zgvMia','zxHWB3j0','AMn3wMq','C2vTyw50Awm','Evz4q20','Aw5PDgLHBgL6yq','zgvIDwC','vuLPD2G','rwrPDa','qLLez0S','q0XbvurflM1K','BNrPB24PlcbJBW','y2HHBMDL','DxbKyxrL','rK5uDwK','tNvPsNG','C29SDxrPB24','DgLTzxn0yw1W','BwfW','uNfhAwS','mJG1ntG2n2P3B2DNuG','y29Kzv9Wyxr0zq','tgrnvhu','BwvTB3j5vhLWzq','zxjYB3jFC29SDq','zw5ZDxjL','uur0C3q','C3fSAxrL','CMv2Awv3','y29Kzs1Wyxr0zq','nduXB2HkzKDm','zMLSDgvY','y29UzMLNDxjL','zMfZDgfWAq','uMLWwgy','DgLVBI9JB2rLxW','AMf2yq','mtKXoty4qvjUEvfX','zxjYB3i','C2XPy2u','w0vYCM9Yxsa','vgX2sey','zw50CMLLCW','uxbdCgC','C+ULVcbku09oioUWSoYxTa','z2v0','yKvYEfC','EvrhrfO','y2XHC3mG','r1nvt1e','zw52AxjVBM1LBG','q29KzsbTB2rPzG','AMvJDf9RBM93Ba','7l2u65oCioU4LoUHNsdSL4BSNBqPoG','BhjPC3e','cGPku09oioUWSoYxToUNJa','ioY2LoY2No2vMoYeUoYALc4k6Rcb6Rcb','ChnRwM0','suPNq2W','ANnVBG','iIb1C2vKia','DhH0'];_0x128a=function(){return _0x244827;};return _0x128a();}function extractTags(_0x38690c,_0x5df936){const _0x3dbc38=[_0x5df936],_0x2d33eb=_0x38690c[_0x22f498(-0xc3,-0x7c)](/[\w/.-]{1,200}\.\w{1,10}/g);if(_0x2d33eb){const _0x586b11=new Set(_0x2d33eb[_0x22f498(-0x117,-0x89)](_0x13389f=>_0x13389f['split']('.')['pop']())[_0x3ba391(0x2fc,0x2c6)](_0x5c3462=>_0x5c3462['length']<=0x5&&_0x5c3462[_0x3ba391(0x344,0x32f)]>0x1)[_0x3ba391(0x2fc,0x2e4)](_0x799c11=>!/^\d+$/[_0x22f498(-0x16e,-0x1f7)](_0x799c11))[_0x3ba391(0x2fc,0x29d)](_0xd3092d=>!LOW_VALUE_EXTS[_0x22f498(-0xbd,-0x12e)](_0xd3092d[_0x3ba391(0x2a3,0x2ae)+'e']()))[_0x3ba391(0x2fc,0x321)](_0x3f711e=>MEANINGFUL_EXTS[_0x22f498(-0xbd,-0xb1)](_0x3f711e[_0x3ba391(0x2a3,0x2e2)+'e']())));_0x3dbc38[_0x3ba391(0x27b,0x2a1)](...[..._0x586b11][_0x3ba391(0x304,0x298)](0x0,0x2));}const _0x17daf6=_0x38690c[_0x22f498(-0x163,-0x17e)+'e']();for(const _0xb18f of TECH_NAMES){_0x17daf6[_0x22f498(-0xe6,-0xbf)](_0xb18f)&&_0x3dbc38[_0x3ba391(0x27b,0x29b)](_0xb18f);}function _0x3ba391(_0xfa802c,_0x136106){return _0x4a6f38(_0xfa802c- -0x22e,_0x136106);}for(const _0x35bae5 of WORK_TYPES){if(_0x17daf6['includes'](_0x35bae5)){_0x3dbc38[_0x22f498(-0x18b,-0x1aa)](_0x35bae5);break;}}function _0x22f498(_0x599bad,_0x3929a9){return _0x4a6f38(_0x599bad- -0x634,_0x3929a9);}return[...new Set(_0x3dbc38)][_0x22f498(-0x10a,-0x11a)](_0x1729dd=>_0x1729dd['length']>=0x2&&!/^\d+$/['test'](_0x1729dd))[_0x3ba391(0x2ef,0x2f8)](_0x515725=>_0x515725[_0x3ba391(0x2a3,0x31f)+'e']())['slice'](0x0,0x5);}function deduplicateMemories(_0xf5d99c){return deduplicateByContent(_0xf5d99c,0.7);}const CLASSIFIABLE_CATEGORIES=[_0x1a7f77(0x6e,-0x1b)+_0x1a7f77(0x9f,0x5e),_0x1a7f77(0x6b,0x92)+'rn',_0x4a6f38(0x4bf,0x506),'convention',_0x4a6f38(0x59b,0x615),_0x1a7f77(0xf7,0xf2)+_0x1a7f77(0xa0,0xaa),_0x4a6f38(0x578,0x602)];async function _llmExtractSupplemental(_0x1a80e7,_0x50399a,_0x4bc6dc){const _0x21127d={'lrisq':_0x22e2f9(0x57,0xa8)},_0x314e14=_0x1a80e7[_0x22e2f9(0xbe,0xde)](-0x14);function _0x22e2f9(_0x4be2a3,_0x21b10b){return _0x4a6f38(_0x21b10b- -0x454,_0x4be2a3);}const _0x3837f6=_0x314e14[_0x22e2f9(0xc3,0xc9)](_0x2e6e8a=>{function _0x56e59f(_0x54dd4f,_0x47ab09){return _0x22e2f9(_0x47ab09,_0x54dd4f-0x2db);}function _0x216244(_0x357382,_0x31ca47){return _0x22e2f9(_0x31ca47,_0x357382-0x3e9);}const _0x12fb97=_0x2e6e8a[_0x56e59f(0x37c,0x3af)]===_0x21127d[_0x216244(0x4d6,0x525)]?'User':'Assistant',_0x5644db=getFullText(_0x2e6e8a)[_0x56e59f(0x3b9,0x43d)](0x0,0x1f4);return'['+_0x12fb97+']:\x20'+_0x5644db;})['filter'](_0x16b6f2=>_0x16b6f2[_0x49259c(-0x117,-0xc0)]>0xa)[_0x22e2f9(0x122,0x14a)]('\x0a\x0a')['slice'](0x0,0x1770);if(!_0x3837f6)return[];const _0x22b088=_0x49259c(-0xd1,-0x109)+_0x22e2f9(0x3e,0x76)+_0x49259c(-0x1e5,-0x183)+_0x49259c(-0xe9,-0x89)+'tags\x22:\x20[\x22.'+'..\x22]}]',_0x470fb0=_0x49259c(-0x13d,-0x121)+_0x22e2f9(-0x9,0x4e)+_0x22e2f9(0xe1,0xb5)+_0x22e2f9(0x159,0xef)+'\x20category('+'error_solu'+_0x49259c(-0x15b,-0x1db)+_0x22e2f9(0x1bf,0x14b)+_0x49259c(-0x1dc,-0x1a2)+_0x49259c(-0x14a,-0x1c7)+'edge/conve'+_0x49259c(-0x173,-0x1b9)+_0x22e2f9(0x98,0x110)+_0x49259c(-0x152,-0x121)+_0x49259c(-0xfa,-0x119)+'\x0a'+_0x3837f6+(_0x22e2f9(0x8b,0xee)+_0x49259c(-0x127,-0x1ac)+_0x49259c(-0x149,-0x11d)+'\x0a')+_0x22b088;function _0x49259c(_0x164e85,_0x44c104){return _0x4a6f38(_0x164e85- -0x689,_0x44c104);}try{const _0x4778e4=await _0x50399a[_0x22e2f9(0x161,0x16d)](_0x470fb0),_0x4ff64a=_0x4778e4[_0x49259c(-0x188,-0x197)](/```(?:json)?\s*\n?([\s\S]*?)\n?```/g,'$1')[_0x22e2f9(0xd0,0x82)](),_0x4a79d5=JSON[_0x22e2f9(0xe6,0x71)](_0x4ff64a);if(!Array['isArray'](_0x4a79d5))return[];return _0x4a79d5[_0x22e2f9(0xa2,0xd6)](_0x1e1272=>_0x1e1272[_0x49259c(-0xf9,-0x75)]&&_0x1e1272[_0x49259c(-0xf9,-0x7b)][_0x22e2f9(0x8c,0x11e)]>=0x32&&CLASSIFIABLE_CATEGORIES[_0x49259c(-0x13b,-0x162)](_0x1e1272[_0x22e2f9(0xf1,0x92)]))[_0x49259c(-0x16c,-0x11a)](_0x524d8a=>({'content':_0x524d8a['content'][_0x22e2f9(0x144,0xde)](0x0,0x320),'category':_0x524d8a[_0x49259c(-0x1a3,-0x138)],'tier':_0x22e2f9(0xde,0xba),'tags':Array[_0x22e2f9(0x111,0x150)](_0x524d8a[_0x22e2f9(0x72,0x4f)])?_0x524d8a[_0x22e2f9(0xc4,0x4f)][_0x49259c(-0x157,-0x153)](0x0,0x5):[_0x49259c(-0x13e,-0xd4)+_0x22e2f9(0xb2,0x83)],'projectPath':_0x4bc6dc}));}catch{return[];}}export async function extractMemoriesWithLLM(_0x5ed0e3,_0x288d4e,_0x16b3e8){const _0x2bacc2={'SprST':function(_0x58d7b0,_0xc58485){return _0x58d7b0>=_0xc58485;},'HScwR':function(_0x1029f4,_0x328e7f,_0x157da7,_0x40a7e3){return _0x1029f4(_0x328e7f,_0x157da7,_0x40a7e3);},'pskZm':_0x37fe08(0x2be,0x327)},_0x2a9dd6=extractMemories(_0x5ed0e3,_0x288d4e);if(!_0x16b3e8)return _0x2a9dd6;function _0x19d70b(_0x3fabc7,_0x1682f6){return _0x1a7f77(_0x1682f6-0x82,_0x3fabc7);}if(_0x2a9dd6['memories'][_0x37fe08(0x371,0x36b)]<=0x3&&_0x2bacc2[_0x19d70b(0x19a,0x164)](_0x5ed0e3['length'],0xa))try{const _0x410ad8=await _0x2bacc2[_0x37fe08(0x2b5,0x325)](_llmExtractSupplemental,_0x5ed0e3,_0x16b3e8,_0x288d4e);_0x2a9dd6[_0x19d70b(0x130,0x180)]['push'](..._0x410ad8);}catch{}function _0x37fe08(_0x2f3997,_0x159cf3){return _0x1a7f77(_0x2f3997-0x2b4,_0x159cf3);}const _0x28db44=[_0x19d70b(0x19c,0x191),_0x2bacc2[_0x19d70b(0x9e,0x111)],'convention'];for(let _0x3149d9=0x0;_0x3149d9<_0x2a9dd6['memories']['length'];_0x3149d9++){if(!_0x28db44[_0x37fe08(0x34d,0x3d0)](_0x2a9dd6['memories'][_0x3149d9]['category']))continue;try{const _0xe209c7=await _0x16b3e8[_0x37fe08(0x3a5,0x325)](_0x2a9dd6[_0x37fe08(0x3b2,0x350)][_0x3149d9][_0x19d70b(0xd7,0x15d)],CLASSIFIABLE_CATEGORIES);CLASSIFIABLE_CATEGORIES['includes'](_0xe209c7)&&(_0x2a9dd6[_0x19d70b(0x1dd,0x180)][_0x3149d9]={..._0x2a9dd6['memories'][_0x3149d9],'category':_0xe209c7});}catch{}}return _0x2a9dd6;}export async function summarizeSession(_0x52c37c,_0x5d66d4){const _0x4624cb=_0x52c37c['filter'](_0xc47bac=>_0xc47bac[_0x390e3e(0x10c,0x105)]===_0x114a05(0x27,-0x14))[_0x114a05(-0xc4,-0xb5)](_0x78fea9=>{function _0x1de79f(_0xb797b3,_0xb7ce23){return _0x390e3e(_0xb797b3,_0xb7ce23-0x19c);}if(typeof _0x78fea9[_0x1d5650(0x4c7,0x4c3)][_0x1d5650(0x5ac,0x593)]===_0x1de79f(0x2ac,0x279))return _0x78fea9[_0x1d5650(0x545,0x4c3)]['content'];function _0x1d5650(_0x51c2f2,_0x1bd52e){return _0x390e3e(_0x51c2f2,_0x1bd52e-0x3f3);}return _0x78fea9[_0x1de79f(0x2de,0x26c)][_0x1de79f(0x2f0,0x33c)][_0x1d5650(0x536,0x52d)](_0x535466=>_0x535466['type']===_0x1d5650(0x51f,0x4bd)&&_0x535466[_0x1de79f(0x2bb,0x266)])[_0x1d5650(0x498,0x520)](_0x37c72c=>_0x37c72c[_0x1de79f(0x2ea,0x266)])[_0x1de79f(0x37c,0x34a)]('\x0a');})[_0x114a05(-0x9d,-0xa8)](_0x48c750=>_0x48c750['length']>0x14)['slice'](0x0,0xa);function _0x390e3e(_0x5245ac,_0x121d0a){return _0x4a6f38(_0x121d0a- -0x3f0,_0x5245ac);}function _0x114a05(_0x54445b,_0x2f0e3e){return _0x4a6f38(_0x2f0e3e- -0x5d2,_0x54445b);}if(_0x4624cb['length']===0x0)return'';return _0x5d66d4[_0x390e3e(0x1c0,0x177)](_0x4624cb);}
|