@bobfrankston/mailx 1.0.451 → 1.0.453

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 (205) hide show
  1. package/bin/mailx.js.map +1 -0
  2. package/bin/mailx.ts +1498 -0
  3. package/bin/postinstall.js.map +1 -0
  4. package/bin/postinstall.ts +41 -0
  5. package/bin/tsconfig.json +10 -0
  6. package/client/.gitattributes +10 -0
  7. package/client/app.js +51 -2
  8. package/client/app.js.map +1 -0
  9. package/client/app.ts +3112 -0
  10. package/client/components/address-book.js.map +1 -0
  11. package/client/components/address-book.ts +204 -0
  12. package/client/components/alarms.js.map +1 -0
  13. package/client/components/alarms.ts +276 -0
  14. package/client/components/calendar-sidebar.js.map +1 -0
  15. package/client/components/calendar-sidebar.ts +474 -0
  16. package/client/components/calendar.js.map +1 -0
  17. package/client/components/calendar.ts +211 -0
  18. package/client/components/context-menu.js.map +1 -0
  19. package/client/components/context-menu.ts +95 -0
  20. package/client/components/folder-picker.js.map +1 -0
  21. package/client/components/folder-picker.ts +127 -0
  22. package/client/components/folder-tree.js.map +1 -0
  23. package/client/components/folder-tree.ts +1069 -0
  24. package/client/components/message-list.js.map +1 -0
  25. package/client/components/message-list.ts +1129 -0
  26. package/client/components/message-viewer.js.map +1 -0
  27. package/client/components/message-viewer.ts +1257 -0
  28. package/client/components/outbox-view.js.map +1 -0
  29. package/client/components/outbox-view.ts +102 -0
  30. package/client/components/tasks.js.map +1 -0
  31. package/client/components/tasks.ts +234 -0
  32. package/client/compose/compose.js.map +1 -0
  33. package/client/compose/compose.ts +1231 -0
  34. package/client/compose/editor.js.map +1 -0
  35. package/client/compose/editor.ts +599 -0
  36. package/client/compose/ghost-text.js.map +1 -0
  37. package/client/compose/ghost-text.ts +140 -0
  38. package/client/index.html +1 -0
  39. package/client/lib/android-bootstrap.js.map +1 -0
  40. package/client/lib/android-bootstrap.ts +9 -0
  41. package/client/lib/api-client.js.map +1 -0
  42. package/client/lib/api-client.ts +439 -0
  43. package/client/lib/local-service.js.map +1 -0
  44. package/client/lib/local-service.ts +646 -0
  45. package/client/lib/local-store.js.map +1 -0
  46. package/client/lib/local-store.ts +283 -0
  47. package/client/lib/message-state.js.map +1 -0
  48. package/client/lib/message-state.ts +140 -0
  49. package/client/tsconfig.json +19 -0
  50. package/package.json +18 -16
  51. package/packages/mailx-api/.gitattributes +10 -0
  52. package/packages/mailx-api/index.d.ts.map +1 -0
  53. package/packages/mailx-api/index.js.map +1 -0
  54. package/packages/mailx-api/index.ts +283 -0
  55. package/packages/mailx-api/package.json +1 -1
  56. package/packages/mailx-api/tsconfig.json +9 -0
  57. package/packages/mailx-compose/.gitattributes +10 -0
  58. package/packages/mailx-compose/index.d.ts.map +1 -0
  59. package/packages/mailx-compose/index.js.map +1 -0
  60. package/packages/mailx-compose/index.ts +85 -0
  61. package/packages/mailx-compose/tsconfig.json +9 -0
  62. package/packages/mailx-core/index.d.ts.map +1 -0
  63. package/packages/mailx-core/index.js.map +1 -0
  64. package/packages/mailx-core/index.ts +424 -0
  65. package/packages/mailx-core/ipc.d.ts.map +1 -0
  66. package/packages/mailx-core/ipc.js.map +1 -0
  67. package/packages/mailx-core/ipc.ts +62 -0
  68. package/packages/mailx-core/package.json +1 -1
  69. package/packages/mailx-core/tsconfig.json +9 -0
  70. package/packages/mailx-host/.gitattributes +10 -0
  71. package/packages/mailx-host/index.d.ts.map +1 -0
  72. package/packages/mailx-host/index.js.map +1 -0
  73. package/packages/mailx-host/index.ts +38 -0
  74. package/packages/mailx-host/package.json +10 -2
  75. package/packages/mailx-host/tsconfig.json +9 -0
  76. package/packages/mailx-send/.gitattributes +10 -0
  77. package/packages/mailx-send/cli-queue.d.ts.map +1 -0
  78. package/packages/mailx-send/cli-queue.js.map +1 -0
  79. package/packages/mailx-send/cli-queue.ts +62 -0
  80. package/packages/mailx-send/cli-send.d.ts.map +1 -0
  81. package/packages/mailx-send/cli-send.js.map +1 -0
  82. package/packages/mailx-send/cli-send.ts +83 -0
  83. package/packages/mailx-send/cli.d.ts.map +1 -0
  84. package/packages/mailx-send/cli.js.map +1 -0
  85. package/packages/mailx-send/cli.ts +126 -0
  86. package/packages/mailx-send/index.d.ts.map +1 -0
  87. package/packages/mailx-send/index.js.map +1 -0
  88. package/packages/mailx-send/index.ts +333 -0
  89. package/packages/mailx-send/mailsend/cli.d.ts.map +1 -0
  90. package/packages/mailx-send/mailsend/cli.js.map +1 -0
  91. package/packages/mailx-send/mailsend/cli.ts +81 -0
  92. package/packages/mailx-send/mailsend/index.d.ts.map +1 -0
  93. package/packages/mailx-send/mailsend/index.js.map +1 -0
  94. package/packages/mailx-send/mailsend/index.ts +333 -0
  95. package/packages/mailx-send/mailsend/package-lock.json +65 -0
  96. package/packages/mailx-send/mailsend/tsconfig.json +21 -0
  97. package/packages/mailx-send/package-lock.json +65 -0
  98. package/packages/mailx-send/package.json +1 -1
  99. package/packages/mailx-send/tsconfig.json +21 -0
  100. package/packages/mailx-server/.gitattributes +10 -0
  101. package/packages/mailx-server/index.d.ts.map +1 -0
  102. package/packages/mailx-server/index.js.map +1 -0
  103. package/packages/mailx-server/index.ts +429 -0
  104. package/packages/mailx-server/package.json +1 -1
  105. package/packages/mailx-server/tsconfig.json +9 -0
  106. package/packages/mailx-service/google-sync.d.ts.map +1 -0
  107. package/packages/mailx-service/google-sync.js.map +1 -0
  108. package/packages/mailx-service/google-sync.ts +238 -0
  109. package/packages/mailx-service/index.d.ts.map +1 -0
  110. package/packages/mailx-service/index.js.map +1 -0
  111. package/packages/mailx-service/index.ts +2461 -0
  112. package/packages/mailx-service/jsonrpc.d.ts.map +1 -0
  113. package/packages/mailx-service/jsonrpc.js.map +1 -0
  114. package/packages/mailx-service/jsonrpc.ts +268 -0
  115. package/packages/mailx-service/package.json +1 -1
  116. package/packages/mailx-service/tsconfig.json +9 -0
  117. package/packages/mailx-settings/.gitattributes +10 -0
  118. package/packages/mailx-settings/cloud.d.ts.map +1 -0
  119. package/packages/mailx-settings/cloud.js.map +1 -0
  120. package/packages/mailx-settings/cloud.ts +388 -0
  121. package/packages/mailx-settings/index.d.ts.map +1 -0
  122. package/packages/mailx-settings/index.js.map +1 -0
  123. package/packages/mailx-settings/index.ts +892 -0
  124. package/packages/mailx-settings/package.json +1 -1
  125. package/packages/mailx-settings/tsconfig.json +9 -0
  126. package/packages/mailx-store/.gitattributes +10 -0
  127. package/packages/mailx-store/db.d.ts.map +1 -0
  128. package/packages/mailx-store/db.js.map +1 -0
  129. package/packages/mailx-store/db.ts +2007 -0
  130. package/packages/mailx-store/file-store.d.ts.map +1 -0
  131. package/packages/mailx-store/file-store.js.map +1 -0
  132. package/packages/mailx-store/file-store.ts +82 -0
  133. package/packages/mailx-store/index.d.ts.map +1 -0
  134. package/packages/mailx-store/index.js.map +1 -0
  135. package/packages/mailx-store/index.ts +7 -0
  136. package/packages/mailx-store/package.json +1 -1
  137. package/packages/mailx-store/tsconfig.json +9 -0
  138. package/packages/mailx-store-web/android-bootstrap.d.ts.map +1 -0
  139. package/packages/mailx-store-web/android-bootstrap.js.map +1 -0
  140. package/packages/mailx-store-web/android-bootstrap.ts +1262 -0
  141. package/packages/mailx-store-web/db.d.ts.map +1 -0
  142. package/packages/mailx-store-web/db.js.map +1 -0
  143. package/packages/mailx-store-web/db.ts +756 -0
  144. package/packages/mailx-store-web/gmail-api-web.d.ts.map +1 -0
  145. package/packages/mailx-store-web/gmail-api-web.js.map +1 -0
  146. package/packages/mailx-store-web/gmail-api-web.ts +11 -0
  147. package/packages/mailx-store-web/imap-web-provider.d.ts.map +1 -0
  148. package/packages/mailx-store-web/imap-web-provider.js.map +1 -0
  149. package/packages/mailx-store-web/imap-web-provider.ts +156 -0
  150. package/packages/mailx-store-web/index.d.ts.map +1 -0
  151. package/packages/mailx-store-web/index.js.map +1 -0
  152. package/packages/mailx-store-web/index.ts +10 -0
  153. package/packages/mailx-store-web/main-thread-host.d.ts.map +1 -0
  154. package/packages/mailx-store-web/main-thread-host.js.map +1 -0
  155. package/packages/mailx-store-web/main-thread-host.ts +322 -0
  156. package/packages/mailx-store-web/package.json +4 -4
  157. package/packages/mailx-store-web/provider-types.d.ts.map +1 -0
  158. package/packages/mailx-store-web/provider-types.js.map +1 -0
  159. package/packages/mailx-store-web/provider-types.ts +7 -0
  160. package/packages/mailx-store-web/sync-manager.d.ts.map +1 -0
  161. package/packages/mailx-store-web/sync-manager.js.map +1 -0
  162. package/packages/mailx-store-web/sync-manager.ts +508 -0
  163. package/packages/mailx-store-web/tsconfig.json +10 -0
  164. package/packages/mailx-store-web/web-jsonrpc.d.ts.map +1 -0
  165. package/packages/mailx-store-web/web-jsonrpc.js.map +1 -0
  166. package/packages/mailx-store-web/web-jsonrpc.ts +116 -0
  167. package/packages/mailx-store-web/web-message-store.d.ts.map +1 -0
  168. package/packages/mailx-store-web/web-message-store.js.map +1 -0
  169. package/packages/mailx-store-web/web-message-store.ts +97 -0
  170. package/packages/mailx-store-web/web-service.d.ts.map +1 -0
  171. package/packages/mailx-store-web/web-service.js.map +1 -0
  172. package/packages/mailx-store-web/web-service.ts +616 -0
  173. package/packages/mailx-store-web/web-settings.d.ts.map +1 -0
  174. package/packages/mailx-store-web/web-settings.js.map +1 -0
  175. package/packages/mailx-store-web/web-settings.ts +522 -0
  176. package/packages/mailx-store-web/worker-entry.d.ts.map +1 -0
  177. package/packages/mailx-store-web/worker-entry.js.map +1 -0
  178. package/packages/mailx-store-web/worker-entry.ts +215 -0
  179. package/packages/mailx-store-web/worker-tcp-transport.d.ts.map +1 -0
  180. package/packages/mailx-store-web/worker-tcp-transport.js.map +1 -0
  181. package/packages/mailx-store-web/worker-tcp-transport.ts +101 -0
  182. package/packages/mailx-types/.gitattributes +10 -0
  183. package/packages/mailx-types/index.d.ts.map +1 -0
  184. package/packages/mailx-types/index.js.map +1 -0
  185. package/packages/mailx-types/index.ts +498 -0
  186. package/packages/mailx-types/package.json +1 -1
  187. package/packages/mailx-types/tsconfig.json +9 -0
  188. package/tsconfig.base.json +2 -1
  189. package/tsconfig.json +9 -0
  190. package/build-apk.cmd +0 -3
  191. package/npmg.bat +0 -6
  192. package/packages/mailx-imap/index.d.ts +0 -442
  193. package/packages/mailx-imap/index.js +0 -3684
  194. package/packages/mailx-imap/package.json +0 -25
  195. package/packages/mailx-imap/providers/gmail-api.d.ts +0 -8
  196. package/packages/mailx-imap/providers/gmail-api.js +0 -8
  197. package/packages/mailx-imap/providers/types.d.ts +0 -9
  198. package/packages/mailx-imap/providers/types.js +0 -9
  199. package/packages/mailx-imap/tsconfig.tsbuildinfo +0 -1
  200. package/rebuild.cmd +0 -23
  201. package/tdview.cmd +0 -2
  202. package/temp.ps1 +0 -10
  203. package/test-smtp-direct.mjs +0 -4
  204. package/unbash.cmd +0 -55
  205. package/unwedge.cmd +0 -1
