@hippodid/openclaw-plugin 1.0.0 → 1.0.2

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.
Files changed (47) hide show
  1. package/dist/file-sync.d.ts +18 -0
  2. package/dist/file-sync.d.ts.map +1 -0
  3. package/dist/file-sync.js +172 -0
  4. package/dist/file-sync.js.map +1 -0
  5. package/dist/hippodid-client.d.ts +11 -0
  6. package/dist/hippodid-client.d.ts.map +1 -0
  7. package/dist/hippodid-client.js +155 -0
  8. package/dist/hippodid-client.js.map +1 -0
  9. package/dist/hooks/auto-capture.d.ts +7 -0
  10. package/dist/hooks/auto-capture.d.ts.map +1 -0
  11. package/dist/hooks/auto-capture.js +45 -0
  12. package/dist/hooks/auto-capture.js.map +1 -0
  13. package/dist/hooks/auto-recall.d.ts +7 -0
  14. package/dist/hooks/auto-recall.d.ts.map +1 -0
  15. package/dist/hooks/auto-recall.js +46 -0
  16. package/dist/hooks/auto-recall.js.map +1 -0
  17. package/dist/hooks/memory-flush.d.ts +7 -0
  18. package/dist/hooks/memory-flush.d.ts.map +1 -0
  19. package/dist/hooks/memory-flush.js +14 -0
  20. package/dist/hooks/memory-flush.js.map +1 -0
  21. package/dist/hooks/session-lifecycle.d.ts +8 -0
  22. package/dist/hooks/session-lifecycle.d.ts.map +1 -0
  23. package/dist/hooks/session-lifecycle.js +29 -0
  24. package/dist/hooks/session-lifecycle.js.map +1 -0
  25. package/dist/index.d.ts +4 -0
  26. package/dist/index.d.ts.map +1 -0
  27. package/dist/index.js +164 -0
  28. package/dist/index.js.map +1 -0
  29. package/dist/tier-manager.d.ts +16 -0
  30. package/dist/tier-manager.d.ts.map +1 -0
  31. package/dist/tier-manager.js +57 -0
  32. package/dist/tier-manager.js.map +1 -0
  33. package/dist/types.d.ts +123 -0
  34. package/dist/types.d.ts.map +1 -0
  35. package/dist/types.js +8 -0
  36. package/dist/types.js.map +1 -0
  37. package/dist/workspace-detector.d.ts +5 -0
  38. package/dist/workspace-detector.d.ts.map +1 -0
  39. package/dist/workspace-detector.js +88 -0
  40. package/dist/workspace-detector.js.map +1 -0
  41. package/package.json +8 -2
  42. package/src/hooks/auto-capture.ts +1 -1
  43. package/src/hooks/auto-recall.ts +1 -1
  44. package/src/hooks/memory-flush.ts +1 -1
  45. package/src/hooks/session-lifecycle.ts +2 -2
  46. package/src/index.ts +136 -62
  47. package/src/types.ts +2 -4
