myceliumail 1.0.1

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 (150) hide show
  1. package/.context7 +87 -0
  2. package/.env.example +12 -0
  3. package/.eslintrc.json +29 -0
  4. package/CLAUDE.md +35 -0
  5. package/COMPLETE.md +51 -0
  6. package/LICENSE +21 -0
  7. package/MYCELIUMAIL_STARTER_KIT.md +603 -0
  8. package/NEXT_STEPS.md +96 -0
  9. package/README.md +229 -0
  10. package/desktop/README.md +102 -0
  11. package/desktop/assets/icon.icns +0 -0
  12. package/desktop/assets/icon.iconset/icon_128x128.png +0 -0
  13. package/desktop/assets/icon.iconset/icon_128x128@2x.png +0 -0
  14. package/desktop/assets/icon.iconset/icon_16x16.png +0 -0
  15. package/desktop/assets/icon.iconset/icon_16x16@2x.png +0 -0
  16. package/desktop/assets/icon.iconset/icon_256x256.png +0 -0
  17. package/desktop/assets/icon.iconset/icon_256x256@2x.png +0 -0
  18. package/desktop/assets/icon.iconset/icon_32x32.png +0 -0
  19. package/desktop/assets/icon.iconset/icon_32x32@2x.png +0 -0
  20. package/desktop/assets/icon.iconset/icon_512x512.png +0 -0
  21. package/desktop/assets/icon.iconset/icon_512x512@2x.png +0 -0
  22. package/desktop/assets/icon.png +0 -0
  23. package/desktop/assets/tray-icon.png +0 -0
  24. package/desktop/main.js +257 -0
  25. package/desktop/package-lock.json +4198 -0
  26. package/desktop/package.json +48 -0
  27. package/desktop/preload.js +11 -0
  28. package/dist/bin/myceliumail.d.ts +8 -0
  29. package/dist/bin/myceliumail.d.ts.map +1 -0
  30. package/dist/bin/myceliumail.js +44 -0
  31. package/dist/bin/myceliumail.js.map +1 -0
  32. package/dist/commands/broadcast.d.ts +9 -0
  33. package/dist/commands/broadcast.d.ts.map +1 -0
  34. package/dist/commands/broadcast.js +59 -0
  35. package/dist/commands/broadcast.js.map +1 -0
  36. package/dist/commands/dashboard.d.ts +3 -0
  37. package/dist/commands/dashboard.d.ts.map +1 -0
  38. package/dist/commands/dashboard.js +18 -0
  39. package/dist/commands/dashboard.js.map +1 -0
  40. package/dist/commands/inbox.d.ts +6 -0
  41. package/dist/commands/inbox.d.ts.map +1 -0
  42. package/dist/commands/inbox.js +65 -0
  43. package/dist/commands/inbox.js.map +1 -0
  44. package/dist/commands/key-import.d.ts +6 -0
  45. package/dist/commands/key-import.d.ts.map +1 -0
  46. package/dist/commands/key-import.js +31 -0
  47. package/dist/commands/key-import.js.map +1 -0
  48. package/dist/commands/keygen.d.ts +6 -0
  49. package/dist/commands/keygen.d.ts.map +1 -0
  50. package/dist/commands/keygen.js +33 -0
  51. package/dist/commands/keygen.js.map +1 -0
  52. package/dist/commands/keys.d.ts +6 -0
  53. package/dist/commands/keys.d.ts.map +1 -0
  54. package/dist/commands/keys.js +47 -0
  55. package/dist/commands/keys.js.map +1 -0
  56. package/dist/commands/read.d.ts +6 -0
  57. package/dist/commands/read.d.ts.map +1 -0
  58. package/dist/commands/read.js +89 -0
  59. package/dist/commands/read.js.map +1 -0
  60. package/dist/commands/send.d.ts +8 -0
  61. package/dist/commands/send.d.ts.map +1 -0
  62. package/dist/commands/send.js +73 -0
  63. package/dist/commands/send.js.map +1 -0
  64. package/dist/commands/watch.d.ts +8 -0
  65. package/dist/commands/watch.d.ts.map +1 -0
  66. package/dist/commands/watch.js +88 -0
  67. package/dist/commands/watch.js.map +1 -0
  68. package/dist/dashboard/public/app.js +523 -0
  69. package/dist/dashboard/public/index.html +75 -0
  70. package/dist/dashboard/public/styles.css +68 -0
  71. package/dist/dashboard/routes.d.ts +3 -0
  72. package/dist/dashboard/routes.d.ts.map +1 -0
  73. package/dist/dashboard/routes.js +103 -0
  74. package/dist/dashboard/routes.js.map +1 -0
  75. package/dist/dashboard/server.d.ts +3 -0
  76. package/dist/dashboard/server.d.ts.map +1 -0
  77. package/dist/dashboard/server.js +29 -0
  78. package/dist/dashboard/server.js.map +1 -0
  79. package/dist/lib/config.d.ts +28 -0
  80. package/dist/lib/config.d.ts.map +1 -0
  81. package/dist/lib/config.js +90 -0
  82. package/dist/lib/config.js.map +1 -0
  83. package/dist/lib/crypto.d.ts +72 -0
  84. package/dist/lib/crypto.d.ts.map +1 -0
  85. package/dist/lib/crypto.js +169 -0
  86. package/dist/lib/crypto.js.map +1 -0
  87. package/dist/lib/realtime.d.ts +36 -0
  88. package/dist/lib/realtime.d.ts.map +1 -0
  89. package/dist/lib/realtime.js +73 -0
  90. package/dist/lib/realtime.js.map +1 -0
  91. package/dist/storage/local.d.ts +46 -0
  92. package/dist/storage/local.d.ts.map +1 -0
  93. package/dist/storage/local.js +160 -0
  94. package/dist/storage/local.js.map +1 -0
  95. package/dist/storage/supabase.d.ts +43 -0
  96. package/dist/storage/supabase.d.ts.map +1 -0
  97. package/dist/storage/supabase.js +256 -0
  98. package/dist/storage/supabase.js.map +1 -0
  99. package/dist/types/index.d.ts +48 -0
  100. package/dist/types/index.d.ts.map +1 -0
  101. package/dist/types/index.js +5 -0
  102. package/dist/types/index.js.map +1 -0
  103. package/docs/20251215_Treebird-Ecosystem_Knowledge-Base_v2.md +292 -0
  104. package/docs/20251215_Treebird-Ecosystem_Project-Instructions_v2.md +176 -0
  105. package/docs/AGENT_DELEGATION_WORKFLOW.md +453 -0
  106. package/docs/AGENT_STARTER_KIT.md +145 -0
  107. package/docs/ANNOUNCEMENT_DRAFTS.md +55 -0
  108. package/docs/DASHBOARD_AGENT_HANDOFF.md +429 -0
  109. package/docs/DASHBOARD_AGENT_PROMPT.md +32 -0
  110. package/docs/DASHBOARD_BUILD_ROADMAP.md +61 -0
  111. package/docs/DEPLOYMENT.md +59 -0
  112. package/docs/MCP_PUBLISHING_ROADMAP.md +113 -0
  113. package/docs/MCP_STARTER_KIT.md +117 -0
  114. package/docs/SSAN_MESSAGES_SUMMARY.md +92 -0
  115. package/docs/STORAGE_ARCHITECTURE.md +114 -0
  116. package/mcp-server/README.md +143 -0
  117. package/mcp-server/assets/icon.png +0 -0
  118. package/mcp-server/myceliumail-mcp-1.0.0.tgz +0 -0
  119. package/mcp-server/package-lock.json +1142 -0
  120. package/mcp-server/package.json +49 -0
  121. package/mcp-server/src/lib/config.ts +21 -0
  122. package/mcp-server/src/lib/crypto.ts +150 -0
  123. package/mcp-server/src/lib/storage.ts +257 -0
  124. package/mcp-server/src/server.ts +387 -0
  125. package/mcp-server/tsconfig.json +26 -0
  126. package/package.json +54 -0
  127. package/src/bin/myceliumail.ts +52 -0
  128. package/src/commands/broadcast.ts +70 -0
  129. package/src/commands/dashboard.ts +19 -0
  130. package/src/commands/inbox.ts +75 -0
  131. package/src/commands/key-import.ts +35 -0
  132. package/src/commands/keygen.ts +44 -0
  133. package/src/commands/keys.ts +55 -0
  134. package/src/commands/read.ts +97 -0
  135. package/src/commands/send.ts +89 -0
  136. package/src/commands/watch.ts +101 -0
  137. package/src/dashboard/public/app.js +523 -0
  138. package/src/dashboard/public/index.html +75 -0
  139. package/src/dashboard/public/styles.css +68 -0
  140. package/src/dashboard/routes.ts +128 -0
  141. package/src/dashboard/server.ts +33 -0
  142. package/src/lib/config.ts +104 -0
  143. package/src/lib/crypto.ts +210 -0
  144. package/src/lib/realtime.ts +109 -0
  145. package/src/storage/local.ts +209 -0
  146. package/src/storage/supabase.ts +336 -0
  147. package/src/types/index.ts +53 -0
  148. package/supabase/migrations/000_myceliumail_setup.sql +93 -0
  149. package/supabase/migrations/001_enable_realtime.sql +10 -0
  150. package/tsconfig.json +28 -0