@@ -0,0 +1,140 @@
1
+ /**
2
+ * Ghost text autocomplete — shows AI suggestions as translucent overlay at cursor.
3
+ * Tab accepts, Escape dismisses, any other key dismisses and re-triggers after debounce.
4
+ * Editor-agnostic: works with both Quill and tiptap via MailxEditor interface.
5
+ */
6
+
7
+ import type { MailxEditor } from "./editor.js";
8
+ import { autocomplete } from "../lib/api-client.js";
9
+
10
+ interface GhostTextContext {
11
+ getSubject: () => string;
12
+ getTo: () => string;
13
+ }
14
+
15
+ let ghostEl: HTMLElement | null = null;
16
+ let currentSuggestion: string | null = null;
17
+ let debounceTimer: ReturnType<typeof setTimeout> | null = null;
18
+ let abortController: AbortController | null = null;
19
+ let activeEditor: MailxEditor | null = null;
20
+ let debounceMs = 600;
21
+
22
+ function dismiss(): void {
23
+ currentSuggestion = null;
24
+ if (ghostEl) {
25
+ ghostEl.remove();
26
+ ghostEl = null;
27
+ }
28
+ }
29
+
30
+ function positionGhost(editor: MailxEditor, text: string): void {
31
+ dismiss();
32
+
33
+ const sel = window.getSelection();
34
+ if (!sel || sel.rangeCount === 0 || !sel.isCollapsed) return;
35
+
36
+ const range = sel.getRangeAt(0);
37
+ let rect = range.getBoundingClientRect();
38
+
39
+ // Collapsed range may return zero-width rect — use a temp span to measure
40
+ if (rect.width === 0 && rect.height === 0) {
41
+ const span = document.createElement("span");
42
+ span.textContent = "\u200B"; // zero-width space
43
+ range.insertNode(span);
44
+ rect = span.getBoundingClientRect();
45
+ span.remove();
46
+ // Restore selection
47
+ sel.removeAllRanges();
48
+ sel.addRange(range);
49
+ }
50
+
51
+ const container = editor.getScrollContainer();
52
+ const containerRect = container.getBoundingClientRect();
53
+
54
+ ghostEl = document.createElement("span");
55
+ ghostEl.className = "ghost-text";
56
+ ghostEl.textContent = text;
57
+ ghostEl.style.top = `${rect.top - containerRect.top + container.scrollTop}px`;
58
+ ghostEl.style.left = `${rect.left - containerRect.left + container.scrollLeft}px`;
59
+ container.appendChild(ghostEl);
60
+
61
+ currentSuggestion = text;
62
+ }
63
+
64
+ function requestSuggestion(editor: MailxEditor, context: GhostTextContext): void {
65
+ // Cancel any in-flight request
66
+ if (abortController) {
67
+ abortController.abort();
68
+ abortController = null;
69
+ }
70
+
71
+ const bodyText = editor.getText();
72
+ if (!bodyText || bodyText.trim().length < 3) return; // need at least a few characters
73
+
74
+ abortController = new AbortController();
75
+ const signal = abortController.signal;
76
+
77
+ autocomplete({
78
+ subject: context.getSubject(),
79
+ to: context.getTo(),
80
+ bodyText,
81
+ cursorOffset: bodyText.length,
82
+ }, signal).then((result: any) => {
83
+ if (signal.aborted) return;
84
+ if (result.suggestion) {
85
+ positionGhost(editor, result.suggestion);
86
+ }
87
+ }).catch((e: any) => {
88
+ if (e.name === "AbortError") return;
89
+ // Silently ignore autocomplete errors
90
+ });
91
+ }
92
+
93
+ export function initGhostText(editor: MailxEditor, context: GhostTextContext, options?: { debounceMs?: number }): void {
94
+ activeEditor = editor;
95
+ if (options?.debounceMs) debounceMs = options.debounceMs;
96
+
97
+ // Debounced content change → request suggestion
98
+ editor.onContentChange(() => {
99
+ dismiss();
100
+ if (debounceTimer) clearTimeout(debounceTimer);
101
+ debounceTimer = setTimeout(() => {
102
+ requestSuggestion(editor, context);
103
+ }, debounceMs);
104
+ });
105
+
106
+ // Key handler: Tab accepts, Escape dismisses
107
+ editor.onKeyDown((e: KeyboardEvent) => {
108
+ if (!currentSuggestion) return;
109
+
110
+ if (e.key === "Tab") {
111
+ e.preventDefault();
112
+ e.stopPropagation();
113
+ const text = currentSuggestion;
114
+ dismiss();
115
+ editor.insertTextAtCursor(text);
116
+ return;
117
+ }
118
+
119
+ if (e.key === "Escape") {
120
+ e.preventDefault();
121
+ e.stopPropagation();
122
+ dismiss();
123
+ return;
124
+ }
125
+
126
+ // Any other key: dismiss (new suggestion will come after debounce)
127
+ dismiss();
128
+ });
129
+
130
+ // Dismiss on blur/scroll
131
+ editor.root.addEventListener("blur", dismiss);
132
+ editor.getScrollContainer().addEventListener("scroll", dismiss);
133
+ }
134
+
135
+ export function destroyGhostText(): void {
136
+ dismiss();
137
+ if (debounceTimer) clearTimeout(debounceTimer);
138
+ if (abortController) abortController.abort();
139
+ activeEditor = null;
140
+ }
package/client/index.html CHANGED
@@ -104,6 +104,7 @@
104
104
  <button class="rail-btn" id="rail-tasks" title="Tasks" aria-label="Tasks">☑</button>