package/dist/index.js ADDED
@@ -0,0 +1,164 @@
1
+ import { readFile } from 'node:fs/promises';
2
+ import { resolve } from 'node:path';
3
+ import { createClient } from './hippodid-client.js';
4
+ import { createFileSync } from './file-sync.js';
5
+ import { resolveWatchPaths } from './workspace-detector.js';
6
+ import { createTierManager } from './tier-manager.js';
7
+ import { createMemoryFlushHook } from './hooks/memory-flush.js';
8
+ import { createSessionHooks } from './hooks/session-lifecycle.js';
9
+ import { createAutoRecallHook } from './hooks/auto-recall.js';
10
+ import { createAutoCaptureHook } from './hooks/auto-capture.js';
11
+ export const id = 'hippodid';
12
+ const VERSION = '1.0.0';
13
+ export default function register(api) {
14
+ try {
15
+ const config = resolveConfig(api.config);
16
+ const logger = api.logger ?? {
17
+ info: (msg) => console.log(msg),
18
+ warn: (msg) => console.warn(msg),
19
+ error: (msg) => console.error(msg),
20
+ };
21
+ const client = createClient(config.apiKey, config.baseUrl);
22
+ const tierManager = createTierManager(client, config.characterId, logger);
23
+ const watchPaths = resolveWatchPaths(config);
24
+ const effectiveSyncInterval = Math.max(config.syncIntervalSeconds, 60);
25
+ const fileSync = createFileSync(client, config, watchPaths, logger, effectiveSyncInterval);
26
+ const registerMemoryFlush = createMemoryFlushHook(fileSync, logger);
27
+ registerMemoryFlush(api);
28
+ const registerSessionHooks = createSessionHooks(fileSync, tierManager, config.autoRecall, logger);
29
+ registerSessionHooks(api);
30
+ tierManager.initialize().then((tier) => {
31
+ if (tierManager.shouldMountAutoRecall(config.autoRecall)) {
32
+ const registerAutoRecall = createAutoRecallHook(client, config, logger);
33
+ registerAutoRecall(api);
34
+ }
35
+ if (tierManager.shouldMountAutoCapture(config.autoCapture)) {
36
+ const registerAutoCapture = createAutoCaptureHook(client, config, logger);
37
+ registerAutoCapture(api);
38
+ }
39
+ if (tierManager.shouldMountFileSync(config.autoCapture)) {
40
+ fileSync.start();
41
+ }
42
+ const autoRecallStatus = tierManager.shouldMountAutoRecall(config.autoRecall)
43
+ ? 'ON'
44
+ : 'OFF';
45
+ const autoCaptureStatus = tierManager.shouldMountAutoCapture(config.autoCapture)
46
+ ? 'ON'
47
+ : 'OFF';
48
+ logger.info(`hippodid: v${VERSION} | character: ${config.characterId} | tier: ${tier.tier} | watching ${watchPaths.length} paths | autoRecall: ${autoRecallStatus} | autoCapture: ${autoCaptureStatus}`);
49
+ }).catch((e) => {
50
+ logger.warn(`hippodid: tier initialization failed, running in free mode: ${e instanceof Error ? e.message : 'unknown'}`);
51
+ fileSync.start();
52
+ });
53
+ registerCommands(api, config, client, fileSync, tierManager, logger);
54
+ }
55
+ catch (e) {
56
+ const msg = e instanceof Error ? e.message : 'unknown';
57
+ (api.logger ?? console).error(`hippodid: plugin initialization failed: ${msg}`);
58
+ }
59
+ }
60
+ function resolveConfig(raw) {
61
+ return {
62
+ apiKey: raw.apiKey,
63
+ characterId: raw.characterId,
64
+ baseUrl: raw.baseUrl ?? 'https://api.hippodid.com',
65
+ syncIntervalSeconds: raw.syncIntervalSeconds ?? 300,
66
+ autoRecall: raw.autoRecall ?? false,
67
+ autoCapture: raw.autoCapture ?? false,
68
+ additionalPaths: raw.additionalPaths ?? [],
69
+ };
70
+ }
71
+ function registerCommands(api, config, client, fileSync, tierManager, logger) {
72
+ api.commands.register('hippodid:status', {
73
+ description: 'Show HippoDid tier, sync status, and watched paths',
74
+ handler: async () => {
75
+ const tier = tierManager.getCurrentTier();
76
+ const statusResult = await client.getSyncStatus(config.characterId);
77
+ logger.info(`--- HippoDid Status ---`);
78
+ logger.info(`Character: ${config.characterId}`);
79
+ logger.info(`Tier: ${tier.tier}`);
80
+ logger.info(`Auto-Recall: ${tier.features.autoRecallAvailable ? 'available' : 'unavailable'} (config: ${config.autoRecall ? 'ON' : 'OFF'})`);
81
+ logger.info(`Auto-Capture: ${tier.features.autoCaptureAvailable ? 'available' : 'unavailable'} (config: ${config.autoCapture ? 'ON' : 'OFF'})`);
82
+ if (statusResult.ok) {
83
+ logger.info(`Synced sources: ${statusResult.value.entries.length}`);
84
+ for (const entry of statusResult.value.entries) {
85
+ logger.info(` ${entry.sourcePath} (${entry.label}) — last sync: ${entry.lastSyncedAt}`);
86
+ }
87
+ }
88
+ else {
89
+ logger.warn(`Could not fetch sync status: ${statusResult.error.message}`);
90
+ }
91
+ },
92
+ });
93
+ api.commands.register('hippodid:sync', {
94
+ description: 'Trigger immediate sync of all watched files',
95
+ handler: async () => {
96
+ logger.info('hippodid: manual sync triggered...');
97
+ const { synced, changed } = await fileSync.flushNow();
98
+ logger.info(`hippodid: manual sync complete — ${synced} files (${changed} changed)`);
99
+ },
100
+ });
101
+ api.commands.register('hippodid:import', {
102
+ description: 'Import existing workspace memory into HippoDid character',
103
+ args: [
104
+ {
105
+ name: 'workspace',
106
+ description: 'Path to OpenClaw workspace (default: auto-detect)',
107
+ required: false,
108
+ },
109
+ ],
110
+ handler: async (args) => {
111
+ const { readdir } = await import('node:fs/promises');
112
+ const { join, extname } = await import('node:path');
113
+ const { createHash } = await import('node:crypto');
114
+ const workspacePath = args['workspace']
115
+ ? resolve(args['workspace'])
116
+ : resolve(process.cwd());
117
+ const memoryDir = join(workspacePath, 'memory');
118
+ const memoryMd = join(workspacePath, 'MEMORY.md');
119
+ const filesToImport = [];
120
+ try {
121
+ const entries = await readdir(memoryDir);
122
+ for (const entry of entries) {
123
+ if (extname(entry) === '.md') {
124
+ filesToImport.push({
125
+ path: join(memoryDir, entry),
126
+ label: 'workspace-memory',
127
+ });
128
+ }
129
+ }
130
+ }
131
+ catch {
132
+ // memory dir may not exist
133
+ }
134
+ try {
135
+ await readFile(memoryMd);
136
+ filesToImport.push({ path: memoryMd, label: 'MEMORY.md' });
137
+ }
138
+ catch {
139
+ // MEMORY.md may not exist
140
+ }
141
+ if (filesToImport.length === 0) {
142
+ logger.info('hippodid: no memory files found to import');
143
+ return;
144
+ }
145
+ logger.info(`hippodid: importing ${filesToImport.length} files from ${workspacePath}...`);
146
+ let imported = 0;
147
+ for (const file of filesToImport) {
148
+ try {
149
+ const content = await readFile(file.path);
150
+ const hash = createHash('sha256').update(content).digest('hex');
151
+ const base64 = content.toString('base64');
152
+ const result = await client.syncFile(config.characterId, file.path, file.label, base64, hash);
153
+ if (result.ok)
154
+ imported++;
155
+ }
156
+ catch (e) {
157
+ logger.warn(`hippodid: import failed for ${file.path}: ${e instanceof Error ? e.message : 'unknown'}`);
158
+ }
159
+ }
160
+ logger.info(`hippodid: import complete — ${imported}/${filesToImport.length} files imported`);
161
+ },
162
+ });
163
+ }
164
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAC5C,OAAO,EAAE,OAAO,EAAE,MAAM,WAAW,CAAC;AAEpC,OAAO,EAAE,YAAY,EAAuB,MAAM,sBAAsB,CAAC;AACzE,OAAO,EAAE,cAAc,EAAiB,MAAM,gBAAgB,CAAC;AAC/D,OAAO,EAAE,iBAAiB,EAAE,MAAM,yBAAyB,CAAC;AAC5D,OAAO,EAAE,iBAAiB,EAAoB,MAAM,mBAAmB,CAAC;AACxE,OAAO,EAAE,qBAAqB,EAAE,MAAM,yBAAyB,CAAC;AAChE,OAAO,EAAE,kBAAkB,EAAE,MAAM,8BAA8B,CAAC;AAClE,OAAO,EAAE,oBAAoB,EAAE,MAAM,wBAAwB,CAAC;AAC9D,OAAO,EAAE,qBAAqB,EAAE,MAAM,yBAAyB,CAAC;AAEhE,MAAM,CAAC,MAAM,EAAE,GAAG,UAAU,CAAC;AAE7B,MAAM,OAAO,GAAG,OAAO,CAAC;AAExB,MAAM,CAAC,OAAO,UAAU,QAAQ,CAAC,GAAsB;IACrD,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,aAAa,CAAC,GAAG,CAAC,MAAM,CAAC,CAAC;QACzC,MAAM,MAAM,GAAG,GAAG,CAAC,MAAM,IAAI;YAC3B,IAAI,EAAE,CAAC,GAAW,EAAE,EAAE,CAAC,OAAO,CAAC,GAAG,CAAC,GAAG,CAAC;YACvC,IAAI,EAAE,CAAC,GAAW,EAAE,EAAE,CAAC,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC;YACxC,KAAK,EAAE,CAAC,GAAW,EAAE,EAAE,CAAC,OAAO,CAAC,KAAK,CAAC,GAAG,CAAC;SAC3C,CAAC;QAEF,MAAM,MAAM,GAAG,YAAY,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,OAAO,CAAC,CAAC;QAC3D,MAAM,WAAW,GAAG,iBAAiB,CAAC,MAAM,EAAE,MAAM,CAAC,WAAW,EAAE,MAAM,CAAC,CAAC;QAC1E,MAAM,UAAU,GAAG,iBAAiB,CAAC,MAAM,CAAC,CAAC;QAC7C,MAAM,qBAAqB,GAAG,IAAI,CAAC,GAAG,CAAC,MAAM,CAAC,mBAAmB,EAAE,EAAE,CAAC,CAAC;QACvE,MAAM,QAAQ,GAAG,cAAc,CAAC,MAAM,EAAE,MAAM,EAAE,UAAU,EAAE,MAAM,EAAE,qBAAqB,CAAC,CAAC;QAE3F,MAAM,mBAAmB,GAAG,qBAAqB,CAAC,QAAQ,EAAE,MAAM,CAAC,CAAC;QACpE,mBAAmB,CAAC,GAAG,CAAC,CAAC;QAEzB,MAAM,oBAAoB,GAAG,kBAAkB,CAC7C,QAAQ,EACR,WAAW,EACX,MAAM,CAAC,UAAU,EACjB,MAAM,CACP,CAAC;QACF,oBAAoB,CAAC,GAAG,CAAC,CAAC;QAE1B,WAAW,CAAC,UAAU,EAAE,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,EAAE;YACrC,IAAI,WAAW,CAAC,qBAAqB,CAAC,MAAM,CAAC,UAAU,CAAC,EAAE,CAAC;gBACzD,MAAM,kBAAkB,GAAG,oBAAoB,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC,CAAC;gBACxE,kBAAkB,CAAC,GAAG,CAAC,CAAC;YAC1B,CAAC;YAED,IAAI,WAAW,CAAC,sBAAsB,CAAC,MAAM,CAAC,WAAW,CAAC,EAAE,CAAC;gBAC3D,MAAM,mBAAmB,GAAG,qBAAqB,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC,CAAC;gBAC1E,mBAAmB,CAAC,GAAG,CAAC,CAAC;YAC3B,CAAC;YAED,IAAI,WAAW,CAAC,mBAAmB,CAAC,MAAM,CAAC,WAAW,CAAC,EAAE,CAAC;gBACxD,QAAQ,CAAC,KAAK,EAAE,CAAC;YACnB,CAAC;YAED,MAAM,gBAAgB,GAAG,WAAW,CAAC,qBAAqB,CAAC,MAAM,CAAC,UAAU,CAAC;gBAC3E,CAAC,CAAC,IAAI;gBACN,CAAC,CAAC,KAAK,CAAC;YACV,MAAM,iBAAiB,GAAG,WAAW,CAAC,sBAAsB,CAAC,MAAM,CAAC,WAAW,CAAC;gBAC9E,CAAC,CAAC,IAAI;gBACN,CAAC,CAAC,KAAK,CAAC;YAEV,MAAM,CAAC,IAAI,CACT,cAAc,OAAO,iBAAiB,MAAM,CAAC,WAAW,YAAY,IAAI,CAAC,IAAI,eAAe,UAAU,CAAC,MAAM,wBAAwB,gBAAgB,mBAAmB,iBAAiB,EAAE,CAC5L,CAAC;QACJ,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE;YACb,MAAM,CAAC,IAAI,CACT,+DAA+D,CAAC,YAAY,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,SAAS,EAAE,CAC5G,CAAC;YACF,QAAQ,CAAC,KAAK,EAAE,CAAC;QACnB,CAAC,CAAC,CAAC;QAEH,gBAAgB,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,CAAC,CAAC;IACvE,CAAC;IAAC,OAAO,CAAC,EAAE,CAAC;QACX,MAAM,GAAG,GAAG,CAAC,YAAY,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,SAAS,CAAC;QACvD,CAAC,GAAG,CAAC,MAAM,IAAI,OAAO,CAAC,CAAC,KAAK,CAAC,2CAA2C,GAAG,EAAE,CAAC,CAAC;IAClF,CAAC;AACH,CAAC;AAED,SAAS,aAAa,CAAC,GAAiB;IACtC,OAAO;QACL,MAAM,EAAE,GAAG,CAAC,MAAM;QAClB,WAAW,EAAE,GAAG,CAAC,WAAW;QAC5B,OAAO,EAAE,GAAG,CAAC,OAAO,IAAI,0BAA0B;QAClD,mBAAmB,EAAE,GAAG,CAAC,mBAAmB,IAAI,GAAG;QACnD,UAAU,EAAE,GAAG,CAAC,UAAU,IAAI,KAAK;QACnC,WAAW,EAAE,GAAG,CAAC,WAAW,IAAI,KAAK;QACrC,eAAe,EAAE,GAAG,CAAC,eAAe,IAAI,EAAE;KAC3C,CAAC;AACJ,CAAC;AAED,SAAS,gBAAgB,CACvB,GAAsB,EACtB,MAAoB,EACpB,MAAsB,EACtB,QAAkB,EAClB,WAAwB,EACxB,MAA4D;IAE5D,GAAG,CAAC,QAAQ,CAAC,QAAQ,CAAC,iBAAiB,EAAE;QACvC,WAAW,EAAE,oDAAoD;QACjE,OAAO,EAAE,KAAK,IAAI,EAAE;YAClB,MAAM,IAAI,GAAG,WAAW,CAAC,cAAc,EAAE,CAAC;YAC1C,MAAM,YAAY,GAAG,MAAM,MAAM,CAAC,aAAa,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC;YAEpE,MAAM,CAAC,IAAI,CAAC,yBAAyB,CAAC,CAAC;YACvC,MAAM,CAAC,IAAI,CAAC,cAAc,MAAM,CAAC,WAAW,EAAE,CAAC,CAAC;YAChD,MAAM,CAAC,IAAI,CAAC,SAAS,IAAI,CAAC,IAAI,EAAE,CAAC,CAAC;YAClC,MAAM,CAAC,IAAI,CACT,gBAAgB,IAAI,CAAC,QAAQ,CAAC,mBAAmB,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,aAAa,aAAa,MAAM,CAAC,UAAU,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,GAAG,CAChI,CAAC;YACF,MAAM,CAAC,IAAI,CACT,iBAAiB,IAAI,CAAC,QAAQ,CAAC,oBAAoB,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,aAAa,aAAa,MAAM,CAAC,WAAW,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,KAAK,GAAG,CACnI,CAAC;YAEF,IAAI,YAAY,CAAC,EAAE,EAAE,CAAC;gBACpB,MAAM,CAAC,IAAI,CAAC,mBAAmB,YAAY,CAAC,KAAK,CAAC,OAAO,CAAC,MAAM,EAAE,CAAC,CAAC;gBACpE,KAAK,MAAM,KAAK,IAAI,YAAY,CAAC,KAAK,CAAC,OAAO,EAAE,CAAC;oBAC/C,MAAM,CAAC,IAAI,CACT,KAAK,KAAK,CAAC,UAAU,KAAK,KAAK,CAAC,KAAK,kBAAkB,KAAK,CAAC,YAAY,EAAE,CAC5E,CAAC;gBACJ,CAAC;YACH,CAAC;iBAAM,CAAC;gBACN,MAAM,CAAC,IAAI,CAAC,gCAAgC,YAAY,CAAC,KAAK,CAAC,OAAO,EAAE,CAAC,CAAC;YAC5E,CAAC;QACH,CAAC;KACF,CAAC,CAAC;IAEH,GAAG,CAAC,QAAQ,CAAC,QAAQ,CAAC,eAAe,EAAE;QACrC,WAAW,EAAE,6CAA6C;QAC1D,OAAO,EAAE,KAAK,IAAI,EAAE;YAClB,MAAM,CAAC,IAAI,CAAC,oCAAoC,CAAC,CAAC;YAClD,MAAM,EAAE,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,QAAQ,CAAC,QAAQ,EAAE,CAAC;YACtD,MAAM,CAAC,IAAI,CACT,oCAAoC,MAAM,WAAW,OAAO,WAAW,CACxE,CAAC;QACJ,CAAC;KACF,CAAC,CAAC;IAEH,GAAG,CAAC,QAAQ,CAAC,QAAQ,CAAC,iBAAiB,EAAE;QACvC,WAAW,EAAE,0DAA0D;QACvE,IAAI,EAAE;YACJ;gBACE,IAAI,EAAE,WAAW;gBACjB,WAAW,EAAE,mDAAmD;gBAChE,QAAQ,EAAE,KAAK;aAChB;SACF;QACD,OAAO,EAAE,KAAK,EAAE,IAA4B,EAAE,EAAE;YAC9C,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,MAAM,CAAC,kBAAkB,CAAC,CAAC;YACrD,MAAM,EAAE,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC;YACpD,MAAM,EAAE,UAAU,EAAE,GAAG,MAAM,MAAM,CAAC,aAAa,CAAC,CAAC;YAEnD,MAAM,aAAa,GAAG,IAAI,CAAC,WAAW,CAAC;gBACrC,CAAC,CAAC,OAAO,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC;gBAC5B,CAAC,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,EAAE,CAAC,CAAC;YAE3B,MAAM,SAAS,GAAG,IAAI,CAAC,aAAa,EAAE,QAAQ,CAAC,CAAC;YAChD,MAAM,QAAQ,GAAG,IAAI,CAAC,aAAa,EAAE,WAAW,CAAC,CAAC;YAClD,MAAM,aAAa,GAA2C,EAAE,CAAC;YAEjE,IAAI,CAAC;gBACH,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,SAAS,CAAC,CAAC;gBACzC,KAAK,MAAM,KAAK,IAAI,OAAO,EAAE,CAAC;oBAC5B,IAAI,OAAO,CAAC,KAAK,CAAC,KAAK,KAAK,EAAE,CAAC;wBAC7B,aAAa,CAAC,IAAI,CAAC;4BACjB,IAAI,EAAE,IAAI,CAAC,SAAS,EAAE,KAAK,CAAC;4BAC5B,KAAK,EAAE,kBAAkB;yBAC1B,CAAC,CAAC;oBACL,CAAC;gBACH,CAAC;YACH,CAAC;YAAC,MAAM,CAAC;gBACP,2BAA2B;YAC7B,CAAC;YAED,IAAI,CAAC;gBACH,MAAM,QAAQ,CAAC,QAAQ,CAAC,CAAC;gBACzB,aAAa,CAAC,IAAI,CAAC,EAAE,IAAI,EAAE,QAAQ,EAAE,KAAK,EAAE,WAAW,EAAE,CAAC,CAAC;YAC7D,CAAC;YAAC,MAAM,CAAC;gBACP,0BAA0B;YAC5B,CAAC;YAED,IAAI,aAAa,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;gBAC/B,MAAM,CAAC,IAAI,CAAC,2CAA2C,CAAC,CAAC;gBACzD,OAAO;YACT,CAAC;YAED,MAAM,CAAC,IAAI,CACT,uBAAuB,aAAa,CAAC,MAAM,eAAe,aAAa,KAAK,CAC7E,CAAC;YAEF,IAAI,QAAQ,GAAG,CAAC,CAAC;YACjB,KAAK,MAAM,IAAI,IAAI,aAAa,EAAE,CAAC;gBACjC,IAAI,CAAC;oBACH,MAAM,OAAO,GAAG,MAAM,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;oBAC1C,MAAM,IAAI,GAAG,UAAU,CAAC,QAAQ,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;oBAChE,MAAM,MAAM,GAAG,OAAO,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;oBAC1C,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,QAAQ,CAClC,MAAM,CAAC,WAAW,EAClB,IAAI,CAAC,IAAI,EACT,IAAI,CAAC,KAAK,EACV,MAAM,EACN,IAAI,CACL,CAAC;oBACF,IAAI,MAAM,CAAC,EAAE;wBAAE,QAAQ,EAAE,CAAC;gBAC5B,CAAC;gBAAC,OAAO,CAAC,EAAE,CAAC;oBACX,MAAM,CAAC,IAAI,CACT,+BAA+B,IAAI,CAAC,IAAI,KAAK,CAAC,YAAY,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,SAAS,EAAE,CAC1F,CAAC;gBACJ,CAAC;YACH,CAAC;YAED,MAAM,CAAC,IAAI,CACT,+BAA+B,QAAQ,IAAI,aAAa,CAAC,MAAM,iBAAiB,CACjF,CAAC;QACJ,CAAC;KACF,CAAC,CAAC;AACL,CAAC"}
@@ -0,0 +1,16 @@
1
+ import type { HippoDidClient } from './hippodid-client.js';
2
+ import type { TierInfo } from './types.js';
3
+ export interface TierManager {
4
+ initialize(): Promise<TierInfo>;
5
+ getCurrentTier(): TierInfo;
6
+ shouldMountFileSync(autoCaptureEnabled: boolean): boolean;
7
+ shouldMountAutoRecall(autoRecallEnabled: boolean): boolean;
8
+ shouldMountAutoCapture(autoCaptureEnabled: boolean): boolean;
9
+ shouldHydrateOnStart(autoRecallEnabled: boolean): boolean;
10
+ getEffectiveSyncInterval(configInterval: number): number;
11
+ }
12
+ export declare function createTierManager(client: HippoDidClient, characterId: string, logger: {
13
+ info(msg: string): void;
14
+ warn(msg: string): void;
15
+ }): TierManager;
16
+ //# sourceMappingURL=tier-manager.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tier-manager.d.ts","sourceRoot":"","sources":["../src/tier-manager.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,sBAAsB,CAAC;AAC3D,OAAO,KAAK,EAAE,QAAQ,EAAE,MAAM,YAAY,CAAC;AAE3C,MAAM,WAAW,WAAW;IAC1B,UAAU,IAAI,OAAO,CAAC,QAAQ,CAAC,CAAC;IAChC,cAAc,IAAI,QAAQ,CAAC;IAC3B,mBAAmB,CAAC,kBAAkB,EAAE,OAAO,GAAG,OAAO,CAAC;IAC1D,qBAAqB,CAAC,iBAAiB,EAAE,OAAO,GAAG,OAAO,CAAC;IAC3D,sBAAsB,CAAC,kBAAkB,EAAE,OAAO,GAAG,OAAO,CAAC;IAC7D,oBAAoB,CAAC,iBAAiB,EAAE,OAAO,GAAG,OAAO,CAAC;IAC1D,wBAAwB,CAAC,cAAc,EAAE,MAAM,GAAG,MAAM,CAAC;CAC1D;AAWD,wBAAgB,iBAAiB,CAC/B,MAAM,EAAE,cAAc,EACtB,WAAW,EAAE,MAAM,EACnB,MAAM,EAAE;IAAE,IAAI,CAAC,GAAG,EAAE,MAAM,GAAG,IAAI,CAAC;IAAC,IAAI,CAAC,GAAG,EAAE,MAAM,GAAG,IAAI,CAAA;CAAE,GAC3D,WAAW,CA2Db"}
@@ -0,0 +1,57 @@
1
+ const FREE_TIER_FALLBACK = {
2
+ tier: 'free',
3
+ features: {
4
+ autoRecallAvailable: false,
5
+ autoCaptureAvailable: false,
6
+ minSyncIntervalSeconds: 60,
7
+ },
8
+ };
9
+ export function createTierManager(client, characterId, logger) {
10
+ let currentTier = FREE_TIER_FALLBACK;
11
+ return {
12
+ async initialize() {
13
+ const result = await client.getTier(characterId);
14
+ if (result.ok) {
15
+ currentTier = result.value;
16
+ }
17
+ else {
18
+ logger.warn(`hippodid: failed to fetch tier, defaulting to free: ${result.error.message}`);
19
+ currentTier = FREE_TIER_FALLBACK;
20
+ }
21
+ logger.info(`hippodid: tier=${currentTier.tier}, autoRecall=${currentTier.features.autoRecallAvailable ? 'available' : 'unavailable'}, autoCapture=${currentTier.features.autoCaptureAvailable ? 'available' : 'unavailable'}`);
22
+ return currentTier;
23
+ },
24
+ getCurrentTier() {
25
+ return currentTier;
26
+ },
27
+ shouldMountFileSync(autoCaptureEnabled) {
28
+ const isFree = !isPaidTier(currentTier);
29
+ if (isFree)
30
+ return true;
31
+ return !autoCaptureEnabled;
32
+ },
33
+ shouldMountAutoRecall(autoRecallEnabled) {
34
+ return (isPaidTier(currentTier) &&
35
+ autoRecallEnabled &&
36
+ currentTier.features.autoRecallAvailable);
37
+ },
38
+ shouldMountAutoCapture(autoCaptureEnabled) {
39
+ return (isPaidTier(currentTier) &&
40
+ autoCaptureEnabled &&
41
+ currentTier.features.autoCaptureAvailable);
42
+ },
43
+ shouldHydrateOnStart(autoRecallEnabled) {
44
+ const isFree = !isPaidTier(currentTier);
45
+ if (isFree)
46
+ return true;
47
+ return !autoRecallEnabled;
48
+ },
49
+ getEffectiveSyncInterval(configInterval) {
50
+ return Math.max(configInterval, currentTier.features.minSyncIntervalSeconds);
51
+ },
52
+ };
53
+ }
54
+ function isPaidTier(tier) {
55
+ return tier.tier !== 'free';
56
+ }
57
+ //# sourceMappingURL=tier-manager.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tier-manager.js","sourceRoot":"","sources":["../src/tier-manager.ts"],"names":[],"mappings":"AAaA,MAAM,kBAAkB,GAAa;IACnC,IAAI,EAAE,MAAM;IACZ,QAAQ,EAAE;QACR,mBAAmB,EAAE,KAAK;QAC1B,oBAAoB,EAAE,KAAK;QAC3B,sBAAsB,EAAE,EAAE;KAC3B;CACF,CAAC;AAEF,MAAM,UAAU,iBAAiB,CAC/B,MAAsB,EACtB,WAAmB,EACnB,MAA4D;IAE5D,IAAI,WAAW,GAAa,kBAAkB,CAAC;IAE/C,OAAO;QACL,KAAK,CAAC,UAAU;YACd,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,OAAO,CAAC,WAAW,CAAC,CAAC;YAEjD,IAAI,MAAM,CAAC,EAAE,EAAE,CAAC;gBACd,WAAW,GAAG,MAAM,CAAC,KAAK,CAAC;YAC7B,CAAC;iBAAM,CAAC;gBACN,MAAM,CAAC,IAAI,CACT,uDAAuD,MAAM,CAAC,KAAK,CAAC,OAAO,EAAE,CAC9E,CAAC;gBACF,WAAW,GAAG,kBAAkB,CAAC;YACnC,CAAC;YAED,MAAM,CAAC,IAAI,CACT,kBAAkB,WAAW,CAAC,IAAI,gBAAgB,WAAW,CAAC,QAAQ,CAAC,mBAAmB,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,aAAa,iBAAiB,WAAW,CAAC,QAAQ,CAAC,oBAAoB,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC,CAAC,aAAa,EAAE,CACnN,CAAC;YAEF,OAAO,WAAW,CAAC;QACrB,CAAC;QAED,cAAc;YACZ,OAAO,WAAW,CAAC;QACrB,CAAC;QAED,mBAAmB,CAAC,kBAA2B;YAC7C,MAAM,MAAM,GAAG,CAAC,UAAU,CAAC,WAAW,CAAC,CAAC;YACxC,IAAI,MAAM;gBAAE,OAAO,IAAI,CAAC;YACxB,OAAO,CAAC,kBAAkB,CAAC;QAC7B,CAAC;QAED,qBAAqB,CAAC,iBAA0B;YAC9C,OAAO,CACL,UAAU,CAAC,WAAW,CAAC;gBACvB,iBAAiB;gBACjB,WAAW,CAAC,QAAQ,CAAC,mBAAmB,CACzC,CAAC;QACJ,CAAC;QAED,sBAAsB,CAAC,kBAA2B;YAChD,OAAO,CACL,UAAU,CAAC,WAAW,CAAC;gBACvB,kBAAkB;gBAClB,WAAW,CAAC,QAAQ,CAAC,oBAAoB,CAC1C,CAAC;QACJ,CAAC;QAED,oBAAoB,CAAC,iBAA0B;YAC7C,MAAM,MAAM,GAAG,CAAC,UAAU,CAAC,WAAW,CAAC,CAAC;YACxC,IAAI,MAAM;gBAAE,OAAO,IAAI,CAAC;YACxB,OAAO,CAAC,iBAAiB,CAAC;QAC5B,CAAC;QAED,wBAAwB,CAAC,cAAsB;YAC7C,OAAO,IAAI,CAAC,GAAG,CAAC,cAAc,EAAE,WAAW,CAAC,QAAQ,CAAC,sBAAsB,CAAC,CAAC;QAC/E,CAAC;KACF,CAAC;AACJ,CAAC;AAED,SAAS,UAAU,CAAC,IAAc;IAChC,OAAO,IAAI,CAAC,IAAI,KAAK,MAAM,CAAC;AAC9B,CAAC"}
@@ -0,0 +1,123 @@
1
+ export type Result<T, E = ApiError> = {
2
+ ok: true;
3
+ value: T;
4
+ } | {
5
+ ok: false;
6
+ error: E;
7
+ };
8
+ export declare function ok<T>(value: T): Result<T, never>;
9
+ export declare function err<E>(error: E): Result<never, E>;
10
+ export interface ApiError {
11
+ status: number;
12
+ message: string;
13
+ retryable: boolean;
14
+ }
15
+ export interface PluginConfig {
16
+ apiKey: string;
17
+ characterId: string;
18
+ baseUrl: string;
19
+ syncIntervalSeconds: number;
20
+ autoRecall: boolean;
21
+ autoCapture: boolean;
22
+ additionalPaths: WatchPathConfig[];
23
+ }
24
+ export interface WatchPathConfig {
25
+ path: string;
26
+ label?: string;
27
+ }
28
+ export interface WatchPath {
29
+ path: string;
30
+ label: string;
31
+ source: 'auto-detected' | 'user-specified';
32
+ }
33
+ export interface TierInfo {
34
+ tier: string;
35
+ features: {
36
+ autoRecallAvailable: boolean;
37
+ autoCaptureAvailable: boolean;
38
+ minSyncIntervalSeconds: number;
39
+ };
40
+ }
41
+ export interface TierApiResponse {
42
+ tier: string;
43
+ features: {
44
+ auto_recall_available: boolean;
45
+ auto_capture_available: boolean;
46
+ min_sync_interval_seconds: number;
47
+ };
48
+ }
49
+ export interface SyncResponse {
50
+ status: string;
51
+ snapshotId: string;
52
+ changed: boolean;
53
+ }
54
+ export interface SyncApiResponse {
55
+ status: string;
56
+ snapshot_id: string;
57
+ changed: boolean;
58
+ }
59
+ export interface SyncLatestResponse {
60
+ sourcePath: string;
61
+ fileContent: string;
62
+ snapshotId: string;
63
+ syncedAt: string;
64
+ }
65
+ export interface SyncLatestApiResponse {
66
+ source_path: string;
67
+ file_content: string;
68
+ snapshot_id: string;
69
+ synced_at: string;
70
+ }
71
+ export interface SyncStatusEntry {
72
+ sourcePath: string;
73
+ label: string;
74
+ lastSyncedAt: string;
75
+ snapshotId: string;
76
+ }
77
+ export interface SyncStatusResponse {
78
+ entries: SyncStatusEntry[];
79
+ }
80
+ export interface SearchResult {
81
+ content: string;
82
+ category: string;
83
+ score: number;
84
+ createdAt: string;
85
+ }
86
+ export interface SearchResultApiResponse {
87
+ content: string;
88
+ category: string;
89
+ score: number;
90
+ created_at: string;
91
+ }
92
+ export interface FileTrackingEntry {
93
+ hash: string;
94
+ lastSyncedAt: Date;
95
+ }
96
+ export interface OpenClawPluginAPI {
97
+ config: PluginConfig;
98
+ logger: {
99
+ info(message: string): void;
100
+ warn(message: string): void;
101
+ error(message: string): void;
102
+ };
103
+ hooks: {
104
+ on(event: string, handler: (...args: any[]) => void | Promise<void>): void;
105
+ };
106
+ context: {
107
+ prepend(content: string): void;
108
+ };
109
+ commands: {
110
+ register(name: string, options: CommandOptions): void;
111
+ };
112
+ }
113
+ export interface CommandOptions {
114
+ description: string;
115
+ args?: CommandArg[];
116
+ handler: (args: Record<string, string>) => void | Promise<void>;
117
+ }
118
+ export interface CommandArg {
119
+ name: string;
120
+ description: string;
121
+ required?: boolean;
122
+ }
123
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"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"}
package/dist/types.js ADDED
@@ -0,0 +1,8 @@
1
+ // --- Result type (discriminated union, zero deps) ---
2
+ export function ok(value) {
3
+ return { ok: true, value };
4
+ }
5
+ export function err(error) {
6
+ return { ok: false, error };
7
+ }
8
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA,uDAAuD;AAMvD,MAAM,UAAU,EAAE,CAAI,KAAQ;IAC5B,OAAO,EAAE,EAAE,EAAE,IAAI,EAAE,KAAK,EAAE,CAAC;AAC7B,CAAC;AAED,MAAM,UAAU,GAAG,CAAI,KAAQ;IAC7B,OAAO,EAAE,EAAE,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC;AAC9B,CAAC"}
@@ -0,0 +1,5 @@
1
+ import type { PluginConfig, WatchPath } from './types.js';
2
+ export declare function detectWorkspaceMemoryDir(): string | null;
3
+ export declare function detectMemoryMdPath(): string | null;
4
+ export declare function resolveWatchPaths(config: PluginConfig): WatchPath[];
5
+ //# sourceMappingURL=workspace-detector.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"workspace-detector.d.ts","sourceRoot":"","sources":["../src/workspace-detector.ts"],"names":[],"mappings":"AAGA,OAAO,KAAK,EAAE,YAAY,EAAE,SAAS,EAAE,MAAM,YAAY,CAAC;AAE1D,wBAAgB,wBAAwB,IAAI,MAAM,GAAG,IAAI,CAkBxD;AAED,wBAAgB,kBAAkB,IAAI,MAAM,GAAG,IAAI,CAoBlD;AAED,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,YAAY,GAAG,SAAS,EAAE,CA2CnE"}
@@ -0,0 +1,88 @@
1
+ import { existsSync, readdirSync, statSync } from 'node:fs';
2
+ import { resolve, join } from 'node:path';
3
+ import { homedir } from 'node:os';
4
+ export function detectWorkspaceMemoryDir() {
5
+ const candidates = [];
6
+ const envWorkspace = process.env['OPENCLAW_WORKSPACE'];
7
+ if (envWorkspace) {
8
+ candidates.push(resolve(join(envWorkspace, 'memory')));
9
+ }
10
+ candidates.push(resolve(join(homedir(), '.openclaw', 'workspace', 'memory')));
11
+ candidates.push(resolve(join(process.cwd(), 'memory')));
12
+ for (const candidate of candidates) {
13
+ if (isValidMemoryDir(candidate)) {
14
+ return candidate;
15
+ }
16
+ }
17
+ return null;
18
+ }
19
+ export function detectMemoryMdPath() {
20
+ const candidates = [];
21
+ const envWorkspace = process.env['OPENCLAW_WORKSPACE'];
22
+ if (envWorkspace) {
23
+ candidates.push(resolve(join(envWorkspace, 'MEMORY.md')));
24
+ }
25
+ candidates.push(resolve(join(homedir(), '.openclaw', 'workspace', 'MEMORY.md')));
26
+ candidates.push(resolve(join(process.cwd(), 'MEMORY.md')));
27
+ for (const candidate of candidates) {
28
+ if (existsSync(candidate)) {
29
+ return candidate;
30
+ }
31
+ }
32
+ return null;
33
+ }
34
+ export function resolveWatchPaths(config) {
35
+ const paths = [];
36
+ const seen = new Set();
37
+ const memoryDir = detectWorkspaceMemoryDir();
38
+ if (memoryDir) {
39
+ const resolved = resolve(memoryDir);
40
+ if (!seen.has(resolved)) {
41
+ seen.add(resolved);
42
+ paths.push({
43
+ path: resolved,
44
+ label: 'workspace-memory',
45
+ source: 'auto-detected',
46
+ });
47
+ }
48
+ }
49
+ const memoryMd = detectMemoryMdPath();
50
+ if (memoryMd) {
51
+ const resolved = resolve(memoryMd);
52
+ if (!seen.has(resolved)) {
53
+ seen.add(resolved);
54
+ paths.push({
55
+ path: resolved,
56
+ label: 'MEMORY.md',
57
+ source: 'auto-detected',
58
+ });
59
+ }
60
+ }
61
+ for (const additional of config.additionalPaths) {
62
+ const resolved = resolve(additional.path);
63
+ if (!seen.has(resolved)) {
64
+ seen.add(resolved);
65
+ paths.push({
66
+ path: resolved,
67
+ label: additional.label ?? resolved,
68
+ source: 'user-specified',
69
+ });
70
+ }
71
+ }
72
+ return paths;
73
+ }
74
+ function isValidMemoryDir(dirPath) {
75
+ try {
76
+ if (!existsSync(dirPath))
77
+ return false;
78
+ const s = statSync(dirPath);
79
+ if (!s.isDirectory())
80
+ return false;
81
+ const entries = readdirSync(dirPath);
82
+ return entries.some((e) => e.endsWith('.md'));
83
+ }
84
+ catch {
85
+ return false;
86
+ }
87
+ }
88
+ //# sourceMappingURL=workspace-detector.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"workspace-detector.js","sourceRoot":"","sources":["../src/workspace-detector.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hippodid/openclaw-plugin",
3
- "version": "1.0.0",
3
+ "version": "1.0.2",
4
4
  "description": "Cloud sync for MEMORY.md with structured character memory. Survives context compaction.",
