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,241 +1 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Memory Synchronizer
|
|
3
|
-
* 로컬 메모리(캐시)와 원격 A2A 서버(Single Source of Truth) 간 동기화
|
|
4
|
-
*/
|
|
5
|
-
import { SyncQueue, mapCategory, mapTier } from './queue.js';
|
|
6
|
-
import { TeamSynchronizer } from './team-synchronizer.js';
|
|
7
|
-
const DEFAULT_PAGE_SIZE = 100;
|
|
8
|
-
export class MemorySynchronizer {
|
|
9
|
-
db;
|
|
10
|
-
client;
|
|
11
|
-
teamPath;
|
|
12
|
-
nodeId;
|
|
13
|
-
queue;
|
|
14
|
-
failures = 0;
|
|
15
|
-
lastFailureAt = 0;
|
|
16
|
-
maxFailures = 3;
|
|
17
|
-
cooldownMs = 30000;
|
|
18
|
-
constructor(db, client, teamPath, nodeId) {
|
|
19
|
-
this.db = db;
|
|
20
|
-
this.client = client;
|
|
21
|
-
this.teamPath = teamPath;
|
|
22
|
-
this.nodeId = nodeId;
|
|
23
|
-
this.queue = new SyncQueue(db, client);
|
|
24
|
-
}
|
|
25
|
-
isCircuitOpen() {
|
|
26
|
-
if (this.failures < this.maxFailures)
|
|
27
|
-
return false;
|
|
28
|
-
return (Date.now() - this.lastFailureAt) < this.cooldownMs;
|
|
29
|
-
}
|
|
30
|
-
recordSuccess() {
|
|
31
|
-
this.failures = 0;
|
|
32
|
-
}
|
|
33
|
-
recordFailure() {
|
|
34
|
-
this.failures++;
|
|
35
|
-
this.lastFailureAt = Date.now();
|
|
36
|
-
}
|
|
37
|
-
/**
|
|
38
|
-
* 양방향 동기화 (team 모드 시 TeamSynchronizer에 위임)
|
|
39
|
-
*/
|
|
40
|
-
async sync() {
|
|
41
|
-
if (this.teamPath && this.nodeId) {
|
|
42
|
-
const teamSync = new TeamSynchronizer(this.db, this.client, this.teamPath, this.nodeId);
|
|
43
|
-
const teamResult = await teamSync.syncDelta();
|
|
44
|
-
return {
|
|
45
|
-
pushed: teamResult.pushed,
|
|
46
|
-
pulled: teamResult.pulled,
|
|
47
|
-
conflicts: teamResult.conflicts,
|
|
48
|
-
errors: teamResult.errors,
|
|
49
|
-
duration: teamResult.duration,
|
|
50
|
-
};
|
|
51
|
-
}
|
|
52
|
-
return this.syncLocal();
|
|
53
|
-
}
|
|
54
|
-
/**
|
|
55
|
-
* 로컬 양방향 동기화 (기존 로직)
|
|
56
|
-
*/
|
|
57
|
-
async syncLocal() {
|
|
58
|
-
const startTime = Date.now();
|
|
59
|
-
const result = {
|
|
60
|
-
pushed: 0,
|
|
61
|
-
pulled: 0,
|
|
62
|
-
conflicts: 0,
|
|
63
|
-
errors: [],
|
|
64
|
-
duration: 0,
|
|
65
|
-
};
|
|
66
|
-
try {
|
|
67
|
-
// 1. Push (로컬→원격)
|
|
68
|
-
const pushResult = await this.push();
|
|
69
|
-
result.pushed = pushResult.pushed;
|
|
70
|
-
result.errors.push(...pushResult.errors);
|
|
71
|
-
// 2. Pull (원격→로컬)
|
|
72
|
-
const pullResult = await this.pull();
|
|
73
|
-
result.pulled = pullResult.pulled;
|
|
74
|
-
result.conflicts = pullResult.conflicts;
|
|
75
|
-
result.errors.push(...pullResult.errors);
|
|
76
|
-
}
|
|
77
|
-
catch (error) {
|
|
78
|
-
if (error instanceof Error) {
|
|
79
|
-
result.errors.push(error.message);
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
result.duration = Date.now() - startTime;
|
|
83
|
-
return result;
|
|
84
|
-
}
|
|
85
|
-
/**
|
|
86
|
-
* 로컬→원격 (SyncQueue에 위임)
|
|
87
|
-
*/
|
|
88
|
-
async push(options) {
|
|
89
|
-
if (this.isCircuitOpen()) {
|
|
90
|
-
return { pushed: 0, pulled: 0, conflicts: 0, errors: ['Circuit breaker open: too many consecutive failures'], duration: 0 };
|
|
91
|
-
}
|
|
92
|
-
const startTime = Date.now();
|
|
93
|
-
try {
|
|
94
|
-
const flushResult = await this.queue.flush({
|
|
95
|
-
timeoutMs: options?.timeoutMs,
|
|
96
|
-
});
|
|
97
|
-
// tombstone 동기화 (삭제된 메모리 원격 삭제)
|
|
98
|
-
const tombstoneResult = await this.queue.flushTombstones();
|
|
99
|
-
const allErrors = [...flushResult.errors, ...tombstoneResult.errors];
|
|
100
|
-
if (allErrors.length > 0) {
|
|
101
|
-
this.recordFailure();
|
|
102
|
-
}
|
|
103
|
-
else {
|
|
104
|
-
this.recordSuccess();
|
|
105
|
-
}
|
|
106
|
-
return {
|
|
107
|
-
pushed: flushResult.pushed,
|
|
108
|
-
pulled: tombstoneResult.deleted,
|
|
109
|
-
conflicts: 0,
|
|
110
|
-
errors: allErrors,
|
|
111
|
-
duration: Date.now() - startTime,
|
|
112
|
-
};
|
|
113
|
-
}
|
|
114
|
-
catch (error) {
|
|
115
|
-
this.recordFailure();
|
|
116
|
-
throw error;
|
|
117
|
-
}
|
|
118
|
-
}
|
|
119
|
-
/**
|
|
120
|
-
* 원격→로컬 (페이지네이션 적용)
|
|
121
|
-
*/
|
|
122
|
-
async pull() {
|
|
123
|
-
if (this.isCircuitOpen()) {
|
|
124
|
-
return { pushed: 0, pulled: 0, conflicts: 0, errors: ['Circuit breaker open: too many consecutive failures'], duration: 0 };
|
|
125
|
-
}
|
|
126
|
-
const startTime = Date.now();
|
|
127
|
-
const result = {
|
|
128
|
-
pushed: 0,
|
|
129
|
-
pulled: 0,
|
|
130
|
-
conflicts: 0,
|
|
131
|
-
errors: [],
|
|
132
|
-
duration: 0,
|
|
133
|
-
};
|
|
134
|
-
try {
|
|
135
|
-
let offset = 0;
|
|
136
|
-
let hasMore = true;
|
|
137
|
-
while (hasMore) {
|
|
138
|
-
const remoteMemories = await this.client.listMemories({
|
|
139
|
-
limit: DEFAULT_PAGE_SIZE,
|
|
140
|
-
offset,
|
|
141
|
-
includeEmbedding: true,
|
|
142
|
-
});
|
|
143
|
-
if (remoteMemories.length === 0) {
|
|
144
|
-
hasMore = false;
|
|
145
|
-
break;
|
|
146
|
-
}
|
|
147
|
-
// Parent-first: parent_id가 없는 것(Parent/독립) 먼저 처리하여 FK 참조 무결성 보장
|
|
148
|
-
remoteMemories.sort((a, b) => {
|
|
149
|
-
const aIsChild = a.parent_id ? 1 : 0;
|
|
150
|
-
const bIsChild = b.parent_id ? 1 : 0;
|
|
151
|
-
return aIsChild - bIsChild;
|
|
152
|
-
});
|
|
153
|
-
for (const remote of remoteMemories) {
|
|
154
|
-
try {
|
|
155
|
-
const existing = this.db.findMemoryByRemoteId(remote.id);
|
|
156
|
-
if (!existing) {
|
|
157
|
-
// 새로운 메모리 — category/tier 매핑 적용
|
|
158
|
-
const created = this.db.createMemory({
|
|
159
|
-
content: remote.content,
|
|
160
|
-
category: mapCategory(remote.category),
|
|
161
|
-
tier: mapTier(remote.tier ?? 'episodic'),
|
|
162
|
-
tags: remote.tags ?? [],
|
|
163
|
-
parentId: remote.parent_id ?? undefined,
|
|
164
|
-
chunkIndex: remote.chunk_index ?? undefined,
|
|
165
|
-
chunkTotal: remote.chunk_total ?? undefined,
|
|
166
|
-
});
|
|
167
|
-
// 임베딩 저장
|
|
168
|
-
if (remote.embedding && remote.embedding.length > 0) {
|
|
169
|
-
this.db.saveEmbedding(created.id, remote.embedding);
|
|
170
|
-
}
|
|
171
|
-
this.db.setSyncStatus(created.id, remote.id, 'synced');
|
|
172
|
-
result.pulled++;
|
|
173
|
-
}
|
|
174
|
-
else {
|
|
175
|
-
// 충돌 검사 (updated_at 비교)
|
|
176
|
-
const remoteUpdated = new Date(remote.updated_at);
|
|
177
|
-
const localUpdated = new Date(existing.updatedAt);
|
|
178
|
-
if (remoteUpdated > localUpdated) {
|
|
179
|
-
this.db.updateMemory(existing.id, {
|
|
180
|
-
content: remote.content,
|
|
181
|
-
category: mapCategory(remote.category),
|
|
182
|
-
tier: mapTier(remote.tier ?? existing.tier),
|
|
183
|
-
tags: remote.tags ?? existing.tags,
|
|
184
|
-
});
|
|
185
|
-
// 임베딩 업데이트
|
|
186
|
-
if (remote.embedding && remote.embedding.length > 0) {
|
|
187
|
-
this.db.saveEmbedding(existing.id, remote.embedding);
|
|
188
|
-
}
|
|
189
|
-
this.db.setSyncStatus(existing.id, remote.id, 'synced');
|
|
190
|
-
result.conflicts++;
|
|
191
|
-
}
|
|
192
|
-
}
|
|
193
|
-
}
|
|
194
|
-
catch (error) {
|
|
195
|
-
if (error instanceof Error) {
|
|
196
|
-
result.errors.push(`메모리 ${remote.id} 풀 실패: ${error.message}`);
|
|
197
|
-
}
|
|
198
|
-
}
|
|
199
|
-
}
|
|
200
|
-
// 다음 페이지
|
|
201
|
-
if (remoteMemories.length < DEFAULT_PAGE_SIZE) {
|
|
202
|
-
hasMore = false;
|
|
203
|
-
}
|
|
204
|
-
else {
|
|
205
|
-
offset += DEFAULT_PAGE_SIZE;
|
|
206
|
-
}
|
|
207
|
-
}
|
|
208
|
-
this.recordSuccess();
|
|
209
|
-
}
|
|
210
|
-
catch (error) {
|
|
211
|
-
this.recordFailure();
|
|
212
|
-
if (error instanceof Error) {
|
|
213
|
-
result.errors.push(error.message);
|
|
214
|
-
}
|
|
215
|
-
}
|
|
216
|
-
result.duration = Date.now() - startTime;
|
|
217
|
-
return result;
|
|
218
|
-
}
|
|
219
|
-
/**
|
|
220
|
-
* 동기화 상태 확인
|
|
221
|
-
*/
|
|
222
|
-
async getStatus() {
|
|
223
|
-
const pendingPush = this.queue.getPendingCount();
|
|
224
|
-
let pendingPull = 0;
|
|
225
|
-
try {
|
|
226
|
-
const remote = await this.client.listMemories({ limit: 10000 });
|
|
227
|
-
const localSynced = this.db.getSyncedMemoryCount();
|
|
228
|
-
pendingPull = Math.max(0, remote.length - localSynced);
|
|
229
|
-
}
|
|
230
|
-
catch {
|
|
231
|
-
// 원격 접속 실패 시 0
|
|
232
|
-
}
|
|
233
|
-
const lastSyncedAt = this.db.getLastSyncedAt();
|
|
234
|
-
return {
|
|
235
|
-
pendingPush,
|
|
236
|
-
pendingPull,
|
|
237
|
-
lastSyncedAt: lastSyncedAt ?? undefined,
|
|
238
|
-
};
|
|
239
|
-
}
|
|
240
|
-
}
|
|
241
|
-
//# sourceMappingURL=synchronizer.js.map
|
|
1
|
+
(function(_0xd8a5c8,_0x47e659){function _0x35131b(_0x359dc3,_0x37d075){return _0x21f8(_0x37d075- -0x1b4,_0x359dc3);}const _0x3204ee=_0xd8a5c8();function _0x311d32(_0x10c58c,_0x5e053f){return _0x21f8(_0x10c58c- -0x10a,_0x5e053f);}while(!![]){try{const _0x2bac11=parseInt(_0x311d32(0x11a,0x142))/0x1+-parseInt(_0x311d32(0x13e,0x130))/0x2+-parseInt(_0x35131b(0x56,0x5e))/0x3*(parseInt(_0x35131b(0xa4,0x95))/0x4)+-parseInt(_0x35131b(0x64,0x87))/0x5*(-parseInt(_0x35131b(0x62,0x3f))/0x6)+-parseInt(_0x35131b(0x3c,0x55))/0x7+parseInt(_0x311d32(0xea,0xcc))/0x8*(-parseInt(_0x35131b(0x46,0x50))/0x9)+parseInt(_0x35131b(0x6e,0x7b))/0xa*(parseInt(_0x311d32(0xf5,0xdb))/0xb);if(_0x2bac11===_0x47e659)break;else _0x3204ee['push'](_0x3204ee['shift']());}catch(_0x578e48){_0x3204ee['push'](_0x3204ee['shift']());}}}(_0x2dc4,0x75813));function _0x21f8(_0x46903b,_0x514c38){_0x46903b=_0x46903b-0x1ee;const _0x2dc40a=_0x2dc4();let _0x21f8a0=_0x2dc40a[_0x46903b];if(_0x21f8['pONIet']===undefined){var _0x2c59c5=function(_0x39521c){const _0x5bc54d='abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=';let _0x365c6b='',_0x4e06b5='';for(let _0x2d1c85=0x0,_0x139022,_0x2acc0b,_0x188dfd=0x0;_0x2acc0b=_0x39521c['charAt'](_0x188dfd++);~_0x2acc0b&&(_0x139022=_0x2d1c85%0x4?_0x139022*0x40+_0x2acc0b:_0x2acc0b,_0x2d1c85++%0x4)?_0x365c6b+=String['fromCharCode'](0xff&_0x139022>>(-0x2*_0x2d1c85&0x6)):0x0){_0x2acc0b=_0x5bc54d['indexOf'](_0x2acc0b);}for(let _0x431d63=0x0,_0x14d88b=_0x365c6b['length'];_0x431d63<_0x14d88b;_0x431d63++){_0x4e06b5+='%'+('00'+_0x365c6b['charCodeAt'](_0x431d63)['toString'](0x10))['slice'](-0x2);}return decodeURIComponent(_0x4e06b5);};_0x21f8['fxOQSS']=_0x2c59c5,_0x21f8['OPkRAI']={},_0x21f8['pONIet']=!![];}const _0x15fa2d=_0x2dc40a[0x0],_0x2ed208=_0x46903b+_0x15fa2d,_0x260b54=_0x21f8['OPkRAI'][_0x2ed208];return!_0x260b54?(_0x21f8a0=_0x21f8['fxOQSS'](_0x21f8a0),_0x21f8['OPkRAI'][_0x2ed208]=_0x21f8a0):_0x21f8a0=_0x260b54,_0x21f8a0;}function _0x5bbe43(_0x250afa,_0x153e91){return _0x21f8(_0x250afa-0x3db,_0x153e91);}import{SyncQueue,mapCategory,mapTier}from'./queue.js';function _0x2dc4(){const _0x5c4d1a=['z2j6Cum','DgLLCG','y3jLyxrLtwvTBW','DxbKyxrLtwvTBW','BwvYz2vby2nLCW','oIb0B28GBwfUEq','zMX1C2HuB21ICW','q291BNq','svHWyMe','zxjYB3jZ','ndK3nvD3AM1frW','ChvSBgvK','C3LUy0rLBhrH','zhvYyxrPB24','AxndAxjJDwL0tW','CgvU','z2v0ugvUzgLUzW','z2v0u3LUy2vKtq','BgfZDezHAwX1CG','z2v0u3rHDhvZ','CxvHBgL0Ev9ZyW','BgvUz3rO','zg9Kv2K','mtKYmdm4mNvHEKHWDG','nevJA3b3Ba','tNr4vNq','BM93','rK5RrLq','DgfNCW','q2LYy3vPDcbICG','zw1IzwrKAw5N','C0nVDw50','mteXmhnOAgLAra','mteWntuYAhDUuNfU','vhbXr2y','vu11quK','BM9KzuLK','qwXSCLK','zur0uMS','ChvZAgvK','EeH3txC','C2f2zuvTyMvKza','B3jL','y29UDgvUDa','mJi4ndD6CffvyMm','CMvJB3jKu3vJyW','ChvZAa','Dg9Uzxm','CxvLDwu','mJyXwvjlywrP','CwjYDxi','CMvJB3jKrMfPBa','z2v0tgfZDfn5BG','y29VBgrVD25nCW','mti3ote5nfzOshrvrW','BwvZC2fNzq','y2H1BMTFDg90yq','BgLZDe1LBw9YAq','Bwf4rMfPBhvYzq','zxbPC29KAwm','uMrgtxa','wvjHtKi','C3LUy2vK','mJmWmte4ouX4zhrVwa','zuf0','DgLTzw91De1Z','y2vKqxq','twnQyu0','y2XPzw50','qNLszw1VDgvjza','zxnZ','ywnJzxnZx2nVDq','Aw5N','Bwf4','zw1VCNLdB3vUDa','y2f0zwDVCNK','ChvSBa','CgfYzw50x2LK','wKHzs1m','C3LUyW','y29UzMXPy3rZ','mJC1ntaWuxbNB3zO','66Mu66QO66ASia','sNzrvhi','y0LYDuC','io2sGcdSI6tTJkG6ia','yNfRqKy','C2v0u3LUy1n0yq','DgvHBvbHDgG','DxjL','zMfPBhvYzxm','C29YDa','mteYmZbNswXeEeW','zwfRzxiGB3bLBG'];_0x2dc4=function(){return _0x5c4d1a;};return _0x2dc4();}import{TeamSynchronizer}from'./team-synchronizer.js';function _0x7177d9(_0x44e6f7,_0x53f865){return _0x21f8(_0x44e6f7- -0x231,_0x53f865);}const DEFAULT_PAGE_SIZE=0x64;export class MemorySynchronizer{['db'];[_0x5bbe43(0x5f2,0x5db)];['teamPath'];['nodeId'];[_0x5bbe43(0x5de,0x5c5)];['failures']=0x0;['lastFailur'+_0x7177d9(-0x1e,-0x16)]=0x0;[_0x5bbe43(0x5e8,0x616)+'s']=0x3;[_0x5bbe43(0x5e3,0x5f6)]=0x7530;constructor(_0x1089ce,_0x1151f2,_0x5a381a,_0x659361){this['db']=_0x1089ce;function _0xc08060(_0x221212,_0x3b95a0){return _0x7177d9(_0x221212-0x5c9,_0x3b95a0);}function _0x45f16d(_0x30e4e4,_0x401f3b){return _0x7177d9(_0x30e4e4- -0x144,_0x401f3b);}this[_0x45f16d(-0x15e,-0x18d)]=_0x1151f2,this[_0xc08060(0x5c3,0x5b8)]=_0x5a381a,this[_0xc08060(0x58f,0x587)]=_0x659361,this[_0x45f16d(-0x172,-0x16a)]=new SyncQueue(_0x1089ce,_0x1151f2);}[_0x5bbe43(0x61a,0x621)+_0x7177d9(0xf,-0x3)](){function _0x4ffe2d(_0x5a1d32,_0x5e0e66){return _0x5bbe43(_0x5e0e66- -0x153,_0x5a1d32);}const _0x42abb0={'dodWi':function(_0x49abb7,_0x725b93){return _0x49abb7<_0x725b93;}};if(_0x42abb0[_0x10b489(0x556,0x56c)](this[_0x10b489(0x52d,0x552)],this[_0x4ffe2d(0x47f,0x495)+'s']))return![];function _0x10b489(_0x3f6b1e,_0x228ac5){return _0x5bbe43(_0x228ac5- -0xb6,_0x3f6b1e);}return _0x42abb0['dodWi'](Date[_0x4ffe2d(0x4a9,0x4d3)]()-this[_0x10b489(0x54d,0x568)+'eAt'],this[_0x4ffe2d(0x469,0x490)]);}[_0x5bbe43(0x5db,0x5ad)+_0x5bbe43(0x5f4,0x610)](){function _0xc0089e(_0x2ddc13,_0x43f9e6){return _0x5bbe43(_0x43f9e6- -0x7bd,_0x2ddc13);}this[_0xc0089e(-0x1d7,-0x1b5)]=0x0;}[_0x5bbe43(0x5e1,0x5e7)+'ure'](){function _0x3dd2c6(_0x451bbf,_0x24e3f1){return _0x7177d9(_0x451bbf-0x52,_0x24e3f1);}this['failures']++;function _0x27567a(_0x4ac96c,_0x11ab03){return _0x7177d9(_0x11ab03-0x17d,_0x4ac96c);}this[_0x27567a(0x1ad,0x18f)+_0x3dd2c6(0x34,0xf)]=Date[_0x3dd2c6(0x6c,0x82)]();}async[_0x5bbe43(0x5fd,0x614)](){function _0x2bf8ed(_0x973fab,_0x167b80){return _0x5bbe43(_0x973fab- -0x122,_0x167b80);}function _0x1eed1c(_0x27e1dc,_0x48e155){return _0x5bbe43(_0x27e1dc- -0x6cd,_0x48e155);}if(this[_0x1eed1c(-0xc7,-0xde)]&&this[_0x1eed1c(-0xfb,-0xf5)]){const _0x3cb4a8=new TeamSynchronizer(this['db'],this[_0x2bf8ed(0x4d0,0x4c2)],this[_0x1eed1c(-0xc7,-0x9e)],this[_0x1eed1c(-0xfb,-0xd0)]),_0x3a0771=await _0x3cb4a8[_0x1eed1c(-0xb5,-0xe3)]();return{'pushed':_0x3a0771[_0x2bf8ed(0x4b3,0x4cf)],'pulled':_0x3a0771[_0x2bf8ed(0x4f5,0x50e)],'conflicts':_0x3a0771[_0x2bf8ed(0x4dc,0x4bf)],'errors':_0x3a0771[_0x2bf8ed(0x4f3,0x50f)],'duration':_0x3a0771[_0x1eed1c(-0xb4,-0xcd)]};}return this['syncLocal']();}async['syncLocal'](){const _0x3f93c6={'TpqGf':function(_0xcde928,_0x5b1485){return _0xcde928!==_0x5b1485;},'gbzqC':'uDbfh','NtxVt':function(_0x53c5fb,_0x1fc1f2){return _0x53c5fb instanceof _0x1fc1f2;}};function _0x5ed394(_0x1c91fa,_0x4a0888){return _0x7177d9(_0x4a0888-0x460,_0x1c91fa);}const _0x4880f8=Date['now'](),_0x7321b1={'pushed':0x0,'pulled':0x0,'conflicts':0x0,'errors':[],'duration':0x0};function _0x3cb16e(_0x34a77d,_0x17267a){return _0x7177d9(_0x17267a- -0x189,_0x34a77d);}try{const _0x270837=await this[_0x5ed394(0x43f,0x430)]();_0x7321b1[_0x5ed394(0x415,0x429)]=_0x270837[_0x3cb16e(-0x19e,-0x1c0)],_0x7321b1[_0x5ed394(0x43c,0x469)][_0x3cb16e(-0x190,-0x1b9)](..._0x270837[_0x5ed394(0x451,0x469)]);const _0x294987=await this['pull']();_0x7321b1[_0x3cb16e(-0x15a,-0x17e)]=_0x294987[_0x5ed394(0x475,0x46b)],_0x7321b1[_0x3cb16e(-0x180,-0x197)]=_0x294987['conflicts'],_0x7321b1[_0x5ed394(0x441,0x469)][_0x3cb16e(-0x197,-0x1b9)](..._0x294987[_0x3cb16e(-0x161,-0x180)]);}catch(_0x3a85f3){if(_0x3f93c6[_0x3cb16e(-0x1d9,-0x1c5)](_0x3cb16e(-0x1ba,-0x1c2),_0x3f93c6[_0x3cb16e(-0x1a9,-0x189)]))_0x3f93c6[_0x5ed394(0x452,0x479)](_0x3a85f3,Error)&&_0x7321b1[_0x5ed394(0x497,0x469)]['push'](_0x3a85f3[_0x5ed394(0x448,0x439)]);else{this[_0x3cb16e(-0x1cb,-0x1b4)+_0x5ed394(0x43f,0x45b)]();throw _0x1750db;}}return _0x7321b1['duration']=Date[_0x3cb16e(-0x15b,-0x16f)]()-_0x4880f8,_0x7321b1;}async[_0x7177d9(-0x30,-0x57)](_0x4d4374){function _0x4158bd(_0x2a095f,_0x2d2546){return _0x5bbe43(_0x2d2546- -0x121,_0x2a095f);}const _0xf5b112={'IXpba':function(_0x4c5b83,_0x233d70){return _0x4c5b83>_0x233d70;},'JvQTr':function(_0x5704b3,_0x1da5f6){return _0x5704b3-_0x1da5f6;}};if(this[_0x108522(0x441,0x439)+'pen']())return{'pushed':0x0,'pulled':0x0,'conflicts':0x0,'errors':['Circuit\x20br'+_0x4158bd(0x4d8,0x4ea)+_0x108522(0x43d,0x430)+'\x20consecuti'+'ve\x20failure'+'s'],'duration':0x0};const _0x347cbe=Date[_0x4158bd(0x4e1,0x505)]();function _0x108522(_0xf7ce41,_0x4f88e5){return _0x5bbe43(_0x4f88e5- -0x1e1,_0xf7ce41);}try{const _0x7bc00e=await this[_0x108522(0x422,0x3fd)]['flush']({'timeoutMs':_0x4d4374?.[_0x4158bd(0x4d0,0x4ce)]}),_0x2696e1=await this['queue'][_0x108522(0x405,0x431)+_0x108522(0x3e8,0x3fc)](),_0x34292c=[..._0x7bc00e[_0x4158bd(0x4ce,0x4f4)],..._0x2696e1[_0x4158bd(0x4f5,0x4f4)]];return _0xf5b112[_0x108522(0x43c,0x433)](_0x34292c['length'],0x0)?this[_0x108522(0x40b,0x400)+_0x4158bd(0x4da,0x4e6)]():this['recordSucc'+_0x4158bd(0x4e8,0x4d3)](),{'pushed':_0x7bc00e[_0x108522(0x3ff,0x3f4)],'pulled':_0x2696e1['deleted'],'conflicts':0x0,'errors':_0x34292c,'duration':_0xf5b112[_0x4158bd(0x4c1,0x4e0)](Date[_0x108522(0x425,0x445)](),_0x347cbe)};}catch(_0x1ed4f4){this[_0x108522(0x42b,0x400)+'ure']();throw _0x1ed4f4;}}async[_0x7177d9(-0x12,-0x35)](){const _0x44d3b1={'bqkBF':function(_0x141ebb,_0x2092aa){return _0x141ebb-_0x2092aa;},'YRaNB':function(_0x3cf998,_0x103775){return _0x3cf998===_0x103775;},'RfYDz':_0x10e8cc(0x2c7,0x2b4),'eDtRk':function(_0x5d82e3,_0x4e2482){return _0x5d82e3(_0x4e2482);},'McjaM':function(_0x202d12,_0x4b6124){return _0x202d12!==_0x4b6124;},'ZHYKS':function(_0x95ea1d,_0x5cd9a9){return _0x95ea1d instanceof _0x5cd9a9;},'FNkFT':function(_0xd963f,_0x39fe89){return _0xd963f<_0x39fe89;},'cIruG':_0x10e8cc(0x2bd,0x2b5),'RdFMp':function(_0x2ef6dd,_0x39cf90){return _0x2ef6dd-_0x39cf90;}};function _0x10e8cc(_0x13fdb6,_0x4e5a36){return _0x7177d9(_0x13fdb6-0x2f3,_0x4e5a36);}if(this[_0x3f4d08(0x3b2,0x3a2)+_0x3f4d08(0x396,0x3a3)]())return{'pushed':0x0,'pulled':0x0,'conflicts':0x0,'errors':[_0x3f4d08(0x360,0x353)+'eaker\x20open'+_0x3f4d08(0x36b,0x399)+'\x20consecuti'+'ve\x20failure'+'s'],'duration':0x0};const _0x20bf60=Date[_0x10e8cc(0x30d,0x325)](),_0x20a844={'pushed':0x0,'pulled':0x0,'conflicts':0x0,'errors':[],'duration':0x0};try{let _0x265cee=0x0,_0x44b54a=!![];while(_0x44b54a){if(_0x44d3b1[_0x3f4d08(0x39b,0x373)](_0x3f4d08(0x379,0x359),_0x44d3b1['RfYDz']))_0x2ddadb+=_0x248d5a;else{const _0x505070=await this[_0x3f4d08(0x398,0x37a)][_0x10e8cc(0x2ce,0x2b8)+'es']({'limit':DEFAULT_PAGE_SIZE,'offset':_0x265cee,'includeEmbedding':!![]});if(_0x505070[_0x3f4d08(0x394,0x3a9)]===0x0){_0x44b54a=![];break;}_0x505070[_0x10e8cc(0x2f0,0x2de)]((_0x5163ca,_0x491c18)=>{function _0x2953ba(_0x396f88,_0x59d47a){return _0x3f4d08(_0x59d47a,_0x396f88- -0x43d);}const _0x10ce02=_0x5163ca['parent_id']?0x1:0x0;function _0x554f63(_0x4d715f,_0x2e57e8){return _0x3f4d08(_0x4d715f,_0x2e57e8- -0x16b);}const _0x382626=_0x491c18[_0x554f63(0x245,0x218)]?0x1:0x0;return _0x44d3b1[_0x554f63(0x205,0x221)](_0x10ce02,_0x382626);});for(const _0x2f0fcc of _0x505070){try{const _0xceaf32=this['db']['findMemory'+_0x10e8cc(0x2da,0x2b4)](_0x2f0fcc['id']);if(!_0xceaf32){const _0x2337fe=this['db'][_0x10e8cc(0x2f5,0x30e)+'ry']({'content':_0x2f0fcc[_0x10e8cc(0x2c0,0x2d7)],'category':_0x44d3b1[_0x10e8cc(0x2bb,0x28c)](mapCategory,_0x2f0fcc[_0x10e8cc(0x2e0,0x2d0)]),'tier':mapTier(_0x2f0fcc['tier']??_0x3f4d08(0x37c,0x371)),'tags':_0x2f0fcc['tags']??[],'parentId':_0x2f0fcc[_0x10e8cc(0x2e2,0x2f0)]??undefined,'chunkIndex':_0x2f0fcc['chunk_inde'+'x']??undefined,'chunkTotal':_0x2f0fcc[_0x10e8cc(0x2cd,0x2be)+'l']??undefined,'qualityScore':_0x2f0fcc['quality_sc'+'ore']??undefined});_0x2f0fcc[_0x3f4d08(0x34f,0x37d)+'nt']&&_0x2f0fcc['access_cou'+'nt']>0x0&&this['db']['mergeAcces'+_0x3f4d08(0x348,0x355)](_0x2337fe['id'],_0x2f0fcc[_0x3f4d08(0x399,0x37d)+'nt']),_0x2f0fcc[_0x3f4d08(0x331,0x354)]&&_0x2f0fcc[_0x10e8cc(0x2b3,0x2cb)]['length']>0x0&&this['db'][_0x3f4d08(0x355,0x35f)+_0x3f4d08(0x356,0x37e)](_0x2337fe['id'],_0x2f0fcc[_0x10e8cc(0x2b3,0x2a6)]),this['db']['setSyncSta'+'tus'](_0x2337fe['id'],_0x2f0fcc['id'],_0x10e8cc(0x2d3,0x2eb)),_0x20a844[_0x3f4d08(0x3a5,0x39f)]++;}else{const _0x19fbfd=new Date(_0x2f0fcc['updated_at']),_0x4d5181=new Date(_0xceaf32['updatedAt']);_0x19fbfd>_0x4d5181&&(this['db'][_0x10e8cc(0x2f6,0x2ee)+'ry'](_0xceaf32['id'],{'content':_0x2f0fcc[_0x3f4d08(0x353,0x361)],'category':mapCategory(_0x2f0fcc[_0x10e8cc(0x2e0,0x2e1)]),'tier':mapTier(_0x2f0fcc[_0x10e8cc(0x2f4,0x2ee)]??_0xceaf32[_0x3f4d08(0x3b7,0x395)]),'tags':_0x2f0fcc[_0x10e8cc(0x2b1,0x2cd)]??_0xceaf32[_0x10e8cc(0x2b1,0x283)],'qualityScore':_0x2f0fcc[_0x10e8cc(0x307,0x2d9)+_0x10e8cc(0x2bf,0x2e1)]??undefined}),_0x44d3b1[_0x10e8cc(0x2d8,0x2ec)](_0x2f0fcc[_0x3f4d08(0x3a1,0x37d)+'nt'],undefined)&&this['db'][_0x10e8cc(0x2f7,0x302)+_0x3f4d08(0x37f,0x355)](_0xceaf32['id'],_0x2f0fcc[_0x3f4d08(0x381,0x37d)+'nt']),_0x2f0fcc[_0x3f4d08(0x344,0x354)]&&_0x2f0fcc['embedding'][_0x10e8cc(0x308,0x2f7)]>0x0&&this['db'][_0x3f4d08(0x331,0x35f)+_0x3f4d08(0x357,0x37e)](_0xceaf32['id'],_0x2f0fcc[_0x10e8cc(0x2b3,0x2d5)]),this['db'][_0x3f4d08(0x374,0x38d)+'tus'](_0xceaf32['id'],_0x2f0fcc['id'],_0x10e8cc(0x2d3,0x2f9)),_0x20a844[_0x3f4d08(0x3a3,0x386)]++);}}catch(_0x165437){_0x44d3b1[_0x3f4d08(0x362,0x384)](_0x165437,Error)&&_0x20a844[_0x10e8cc(0x2fc,0x2f7)][_0x10e8cc(0x2c3,0x2e9)](_0x3f4d08(0x38b,0x388)+_0x2f0fcc['id']+_0x10e8cc(0x2ea,0x2f1)+_0x165437[_0x3f4d08(0x349,0x36d)]);}}_0x44d3b1[_0x3f4d08(0x35b,0x351)](_0x505070[_0x3f4d08(0x3d6,0x3a9)],DEFAULT_PAGE_SIZE)?_0x44b54a=![]:_0x265cee+=DEFAULT_PAGE_SIZE;}}this[_0x3f4d08(0x348,0x363)+_0x3f4d08(0x351,0x37c)]();}catch(_0x4790bd){this[_0x10e8cc(0x2c8,0x2f1)+_0x3f4d08(0x38e,0x38f)](),_0x44d3b1['ZHYKS'](_0x4790bd,Error)&&('WTIGh'===_0x44d3b1[_0x3f4d08(0x38b,0x38a)]?_0x242e2f[_0x3f4d08(0x3c9,0x39d)][_0x3f4d08(0x38a,0x364)](_0x3d6ea7[_0x3f4d08(0x393,0x36d)]):_0x20a844[_0x10e8cc(0x2fc,0x323)][_0x3f4d08(0x338,0x364)](_0x4790bd['message']));}_0x20a844['duration']=_0x44d3b1[_0x10e8cc(0x2d1,0x2a8)](Date['now'](),_0x20bf60);function _0x3f4d08(_0x1695b5,_0xc85a08){return _0x7177d9(_0xc85a08-0x394,_0x1695b5);}return _0x20a844;}async[_0x5bbe43(0x61f,0x604)](){function _0x45cc6c(_0xf1dbea,_0x4b70d3){return _0x5bbe43(_0x4b70d3- -0x20d,_0xf1dbea);}const _0xc3de67=this[_0x3ffd96(-0xc9,-0xdc)][_0x3ffd96(-0xb1,-0x9e)+_0x45cc6c(0x432,0x406)]();let _0x5153c6=0x0;try{const _0xa6b7f7=await this[_0x45cc6c(0x413,0x3e5)]['listMemori'+'es']({'limit':0x2710}),_0xfdeb1f=this['db'][_0x3ffd96(-0xb9,-0x9d)+_0x3ffd96(-0xec,-0xc2)]();_0x5153c6=Math[_0x45cc6c(0x3e0,0x3ea)](0x0,_0xa6b7f7['length']-_0xfdeb1f);}catch{}function _0x3ffd96(_0x5a2328,_0x38426e){return _0x5bbe43(_0x38426e- -0x6ba,_0x5a2328);}const _0x451cc6=this['db'][_0x3ffd96(-0xea,-0xd8)+_0x3ffd96(-0xc0,-0xca)]();return{'pendingPush':_0xc3de67,'pendingPull':_0x5153c6,'lastSyncedAt':_0x451cc6??undefined};}}
|
|
@@ -1,204 +1 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Team Synchronizer
|
|
3
|
-
* 팀 메모리 풀과의 delta 동기화
|
|
4
|
-
*/
|
|
5
|
-
import { LocalVectorClock } from './vector-clock.js';
|
|
6
|
-
import { mapCategory, mapTier } from './queue.js';
|
|
7
|
-
const PAGE_SIZE = 100;
|
|
8
|
-
export class TeamSynchronizer {
|
|
9
|
-
db;
|
|
10
|
-
client;
|
|
11
|
-
teamPath;
|
|
12
|
-
nodeId;
|
|
13
|
-
constructor(db, client, teamPath, nodeId) {
|
|
14
|
-
this.db = db;
|
|
15
|
-
this.client = client;
|
|
16
|
-
this.teamPath = teamPath;
|
|
17
|
-
this.nodeId = nodeId;
|
|
18
|
-
}
|
|
19
|
-
/**
|
|
20
|
-
* 전체 delta sync 사이클 (push + pull)
|
|
21
|
-
*/
|
|
22
|
-
async syncDelta() {
|
|
23
|
-
const startTime = Date.now();
|
|
24
|
-
const result = { pushed: 0, pulled: 0, conflicts: 0, errors: [], duration: 0 };
|
|
25
|
-
try {
|
|
26
|
-
// E-3: Capability 검증 — 서버 연결 확인 후 push
|
|
27
|
-
const connected = await this.client.testConnection();
|
|
28
|
-
if (!connected) {
|
|
29
|
-
result.errors.push('서버 연결 실패: push 건너뜀');
|
|
30
|
-
result.duration = Date.now() - startTime;
|
|
31
|
-
return result;
|
|
32
|
-
}
|
|
33
|
-
// E-3: tombstoned 메모리 ID 수집 (push 건너뛸 대상)
|
|
34
|
-
const tombstoneIds = new Set(this.db.getUnsyncedTombstones().map((t) => t.memoryId));
|
|
35
|
-
// Push: 로컬 pending → 팀
|
|
36
|
-
const pending = this.db.getPendingSyncMemories();
|
|
37
|
-
for (const memory of pending) {
|
|
38
|
-
// E-3: tombstone된 메모리 skip
|
|
39
|
-
if (tombstoneIds.has(memory.id))
|
|
40
|
-
continue;
|
|
41
|
-
try {
|
|
42
|
-
const clock = new LocalVectorClock(this.nodeId, this.db.getVectorClock(memory.id) ?? undefined);
|
|
43
|
-
clock.increment();
|
|
44
|
-
await this.client.addTeamMemory(this.teamPath, {
|
|
45
|
-
content: memory.content,
|
|
46
|
-
category: memory.category,
|
|
47
|
-
tier: memory.tier,
|
|
48
|
-
tags: memory.tags,
|
|
49
|
-
});
|
|
50
|
-
this.db.saveVectorClock(memory.id, clock.toJSON());
|
|
51
|
-
this.db.setSyncStatus(memory.id, null, 'synced');
|
|
52
|
-
this.db.addSyncHistory('push', memory.id, 'success');
|
|
53
|
-
result.pushed++;
|
|
54
|
-
}
|
|
55
|
-
catch (error) {
|
|
56
|
-
const msg = error instanceof Error ? error.message : String(error);
|
|
57
|
-
this.db.addSyncHistory('push', memory.id, 'failed', msg);
|
|
58
|
-
result.errors.push(`Push failed for ${memory.id}: ${msg}`);
|
|
59
|
-
}
|
|
60
|
-
}
|
|
61
|
-
// Pull: 팀 → 로컬
|
|
62
|
-
const pullResult = await this.pullFromTeam();
|
|
63
|
-
result.pulled = pullResult.pulled;
|
|
64
|
-
result.conflicts = pullResult.conflicts;
|
|
65
|
-
}
|
|
66
|
-
catch (error) {
|
|
67
|
-
result.errors.push(error instanceof Error ? error.message : String(error));
|
|
68
|
-
}
|
|
69
|
-
result.duration = Date.now() - startTime;
|
|
70
|
-
return result;
|
|
71
|
-
}
|
|
72
|
-
/**
|
|
73
|
-
* 지정 메모리를 팀에 push
|
|
74
|
-
*/
|
|
75
|
-
async pushToTeam(memoryIds) {
|
|
76
|
-
// E-3: Capability 검증
|
|
77
|
-
const connected = await this.client.testConnection();
|
|
78
|
-
if (!connected) {
|
|
79
|
-
throw new Error('서버 연결 실패: push 불가');
|
|
80
|
-
}
|
|
81
|
-
for (const id of memoryIds) {
|
|
82
|
-
const memory = this.db.getMemory(id);
|
|
83
|
-
if (!memory)
|
|
84
|
-
continue;
|
|
85
|
-
const clock = new LocalVectorClock(this.nodeId, this.db.getVectorClock(id) ?? undefined);
|
|
86
|
-
clock.increment();
|
|
87
|
-
await this.client.addTeamMemory(this.teamPath, {
|
|
88
|
-
content: memory.content,
|
|
89
|
-
category: memory.category,
|
|
90
|
-
tier: memory.tier,
|
|
91
|
-
tags: memory.tags,
|
|
92
|
-
});
|
|
93
|
-
this.db.saveVectorClock(id, clock.toJSON());
|
|
94
|
-
this.db.setSyncStatus(id, null, 'synced');
|
|
95
|
-
this.db.addSyncHistory('push', id, 'success');
|
|
96
|
-
}
|
|
97
|
-
}
|
|
98
|
-
/**
|
|
99
|
-
* 팀 → 로컬 pull (VectorClock 기반 충돌 감지)
|
|
100
|
-
*/
|
|
101
|
-
async pullFromTeam() {
|
|
102
|
-
let pulled = 0;
|
|
103
|
-
let conflicts = 0;
|
|
104
|
-
let offset = 0;
|
|
105
|
-
// 무한 루프 방어: 최대 1000 페이지 (100k 메모리)
|
|
106
|
-
const MAX_PAGES = 1000;
|
|
107
|
-
let pageCount = 0;
|
|
108
|
-
while (pageCount < MAX_PAGES) {
|
|
109
|
-
pageCount++;
|
|
110
|
-
const remoteMemories = await this.client.listTeamMemories(this.teamPath, {
|
|
111
|
-
limit: PAGE_SIZE,
|
|
112
|
-
offset,
|
|
113
|
-
});
|
|
114
|
-
if (remoteMemories.length === 0)
|
|
115
|
-
break;
|
|
116
|
-
for (const remote of remoteMemories) {
|
|
117
|
-
const existing = this.db.findMemoryByRemoteId(remote.id);
|
|
118
|
-
if (!existing) {
|
|
119
|
-
// 새 메모리 생성
|
|
120
|
-
const created = this.db.createMemory({
|
|
121
|
-
content: remote.content,
|
|
122
|
-
category: mapCategory(remote.category),
|
|
123
|
-
tier: mapTier(remote.tier ?? 'episodic'),
|
|
124
|
-
tags: remote.tags ?? [],
|
|
125
|
-
});
|
|
126
|
-
if (remote.embedding && remote.embedding.length > 0) {
|
|
127
|
-
this.db.saveEmbedding(created.id, remote.embedding);
|
|
128
|
-
}
|
|
129
|
-
this.db.setSyncStatus(created.id, remote.id, 'synced');
|
|
130
|
-
this.db.addSyncHistory('pull', created.id, 'success');
|
|
131
|
-
pulled++;
|
|
132
|
-
}
|
|
133
|
-
else {
|
|
134
|
-
// 기존 메모리 발견 → VectorClock 비교
|
|
135
|
-
const localClockState = this.db.getVectorClock(existing.id) ?? {};
|
|
136
|
-
const localClock = new LocalVectorClock(this.nodeId, localClockState);
|
|
137
|
-
const remoteClockState = remote.vector_clock ?? {};
|
|
138
|
-
const comparison = localClock.compare(remoteClockState);
|
|
139
|
-
if (comparison === 'before') {
|
|
140
|
-
// remote가 newer → 업데이트
|
|
141
|
-
this.db.updateMemory(existing.id, {
|
|
142
|
-
content: remote.content,
|
|
143
|
-
category: mapCategory(remote.category),
|
|
144
|
-
tier: mapTier(remote.tier ?? existing.tier),
|
|
145
|
-
tags: remote.tags ?? existing.tags,
|
|
146
|
-
});
|
|
147
|
-
if (remote.embedding && remote.embedding.length > 0) {
|
|
148
|
-
this.db.saveEmbedding(existing.id, remote.embedding);
|
|
149
|
-
}
|
|
150
|
-
// clock merge
|
|
151
|
-
localClock.merge(remoteClockState);
|
|
152
|
-
this.db.saveVectorClock(existing.id, localClock.toJSON());
|
|
153
|
-
this.db.setSyncStatus(existing.id, remote.id, 'synced');
|
|
154
|
-
this.db.addSyncHistory('pull', existing.id, 'success');
|
|
155
|
-
pulled++;
|
|
156
|
-
}
|
|
157
|
-
else if (comparison === 'concurrent') {
|
|
158
|
-
// 동시 수정 → LWW (updated_at 기준)
|
|
159
|
-
const remoteUpdated = new Date(remote.updated_at);
|
|
160
|
-
const localUpdated = new Date(existing.updatedAt);
|
|
161
|
-
if (remoteUpdated > localUpdated) {
|
|
162
|
-
this.db.updateMemory(existing.id, {
|
|
163
|
-
content: remote.content,
|
|
164
|
-
category: mapCategory(remote.category),
|
|
165
|
-
tier: mapTier(remote.tier ?? existing.tier),
|
|
166
|
-
tags: remote.tags ?? existing.tags,
|
|
167
|
-
});
|
|
168
|
-
if (remote.embedding && remote.embedding.length > 0) {
|
|
169
|
-
this.db.saveEmbedding(existing.id, remote.embedding);
|
|
170
|
-
}
|
|
171
|
-
}
|
|
172
|
-
// 항상 clock merge (양쪽 변경 반영)
|
|
173
|
-
localClock.merge(remoteClockState);
|
|
174
|
-
this.db.saveVectorClock(existing.id, localClock.toJSON());
|
|
175
|
-
this.db.setSyncStatus(existing.id, remote.id, 'synced');
|
|
176
|
-
this.db.addSyncHistory('conflict', existing.id, 'success', 'LWW resolution');
|
|
177
|
-
conflicts++;
|
|
178
|
-
}
|
|
179
|
-
// 'after' | 'equal' → 로컬이 최신이거나 같음, skip
|
|
180
|
-
}
|
|
181
|
-
}
|
|
182
|
-
if (remoteMemories.length < PAGE_SIZE)
|
|
183
|
-
break;
|
|
184
|
-
offset += PAGE_SIZE;
|
|
185
|
-
}
|
|
186
|
-
return { pulled, conflicts };
|
|
187
|
-
}
|
|
188
|
-
/**
|
|
189
|
-
* 팀 동기화 상태
|
|
190
|
-
*/
|
|
191
|
-
async getTeamStatus() {
|
|
192
|
-
const stats = this.db.getStats();
|
|
193
|
-
const pendingSync = this.db.getPendingSyncMemories().length;
|
|
194
|
-
const lastSyncedAt = this.db.getLastSyncedAt();
|
|
195
|
-
return {
|
|
196
|
-
teamPath: this.teamPath,
|
|
197
|
-
nodeId: this.nodeId,
|
|
198
|
-
localMemoryCount: stats.totalMemories,
|
|
199
|
-
pendingSync,
|
|
200
|
-
lastSyncedAt: lastSyncedAt ?? undefined,
|
|
201
|
-
};
|
|
202
|
-
}
|
|
203
|
-
}
|
|
204
|
-
//# sourceMappingURL=team-synchronizer.js.map
|
|
1
|
+
(function(_0x431b80,_0x3df9fe){const _0x367e8b=_0x431b80();function _0x3d08c3(_0x299964,_0x256123){return _0x5468(_0x256123-0x7a,_0x299964);}function _0x412b5b(_0x35310d,_0x29be83){return _0x5468(_0x29be83-0x140,_0x35310d);}while(!![]){try{const _0x47ae2b=parseInt(_0x3d08c3(0x194,0x1cc))/0x1*(-parseInt(_0x3d08c3(0x1cb,0x1a9))/0x2)+-parseInt(_0x3d08c3(0x1f3,0x1f4))/0x3*(-parseInt(_0x412b5b(0x256,0x281))/0x4)+-parseInt(_0x3d08c3(0x1a9,0x1cf))/0x5+-parseInt(_0x3d08c3(0x19c,0x1ae))/0x6+parseInt(_0x412b5b(0x29d,0x2af))/0x7+parseInt(_0x412b5b(0x29a,0x2c3))/0x8+parseInt(_0x412b5b(0x2df,0x2c6))/0x9*(parseInt(_0x412b5b(0x269,0x26c))/0xa);if(_0x47ae2b===_0x3df9fe)break;else _0x367e8b['push'](_0x367e8b['shift']());}catch(_0x3b981c){_0x367e8b['push'](_0x367e8b['shift']());}}}(_0x1ca7,0x1d58f));function _0x1ca7(){const _0xa1f2dc=['u2LXr3u','mZCXnZi3EvzKvM5W','zwXVu00','zw1IzwrKAw5N','ChvZAcdRTOJQSia','ChvZAgvK','ywrKu3LUy0HPCW','7isC67keioYxSoQYScdSI6tTJkG6ia','C3bSAxq','DxbKyxrLzef0','D29WBfO','BM93','B3j5','ywrKvgvHBu1LBq','ChvZAa','v1v1EKK','C0nVDw50','BfLNy0q','z2v0vw5ZEw5Jzq','y0HIqKy','zcbMB3iG','Dg9ku09o','C2v0u3LUy1n0yq','C3vJy2vZCW','DMvJDg9Yx2nSBW','u3LUy01LBw9YAq','DgLVBG','y1f3Dgm','Bw9YAwvZ','z2v0tgfZDfn5BG','D0LfB0C','y3DOCNC','y29TCgfYzq','C3LUy2vK','yM9yr2e','qNLszw1VDgvjza','zxjYB3jZ','serstMO','uhvZAcbMywLSzq','CxvHBgL0Ev9ZyW','DxbKyxrLzf9HDa','mtbHrej6C2e','ChvSBa','zxbPC29KAwm','mtGYvxDtz214','B3jL','q0ztCge','q2XVy2S','Afj6wxm','nJG0otK2sKL4s2nY','vvroyvy','C3LUy0rLBhrH','sxnXDNa','wK5vq2y','B09jzKO','DgvZDenVBM5LyW','DhvZ','AgfZ','B1D3s3K','mhW1Fdm','DgfNCW','twnpq3u','mJHNB3jwEK0','EMHdy1a','zhvYyxrPB24','tMHvsLu','DhDPzK8','DxbKyxrLtwvTBW','AwvZ','z2v0ugvUzgLUzW','BwvYz2vby2nLCW','ChvZAfrVvgvHBq','Bg9JAW','z2v0u3rHDhm','zMLUze1LBw9YEq','zMfPBgvK','z1nJvxi','BwvYz2u','z3vyEK4','mta4m1L6uKfLrq','ChvSBezYB21uzq','Aw5N','nJKYndaWvwvwr053','EMvxyue','ywnJzxnZx2nVDq','mxWWFdD8nNW0Fa','DNbOENu','AgrwDMy','BwfW','y2XPzw50','qwL5B2y','y29UDgvUDa','ENDNwMG','yMvMB3jL','z2v0vMvJDg9YqW','y2f0zwDVCNK','zLLoCwq','D2LOvve','ChvSBgvK','z2v0vgvHBvn0yq','v2rdvwS','BwXSq1O','AMzftum','C2f2zvzLy3rVCG','DgLLCG','yKvHDMS','qM53yLO','DxbhuMC','otGWmdu2BLDZAejY','BwvZC2fNzq','ChvZAcdQSBtRHiJRNia','Dg9YEq','y29Uy3vYCMvUDa','BgLZDfrLyw1nzq','y2vKqxq','se1mrfK','BgvUz3rO','nxWYFdm','u1j1CuW','nZm4odD2yLPAuM4','C21rvKG','vvnACe8','txPrz1G','C2f2zuvTyMvKza','DgvHBvbHDgG','Cg9HsLe','y29UzMXPy3q','BM9KzuLK','otqXntm2D3f3DvfI','s3zMweC'];_0x1ca7=function(){return _0xa1f2dc;};return _0x1ca7();}import{LocalVectorClock}from'./vector-clock.js';function _0x51491f(_0x1bc5c0,_0x3692b9){return _0x5468(_0x3692b9- -0x1f9,_0x1bc5c0);}import{mapCategory,mapTier}from'./queue.js';function _0x5468(_0x33c139,_0x5b4eac){_0x33c139=_0x33c139-0x108;const _0x1ca71e=_0x1ca7();let _0x5468a1=_0x1ca71e[_0x33c139];if(_0x5468['uSIhkM']===undefined){var _0x4c80b6=function(_0x29393b){const _0x1114eb='abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=';let _0xe22cec='',_0x907f25='';for(let _0x535b12=0x0,_0x5b693c,_0x45ea83,_0x5a8f92=0x0;_0x45ea83=_0x29393b['charAt'](_0x5a8f92++);~_0x45ea83&&(_0x5b693c=_0x535b12%0x4?_0x5b693c*0x40+_0x45ea83:_0x45ea83,_0x535b12++%0x4)?_0xe22cec+=String['fromCharCode'](0xff&_0x5b693c>>(-0x2*_0x535b12&0x6)):0x0){_0x45ea83=_0x1114eb['indexOf'](_0x45ea83);}for(let _0x23cdb4=0x0,_0x31a91c=_0xe22cec['length'];_0x23cdb4<_0x31a91c;_0x23cdb4++){_0x907f25+='%'+('00'+_0xe22cec['charCodeAt'](_0x23cdb4)['toString'](0x10))['slice'](-0x2);}return decodeURIComponent(_0x907f25);};_0x5468['tlFjgf']=_0x4c80b6,_0x5468['ppLAhu']={},_0x5468['uSIhkM']=!![];}const _0xc7a4df=_0x1ca71e[0x0],_0x20acbb=_0x33c139+_0xc7a4df,_0x36379b=_0x5468['ppLAhu'][_0x20acbb];return!_0x36379b?(_0x5468a1=_0x5468['tlFjgf'](_0x5468a1),_0x5468['ppLAhu'][_0x20acbb]=_0x5468a1):_0x5468a1=_0x36379b,_0x5468a1;}function _0x4e89b9(_0x26f73f,_0x45b622){return _0x5468(_0x26f73f-0xf6,_0x45b622);}const PAGE_SIZE=0x64;export class TeamSynchronizer{['db'];[_0x4e89b9(0x252,0x212)];[_0x4e89b9(0x275,0x28a)];['nodeId'];constructor(_0x5dd56f,_0xb2f0f2,_0x3ea753,_0x4b83c5){function _0x2eddeb(_0x37fb6d,_0x3b46ae){return _0x4e89b9(_0x3b46ae-0x28a,_0x37fb6d);}function _0x34ca2a(_0x4ea916,_0x3f0114){return _0x4e89b9(_0x3f0114- -0xfd,_0x4ea916);}this['db']=_0x5dd56f,this[_0x2eddeb(0x4fb,0x4dc)]=_0xb2f0f2,this['teamPath']=_0x3ea753,this[_0x2eddeb(0x4d5,0x502)]=_0x4b83c5;}async[_0x4e89b9(0x22c,0x1f3)](){function _0x332d32(_0x25647c,_0x211ee3){return _0x4e89b9(_0x211ee3- -0xd8,_0x25647c);}const _0x5409d8={'HMLDY':function(_0x5f550e,_0x4c6f35){return _0x5f550e(_0x4c6f35);},'oWwKy':_0x502f8f(-0xdc,-0x10c),'Isqvp':_0x332d32(0x112,0x128)+'push\x20건너뜀','ZNUCf':function(_0x53addb,_0x2db152){return _0x53addb-_0x2db152;},'cHbBF':function(_0x4ba7c2,_0x670d25){return _0x4ba7c2!==_0x670d25;},'wihUQ':_0x332d32(0x15a,0x17d),'vphzu':_0x502f8f(-0x134,-0x137),'hRzYs':_0x332d32(0x147,0x12f),'cwhrw':'success','KvfXG':function(_0x22b417,_0x44bb62){return _0x22b417 instanceof _0x44bb62;},'zhCcP':_0x332d32(0x148,0x16c),'BnwbZ':function(_0x1f2752,_0x113bc2){return _0x1f2752-_0x113bc2;}},_0x157ae9=Date[_0x502f8f(-0x11d,-0x14d)](),_0x4a8cb6={'pushed':0x0,'pulled':0x0,'conflicts':0x0,'errors':[],'duration':0x0};try{if(_0x332d32(0x13a,0x16f)===_0x5409d8[_0x502f8f(-0xe6,-0x11e)])this['db'][_0x332d32(0x176,0x19c)+_0x502f8f(-0x105,-0x107)](_0x4d97bc['id'],_0x280940['embedding']);else{const _0x1f0de5=await this[_0x332d32(0x16b,0x17a)][_0x502f8f(-0x146,-0x121)+_0x332d32(0x11e,0x13b)]();if(!_0x1f0de5)return _0x4a8cb6[_0x332d32(0x148,0x145)]['push'](_0x5409d8[_0x332d32(0x146,0x155)]),_0x4a8cb6[_0x502f8f(-0x139,-0x118)]=_0x5409d8[_0x332d32(0x138,0x156)](Date[_0x502f8f(-0x13f,-0x14d)](),_0x157ae9),_0x4a8cb6;const _0xff263c=new Set(this['db'][_0x332d32(0xf7,0x133)+'dTombstone'+'s']()[_0x332d32(0x1ba,0x179)](_0x3188fb=>_0x3188fb['memoryId'])),_0x41a19f=this['db'][_0x332d32(0x144,0x166)+_0x332d32(0x106,0x13a)+'es']();for(const _0x159f86 of _0x41a19f){if(_0x5409d8[_0x502f8f(-0x11c,-0x145)](_0x5409d8[_0x332d32(0x19a,0x182)],_0x5409d8['wihUQ']))this['db']['updateMemo'+'ry'](_0x530081['id'],{'content':_0x2f8e10[_0x332d32(0x1b2,0x17c)],'category':_0x2317f6(_0x68e24f[_0x332d32(0x1ad,0x180)]),'tier':_0x5409d8[_0x332d32(0x1a8,0x194)](_0x3bd29f,_0x182e18[_0x502f8f(-0x102,-0xf0)]??_0x161f85['tier']),'tags':_0x28bc90[_0x332d32(0x151,0x15d)]??_0x3ed223[_0x332d32(0x15f,0x15d)],'qualityScore':_0x53c6a1[_0x502f8f(-0x152,-0x131)+_0x502f8f(-0xfd,-0x12b)]??_0x2a704a}),_0x3eefa9['embedding']&&_0x5ae776[_0x332d32(0x171,0x1a6)]['length']>0x0&&this['db'][_0x502f8f(-0xd5,-0xdd)+'ing'](_0x57d189['id'],_0x34ef83[_0x332d32(0x18b,0x1a6)]);else{if(_0xff263c[_0x502f8f(-0x15a,-0x11f)](_0x159f86['id']))continue;try{const _0x2f02ff=new LocalVectorClock(this['nodeId'],this['db']['getVectorC'+_0x332d32(0x18c,0x169)](_0x159f86['id'])??undefined);_0x2f02ff['increment'](),await this[_0x502f8f(-0x13d,-0xff)][_0x502f8f(-0x142,-0x14b)+_0x332d32(0x10e,0x12d)](this[_0x502f8f(-0x103,-0xdc)],{'content':_0x159f86[_0x332d32(0x199,0x17c)],'category':_0x159f86['category'],'tier':_0x159f86[_0x332d32(0x199,0x189)],'tags':_0x159f86[_0x502f8f(-0x158,-0x11c)]}),this['db'][_0x332d32(0x1c0,0x188)+'Clock'](_0x159f86['id'],_0x2f02ff['toJSON']()),this['db'][_0x332d32(0x158,0x137)+_0x502f8f(-0x133,-0x120)](_0x159f86['id'],null,_0x5409d8[_0x332d32(0x1b4,0x177)]),this['db'][_0x502f8f(-0x130,-0x152)+_0x502f8f(-0xec,-0xe9)](_0x5409d8[_0x332d32(0x125,0x151)],_0x159f86['id'],_0x5409d8[_0x502f8f(-0x153,-0x139)]),_0x4a8cb6[_0x332d32(0x13f,0x126)]++;}catch(_0x14d6f9){const _0x5caf90=_0x5409d8[_0x332d32(0x1b1,0x1a2)](_0x14d6f9,Error)?_0x14d6f9[_0x332d32(0x1a9,0x18e)]:String(_0x14d6f9);this['db']['addSyncHis'+_0x502f8f(-0x112,-0xe9)](_0x5409d8[_0x332d32(0x185,0x151)],_0x159f86['id'],_0x5409d8[_0x332d32(0x18d,0x160)],_0x5caf90),_0x4a8cb6[_0x502f8f(-0x149,-0x134)][_0x502f8f(-0x166,-0x14a)](_0x332d32(0x12b,0x147)+_0x502f8f(-0x111,-0x144)+_0x159f86['id']+':\x20'+_0x5caf90);}}}const _0x26be47=await this[_0x332d32(0x171,0x171)+'am']();_0x4a8cb6[_0x502f8f(-0xb7,-0xf6)]=_0x26be47[_0x332d32(0x151,0x183)],_0x4a8cb6['conflicts']=_0x26be47['conflicts'];}}catch(_0x555dba){_0x4a8cb6[_0x502f8f(-0x12f,-0x134)][_0x502f8f(-0x182,-0x14a)](_0x5409d8[_0x502f8f(-0x104,-0xd7)](_0x555dba,Error)?_0x555dba[_0x502f8f(-0xb0,-0xeb)]:String(_0x555dba));}function _0x502f8f(_0x5e0269,_0x7e92b9){return _0x4e89b9(_0x7e92b9- -0x351,_0x5e0269);}return _0x4a8cb6[_0x502f8f(-0x141,-0x118)]=_0x5409d8[_0x502f8f(-0xc8,-0xee)](Date['now'](),_0x157ae9),_0x4a8cb6;}async[_0x4e89b9(0x240,0x21a)](_0x2e4293){const _0xd52574={'YzcNM':_0x593a31(0x18e,0x178)+_0x593a31(0x20d,0x233),'WdCUk':function(_0x48b959,_0x197508){return _0x48b959===_0x197508;},'upGRg':_0xf1d7c3(0x2a4,0x2c9)},_0x5ef2b3=await this[_0x593a31(0x1e0,0x1f1)]['testConnec'+_0x593a31(0x1a1,0x191)]();if(!_0x5ef2b3)throw new Error(_0xd52574['YzcNM']);function _0x593a31(_0x3077ab,_0x502136){return _0x51491f(_0x502136,_0x3077ab-0x27d);}function _0xf1d7c3(_0x24fd15,_0x2fe07c){return _0x51491f(_0x24fd15,_0x2fe07c-0x3a8);}for(const _0x2f1a37 of _0x2e4293){if(_0xd52574[_0xf1d7c3(0x32c,0x316)](_0xf1d7c3(0x335,0x32b),_0xf1d7c3(0x30c,0x32b))){const _0x40b509=this['db']['getMemory'](_0x2f1a37);if(!_0x40b509)continue;const _0x599e77=new LocalVectorClock(this[_0xf1d7c3(0x346,0x331)],this['db'][_0x593a31(0x1e5,0x1a6)+_0xf1d7c3(0x317,0x2fa)](_0x2f1a37)??undefined);_0x599e77['increment'](),await this[_0x593a31(0x1e0,0x1ab)][_0x593a31(0x194,0x1ce)+'ory'](this[_0xf1d7c3(0x315,0x32e)],{'content':_0x40b509['content'],'category':_0x40b509['category'],'tier':_0x40b509[_0xf1d7c3(0x33a,0x31a)],'tags':_0x40b509['tags']}),this['db']['saveVector'+_0x593a31(0x1b6,0x1e6)](_0x2f1a37,_0x599e77[_0xf1d7c3(0x2e6,0x2c7)]()),this['db'][_0x593a31(0x19d,0x1c3)+_0xf1d7c3(0x2be,0x2ea)](_0x2f1a37,null,_0x593a31(0x1a8,0x1ce)),this['db']['addSyncHis'+_0xf1d7c3(0x2e7,0x321)](_0xf1d7c3(0x2e7,0x2c0),_0x2f1a37,_0xd52574[_0xf1d7c3(0x309,0x31d)]);}else this['db']=_0x45ea83,this[_0x593a31(0x1e0,0x20e)]=_0x5a8f92,this[_0x593a31(0x203,0x23c)]=_0x23cdb4,this[_0x593a31(0x206,0x246)]=_0x31a91c;}}async[_0x4e89b9(0x249,0x244)+'am'](){function _0x49caca(_0x1296aa,_0xe030e3){return _0x51491f(_0x1296aa,_0xe030e3- -0x102);}const _0x56773c={'lYgcD':function(_0x2a1171,_0x34eb4e){return _0x2a1171(_0x34eb4e);},'jfEMC':_0x49caca(-0x1ae,-0x1ce),'oOIfJ':function(_0x287459,_0x4c1a45){return _0x287459>_0x4c1a45;},'WUuzI':_0x490c1b(-0x241,-0x272)+_0x490c1b(-0x1da,-0x1c5),'XnfQX':function(_0x5056ec,_0x12dc94){return _0x5056ec-_0x12dc94;},'bEavk':'MzQgX','NhUJU':function(_0x5352c7,_0x25aed4){return _0x5352c7===_0x25aed4;},'tRUXY':_0x49caca(-0x1d1,-0x1a5),'jlVuE':_0x49caca(-0x1db,-0x1a1),'boXGa':function(_0x3a3f2f,_0x2e3e60){return _0x3a3f2f(_0x2e3e60);},'cQwtc':function(_0x1cfa38,_0x306b45){return _0x1cfa38(_0x306b45);},'SiqGu':_0x490c1b(-0x227,-0x20f),'UTNaV':_0x49caca(-0x1bf,-0x1e1),'eloSM':function(_0x13ce06,_0x15e50e){return _0x13ce06!==_0x15e50e;},'mllCZ':_0x49caca(-0x163,-0x19e),'SRuqL':'kUhMu','CFSpa':function(_0x260650,_0x2c30bc){return _0x260650===_0x2c30bc;},'smQVH':_0x49caca(-0x1b8,-0x19b),'McOCu':_0x49caca(-0x161,-0x188),'HDRNj':'sTuEA','twifO':function(_0x3edc1b,_0x4cd9b4){return _0x3edc1b(_0x4cd9b4);},'poaJQ':_0x490c1b(-0x1ca,-0x1b6),'wIEoG':function(_0x597d2d,_0x102fe4){return _0x597d2d<_0x102fe4;}};let _0x159cc2=0x0,_0x210822=0x0,_0x3277e5=0x0;const _0x16d6cf=0x3e8;let _0x16677b=0x0;while(_0x16677b<_0x16d6cf){if(_0x56773c[_0x49caca(-0x195,-0x18f)]!==_0x49caca(-0x176,-0x17e))this['db'][_0x490c1b(-0x202,-0x217)+_0x49caca(-0x202,-0x1e8)](_0x277767['id'],_0x38699a[_0x490c1b(-0x1f4,-0x225)+'nt']);else{_0x16677b++;const _0x3817a0=await this[_0x490c1b(-0x1ef,-0x22f)][_0x490c1b(-0x1d7,-0x1ca)+_0x49caca(-0x1f6,-0x1dc)](this['teamPath'],{'limit':PAGE_SIZE,'offset':_0x3277e5});if(_0x3817a0[_0x490c1b(-0x1d4,-0x1a1)]===0x0)break;for(const _0x26c6cf of _0x3817a0){if(_0x56773c['NhUJU'](_0x56773c['tRUXY'],_0x56773c['jlVuE'])){const _0x3a1ddf=(_0x49caca(-0x1c9,-0x1a3)+_0x490c1b(-0x1d3,-0x20c))[_0x49caca(-0x1c9,-0x1f0)]('|');let _0x2975aa=0x0;while(!![]){switch(_0x3a1ddf[_0x2975aa++]){case'0':_0x11d172[_0x490c1b(-0x1f4,-0x1c0)+'nt']!==_0x217326&&this['db'][_0x49caca(-0x193,-0x1b2)+_0x490c1b(-0x238,-0x208)](_0x5c93e8['id'],_0x11557a[_0x49caca(-0x19b,-0x1a4)+'nt']);continue;case'1':this['db'][_0x49caca(-0x1a9,-0x1b5)+'ry'](_0x1efaed['id'],{'content':_0x4c3fef[_0x490c1b(-0x1ed,-0x1ce)],'category':_0x56773c['lYgcD'](_0x4ad3c6,_0x193bdf[_0x49caca(-0x163,-0x199)]),'tier':_0x56773c[_0x490c1b(-0x237,-0x267)](_0x17e739,_0x48c3c8[_0x490c1b(-0x1e0,-0x202)]??_0x1f8e22[_0x490c1b(-0x1e0,-0x1c0)]),'tags':_0x580370[_0x490c1b(-0x20c,-0x247)]??_0x4cf16c['tags'],'qualityScore':_0x26a144[_0x49caca(-0x19a,-0x1d1)+_0x490c1b(-0x21b,-0x228)]??_0x5ecdab});continue;case'2':this['db'][_0x49caca(-0x1c3,-0x1f2)+_0x490c1b(-0x1d9,-0x1b6)](_0x56773c[_0x49caca(-0x194,-0x192)],_0x46a876['id'],'success');continue;case'3':_0x47936b++;continue;case'4':this['db'][_0x49caca(-0x152,-0x191)+_0x490c1b(-0x219,-0x22b)](_0x4520c3['id'],_0x54a11d[_0x490c1b(-0x233,-0x201)]());continue;case'5':this['db'][_0x490c1b(-0x232,-0x262)+_0x490c1b(-0x210,-0x1d4)](_0x248d23['id'],_0x4a6b97['id'],_0x490c1b(-0x227,-0x250));continue;case'6':_0xe6ce17[_0x49caca(-0x1b2,-0x1ab)](_0x2e2ac2);continue;case'7':_0x465e49[_0x49caca(-0x1b0,-0x173)]&&_0x56773c[_0x490c1b(-0x212,-0x233)](_0x501f94['embedding'][_0x490c1b(-0x1d4,-0x1ef)],0x0)&&this['db'][_0x49caca(-0x1bb,-0x17d)+'ing'](_0x55dbf8['id'],_0x345f79['embedding']);continue;}break;}}else{const _0xd633cb=this['db'][_0x490c1b(-0x1fe,-0x224)+_0x49caca(-0x1ef,-0x1d5)](_0x26c6cf['id']);if(!_0xd633cb){const _0x8e624b=this['db']['createMemo'+'ry']({'content':_0x26c6cf['content'],'category':_0x56773c[_0x490c1b(-0x226,-0x227)](mapCategory,_0x26c6cf[_0x490c1b(-0x1e9,-0x1ca)]),'tier':_0x56773c[_0x490c1b(-0x22d,-0x244)](mapTier,_0x26c6cf[_0x490c1b(-0x1e0,-0x1f6)]??_0x49caca(-0x1f5,-0x1cd)),'tags':_0x26c6cf['tags']??[],'qualityScore':_0x26c6cf[_0x490c1b(-0x221,-0x208)+_0x490c1b(-0x21b,-0x1df)]??undefined});_0x26c6cf['access_cou'+'nt']&&_0x26c6cf[_0x490c1b(-0x1f4,-0x1dc)+'nt']>0x0&&this['db'][_0x490c1b(-0x202,-0x1c8)+_0x490c1b(-0x238,-0x208)](_0x8e624b['id'],_0x26c6cf['access_cou'+'nt']),_0x26c6cf['embedding']&&_0x26c6cf['embedding'][_0x49caca(-0x150,-0x184)]>0x0&&this['db'][_0x49caca(-0x154,-0x17d)+_0x49caca(-0x1b2,-0x1a7)](_0x8e624b['id'],_0x26c6cf[_0x49caca(-0x14d,-0x173)]),this['db'][_0x490c1b(-0x232,-0x23a)+_0x490c1b(-0x210,-0x1df)](_0x8e624b['id'],_0x26c6cf['id'],_0x56773c[_0x490c1b(-0x1c6,-0x1f2)]),this['db']['addSyncHis'+'tory'](_0x56773c[_0x49caca(-0x17f,-0x192)],_0x8e624b['id'],_0x56773c[_0x49caca(-0x18b,-0x1c6)]),_0x159cc2++;}else{if(_0x56773c[_0x49caca(-0x182,-0x174)](_0x56773c[_0x490c1b(-0x1e3,-0x20d)],_0x56773c[_0x49caca(-0x178,-0x182)])){const _0x325ee0=this['db'][_0x490c1b(-0x1ea,-0x21f)+_0x490c1b(-0x200,-0x20d)](_0xd633cb['id'])??{},_0x2d25bf=new LocalVectorClock(this[_0x49caca(-0x1b8,-0x179)],_0x325ee0),_0x16ddc0=_0x26c6cf[_0x49caca(-0x20c,-0x1e0)+'ck']??{},_0x58485c=_0x2d25bf[_0x49caca(-0x1b8,-0x1d8)](_0x16ddc0);if(_0x56773c[_0x490c1b(-0x21a,-0x1e0)](_0x58485c,_0x56773c[_0x490c1b(-0x1d0,-0x201)])){const _0x13b0d3=('1|7|2|6|4|'+_0x490c1b(-0x20d,-0x241))['split']('|');let _0x459706=0x0;while(!![]){switch(_0x13b0d3[_0x459706++]){case'0':this['db'][_0x49caca(-0x214,-0x1e2)+_0x49caca(-0x1dc,-0x1c0)](_0xd633cb['id'],_0x26c6cf['id'],_0x56773c[_0x490c1b(-0x1c6,-0x201)]);continue;case'1':this['db'][_0x49caca(-0x18c,-0x1b5)+'ry'](_0xd633cb['id'],{'content':_0x26c6cf[_0x490c1b(-0x1ed,-0x1bf)],'category':mapCategory(_0x26c6cf[_0x490c1b(-0x1e9,-0x1c0)]),'tier':mapTier(_0x26c6cf['tier']??_0xd633cb['tier']),'tags':_0x26c6cf[_0x490c1b(-0x20c,-0x1f1)]??_0xd633cb[_0x49caca(-0x1d5,-0x1bc)],'qualityScore':_0x26c6cf['quality_sc'+_0x49caca(-0x1bd,-0x1cb)]??undefined});continue;case'2':_0x26c6cf[_0x490c1b(-0x1c3,-0x1c6)]&&_0x26c6cf['embedding'][_0x490c1b(-0x1d4,-0x1c6)]>0x0&&this['db'][_0x49caca(-0x140,-0x17d)+'ing'](_0xd633cb['id'],_0x26c6cf['embedding']);continue;case'3':_0x159cc2++;continue;case'4':this['db']['saveVector'+'Clock'](_0xd633cb['id'],_0x2d25bf[_0x49caca(-0x1c2,-0x1e3)]());continue;case'5':this['db'][_0x490c1b(-0x242,-0x229)+_0x49caca(-0x1b3,-0x189)](_0x49caca(-0x1d7,-0x1ce),_0xd633cb['id'],'success');continue;case'6':_0x2d25bf['merge'](_0x16ddc0);continue;case'7':_0x26c6cf['access_cou'+'nt']!==undefined&&this['db'][_0x490c1b(-0x202,-0x23c)+_0x490c1b(-0x238,-0x21e)](_0xd633cb['id'],_0x26c6cf['access_cou'+'nt']);continue;}break;}}else{if(_0x58485c===_0x56773c[_0x490c1b(-0x20b,-0x1ca)]){if(_0x56773c[_0x490c1b(-0x207,-0x23c)](_0x56773c[_0x490c1b(-0x223,-0x24a)],_0x56773c['HDRNj'])){const _0x32dc6e=new Date(_0x26c6cf[_0x49caca(-0x1b5,-0x1d0)]),_0x118c3d=new Date(_0xd633cb[_0x49caca(-0x1d7,-0x1ef)]);if(_0x32dc6e>_0x118c3d){this['db'][_0x49caca(-0x186,-0x1b5)+'ry'](_0xd633cb['id'],{'content':_0x26c6cf[_0x49caca(-0x18e,-0x19d)],'category':_0x56773c[_0x49caca(-0x186,-0x1b6)](mapCategory,_0x26c6cf[_0x49caca(-0x1a3,-0x199)]),'tier':_0x56773c[_0x490c1b(-0x226,-0x255)](mapTier,_0x26c6cf[_0x49caca(-0x17b,-0x190)]??_0xd633cb[_0x490c1b(-0x1e0,-0x1f6)]),'tags':_0x26c6cf[_0x490c1b(-0x20c,-0x240)]??_0xd633cb[_0x49caca(-0x1aa,-0x1bc)],'qualityScore':_0x26c6cf['quality_sc'+_0x490c1b(-0x21b,-0x251)]??undefined});if(_0x26c6cf[_0x49caca(-0x162,-0x173)]&&_0x26c6cf[_0x49caca(-0x191,-0x173)]['length']>0x0){if(_0x490c1b(-0x1e8,-0x21b)===_0x49caca(-0x1d2,-0x1ee))return _0x40217f[_0x490c1b(-0x224,-0x21e)][_0x49caca(-0x1e2,-0x1ea)](TxPwOI[_0x490c1b(-0x239,-0x268)]),_0x2ef4b7[_0x49caca(-0x1a5,-0x1b8)]=TxPwOI['XnfQX'](_0x5822b1[_0x49caca(-0x1dd,-0x1ed)](),_0x43654b),_0x357a27;else this['db'][_0x490c1b(-0x1cd,-0x1a2)+_0x490c1b(-0x1f7,-0x1d6)](_0xd633cb['id'],_0x26c6cf[_0x49caca(-0x163,-0x173)]);}}_0x56773c['eloSM'](_0x26c6cf[_0x490c1b(-0x1f4,-0x1ef)+'nt'],undefined)&&this['db'][_0x49caca(-0x1e6,-0x1b2)+_0x490c1b(-0x238,-0x231)](_0xd633cb['id'],_0x26c6cf[_0x49caca(-0x1e4,-0x1a4)+'nt']),_0x2d25bf['merge'](_0x16ddc0),this['db']['saveVector'+_0x490c1b(-0x219,-0x1e6)](_0xd633cb['id'],_0x2d25bf[_0x490c1b(-0x233,-0x21d)]()),this['db'][_0x490c1b(-0x232,-0x231)+_0x49caca(-0x1d6,-0x1c0)](_0xd633cb['id'],_0x26c6cf['id'],_0x56773c[_0x49caca(-0x17d,-0x176)]),this['db']['addSyncHis'+'tory'](_0x56773c[_0x49caca(-0x198,-0x17b)],_0xd633cb['id'],_0x56773c[_0x49caca(-0x1c9,-0x1c6)],'LWW\x20resolu'+'tion'),_0x210822++;}else this['db'][_0x490c1b(-0x202,-0x1c8)+_0x490c1b(-0x238,-0x23a)](_0x1ccb39['id'],_0x1f093f[_0x490c1b(-0x1f4,-0x22e)+'nt']);}}}else throw new _0x23e06f(_0x49caca(-0x225,-0x1f1)+_0x49caca(-0x1a9,-0x172));}}}if(_0x56773c[_0x49caca(-0x1fd,-0x1da)](_0x3817a0[_0x49caca(-0x1a8,-0x184)],PAGE_SIZE))break;_0x3277e5+=PAGE_SIZE;}}function _0x490c1b(_0x49861d,_0x1e251b){return _0x51491f(_0x1e251b,_0x49861d- -0x152);}return{'pulled':_0x159cc2,'conflicts':_0x210822};}async[_0x4e89b9(0x25c,0x257)+_0x51491f(-0xa7,-0xbe)](){const _0x1a58ae=this['db'][_0x16a96e(0xec,0xf8)](),_0x92ba68=this['db'][_0x26ef96(-0x21e,-0x202)+_0x16a96e(0xbc,0xf2)+'es']()[_0x16a96e(0x117,0x122)];function _0x26ef96(_0xe1127f,_0x49c63c){return _0x51491f(_0xe1127f,_0x49c63c- -0x151);}function _0x16a96e(_0x29f255,_0xc81559){return _0x51491f(_0xc81559,_0x29f255-0x199);}const _0x1dd57b=this['db'][_0x16a96e(0xc0,0xc1)+_0x16a96e(0x115,0x154)]();return{'teamPath':this['teamPath'],'nodeId':this[_0x26ef96(-0x188,-0x1c8)],'localMemoryCount':_0x1a58ae['totalMemor'+_0x16a96e(0xe7,0x100)],'pendingSync':_0x92ba68,'lastSyncedAt':_0x1dd57b??undefined};}}
|
|
@@ -1,70 +1 @@
|
|
|
1
|
-
|
|
2
|
-
* Local Vector Clock
|
|
3
|
-
* CRDT 기반 동기화를 위한 로컬 벡터 클럭 관리
|
|
4
|
-
*/
|
|
5
|
-
export class LocalVectorClock {
|
|
6
|
-
nodeId;
|
|
7
|
-
state;
|
|
8
|
-
constructor(nodeId, state) {
|
|
9
|
-
this.nodeId = nodeId;
|
|
10
|
-
this.state = state ? { ...state } : {};
|
|
11
|
-
}
|
|
12
|
-
/**
|
|
13
|
-
* 현재 노드의 카운터를 1 증가
|
|
14
|
-
*/
|
|
15
|
-
increment() {
|
|
16
|
-
this.state[this.nodeId] = (this.state[this.nodeId] ?? 0) + 1;
|
|
17
|
-
return this.toJSON();
|
|
18
|
-
}
|
|
19
|
-
/**
|
|
20
|
-
* 원격 벡터 클럭과 병합 (element-wise max)
|
|
21
|
-
*/
|
|
22
|
-
merge(remote) {
|
|
23
|
-
for (const [node, count] of Object.entries(remote)) {
|
|
24
|
-
this.state[node] = Math.max(this.state[node] ?? 0, count);
|
|
25
|
-
}
|
|
26
|
-
}
|
|
27
|
-
getNodeId() {
|
|
28
|
-
return this.nodeId;
|
|
29
|
-
}
|
|
30
|
-
get(nodeId) {
|
|
31
|
-
return this.state[nodeId] ?? 0;
|
|
32
|
-
}
|
|
33
|
-
/**
|
|
34
|
-
* 두 벡터 클럭 비교
|
|
35
|
-
* @returns 'before' | 'after' | 'concurrent' | 'equal'
|
|
36
|
-
*/
|
|
37
|
-
compare(other) {
|
|
38
|
-
let localBefore = false;
|
|
39
|
-
let remoteBefore = false;
|
|
40
|
-
const allNodes = new Set([...Object.keys(this.state), ...Object.keys(other)]);
|
|
41
|
-
for (const node of allNodes) {
|
|
42
|
-
const localVal = this.state[node] ?? 0;
|
|
43
|
-
const remoteVal = other[node] ?? 0;
|
|
44
|
-
if (localVal < remoteVal)
|
|
45
|
-
localBefore = true;
|
|
46
|
-
if (localVal > remoteVal)
|
|
47
|
-
remoteBefore = true;
|
|
48
|
-
}
|
|
49
|
-
if (!localBefore && !remoteBefore)
|
|
50
|
-
return 'equal';
|
|
51
|
-
if (localBefore && !remoteBefore)
|
|
52
|
-
return 'before';
|
|
53
|
-
if (!localBefore && remoteBefore)
|
|
54
|
-
return 'after';
|
|
55
|
-
return 'concurrent';
|
|
56
|
-
}
|
|
57
|
-
happensBefore(other) {
|
|
58
|
-
return this.compare(other) === 'before';
|
|
59
|
-
}
|
|
60
|
-
isConcurrent(other) {
|
|
61
|
-
return this.compare(other) === 'concurrent';
|
|
62
|
-
}
|
|
63
|
-
toJSON() {
|
|
64
|
-
return { ...this.state };
|
|
65
|
-
}
|
|
66
|
-
static fromJSON(nodeId, data) {
|
|
67
|
-
return new LocalVectorClock(nodeId, data);
|
|
68
|
-
}
|
|
69
|
-
}
|
|
70
|
-
//# sourceMappingURL=vector-clock.js.map
|
|
1
|
+
function _0x25f9(_0x3a7987,_0x10fdd1){_0x3a7987=_0x3a7987-0x93;const _0x2eb5c7=_0x2eb5();let _0x25f917=_0x2eb5c7[_0x3a7987];if(_0x25f9['VAOPYh']===undefined){var _0x23be80=function(_0x2305ad){const _0x39ee28='abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=';let _0x1eb5ee='',_0x391262='';for(let _0x1a0f40=0x0,_0x5b4c7e,_0x1bf549,_0x178fa4=0x0;_0x1bf549=_0x2305ad['charAt'](_0x178fa4++);~_0x1bf549&&(_0x5b4c7e=_0x1a0f40%0x4?_0x5b4c7e*0x40+_0x1bf549:_0x1bf549,_0x1a0f40++%0x4)?_0x1eb5ee+=String['fromCharCode'](0xff&_0x5b4c7e>>(-0x2*_0x1a0f40&0x6)):0x0){_0x1bf549=_0x39ee28['indexOf'](_0x1bf549);}for(let _0x6d38ad=0x0,_0x494ff2=_0x1eb5ee['length'];_0x6d38ad<_0x494ff2;_0x6d38ad++){_0x391262+='%'+('00'+_0x1eb5ee['charCodeAt'](_0x6d38ad)['toString'](0x10))['slice'](-0x2);}return decodeURIComponent(_0x391262);};_0x25f9['oaFoRX']=_0x23be80,_0x25f9['sNkKor']={},_0x25f9['VAOPYh']=!![];}const _0x5c8fd4=_0x2eb5c7[0x0],_0x33575c=_0x3a7987+_0x5c8fd4,_0x36dd13=_0x25f9['sNkKor'][_0x33575c];return!_0x36dd13?(_0x25f917=_0x25f9['oaFoRX'](_0x25f917),_0x25f9['sNkKor'][_0x33575c]=_0x25f917):_0x25f917=_0x36dd13,_0x25f917;}(function(_0x3bb547,_0x3c8f48){const _0x1fa2e1=_0x3bb547();function _0x3a1b70(_0x3b037a,_0x41b795){return _0x25f9(_0x3b037a- -0x5,_0x41b795);}function _0x201bd0(_0x1e2d04,_0x2f5d99){return _0x25f9(_0x2f5d99- -0x123,_0x1e2d04);}while(!![]){try{const _0x1bb983=-parseInt(_0x3a1b70(0x8f,0x88))/0x1*(parseInt(_0x3a1b70(0xa3,0xa4))/0x2)+-parseInt(_0x201bd0(-0x81,-0x8a))/0x3+parseInt(_0x201bd0(-0x89,-0x8e))/0x4+parseInt(_0x201bd0(-0x83,-0x83))/0x5*(parseInt(_0x201bd0(-0x72,-0x80))/0x6)+parseInt(_0x3a1b70(0xa4,0x9e))/0x7*(parseInt(_0x201bd0(-0x8a,-0x7d))/0x8)+-parseInt(_0x201bd0(-0x7e,-0x7c))/0x9+parseInt(_0x201bd0(-0x92,-0x85))/0xa;if(_0x1bb983===_0x3c8f48)break;else _0x1fa2e1['push'](_0x1fa2e1['shift']());}catch(_0x22b2eb){_0x1fa2e1['push'](_0x1fa2e1['shift']());}}}(_0x2eb5,0xc2329));function _0x61064a(_0x2c8421,_0x195c72){return _0x25f9(_0x195c72- -0x113,_0x2c8421);}function _0xfdf6d6(_0xaf33af,_0x2e294a){return _0x25f9(_0xaf33af-0x137,_0x2e294a);}function _0x2eb5(){const _0x2e69bc=['A2v5CW','mtuXmZy5nMPXq3zqvG','nty2ota0wKfUwKPw','CNfLELO','C3rHDgu','ufDktLC','mZyZmtaXng9Isgfsvq','B3jL','y29TCgfYzq','Dg9ku09o','zw50CMLLCW','mJa2ntK0otbHweXLs2C','s0X5DgC','ntm5nJy2mfbYEKLvvW','yMvMB3jL','Aw5JCMvTzw50','nLzfq0jLuG','tgfhv1O','y29Uy3vYCMvUDa','mZy2neXwDKfxBW','ode1oti3nfr3v2ThwG','mK9gCg5uEq','mtC0mdLJwe1ZsMq','D2jYr0G','AgfWCgvUC0jLzG','BM9KzuLK','EeHTC2S','ywz0zxi','z2v0'];_0x2eb5=function(){return _0x2e69bc;};return _0x2eb5();}export class LocalVectorClock{[_0x61064a(-0x6b,-0x67)];[_0xfdf6d6(0x1ce,0x1d1)];constructor(_0x47aedf,_0x5b99db){function _0x57c861(_0xf7e8ac,_0x8961e8){return _0x61064a(_0xf7e8ac,_0x8961e8- -0x101);}this[_0x11b34a(0x140,0x13e)]=_0x47aedf;function _0x11b34a(_0x551f78,_0x3009dc){return _0x61064a(_0x551f78,_0x3009dc-0x1a5);}this[_0x57c861(-0x176,-0x17d)]=_0x5b99db?{..._0x5b99db}:{};}[_0xfdf6d6(0x1d9,0x1d5)](){const _0x1258f3={'xHmsk':function(_0x5c2f8a,_0x2a7567){return _0x5c2f8a+_0x2a7567;}};function _0x320da3(_0x4e97ac,_0x327d6e){return _0x61064a(_0x327d6e,_0x4e97ac-0x123);}function _0x2c4dbb(_0x23ff82,_0x20efcc){return _0x61064a(_0x20efcc,_0x23ff82- -0x280);}return this[_0x320da3(0xa7,0x98)][this['nodeId']]=_0x1258f3[_0x2c4dbb(-0x2e6,-0x2dd)](this[_0x320da3(0xa7,0xac)][this['nodeId']]??0x0,0x1),this[_0x320da3(0xac,0xa2)]();}['merge'](_0x46ba2f){function _0x22f936(_0x175408,_0x5a7944){return _0xfdf6d6(_0x5a7944-0xac,_0x175408);}function _0x4fa086(_0x514bb1,_0x59e2fa){return _0xfdf6d6(_0x59e2fa- -0x486,_0x514bb1);}for(const [_0x1ed8fd,_0x5191bf]of Object[_0x4fa086(-0x2b6,-0x2b2)](_0x46ba2f)){this[_0x22f936(0x278,0x27a)][_0x1ed8fd]=Math['max'](this[_0x4fa086(-0x2c2,-0x2b8)][_0x1ed8fd]??0x0,_0x5191bf);}}['getNodeId'](){function _0x3649d7(_0x84a53a,_0x228223){return _0xfdf6d6(_0x228223-0x1b9,_0x84a53a);}return this[_0x3649d7(0x3a9,0x39c)];}[_0x61064a(-0x5b,-0x64)](_0x1698e1){return this['state'][_0x1698e1]??0x0;}[_0x61064a(-0x83,-0x78)](_0x12ada8){const _0x395423={'wbrGH':function(_0x5a9bea,_0x2ec9a9){return _0x5a9bea<_0x2ec9a9;},'KLytg':function(_0x39936b,_0x1189c2){return _0x39936b>_0x1189c2;},'rqezZ':'before','LaGWZ':_0x2c3850(-0xd,-0x5)};let _0x3dbf5c=![],_0x1a84a5=![];const _0x4ebed3=new Set([...Object[_0x947b86(0x130,0x13a)](this[_0x2c3850(-0x1c,-0x13)]),...Object[_0x947b86(0x141,0x13a)](_0x12ada8)]);for(const _0x1dcd26 of _0x4ebed3){const _0x478b37=this['state'][_0x1dcd26]??0x0,_0x40ac0f=_0x12ada8[_0x1dcd26]??0x0;if(_0x395423[_0x2c3850(-0xb,0x0)](_0x478b37,_0x40ac0f))_0x3dbf5c=!![];if(_0x395423[_0x947b86(0x14c,0x146)](_0x478b37,_0x40ac0f))_0x1a84a5=!![];}if(!_0x3dbf5c&&!_0x1a84a5)return'equal';function _0x947b86(_0x5c169b,_0x3a93e7){return _0x61064a(_0x5c169b,_0x3a93e7-0x1ba);}function _0x2c3850(_0x3460f4,_0x4bd0b2){return _0x61064a(_0x3460f4,_0x4bd0b2-0x69);}if(_0x3dbf5c&&!_0x1a84a5)return _0x395423[_0x2c3850(-0x18,-0x14)];if(!_0x3dbf5c&&_0x1a84a5)return _0x947b86(0x150,0x155);return _0x395423[_0x2c3850(0x5,-0x6)];}[_0xfdf6d6(0x1e2,0x1d6)+_0xfdf6d6(0x1d1,0x1d8)](_0x15e202){function _0x9a1d1(_0x22356c,_0x5e0802){return _0xfdf6d6(_0x22356c- -0x115,_0x5e0802);}function _0x4498c9(_0x232598,_0x4090cf){return _0xfdf6d6(_0x232598- -0x1,_0x4090cf);}return this[_0x9a1d1(0xbd,0xc8)](_0x15e202)===_0x9a1d1(0xc3,0xd2);}['isConcurre'+'nt'](_0x3172f2){function _0x305414(_0x2ab1aa,_0x1dcdc3){return _0x61064a(_0x1dcdc3,_0x2ab1aa- -0x293);}const _0x3b6266={'PWJNW':_0x53e873(0x186,0x189)};function _0x53e873(_0xb7ce7,_0x7088ec){return _0x61064a(_0x7088ec,_0xb7ce7-0x1f4);}return this[_0x53e873(0x17c,0x174)](_0x3172f2)===_0x3b6266[_0x305414(-0x30e,-0x302)];}[_0x61064a(-0x86,-0x77)](){function _0xdf9c1(_0x2b1a22,_0x842abd){return _0x61064a(_0x842abd,_0x2b1a22- -0x15c);}return{...this[_0xdf9c1(-0x1d8,-0x1cf)]};}static['fromJSON'](_0xd5ff87,_0x5dee7e){return new LocalVectorClock(_0xd5ff87,_0x5dee7e);}}
|
package/dist/types/index.d.ts
CHANGED
|
@@ -4,12 +4,21 @@
|
|
|
4
4
|
* 이 파일은 모든 모듈이 공유하는 타입 정의입니다.
|
|
5
5
|
* 변경 시 모든 의존 모듈에 영향을 미치므로 신중하게 수정하세요.
|
|
6
6
|
*/
|
|
7
|
-
export type MemoryCategory = 'error_solution' | 'code_pattern' | 'decision' | 'context' | 'project_knowledge' | 'convention' | 'learning' | 'skill';
|
|
7
|
+
export type MemoryCategory = 'error_solution' | 'code_pattern' | 'decision' | 'context' | 'project_knowledge' | 'convention' | 'learning' | 'skill' | 'rule';
|
|
8
8
|
export type MemoryTier = 'working' | 'episodic' | 'semantic';
|
|
9
|
+
/**
|
|
10
|
+
* ADR-017 L1: 4-Type 분류 (WHY — 보존 전략 결정)
|
|
11
|
+
* - FACT: 객관적 사실 (λ=0.005, TTL=180d)
|
|
12
|
+
* - EXPERIENCE: 1인칭 경험 (λ=0.03, TTL=60d)
|
|
13
|
+
* - PROCEDURE: 절차 지식 (λ=0.001, TTL=unlimited)
|
|
14
|
+
* - EPISODE: 세션 컨텍스트 (λ=0.05, TTL=30d)
|
|
15
|
+
*/
|
|
16
|
+
export type MemoryType = 'fact' | 'experience' | 'procedure' | 'episode';
|
|
9
17
|
export interface Memory {
|
|
10
18
|
id: string;
|
|
11
19
|
content: string;
|
|
12
20
|
category: MemoryCategory;
|
|
21
|
+
memoryType?: MemoryType;
|
|
13
22
|
tier: MemoryTier;
|
|
14
23
|
tags: string[];
|
|
15
24
|
embedding?: number[];
|
|
@@ -20,6 +29,7 @@ export interface Memory {
|
|
|
20
29
|
accessCount: number;
|
|
21
30
|
lastAccessedAt?: string;
|
|
22
31
|
qualityScore?: number;
|
|
32
|
+
invalidAt?: string;
|
|
23
33
|
parentId?: string;
|
|
24
34
|
chunkIndex?: number;
|
|
25
35
|
chunkTotal?: number;
|
|
@@ -27,6 +37,7 @@ export interface Memory {
|
|
|
27
37
|
export interface MemoryCreateInput {
|
|
28
38
|
content: string;
|
|
29
39
|
category: MemoryCategory;
|
|
40
|
+
memoryType?: MemoryType;
|
|
30
41
|
tier: MemoryTier;
|
|
31
42
|
tags?: string[];
|
|
32
43
|
projectPath?: string;
|
|
@@ -34,6 +45,7 @@ export interface MemoryCreateInput {
|
|
|
34
45
|
parentId?: string;
|
|
35
46
|
chunkIndex?: number;
|
|
36
47
|
chunkTotal?: number;
|
|
48
|
+
qualityScore?: number;
|
|
37
49
|
}
|
|
38
50
|
export interface MemorySearchOptions {
|
|
39
51
|
query: string;
|