105
105
  </div>
106
106
  <div class="rail-bottom">
107
+ <button class="rail-btn" id="rail-view" title="View options" aria-label="View options">👁</button>
107
108
  <button class="rail-btn" id="rail-settings" title="Settings" aria-label="Settings">⚙</button>
108
109
  <button class="rail-btn" id="rail-theme" title="Toggle theme" aria-label="Toggle theme">◐</button>
109
110
  <button class="rail-btn" id="rail-help" title="Help / About" aria-label="Help">?</button>
@@ -0,0 +1 @@
1
+ {"version":3,"file":"android-bootstrap.js","sourceRoot":"","sources":["android-bootstrap.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG"}
@@ -0,0 +1,9 @@
1
+ /**
2
+ * Stub — the real android bootstrap is in packages/mailx-store-web/android-bootstrap.ts.
3
+ * This file exists only because it was created during development. The Android HTML
4
+ * (client/android.html) loads the bootstrap from the package via import map.
5
+ *
6
+ * This file is excluded from the desktop build (not imported by anything).
7
+ */
8
+
9
+ export {};
@@ -0,0 +1 @@
1
+ {"version":3,"file":"api-client.js","sourceRoot":"","sources":["api-client.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,439 @@
1
+ /**
2
+ * API client — all operations go through the IPC bridge (mailxapi).
3
+ * mailxapi is injected by the launcher (msger on desktop, MAUI on Android).
4
+ */
5
+
6
+ declare const mailxapi: any;
7
+
8
+ function getIpc(): any {
9
+ if (typeof mailxapi !== "undefined" && mailxapi?.isApp) return mailxapi;
10
+ if ((window as any).opener?.mailxapi?.isApp) return (window as any).opener.mailxapi;
11
+ // Compose iframe — check parent
12
+ if ((window as any).parent?.mailxapi?.isApp) return (window as any).parent.mailxapi;
13
+ return null;
14
+ }
15
+
16
+ /** Build a proxy bridge that forwards every method call to the parent window
17
+ * via postMessage. Used when the compose iframe's own attempt to reach
18
+ * msger's IPC silently drops messages — empirically, `sendMessage` and
19
+ * `saveDraft` both hit this (user-visible: "Sending…" spinner forever;
20
+ * "Draft save failed: mailxapi timeout"). The main window's bridge is
21
+ * provably fine, so the iframe routes through it. */
22
+ function buildRelayBridge(): any {
23
+ const pending = new Map<string, { resolve: (v: any) => void; reject: (e: any) => void; timer: any }>();
24
+ window.addEventListener("message", (ev: MessageEvent) => {
25
+ if (!ev.data || ev.data.type !== "mailx-ipc-result" || !ev.data.id) return;
26
+ const entry = pending.get(ev.data.id);
27
+ if (!entry) return;
28
+ pending.delete(ev.data.id);
29
+ clearTimeout(entry.timer);
30
+ if (ev.data.ok) entry.resolve(ev.data.result);
31
+ else entry.reject(new Error(ev.data.error || "parent-relay ipc error"));
32
+ });
33
+ const call = (method: string, args: any[]): Promise<any> => {
34
+ const id = `ipc-${Date.now()}-${Math.random().toString(36).slice(2, 8)}`;
35
+ return new Promise((resolve, reject) => {
36
+ const timer = setTimeout(() => {
37
+ pending.delete(id);
38
+ reject(new Error(`parent-relay timeout: ${method}`));
39
+ }, 120000);
40
+ pending.set(id, { resolve, reject, timer });
41
+ try {
42
+ (window.parent as any).postMessage({ type: "mailx-ipc", id, method, args }, "*");
43
+ } catch (e) {
44
+ clearTimeout(timer);
45
+ pending.delete(id);
46
+ reject(e);
47
+ }
48
+ });
49
+ };
50
+ // Proxy: any property access returns a function that forwards to parent.
51
+ // `isApp` / `platform` / other non-function reads return sensible defaults
52
+ // so existing getIpc-style checks still work.
53
+ return new Proxy({}, {
54
+ get(_t, prop: string) {
55
+ if (prop === "isApp") return true;
56
+ if (prop === "platform") return (window.parent as any)?.mailxapi?.platform || "webview2";
57
+ if (prop === "onEvent") {
58
+ // Event subscription can't be relayed simply — iframes that need
59
+ // events are rare. Fall back to direct parent bridge for onEvent
60
+ // since the subscription path doesn't hit the broken send path.
61
+ return (handler: any) => (window.parent as any)?.mailxapi?.onEvent?.(handler);
62
+ }
63
+ return (...args: any[]) => call(prop, args);
64
+ }
65
+ });
66
+ }
67
+
68
+ let cachedRelayBridge: any = null;
69
+ function ipc(): any {
70
+ // Direct bridge is fine for the top window (main mailx app). The iframe
71
+ // (compose) can't trust its own bridge resolution because msger-routed
72
+ // sendMessage / saveDraft IPCs disappear without trace. So when we're in
73
+ // a child frame with a parent bridge, go through the parent.
74
+ const inIframe = window.parent && window.parent !== window;
75
+ if (inIframe && (window.parent as any)?.mailxapi?.isApp) {
76
+ if (!cachedRelayBridge) cachedRelayBridge = buildRelayBridge();
77
+ return cachedRelayBridge;
78
+ }
79
+ const bridge = getIpc();
80
+ if (!bridge) throw new Error("IPC bridge not available");
81
+ return bridge;
82
+ }
83
+
84
+ // ── Abort controller for message-list requests ──
85
+
86
+ let messageListAbort: AbortController | null = null;
87
+
88
+ export function abortMessageListRequests(): void {
89
+ if (messageListAbort) {
90
+ messageListAbort.abort();
91
+ messageListAbort = null;
92
+ }
93
+ }
94
+
95
+ // ── API Methods ──
96
+
97
+ export function getAccounts() {
98
+ return ipc().getAccounts();
99
+ }
100
+
101
+ export function getFolders(accountId: string) {
102
+ return ipc().getFolders(accountId);
103
+ }
104
+
105
+ export function getMessages(accountId: string, folderId: number, page = 1, pageSize = 50, flaggedOnly = false, sort?: string, sortDir?: string) {
106
+ abortMessageListRequests();
107
+ return ipc().getMessages(accountId, folderId, page, pageSize, sort, sortDir, undefined, flaggedOnly);
108
+ }
109
+
110
+ export function getUnifiedInbox(page = 1, pageSize = 50) {
111
+ abortMessageListRequests();
112
+ return ipc().getUnifiedInbox(page, pageSize);
113
+ }
114
+
115
+ export function searchMessages(query: string, page = 1, pageSize = 50, scope = "all", accountId = "", folderId = 0) {
116
+ return ipc().searchMessages(query, page, pageSize);
117
+ }
118
+
119
+ export function getMessage(accountId: string, uid: number, allowRemote = false, folderId?: number) {
120
+ return ipc().getMessage(accountId, uid, allowRemote, folderId);
121
+ }
122
+
123
+ export function updateFlags(accountId: string, uid: number, flags: string[]) {
124
+ return ipc().updateFlags(accountId, uid, flags);
125
+ }
126
+
127
+ export function triggerSync() {
128
+ return ipc().syncAll();
129
+ }
130
+
131
+ export function syncAccount(accountId: string) {
132
+ return ipc().syncAccount(accountId);
133
+ }
134
+
135
+ export function reauthenticate(accountId: string) {
136
+ return ipc().reauthenticate(accountId);
137
+ }
138
+
139
+ export function reauthGoogleScopes(): Promise<{ cleared: number }> {
140
+ return (ipc() as any).reauthGoogleScopes();
141
+ }
142
+
143
+ export function getSyncPending() {
144
+ return ipc().getSyncPending();
145
+ }
146
+
147
+ export function getDiagnostics(): Promise<any> {
148
+ return ipc().getDiagnostics?.() ?? Promise.resolve([]);
149
+ }
150
+
151
+ /** Account that supplies `feature` data (calendar / tasks / contacts).
152
+ * Resolution: per-feature primary flag → catch-all `primary` → first account.
153
+ * Pass e.g. "calendar" to honor `primaryCalendar:true` overrides; omit for
154
+ * back-compat single-flag behavior. */
155
+ export function getPrimaryAccount(feature?: string): Promise<any> {
156
+ return ipc().getPrimaryAccount?.(feature) ?? Promise.resolve(null);
157
+ }
158
+
159
+ // Calendar / Tasks: two-way cache. Reads return local-cached rows; writes
160
+ // commit locally and queue a push to Google. Service layer handles drain.
161
+ export function getCalendarEvents(fromMs: number, toMs: number): Promise<any[]> {
162
+ return ipc().getCalendarEvents?.(fromMs, toMs) ?? Promise.resolve([]);
163
+ }
164
+ export function createCalendarEvent(ev: {
165
+ title: string; startMs: number; endMs: number; allDay?: boolean;
166
+ location?: string; notes?: string;
167
+ }): Promise<{ uuid: string }> {
168
+ return ipc().createCalendarEvent?.(ev);
169
+ }
170
+ export function updateCalendarEvent(uuid: string, patch: any): Promise<{ ok: boolean }> {
171
+ return ipc().updateCalendarEvent?.(uuid, patch);
172
+ }
173
+ export function deleteCalendarEvent(uuid: string): Promise<{ ok: boolean }> {
174
+ return ipc().deleteCalendarEvent?.(uuid);
175
+ }
176
+ export function getTasks(includeCompleted = false): Promise<any[]> {
177
+ return ipc().getTasks?.(includeCompleted) ?? Promise.resolve([]);
178
+ }
179
+ export function createTask(t: { title: string; notes?: string; dueMs?: number }): Promise<{ uuid: string }> {
180
+ return ipc().createTask?.(t);
181
+ }
182
+ export function updateTask(uuid: string, patch: any): Promise<{ ok: boolean }> {
183
+ return ipc().updateTask?.(uuid, patch);
184
+ }
185
+ export function deleteTask(uuid: string): Promise<{ ok: boolean }> {
186
+ return ipc().deleteTask?.(uuid);
187
+ }
188
+ export function drainStoreSync(): Promise<{ ok: boolean }> {
189
+ return ipc().drainStoreSync?.();
190
+ }
191
+
192
+ /** Report the currently-viewed message as spam → appends a row to
193
+ * `~/.mailx/spam.csv`. Placeholder: no folder move, no flag change, no
194
+ * auto-delete. Training data for a smarter pass later. */
195
+ export function recordSpamReport(accountId: string, uid: number, folderId: number): Promise<{ ok: boolean }> {
196
+ return ipc().recordSpamReport?.(accountId, uid, folderId);
197
+ }
198
+
199
+ export function getOutboxStatus() {
200
+ return (ipc() as any).getOutboxStatus();
201
+ }
202
+
203
+ export function listQueuedOutgoing() {
204
+ return (ipc() as any).listQueuedOutgoing();
205
+ }
206
+
207
+ export function cancelQueuedOutgoing(p: string) {
208
+ return (ipc() as any).cancelQueuedOutgoing(p);
209
+ }
210
+
211
+ export function searchContacts(query: string) {
212
+ return ipc().searchContacts(query);
213
+ }
214
+
215
+ export function hasCcHistoryTo(email: string): Promise<{ hasCc: boolean }> {
216
+ return (ipc() as any).hasCcHistoryTo(email);
217
+ }
218
+
219
+ export function hasBccHistoryTo(email: string): Promise<{ hasBcc: boolean }> {
220
+ return (ipc() as any).hasBccHistoryTo(email);
221
+ }
222
+
223
+ export function listContacts(query: string, page = 1, pageSize = 100) {
224
+ return (ipc() as any).listContacts(query, page, pageSize);
225
+ }
226
+
227
+ export function upsertContact(name: string, email: string) {
228
+ return (ipc() as any).upsertContact(name, email);
229
+ }
230
+
231
+ export function deleteContact(email: string) {
232
+ return (ipc() as any).deleteContact(email);
233
+ }
234
+
235
+ export function addPreferredContact(entry: { name: string; email: string; source?: string; organization?: string }) {
236
+ return (ipc() as any).addPreferredContact(entry.name, entry.email, entry.source, entry.organization);
237
+ }
238
+
239
+ export function addToDenylist(email: string) {
240
+ return (ipc() as any).addToDenylist(email);
241
+ }
242
+
243
+ export function openLocalPath(which: "config" | "log") {
244
+ return (ipc() as any).openLocalPath(which);
245
+ }
246
+
247
+ export function allowRemoteContent(type: string, value: string) {
248
+ return ipc().allowRemoteContent(type, value);
249
+ }
250
+ export function flagSenderOrDomain(type: "sender" | "domain", value: string): Promise<{ flagged: boolean }> {
251
+ return (ipc() as any).flagSenderOrDomain?.(type, value) ?? Promise.resolve({ flagged: false });
252
+ }
253
+
254
+ export function deleteMessage(accountId: string, uid: number) {
255
+ return ipc().deleteMessage?.(accountId, uid);
256
+ }
257
+
258
+ export function deleteMessages(accountId: string, uids: number[]) {
259
+ if (uids.length === 1) return deleteMessage(accountId, uids[0]);
260
+ return ipc().deleteMessages?.(accountId, uids);
261
+ }
262
+
263
+ export function moveMessages(accountId: string, uids: number[], targetFolderId: number, targetAccountId?: string) {
264
+ if (uids.length === 1) return moveMessage(accountId, uids[0], targetFolderId, targetAccountId);
265
+ return ipc().moveMessages?.(accountId, uids, targetFolderId, targetAccountId);
266
+ }
267
+
268
+ export function markAsSpamMessages(accountId: string, uids: number[]): Promise<{ targetFolderId: number; moved: number }> {
269
+ return ipc().markAsSpamMessages?.(accountId, uids);
270
+ }
271
+
272
+ export function undeleteMessage(accountId: string, uid: number, folderId: number) {
273
+ return ipc().undeleteMessage?.(accountId, uid, folderId);
274
+ }
275
+
276
+ export function moveMessage(accountId: string, uid: number, targetFolderId: number, targetAccountId?: string) {
277
+ return ipc().moveMessage?.(accountId, uid, targetFolderId, targetAccountId);
278
+ }
279
+
280
+ export function restartServer() {
281
+ return ipc().restart?.();
282
+ }
283
+
284
+ export function markFolderRead(accountId: string, folderId: number) {
285
+ return ipc().markFolderRead?.(accountId, folderId);
286
+ }
287
+
288
+ export function createFolder(accountId: string, parentPath: string, name: string) {
289
+ return ipc().createFolder?.(accountId, parentPath, name);
290
+ }
291
+
292
+ export function renameFolder(accountId: string, folderId: number, newName: string) {
293
+ return ipc().renameFolder?.(accountId, folderId, newName);
294
+ }
295
+
296
+ export function deleteFolder(accountId: string, folderId: number) {
297
+ return ipc().deleteFolder?.(accountId, folderId);
298
+ }
299
+
300
+ export function emptyFolder(accountId: string, folderId: number) {
301
+ return ipc().emptyFolder?.(accountId, folderId);
302
+ }
303
+
304
+ /** Ship a named event to the Node log as `[client] <tag> <data>`. Fire and
305
+ * forget — never awaits, never throws, never blocks the caller. Tries two
306
+ * paths so a broken primary channel can't swallow the trace:
307
+ * 1. Direct bridge call (self / opener / parent mailxapi).
308
+ * 2. parent.postMessage fallback — the main window listens and relays.
309
+ * The fallback matters because the whole point of tracing is to diagnose
310
+ * a broken iframe bridge; a single-path tracer that goes through that same
311
+ * bridge is useless in exactly the case we need it. */
312
+ export function logClientEvent(tag: string, data?: any): void {
313
+ let delivered = false;
314
+ try {
315
+ const bridge = typeof (globalThis as any).mailxapi !== "undefined" && (globalThis as any).mailxapi?.isApp ? (globalThis as any).mailxapi
316
+ : (window as any).opener?.mailxapi?.isApp ? (window as any).opener.mailxapi
317
+ : (window as any).parent?.mailxapi?.isApp ? (window as any).parent.mailxapi
318
+ : null;
319
+ if (bridge?.logClientEvent) {
320
+ bridge.logClientEvent(tag, data);
321
+ delivered = true;
322
+ }
323
+ } catch { /* never throw from tracing */ }
324
+ try {
325
+ if (window.parent && window.parent !== window) {
326
+ (window.parent as any).postMessage({ type: "mailx-trace", tag, data, bridged: delivered }, "*");
327
+ }
328
+ } catch { /* */ }
329
+ }
330
+
331
+ export function sendMessage(body: any) {
332
+ return ipc().sendMessage?.(body);
333
+ }
334
+
335
+ export function saveDraft(body: any) {
336
+ return ipc().saveDraft?.(body);
337
+ }
338
+
339
+ // ── Events ──
340
+
341
+ type EventHandler = (event: any) => void;
342
+ const eventHandlers: EventHandler[] = [];
343
+
344
+ export function onEvent(handler: EventHandler): void {
345
+ eventHandlers.push(handler);
346
+ }
347
+
348
+ export function connectEvents(): void {
349
+ ipc().onEvent((event: any) => {
350
+ for (const h of eventHandlers) h(event);
351
+ });
352
+ }
353
+
354
+ // ── Autocomplete ──
355
+
356
+ export function autocomplete(body: { subject: string; to: string; bodyText: string; cursorOffset: number }, signal?: AbortSignal) {
357
+ return ipc().autocomplete?.(body);
358
+ }
359
+
360
+ export function getAutocompleteSettings() {
361
+ return ipc().getAutocompleteSettings?.();
362
+ }
363
+
364
+ export function saveAutocompleteSettings(settings: any) {
365
+ return ipc().saveAutocompleteSettings?.(settings);
366
+ }
367
+
368
+ export function getVersion() {
369
+ return ipc().getVersion();
370
+ }
371
+
372
+ export function getSettings() {
373
+ return ipc().getSettings();
374
+ }
375
+
376
+ export function saveSettings(settings: any) {
377
+ return ipc().saveSettingsData?.(settings);
378
+ }
379
+
380
+ export function repairAccounts() {
381
+ return ipc().repairAccounts?.();
382
+ }
383
+
384
+ export function deleteDraft(accountId: string, draftUid: number, draftId?: string) {
385
+ return ipc().deleteDraft?.(accountId, draftUid, draftId);
386
+ }
387
+
388
+ export function addContact(name: string, email: string) {
389
+ return ipc().addContact?.(name, email);
390
+ }
391
+
392
+ export function getThreadMessages(accountId: string, threadId: string) {
393
+ return ipc().getThreadMessages?.(accountId, threadId);
394
+ }
395
+
396
+ export function readJsoncFile(name: string): Promise<{ content: string | null }> {
397
+ return ipc().readJsoncFile?.(name);
398
+ }
399
+ export function writeJsoncFile(name: string, content: string): Promise<{ ok: boolean }> {
400
+ return ipc().writeJsoncFile?.(name, content);
401
+ }
402
+ export function formatJsonc(content: string): Promise<{ content: string }> {
403
+ return (ipc() as any).formatJsonc?.(content);
404
+ }
405
+ export function readConfigHelp(name: string): Promise<{ content: string }> {
406
+ return ipc().readConfigHelp?.(name) ?? Promise.resolve({ content: "" });
407
+ }
408
+ export function unsubscribeOneClick(url: string): Promise<{ ok: boolean; status: number; statusText: string }> {
409
+ return ipc().unsubscribeOneClick?.(url);
410
+ }
411
+ export function openInWord(editId: string, html: string): Promise<{ ok: boolean; path: string; opener: string }> {
412
+ return (ipc() as any).openInWord?.(editId, html) ?? Promise.resolve({ ok: false, path: "", opener: "none" });
413
+ }
414
+ export function closeWordEdit(editId: string): Promise<void> {
415
+ return (ipc() as any).closeWordEdit?.(editId) ?? Promise.resolve();
416
+ }
417
+
418
+ /** Run an AI text transform (translate / proofread / summarize). Returns
419
+ * empty `text` with a `reason` when the feature is disabled or the provider
420
+ * errors — caller should surface `reason` in a status bar, not throw. */
421
+ export function aiTransform(req: { action: "translate" | "proofread" | "summarize"; text: string; targetLang?: string }): Promise<{ text: string; reason?: string }> {
422
+ return ipc().aiTransform?.(req) ?? Promise.resolve({ text: "", reason: "AI not available in this host" });
423
+ }
424
+
425
+ export function setupAccount(name: string, email: string, password: string) {
426
+ return ipc().setupAccount?.(name, email, password);
427
+ }
428
+
429
+ export async function getAttachment(accountId: string, uid: number, attachmentId: number, folderId?: number): Promise<{ content: string; contentType: string; filename: string }> {
430
+ return ipc().getAttachment(accountId, uid, attachmentId, folderId);
431
+ }
432
+
433
+ export async function getDeviceAccounts(): Promise<{ email: string; name: string }[]> {
434
+ return ipc().getDeviceAccounts?.() ?? [];
435
+ }
436
+
437
+ // Legacy exports for backward compatibility
438
+ export const connectWebSocket = connectEvents;
439
+ export const onWsEvent = onEvent;