5
5
  "license": "Apache-2.0",
6
6
  "repository": {
@@ -18,7 +18,8 @@
18
18
  ],
19
19
  "main": "src/index.ts",
20
20
  "files": [
21
- "src/",
21
+ "dist",
22
+ "src",
22
23
  "openclaw.plugin.json",
23
24
  "LICENSE",
24
25
  "README.md"
@@ -34,5 +35,10 @@
34
35
  "@vitest/coverage-v8": "^3.2.4",
35
36
  "typescript": "^5.7.0",
36
37
  "vitest": "^3.0.0"
38
+ },
39
+ "openclaw": {
40
+ "extensions": [
41
+ "./dist/index.js"
42
+ ]
37
43
  }
38
44
  }
@@ -7,7 +7,7 @@ export function createAutoCaptureHook(
7
7
  logger: { info(msg: string): void; warn(msg: string): void },
8
8
  ): (api: OpenClawPluginAPI) => void {
9
9
  return (api: OpenClawPluginAPI) => {
10
- api.hooks.on('agent_end', (...args: unknown[]) => {
10
+ api.on('agent_end', (...args: unknown[]) => {
11
11
  try {
12
12
  const exchange = extractExchange(args);
13
13
  if (!exchange) return;
@@ -7,7 +7,7 @@ export function createAutoRecallHook(
7
7
  logger: { info(msg: string): void; warn(msg: string): void },
8
8
  ): (api: OpenClawPluginAPI) => void {
9
9
  return (api: OpenClawPluginAPI) => {
10
- api.hooks.on('before_agent_start', async (...args: unknown[]) => {
10
+ api.on('before_agent_start', async (...args: unknown[]) => {
11
11
  try {
12
12
  const userMessage = extractUserMessage(args);
13
13
  if (!userMessage) return;
@@ -6,7 +6,7 @@ export function createMemoryFlushHook(
6
6
  logger: { info(msg: string): void; warn(msg: string): void },
7
7
  ): (api: OpenClawPluginAPI) => void {
8
8
  return (api: OpenClawPluginAPI) => {
9
- api.hooks.on('memoryFlush', async () => {
9
+ api.on('memoryFlush', async () => {
10
10
  try {
11
11
  const { synced, changed } = await fileSync.flushNow();
12
12
  logger.info(
@@ -9,7 +9,7 @@ export function createSessionHooks(
9
9
  logger: { info(msg: string): void; warn(msg: string): void },
10
10
  ): (api: OpenClawPluginAPI) => void {
11
11
  return (api: OpenClawPluginAPI) => {
12
- api.hooks.on('session:start', async () => {
12
+ api.on('session:start', async () => {
13
13
  try {
14
14
  await tierManager.initialize();
15
15
 
@@ -26,7 +26,7 @@ export function createSessionHooks(
26
26
  }
27
27
  });
28
28
 
29
- api.hooks.on('session:end', async () => {
29
+ api.on('session:end', async () => {
30
30
  try {
31
31
  const { synced, changed } = await fileSync.flushNow();
32
32
  logger.info(