@@ -0,0 +1,103 @@
1
+ import { loadConfig } from '../lib/config.js';
2
+ import * as storage from '../storage/supabase.js';
3
+ import { loadKeyPair, decryptMessage, listOwnKeys } from '../lib/crypto.js';
4
+ // Try to decrypt a message using any available key
5
+ function tryDecryptWithAllKeys(msg) {
6
+ if (!msg.encrypted || !msg.ciphertext || !msg.nonce || !msg.senderPublicKey) {
7
+ return msg;
8
+ }
9
+ // Get all available keypairs
10
+ const ownKeys = listOwnKeys();
11
+ for (const agentId of ownKeys) {
12
+ const keyPair = loadKeyPair(agentId);
13
+ if (!keyPair)
14
+ continue;
15
+ try {
16
+ const decryptedText = decryptMessage({
17
+ ciphertext: msg.ciphertext,
18
+ nonce: msg.nonce,
19
+ senderPublicKey: msg.senderPublicKey
20
+ }, keyPair);
21
+ if (decryptedText) {
22
+ const parsed = JSON.parse(decryptedText);
23
+ return {
24
+ ...msg,
25
+ subject: parsed.subject,
26
+ body: parsed.body,
27
+ decrypted: true,
28
+ decryptedBy: agentId
29
+ };
30
+ }
31
+ }
32
+ catch (e) {
33
+ // Try next key
34
+ }
35
+ }
36
+ return msg;
37
+ }
38
+ export async function registerRoutes(fastify) {
39
+ const config = loadConfig();
40
+ const agentId = config.agentId;
41
+ // GET /api/inbox
42
+ fastify.get('/api/inbox', async (request, reply) => {
43
+ const messages = await storage.getInbox(agentId, { limit: 100 });
44
+ // Decrypt encrypted messages using all available keys
45
+ const decrypted = messages.map(tryDecryptWithAllKeys);
46
+ return { messages: decrypted, total: decrypted.length };
47
+ });
48
+ // GET /api/message/:id
49
+ fastify.get('/api/message/:id', async (request, reply) => {
50
+ const { id } = request.params;
51
+ const message = await storage.getMessage(id);
52
+ if (!message) {
53
+ return reply.code(404).send({ error: 'Message not found' });
54
+ }
55
+ // Try all keys for decryption
56
+ return tryDecryptWithAllKeys(message);
57
+ });
58
+ // POST /api/message/:id/read
59
+ fastify.post('/api/message/:id/read', async (request, reply) => {
60
+ const { id } = request.params;
61
+ const { readerId } = request.body;
62
+ await storage.markAsRead(id, readerId || agentId);
63
+ return { success: true };
64
+ });
65
+ // POST /api/message/:id/archive
66
+ fastify.post('/api/message/:id/archive', async (request, reply) => {
67
+ const { id } = request.params;
68
+ await storage.archiveMessage(id);
69
+ return { success: true };
70
+ });
71
+ // DELETE /api/message/:id
72
+ fastify.delete('/api/message/:id', async (request, reply) => {
73
+ const { id } = request.params;
74
+ const deleted = await storage.deleteMessage(id);
75
+ return { success: deleted };
76
+ });
77
+ // POST /api/send - Send a new message (supports multi-recipient)
78
+ fastify.post('/api/send', async (request, reply) => {
79
+ const { to, subject, body, from, attachments } = request.body;
80
+ const sender = from || agentId;
81
+ const message = await storage.sendMessage(sender, to, subject, body, { attachments });
82
+ return { success: true, message };
83
+ });
84
+ // GET /api/stats
85
+ fastify.get('/api/stats', async (request, reply) => {
86
+ const messages = await storage.getInbox(agentId);
87
+ const unread = messages.filter(m => !m.readBy?.includes(agentId) && !m.read).length;
88
+ return {
89
+ total: messages.length,
90
+ unread,
91
+ encrypted: messages.filter(m => m.encrypted).length
92
+ };
93
+ });
94
+ // GET /api/config - Provide config for frontend Realtime
95
+ fastify.get('/api/config', async (request, reply) => {
96
+ return {
97
+ agentId: config.agentId,
98
+ supabaseUrl: config.supabaseUrl,
99
+ supabaseKey: config.supabaseKey
100
+ };
101
+ });
102
+ }
103
+ //# sourceMappingURL=routes.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"routes.js","sourceRoot":"","sources":["../../src/dashboard/routes.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ import Fastify from 'fastify';
2
+ export declare function startDashboard(port?: number): Promise<Fastify.FastifyInstance<import("http").Server<typeof import("http").IncomingMessage, typeof import("http").ServerResponse>, import("http").IncomingMessage, import("http").ServerResponse<import("http").IncomingMessage>, Fastify.FastifyBaseLogger, Fastify.FastifyTypeProviderDefault>>;
3
+ //# sourceMappingURL=server.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"server.d.ts","sourceRoot":"","sources":["../../src/dashboard/server.ts"],"names":[],"mappings":"AAAA,OAAO,OAAO,MAAM,SAAS,CAAC;AAQ9B,wBAAsB,cAAc,CAAC,IAAI,SAAO,sSAwB/C"}
@@ -0,0 +1,29 @@
1
+ import Fastify from 'fastify';
2
+ import fastifyStatic from '@fastify/static';
3
+ import { join, dirname } from 'path';
4
+ import { fileURLToPath } from 'url';
5
+ const __filename = fileURLToPath(import.meta.url);
6
+ const __dirname = dirname(__filename);
7
+ export async function startDashboard(port = 3737) {
8
+ const fastify = Fastify({ logger: true });
9
+ // Serve static files
10
+ await fastify.register(fastifyStatic, {
11
+ root: join(__dirname, 'public'),
12
+ prefix: '/'
13
+ });
14
+ // Register routes
15
+ // dynamic import to avoid circular dependencies if any, though here it is clean
16
+ const { registerRoutes } = await import('./routes.js');
17
+ await registerRoutes(fastify);
18
+ // Start server
19
+ try {
20
+ await fastify.listen({ port, host: '127.0.0.1' });
21
+ console.log(`🍄 Dashboard running on http://localhost:${port}`);
22
+ }
23
+ catch (err) {
24
+ fastify.log.error(err);
25
+ process.exit(1);
26
+ }
27
+ return fastify;
28
+ }
29
+ //# sourceMappingURL=server.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"server.js","sourceRoot":"","sources":["../../src/dashboard/server.ts"],"names":[],"mappings":"AAAA,OAAO,OAAO,MAAM,SAAS,CAAC;AAC9B,OAAO,aAAa,MAAM,iBAAiB,CAAC;AAC5C,OAAO,EAAE,IAAI,EAAE,OAAO,EAAE,MAAM,MAAM,CAAC;AACrC,OAAO,EAAE,aAAa,EAAE,MAAM,KAAK,CAAC;AAEpC,MAAM,UAAU,GAAG,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;AAClD,MAAM,SAAS,GAAG,OAAO,CAAC,UAAU,CAAC,CAAC;AAEtC,MAAM,CAAC,KAAK,UAAU,cAAc,CAAC,IAAI,GAAG,IAAI;IAC5C,MAAM,OAAO,GAAG,OAAO,CAAC,EAAE,MAAM,EAAE,IAAI,EAAE,CAAC,CAAC;IAE1C,qBAAqB;IACrB,MAAM,OAAO,CAAC,QAAQ,CAAC,aAAa,EAAE;QAClC,IAAI,EAAE,IAAI,CAAC,SAAS,EAAE,QAAQ,CAAC;QAC/B,MAAM,EAAE,GAAG;KACd,CAAC,CAAC;IAEH,kBAAkB;IAClB,gFAAgF;IAChF,MAAM,EAAE,cAAc,EAAE,GAAG,MAAM,MAAM,CAAC,aAAa,CAAC,CAAC;IACvD,MAAM,cAAc,CAAC,OAAO,CAAC,CAAC;IAE9B,eAAe;IACf,IAAI,CAAC;QACD,MAAM,OAAO,CAAC,MAAM,CAAC,EAAE,IAAI,EAAE,IAAI,EAAE,WAAW,EAAE,CAAC,CAAC;QAClD,OAAO,CAAC,GAAG,CAAC,4CAA4C,IAAI,EAAE,CAAC,CAAC;IACpE,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACX,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC;QACvB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IACpB,CAAC;IAED,OAAO,OAAO,CAAC;AACnB,CAAC"}
@@ -0,0 +1,28 @@
1
+ /**
2
+ * Myceliumail Configuration
3
+ *
4
+ * Handles loading agent configuration from environment or config file.
5
+ */
6
+ export interface Config {
7
+ agentId: string;
8
+ supabaseUrl?: string;
9
+ supabaseKey?: string;
10
+ storageMode: 'auto' | 'supabase' | 'local';
11
+ }
12
+ /**
13
+ * Load configuration from file or environment
14
+ */
15
+ export declare function loadConfig(): Config;
16
+ /**
17
+ * Save configuration to file
18
+ */
19
+ export declare function saveConfig(config: Partial<Config>): void;
20
+ /**
21
+ * Get config directory path
22
+ */
23
+ export declare function getConfigDir(): string;
24
+ /**
25
+ * Check if Supabase is configured
26
+ */
27
+ export declare function hasSupabaseConfig(config: Config): boolean;
28
+ //# sourceMappingURL=config.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../../src/lib/config.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AASH,MAAM,WAAW,MAAM;IACnB,OAAO,EAAE,MAAM,CAAC;IAChB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,EAAE,MAAM,GAAG,UAAU,GAAG,OAAO,CAAC;CAC9C;AAWD;;GAEG;AACH,wBAAgB,UAAU,IAAI,MAAM,CAiCnC;AAED;;GAEG;AACH,wBAAgB,UAAU,CAAC,MAAM,EAAE,OAAO,CAAC,MAAM,CAAC,GAAG,IAAI,CAmBxD;AAED;;GAEG;AACH,wBAAgB,YAAY,IAAI,MAAM,CAErC;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAAC,MAAM,EAAE,MAAM,GAAG,OAAO,CAEzD"}
@@ -0,0 +1,90 @@
1
+ /**
2
+ * Myceliumail Configuration
3
+ *
4
+ * Handles loading agent configuration from environment or config file.
5
+ */
6
+ import { existsSync, readFileSync, writeFileSync, mkdirSync } from 'fs';
7
+ import { join } from 'path';
8
+ import { homedir } from 'os';
9
+ const CONFIG_DIR = join(homedir(), '.myceliumail');
10
+ const CONFIG_FILE = join(CONFIG_DIR, 'config.json');
11
+ /**
12
+ * Ensure config directory exists
13
+ */
14
+ function ensureConfigDir() {
15
+ if (!existsSync(CONFIG_DIR)) {
16
+ mkdirSync(CONFIG_DIR, { recursive: true });
17
+ }
18
+ }
19
+ /**
20
+ * Load configuration from file or environment
21
+ */
22
+ export function loadConfig() {
23
+ // Environment variables take precedence
24
+ const envAgentId = process.env.MYCELIUMAIL_AGENT_ID || process.env.MYCELIUMAIL_AGENT;
25
+ const envSupabaseUrl = process.env.SUPABASE_URL;
26
+ const envSupabaseKey = process.env.SUPABASE_ANON_KEY;
27
+ const envStorageMode = process.env.MYCELIUMAIL_STORAGE;
28
+ // Try to load from config file
29
+ let fileConfig = {};
30
+ if (existsSync(CONFIG_FILE)) {
31
+ try {
32
+ const raw = readFileSync(CONFIG_FILE, 'utf-8');
33
+ const parsed = JSON.parse(raw);
34
+ fileConfig = {
35
+ agentId: parsed.agent_id,
36
+ supabaseUrl: parsed.supabase_url,
37
+ supabaseKey: parsed.supabase_key,
38
+ storageMode: parsed.storage_mode,
39
+ };
40
+ }
41
+ catch {
42
+ // Invalid config file, ignore
43
+ }
44
+ }
45
+ // Merge with env taking precedence
46
+ const config = {
47
+ agentId: envAgentId || fileConfig.agentId || 'anonymous',
48
+ supabaseUrl: envSupabaseUrl || fileConfig.supabaseUrl,
49
+ supabaseKey: envSupabaseKey || fileConfig.supabaseKey,
50
+ storageMode: envStorageMode || fileConfig.storageMode || 'auto',
51
+ };
52
+ return config;
53
+ }
54
+ /**
55
+ * Save configuration to file
56
+ */
57
+ export function saveConfig(config) {
58
+ ensureConfigDir();
59
+ // Load existing config
60
+ let existing = {};
61
+ if (existsSync(CONFIG_FILE)) {
62
+ try {
63
+ existing = JSON.parse(readFileSync(CONFIG_FILE, 'utf-8'));
64
+ }
65
+ catch {
66
+ // Start fresh
67
+ }
68
+ }
69
+ // Merge
70
+ if (config.agentId)
71
+ existing.agent_id = config.agentId;
72
+ if (config.supabaseUrl)
73
+ existing.supabase_url = config.supabaseUrl;
74
+ if (config.supabaseKey)
75
+ existing.supabase_key = config.supabaseKey;
76
+ writeFileSync(CONFIG_FILE, JSON.stringify(existing, null, 2));
77
+ }
78
+ /**
79
+ * Get config directory path
80
+ */
81
+ export function getConfigDir() {
82
+ return CONFIG_DIR;
83
+ }
84
+ /**
85
+ * Check if Supabase is configured
86
+ */
87
+ export function hasSupabaseConfig(config) {
88
+ return !!(config.supabaseUrl && config.supabaseKey);
89
+ }
90
+ //# sourceMappingURL=config.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"config.js","sourceRoot":"","sources":["../../src/lib/config.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,72 @@
1
+ /**
2
+ * Myceliumail Crypto Module
3
+ *
4
+ * E2E encryption for agent messaging using TweetNaCl.
5
+ * Uses X25519 for key exchange and XSalsa20-Poly1305 for encryption.
6
+ */
7
+ export interface KeyPair {
8
+ publicKey: Uint8Array;
9
+ secretKey: Uint8Array;
10
+ }
11
+ export interface EncryptedMessage {
12
+ ciphertext: string;
13
+ nonce: string;
14
+ senderPublicKey: string;
15
+ }
16
+ /**
17
+ * Generate a new keypair for an agent
18
+ */
19
+ export declare function generateKeyPair(): KeyPair;
20
+ /**
21
+ * Save keypair to local storage
22
+ */
23
+ export declare function saveKeyPair(agentId: string, keyPair: KeyPair): void;
24
+ /**
25
+ * Load keypair from local storage
26
+ */
27
+ export declare function loadKeyPair(agentId: string): KeyPair | null;
28
+ /**
29
+ * Check if keypair exists for an agent
30
+ */
31
+ export declare function hasKeyPair(agentId: string): boolean;
32
+ /**
33
+ * Get public key as base64 string
34
+ */
35
+ export declare function getPublicKeyBase64(keyPair: KeyPair): string;
36
+ /**
37
+ * Encrypt a message for a recipient
38
+ */
39
+ export declare function encryptMessage(message: string, recipientPublicKey: Uint8Array, senderKeyPair: KeyPair): EncryptedMessage;
40
+ /**
41
+ * Decrypt a message from a sender
42
+ */
43
+ export declare function decryptMessage(encrypted: EncryptedMessage, recipientKeyPair: KeyPair): string | null;
44
+ /**
45
+ * Known keys registry - maps agent IDs to their public keys
46
+ */
47
+ export declare function loadKnownKeys(): Record<string, string>;
48
+ /**
49
+ * Save a known key for an agent
50
+ */
51
+ export declare function saveKnownKey(agentId: string, publicKeyBase64: string): void;
52
+ /**
53
+ * Get known key for an agent
54
+ */
55
+ export declare function getKnownKey(agentId: string): string | null;
56
+ /**
57
+ * Get all known keys
58
+ */
59
+ export declare function getKnownKeys(): Record<string, string>;
60
+ /**
61
+ * Delete a known key
62
+ */
63
+ export declare function deleteKnownKey(agentId: string): boolean;
64
+ /**
65
+ * List all own keypairs (for agents we have keys for)
66
+ */
67
+ export declare function listOwnKeys(): string[];
68
+ /**
69
+ * Decode a base64 public key to Uint8Array
70
+ */
71
+ export declare function decodePublicKey(base64: string): Uint8Array;
72
+ //# sourceMappingURL=crypto.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"crypto.d.ts","sourceRoot":"","sources":["../../src/lib/crypto.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAWH,MAAM,WAAW,OAAO;IACpB,SAAS,EAAE,UAAU,CAAC;IACtB,SAAS,EAAE,UAAU,CAAC;CACzB;AAED,MAAM,WAAW,gBAAgB;IAC7B,UAAU,EAAE,MAAM,CAAC;IACnB,KAAK,EAAE,MAAM,CAAC;IACd,eAAe,EAAE,MAAM,CAAC;CAC3B;AAWD;;GAEG;AACH,wBAAgB,eAAe,IAAI,OAAO,CAEzC;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,GAAG,IAAI,CAQnE;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,GAAG,IAAI,CAa3D;AAED;;GAEG;AACH,wBAAgB,UAAU,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAGnD;AAED;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,OAAO,EAAE,OAAO,GAAG,MAAM,CAE3D;AAED;;GAEG;AACH,wBAAgB,cAAc,CAC1B,OAAO,EAAE,MAAM,EACf,kBAAkB,EAAE,UAAU,EAC9B,aAAa,EAAE,OAAO,GACvB,gBAAgB,CAgBlB;AAED;;GAEG;AACH,wBAAgB,cAAc,CAC1B,SAAS,EAAE,gBAAgB,EAC3B,gBAAgB,EAAE,OAAO,GAC1B,MAAM,GAAG,IAAI,CAkBf;AAED;;GAEG;AACH,wBAAgB,aAAa,IAAI,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAQtD;AAED;;GAEG;AACH,wBAAgB,YAAY,CAAC,OAAO,EAAE,MAAM,EAAE,eAAe,EAAE,MAAM,GAAG,IAAI,CAK3E;AAED;;GAEG;AACH,wBAAgB,WAAW,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAG1D;AAED;;GAEG;AACH,wBAAgB,YAAY,IAAI,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAErD;AAED;;GAEG;AACH,wBAAgB,cAAc,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAMvD;AAED;;GAEG;AACH,wBAAgB,WAAW,IAAI,MAAM,EAAE,CAUtC;AAED;;GAEG;AACH,wBAAgB,eAAe,CAAC,MAAM,EAAE,MAAM,GAAG,UAAU,CAE1D"}
@@ -0,0 +1,169 @@
1
+ /**
2
+ * Myceliumail Crypto Module
3
+ *
4
+ * E2E encryption for agent messaging using TweetNaCl.
5
+ * Uses X25519 for key exchange and XSalsa20-Poly1305 for encryption.
6
+ */
7
+ import nacl from 'tweetnacl';
8
+ import util from 'tweetnacl-util';
9
+ import { existsSync, mkdirSync, readFileSync, writeFileSync, readdirSync } from 'fs';
10
+ import { join } from 'path';
11
+ import { homedir } from 'os';
12
+ // Key storage location
13
+ const KEYS_DIR = join(homedir(), '.myceliumail', 'keys');
14
+ /**
15
+ * Ensure keys directory exists
16
+ */
17
+ function ensureKeysDir() {
18
+ if (!existsSync(KEYS_DIR)) {
19
+ mkdirSync(KEYS_DIR, { recursive: true });
20
+ }
21
+ }
22
+ /**
23
+ * Generate a new keypair for an agent
24
+ */
25
+ export function generateKeyPair() {
26
+ return nacl.box.keyPair();
27
+ }
28
+ /**
29
+ * Save keypair to local storage
30
+ */
31
+ export function saveKeyPair(agentId, keyPair) {
32
+ ensureKeysDir();
33
+ const serialized = {
34
+ publicKey: util.encodeBase64(keyPair.publicKey),
35
+ secretKey: util.encodeBase64(keyPair.secretKey),
36
+ };
37
+ const path = join(KEYS_DIR, `${agentId}.key.json`);
38
+ writeFileSync(path, JSON.stringify(serialized, null, 2), { mode: 0o600 });
39
+ }
40
+ /**
41
+ * Load keypair from local storage
42
+ */
43
+ export function loadKeyPair(agentId) {
44
+ const path = join(KEYS_DIR, `${agentId}.key.json`);
45
+ if (!existsSync(path))
46
+ return null;
47
+ try {
48
+ const data = JSON.parse(readFileSync(path, 'utf-8'));
49
+ return {
50
+ publicKey: util.decodeBase64(data.publicKey),
51
+ secretKey: util.decodeBase64(data.secretKey),
52
+ };
53
+ }
54
+ catch {
55
+ return null;
56
+ }
57
+ }
58
+ /**
59
+ * Check if keypair exists for an agent
60
+ */
61
+ export function hasKeyPair(agentId) {
62
+ const path = join(KEYS_DIR, `${agentId}.key.json`);
63
+ return existsSync(path);
64
+ }
65
+ /**
66
+ * Get public key as base64 string
67
+ */
68
+ export function getPublicKeyBase64(keyPair) {
69
+ return util.encodeBase64(keyPair.publicKey);
70
+ }
71
+ /**
72
+ * Encrypt a message for a recipient
73
+ */
74
+ export function encryptMessage(message, recipientPublicKey, senderKeyPair) {
75
+ const messageBytes = util.decodeUTF8(message);
76
+ const nonce = nacl.randomBytes(nacl.box.nonceLength);
77
+ const ciphertext = nacl.box(messageBytes, nonce, recipientPublicKey, senderKeyPair.secretKey);
78
+ return {
79
+ ciphertext: util.encodeBase64(ciphertext),
80
+ nonce: util.encodeBase64(nonce),
81
+ senderPublicKey: util.encodeBase64(senderKeyPair.publicKey),
82
+ };
83
+ }
84
+ /**
85
+ * Decrypt a message from a sender
86
+ */
87
+ export function decryptMessage(encrypted, recipientKeyPair) {
88
+ try {
89
+ const ciphertext = util.decodeBase64(encrypted.ciphertext);
90
+ const nonce = util.decodeBase64(encrypted.nonce);
91
+ const senderPublicKey = util.decodeBase64(encrypted.senderPublicKey);
92
+ const decrypted = nacl.box.open(ciphertext, nonce, senderPublicKey, recipientKeyPair.secretKey);
93
+ if (!decrypted)
94
+ return null;
95
+ return util.encodeUTF8(decrypted);
96
+ }
97
+ catch {
98
+ return null;
99
+ }
100
+ }
101
+ /**
102
+ * Known keys registry - maps agent IDs to their public keys
103
+ */
104
+ export function loadKnownKeys() {
105
+ const path = join(KEYS_DIR, 'known_keys.json');
106
+ if (!existsSync(path))
107
+ return {};
108
+ try {
109
+ return JSON.parse(readFileSync(path, 'utf-8'));
110
+ }
111
+ catch {
112
+ return {};
113
+ }
114
+ }
115
+ /**
116
+ * Save a known key for an agent
117
+ */
118
+ export function saveKnownKey(agentId, publicKeyBase64) {
119
+ ensureKeysDir();
120
+ const keys = loadKnownKeys();
121
+ keys[agentId] = publicKeyBase64;
122
+ writeFileSync(join(KEYS_DIR, 'known_keys.json'), JSON.stringify(keys, null, 2));
123
+ }
124
+ /**
125
+ * Get known key for an agent
126
+ */
127
+ export function getKnownKey(agentId) {
128
+ const keys = loadKnownKeys();
129
+ return keys[agentId] || null;
130
+ }
131
+ /**
132
+ * Get all known keys
133
+ */
134
+ export function getKnownKeys() {
135
+ return loadKnownKeys();
136
+ }
137
+ /**
138
+ * Delete a known key
139
+ */
140
+ export function deleteKnownKey(agentId) {
141
+ const keys = loadKnownKeys();
142
+ if (!(agentId in keys))
143
+ return false;
144
+ delete keys[agentId];
145
+ writeFileSync(join(KEYS_DIR, 'known_keys.json'), JSON.stringify(keys, null, 2));
146
+ return true;
147
+ }
148
+ /**
149
+ * List all own keypairs (for agents we have keys for)
150
+ */
151
+ export function listOwnKeys() {
152
+ ensureKeysDir();
153
+ try {
154
+ const files = readdirSync(KEYS_DIR);
155
+ return files
156
+ .filter(f => f.endsWith('.key.json'))
157
+ .map(f => f.replace('.key.json', ''));
158
+ }
159
+ catch {
160
+ return [];
161
+ }
162
+ }
163
+ /**
164
+ * Decode a base64 public key to Uint8Array
165
+ */
166
+ export function decodePublicKey(base64) {
167
+ return util.decodeBase64(base64);
168
+ }
169
+ //# sourceMappingURL=crypto.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"crypto.js","sourceRoot":"","sources":["../../src/lib/crypto.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,36 @@
1
+ /**
2
+ * Supabase Realtime Module
3
+ *
4
+ * Provides real-time subscription to new messages using Supabase Realtime.
5
+ */
6
+ import { RealtimeChannel } from '@supabase/supabase-js';
7
+ interface RealtimeMessage {
8
+ id: string;
9
+ from_agent: string;
10
+ to_agent: string;
11
+ subject: string;
12
+ message: string;
13
+ encrypted: boolean;
14
+ read: boolean;
15
+ created_at: string;
16
+ }
17
+ export interface MessageCallback {
18
+ (message: RealtimeMessage): void;
19
+ }
20
+ export interface StatusCallback {
21
+ (status: 'SUBSCRIBED' | 'CLOSED' | 'CHANNEL_ERROR' | 'TIMED_OUT', error?: Error): void;
22
+ }
23
+ /**
24
+ * Subscribe to new messages for a specific agent
25
+ */
26
+ export declare function subscribeToMessages(agentId: string, onMessage: MessageCallback, onStatus?: StatusCallback): RealtimeChannel | null;
27
+ /**
28
+ * Unsubscribe from a channel
29
+ */
30
+ export declare function unsubscribe(channel: RealtimeChannel): Promise<void>;
31
+ /**
32
+ * Close all realtime connections
33
+ */
34
+ export declare function closeConnection(): Promise<void>;
35
+ export {};
36
+ //# sourceMappingURL=realtime.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"realtime.d.ts","sourceRoot":"","sources":["../../src/lib/realtime.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAgB,eAAe,EAAkB,MAAM,uBAAuB,CAAC;AAGtF,UAAU,eAAe;IACrB,EAAE,EAAE,MAAM,CAAC;IACX,UAAU,EAAE,MAAM,CAAC;IACnB,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,SAAS,EAAE,OAAO,CAAC;IACnB,IAAI,EAAE,OAAO,CAAC;IACd,UAAU,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,eAAe;IAC5B,CAAC,OAAO,EAAE,eAAe,GAAG,IAAI,CAAC;CACpC;AAED,MAAM,WAAW,cAAc;IAC3B,CAAC,MAAM,EAAE,YAAY,GAAG,QAAQ,GAAG,eAAe,GAAG,WAAW,EAAE,KAAK,CAAC,EAAE,KAAK,GAAG,IAAI,CAAC;CAC1F;AA4BD;;GAEG;AACH,wBAAgB,mBAAmB,CAC/B,OAAO,EAAE,MAAM,EACf,SAAS,EAAE,eAAe,EAC1B,QAAQ,CAAC,EAAE,cAAc,GAC1B,eAAe,GAAG,IAAI,CA2BxB;AAED;;GAEG;AACH,wBAAsB,WAAW,CAAC,OAAO,EAAE,eAAe,GAAG,OAAO,CAAC,IAAI,CAAC,CAKzE;AAED;;GAEG;AACH,wBAAsB,eAAe,IAAI,OAAO,CAAC,IAAI,CAAC,CAKrD"}
@@ -0,0 +1,73 @@
1
+ /**
2
+ * Supabase Realtime Module
3
+ *
4
+ * Provides real-time subscription to new messages using Supabase Realtime.
5
+ */
6
+ import { createClient } from '@supabase/supabase-js';
7
+ import { loadConfig, hasSupabaseConfig } from './config.js';
8
+ let supabaseClient = null;
9
+ /**
10
+ * Get or create the Supabase client for Realtime
11
+ */
12
+ function getClient() {
13
+ if (supabaseClient)
14
+ return supabaseClient;
15
+ const config = loadConfig();
16
+ if (!hasSupabaseConfig(config)) {
17
+ console.error('❌ Supabase not configured. Set SUPABASE_URL and SUPABASE_ANON_KEY.');
18
+ return null;
19
+ }
20
+ supabaseClient = createClient(config.supabaseUrl, config.supabaseKey, {
21
+ realtime: {
22
+ params: {
23
+ eventsPerSecond: 10,
24
+ },
25
+ },
26
+ });
27
+ return supabaseClient;
28
+ }
29
+ /**
30
+ * Subscribe to new messages for a specific agent
31
+ */
32
+ export function subscribeToMessages(agentId, onMessage, onStatus) {
33
+ const client = getClient();
34
+ if (!client)
35
+ return null;
36
+ const channel = client
37
+ .channel('inbox-watch')
38
+ .on('postgres_changes', {
39
+ event: 'INSERT',
40
+ schema: 'public',
41
+ table: 'agent_messages',
42
+ filter: `to_agent=eq.${agentId}`,
43
+ }, (payload) => {
44
+ onMessage(payload.new);
45
+ })
46
+ .subscribe((status, err) => {
47
+ if (onStatus) {
48
+ // Only pass error if it exists and has meaningful content
49
+ const error = err && (err.message || err.toString()) ? err : undefined;
50
+ onStatus(status, error);
51
+ }
52
+ });
53
+ return channel;
54
+ }
55
+ /**
56
+ * Unsubscribe from a channel
57
+ */
58
+ export async function unsubscribe(channel) {
59
+ const client = getClient();
60
+ if (client && channel) {
61
+ await client.removeChannel(channel);
62
+ }
63
+ }
64
+ /**
65
+ * Close all realtime connections
66
+ */
67
+ export async function closeConnection() {
68
+ if (supabaseClient) {
69
+ await supabaseClient.removeAllChannels();
70
+ supabaseClient = null;
71
+ }
72
+ }
73
+ //# sourceMappingURL=realtime.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"realtime.js","sourceRoot":"","sources":["../../src/lib/realtime.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,YAAY,EAAmC,MAAM,uBAAuB,CAAC;AACtF,OAAO,EAAE,UAAU,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAqB5D,IAAI,cAAc,GAA0B,IAAI,CAAC;AAEjD;;GAEG;AACH,SAAS,SAAS;IACd,IAAI,cAAc;QAAE,OAAO,cAAc,CAAC;IAE1C,MAAM,MAAM,GAAG,UAAU,EAAE,CAAC;IAE5B,IAAI,CAAC,iBAAiB,CAAC,MAAM,CAAC,EAAE,CAAC;QAC7B,OAAO,CAAC,KAAK,CAAC,oEAAoE,CAAC,CAAC;QACpF,OAAO,IAAI,CAAC;IAChB,CAAC;IAED,cAAc,GAAG,YAAY,CAAC,MAAM,CAAC,WAAY,EAAE,MAAM,CAAC,WAAY,EAAE;QACpE,QAAQ,EAAE;YACN,MAAM,EAAE;gBACJ,eAAe,EAAE,EAAE;aACtB;SACJ;KACJ,CAAC,CAAC;IAEH,OAAO,cAAc,CAAC;AAC1B,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,mBAAmB,CAC/B,OAAe,EACf,SAA0B,EAC1B,QAAyB;IAEzB,MAAM,MAAM,GAAG,SAAS,EAAE,CAAC;IAC3B,IAAI,CAAC,MAAM;QAAE,OAAO,IAAI,CAAC;IAEzB,MAAM,OAAO,GAAG,MAAM;SACjB,OAAO,CAAC,aAAa,CAAC;SACtB,EAAE,CACC,kBAAkB,EAClB;QACI,KAAK,EAAE,QAAQ;QACf,MAAM,EAAE,QAAQ;QAChB,KAAK,EAAE,gBAAgB;QACvB,MAAM,EAAE,eAAe,OAAO,EAAE;KACnC,EACD,CAAC,OAAO,EAAE,EAAE;QACR,SAAS,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC;IAC3B,CAAC,CACJ;SACA,SAAS,CAAC,CAAC,MAAM,EAAE,GAAG,EAAE,EAAE;QACvB,IAAI,QAAQ,EAAE,CAAC;YACX,0DAA0D;YAC1D,MAAM,KAAK,GAAG,GAAG,IAAI,CAAC,GAAG,CAAC,OAAO,IAAI,GAAG,CAAC,QAAQ,EAAE,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,SAAS,CAAC;YACvE,QAAQ,CAAC,MAAiE,EAAE,KAAK,CAAC,CAAC;QACvF,CAAC;IACL,CAAC,CAAC,CAAC;IAEP,OAAO,OAAO,CAAC;AACnB,CAAC;AAED;;GAEG;AACH,MAAM,CAAC,KAAK,UAAU,WAAW,CAAC,OAAwB;IACtD,MAAM,MAAM,GAAG,SAAS,EAAE,CAAC;IAC3B,IAAI,MAAM,IAAI,OAAO,EAAE,CAAC;QACpB,MAAM,MAAM,CAAC,aAAa,CAAC,OAAO,CAAC,CAAC;IACxC,CAAC;AACL,CAAC;AAED;;GAEG;AACH,MAAM,CAAC,KAAK,UAAU,eAAe;IACjC,IAAI,cAAc,EAAE,CAAC;QACjB,MAAM,cAAc,CAAC,iBAAiB,EAAE,CAAC;QACzC,cAAc,GAAG,IAAI,CAAC;IAC1B,CAAC;AACL,CAAC"}