@dawnlit/outlook-bridge 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (117) hide show
  1. package/LICENSE +190 -0
  2. package/README.md +253 -0
  3. package/dist/OutlookService.d.ts +43 -0
  4. package/dist/OutlookService.js +137 -0
  5. package/dist/OutlookService.js.map +1 -0
  6. package/dist/errors.d.ts +112 -0
  7. package/dist/errors.js +140 -0
  8. package/dist/errors.js.map +1 -0
  9. package/dist/index.d.ts +11 -0
  10. package/dist/index.js +71 -0
  11. package/dist/index.js.map +1 -0
  12. package/dist/mac/accounts.d.ts +5 -0
  13. package/dist/mac/accounts.js +17 -0
  14. package/dist/mac/accounts.js.map +1 -0
  15. package/dist/mac/attachments.d.ts +28 -0
  16. package/dist/mac/attachments.js +120 -0
  17. package/dist/mac/attachments.js.map +1 -0
  18. package/dist/mac/bounces.d.ts +32 -0
  19. package/dist/mac/bounces.js +285 -0
  20. package/dist/mac/bounces.js.map +1 -0
  21. package/dist/mac/cleanup.d.ts +29 -0
  22. package/dist/mac/cleanup.js +219 -0
  23. package/dist/mac/cleanup.js.map +1 -0
  24. package/dist/mac/drafts.d.ts +27 -0
  25. package/dist/mac/drafts.js +214 -0
  26. package/dist/mac/drafts.js.map +1 -0
  27. package/dist/mac/folders.d.ts +28 -0
  28. package/dist/mac/folders.js +127 -0
  29. package/dist/mac/folders.js.map +1 -0
  30. package/dist/mac/index.d.ts +22 -0
  31. package/dist/mac/index.js +119 -0
  32. package/dist/mac/index.js.map +1 -0
  33. package/dist/mac/read.d.ts +46 -0
  34. package/dist/mac/read.js +406 -0
  35. package/dist/mac/read.js.map +1 -0
  36. package/dist/mac/run.d.ts +64 -0
  37. package/dist/mac/run.js +250 -0
  38. package/dist/mac/run.js.map +1 -0
  39. package/dist/mac/scripts.d.ts +137 -0
  40. package/dist/mac/scripts.js +337 -0
  41. package/dist/mac/scripts.js.map +1 -0
  42. package/dist/mac/send.d.ts +23 -0
  43. package/dist/mac/send.js +135 -0
  44. package/dist/mac/send.js.map +1 -0
  45. package/dist/mac/signatures.d.ts +4 -0
  46. package/dist/mac/signatures.js +36 -0
  47. package/dist/mac/signatures.js.map +1 -0
  48. package/dist/mac/templates.d.ts +34 -0
  49. package/dist/mac/templates.js +266 -0
  50. package/dist/mac/templates.js.map +1 -0
  51. package/dist/mail.d.ts +72 -0
  52. package/dist/mail.js +131 -0
  53. package/dist/mail.js.map +1 -0
  54. package/dist/outlookTemplateSections.d.ts +62 -0
  55. package/dist/outlookTemplateSections.js +313 -0
  56. package/dist/outlookTemplateSections.js.map +1 -0
  57. package/dist/runtime.d.ts +76 -0
  58. package/dist/runtime.js +123 -0
  59. package/dist/runtime.js.map +1 -0
  60. package/dist/shared/attachmentMatch.d.ts +32 -0
  61. package/dist/shared/attachmentMatch.js +50 -0
  62. package/dist/shared/attachmentMatch.js.map +1 -0
  63. package/dist/shared/bounceRules.d.ts +33 -0
  64. package/dist/shared/bounceRules.js +104 -0
  65. package/dist/shared/bounceRules.js.map +1 -0
  66. package/dist/shared/capabilities.d.ts +3 -0
  67. package/dist/shared/capabilities.js +9 -0
  68. package/dist/shared/capabilities.js.map +1 -0
  69. package/dist/shared/json.d.ts +11 -0
  70. package/dist/shared/json.js +45 -0
  71. package/dist/shared/json.js.map +1 -0
  72. package/dist/shared/replyBody.d.ts +49 -0
  73. package/dist/shared/replyBody.js +113 -0
  74. package/dist/shared/replyBody.js.map +1 -0
  75. package/dist/types.d.ts +365 -0
  76. package/dist/types.js +13 -0
  77. package/dist/types.js.map +1 -0
  78. package/dist/windows/accounts.d.ts +2 -0
  79. package/dist/windows/accounts.js +22 -0
  80. package/dist/windows/accounts.js.map +1 -0
  81. package/dist/windows/attachments.d.ts +28 -0
  82. package/dist/windows/attachments.js +141 -0
  83. package/dist/windows/attachments.js.map +1 -0
  84. package/dist/windows/bounces.d.ts +34 -0
  85. package/dist/windows/bounces.js +267 -0
  86. package/dist/windows/bounces.js.map +1 -0
  87. package/dist/windows/cleanup.d.ts +29 -0
  88. package/dist/windows/cleanup.js +165 -0
  89. package/dist/windows/cleanup.js.map +1 -0
  90. package/dist/windows/drafts.d.ts +29 -0
  91. package/dist/windows/drafts.js +253 -0
  92. package/dist/windows/drafts.js.map +1 -0
  93. package/dist/windows/folders.d.ts +16 -0
  94. package/dist/windows/folders.js +88 -0
  95. package/dist/windows/folders.js.map +1 -0
  96. package/dist/windows/index.d.ts +27 -0
  97. package/dist/windows/index.js +100 -0
  98. package/dist/windows/index.js.map +1 -0
  99. package/dist/windows/read.d.ts +54 -0
  100. package/dist/windows/read.js +372 -0
  101. package/dist/windows/read.js.map +1 -0
  102. package/dist/windows/run.d.ts +54 -0
  103. package/dist/windows/run.js +161 -0
  104. package/dist/windows/run.js.map +1 -0
  105. package/dist/windows/scripts.d.ts +56 -0
  106. package/dist/windows/scripts.js +163 -0
  107. package/dist/windows/scripts.js.map +1 -0
  108. package/dist/windows/send.d.ts +11 -0
  109. package/dist/windows/send.js +114 -0
  110. package/dist/windows/send.js.map +1 -0
  111. package/dist/windows/signatures.d.ts +14 -0
  112. package/dist/windows/signatures.js +69 -0
  113. package/dist/windows/signatures.js.map +1 -0
  114. package/dist/windows/templates.d.ts +25 -0
  115. package/dist/windows/templates.js +246 -0
  116. package/dist/windows/templates.js.map +1 -0
  117. package/package.json +50 -0
@@ -0,0 +1,406 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.readInboxEmails = readInboxEmails;
4
+ exports.readEmailBody = readEmailBody;
5
+ exports.searchInboxByFilter = searchInboxByFilter;
6
+ exports.readSelectedEmail = readSelectedEmail;
7
+ exports.openOutlookEmail = openOutlookEmail;
8
+ // Reading mail on macOS: one folder, one item, a whole Inbox tree, or whatever
9
+ // is selected in the running Outlook.
10
+ //
11
+ // Every reader here is two passes. Pass 1 indexes a folder with bulk property
12
+ // reads (one Apple event each); pass 2 fetches the expensive fields — body,
13
+ // attachments, sender — only for the messages that survived. Reading
14
+ // per-message in a loop costs an event per property and is unusably slow on a
15
+ // real mailbox, which is the whole reason for the shape.
16
+ const run_1 = require("./run");
17
+ const scripts_1 = require("./scripts");
18
+ const mail_1 = require("../mail");
19
+ const errors_1 = require("../errors");
20
+ /** How much of a body readInboxEmails previews, matching the Windows reader. */
21
+ const PREVIEW_CHARS = 600;
22
+ /**
23
+ * Read recent messages for the given account, newest first.
24
+ *
25
+ * `entryId` here is Outlook for Mac's small integer message id (e.g. "779"), not
26
+ * the MAPI EntryID string Windows returns. The two are not interchangeable, so
27
+ * don't persist one and look it up on the other platform.
28
+ */
29
+ async function readInboxEmails(emailAccount, daysBack = 60, limit = 50, folder) {
30
+ const days = Math.max(0, Math.floor(daysBack));
31
+ const cap = Math.max(0, Math.floor(limit));
32
+ if (cap === 0)
33
+ return [];
34
+ const ref = folder ? (0, mail_1.mailFolderRef)(folder) : { rootId: 6, rootLabel: 'Inbox', segments: [] };
35
+ // A folder argument that trims away to nothing ("\\", " ") would otherwise
36
+ // read the Inbox root and look like it had scoped — the exact silent
37
+ // mis-scoping this parameter exists to prevent. Mirrors the Windows check.
38
+ if (folder && folder.trim() && ref.segments.length === 0 && ref.rootId === 6
39
+ && folder.trim().toLowerCase() !== 'inbox') {
40
+ throw new errors_1.NotFoundError('folder', `Folder '${folder}' does not name a folder under the Inbox.`);
41
+ }
42
+ const resolveScope = (0, scripts_1.mailScopeSnippet)(ref, folder || '');
43
+ const folderPath = (0, scripts_1.macFolderPath)(emailAccount, ref.rootLabel, ref.segments);
44
+ const isOutgoing = (0, mail_1.isOutgoingRoot)(ref.rootId);
45
+ // Pass 1 — index the folder. Folder order isn't documented, so sort here
46
+ // rather than trusting Outlook to hand back newest-first.
47
+ const indexScript = `tell application "Microsoft Outlook"
48
+ ${(0, scripts_1.accountLookupSnippet)(emailAccount)}
49
+ ${resolveScope}
50
+ set cutoff to (current date) - (${days} * days)
51
+ set idList to id of every message of scopeFolder
52
+ try
53
+ set timeList to ${(0, scripts_1.dateProperty)(ref.rootId)} of every message of scopeFolder
54
+ on error
55
+ set timeList to {}
56
+ end try
57
+ set hasTimes to ((count of timeList) is (count of idList))
58
+ set out to ""
59
+ repeat with i from 1 to (count of idList)
60
+ set d to missing value
61
+ if hasTimes then set d to item i of timeList
62
+ -- An item carrying no timestamp of its own (an unsent draft filed into a
63
+ -- mail folder) is skipped rather than crashing the walk, matching what the
64
+ -- Windows Restrict on the same property does with it.
65
+ if d is not missing value and d is greater than or equal to cutoff then
66
+ set out to out & (item i of idList as string) & tab & my isoDate(d) & linefeed
67
+ end if
68
+ end repeat
69
+ return out
70
+ end tell`;
71
+ const index = (await (0, run_1.runOsaScript)(indexScript, 60000))
72
+ .split('\n')
73
+ .map(line => line.trim())
74
+ .filter(Boolean)
75
+ .map(line => {
76
+ const [id, receivedTime] = line.split('\t');
77
+ return { id, receivedTime: receivedTime || '' };
78
+ });
79
+ // 'yyyy-MM-dd HH:mm' is lexicographically ordered, so plain string compare sorts it.
80
+ index.sort((a, b) => b.receivedTime.localeCompare(a.receivedTime));
81
+ const chosen = index.slice(0, cap);
82
+ if (chosen.length === 0)
83
+ return [];
84
+ // Pass 2 — the expensive reads, only for messages we keep.
85
+ const detailScript = `tell application "Microsoft Outlook"
86
+ set wanted to {${chosen.map(c => c.id).join(', ')}}
87
+ set out to ""
88
+ repeat with k from 1 to (count of wanted)
89
+ set theMsg to missing value
90
+ try
91
+ set theMsg to message id (item k of wanted)
92
+ end try
93
+ if theMsg is not missing value then
94
+ set subj to ""
95
+ try
96
+ set subj to (subject of theMsg) as string
97
+ end try
98
+ ${isOutgoing ? (0, scripts_1.firstRecipientSnippet)('theMsg', ' ') : (0, scripts_1.senderSnippet)('theMsg', ' ')}
99
+ set bodyText to ""
100
+ try
101
+ set bodyText to (plain text content of theMsg) as string
102
+ end try
103
+ if (length of bodyText) > ${PREVIEW_CHARS} then set bodyText to text 1 thru ${PREVIEW_CHARS} of bodyText
104
+ set attNames to {}
105
+ try
106
+ set attNames to name of every attachment of theMsg
107
+ end try
108
+ set out to out & ${(0, run_1.asRow)([
109
+ '(id of theMsg as string)',
110
+ 'subj',
111
+ 'sndName',
112
+ 'sndAddr',
113
+ 'bodyText',
114
+ 'my sanitizeList(attNames)',
115
+ ])}
116
+ end if
117
+ end repeat
118
+ return out
119
+ end tell`;
120
+ const byId = new Map(chosen.map(c => [c.id, c.receivedTime]));
121
+ return (0, run_1.splitRecords)(await (0, run_1.runOsaScript)(detailScript, 120000)).map(record => {
122
+ const parts = (0, run_1.splitFields)(record);
123
+ const id = (0, run_1.field)(parts, 0);
124
+ const attachmentNames = (0, run_1.splitList)((0, run_1.field)(parts, 5));
125
+ return {
126
+ entryId: id,
127
+ storeId: '', // macOS AppleScript has no StoreID equivalent
128
+ subject: (0, run_1.field)(parts, 1).trim(),
129
+ senderName: (0, run_1.field)(parts, 2),
130
+ senderEmail: (0, run_1.field)(parts, 3),
131
+ receivedTime: byId.get(id) || '',
132
+ bodyPreview: (0, run_1.field)(parts, 4),
133
+ attachmentNames,
134
+ attachmentCount: attachmentNames.length,
135
+ folderPath,
136
+ };
137
+ });
138
+ }
139
+ /**
140
+ * Read one email's full plain-text body by message id.
141
+ *
142
+ * `storeId` is accepted for signature parity and ignored: macOS has no StoreID,
143
+ * and `message id N` resolves against the application rather than one folder, so
144
+ * the message is found wherever it currently sits — including a subfolder.
145
+ *
146
+ * Uses `plain text content`, matching the Windows reader's use of `.Body`: the
147
+ * same tradeoff applies, so an HTML table's rows flatten and tabular figures are
148
+ * better read from an attachment.
149
+ */
150
+ async function readEmailBody(entryId, _storeId, maxChars = 8000, includeQuoted = false) {
151
+ const id = (0, scripts_1.macMessageId)(entryId);
152
+ const script = `tell application "Microsoft Outlook"
153
+ ${(0, scripts_1.messageLookupSnippet)(id)}
154
+ ${(0, scripts_1.messageDetailSnippet)(true)}
155
+ return ${(0, run_1.asRow)((0, scripts_1.messageDetailFields)(true))}
156
+ end tell`;
157
+ // The body is emitted LAST so a stray separator in earlier fields can't shift it.
158
+ const parts = (0, run_1.summaryFields)(await (0, run_1.runOsaScript)(script, 60000));
159
+ const attachmentNames = (0, run_1.splitList)((0, run_1.field)(parts, scripts_1.MessageDetail.attachmentNames));
160
+ const { body, quoted, separator } = (0, mail_1.splitQuotedOriginal)((0, run_1.field)(parts, scripts_1.MessageDetail.body));
161
+ // The quoted thread is context, never the priced content, so it is capped
162
+ // harder than the reply itself — matching the Windows reader.
163
+ const quotedCap = Math.min(maxChars, 4000);
164
+ return {
165
+ entryId: (0, run_1.field)(parts, scripts_1.MessageDetail.id) || id,
166
+ subject: (0, run_1.field)(parts, scripts_1.MessageDetail.subject).trim(),
167
+ senderName: (0, run_1.field)(parts, scripts_1.MessageDetail.senderName),
168
+ senderEmail: (0, run_1.field)(parts, scripts_1.MessageDetail.senderEmail),
169
+ receivedTime: (0, run_1.field)(parts, scripts_1.MessageDetail.receivedTime),
170
+ body: body.length > maxChars ? body.slice(0, maxChars) : body,
171
+ truncated: body.length > maxChars,
172
+ bodyLength: body.length,
173
+ quoteSeparator: separator,
174
+ quotedLength: quoted.length,
175
+ quotedOriginal: includeQuoted ? quoted.slice(0, quotedCap) : '',
176
+ attachmentNames,
177
+ attachmentCount: attachmentNames.length,
178
+ };
179
+ }
180
+ /**
181
+ * Translate a Restrict-style `like` pattern to a regex.
182
+ *
183
+ * Windows hands `subjectLike` to Outlook's server-side Restrict; AppleScript has
184
+ * no equivalent, so the same pattern is applied here instead. `%` and `*` are
185
+ * the any-run wildcards, `_` and `?` match one character, and the match is
186
+ * anchored because that is what SQL `like` means.
187
+ */
188
+ function likePattern(pattern) {
189
+ let source = '';
190
+ for (const ch of pattern) {
191
+ if (ch === '%' || ch === '*')
192
+ source += '.*';
193
+ else if (ch === '_' || ch === '?')
194
+ source += '.';
195
+ else
196
+ source += ch.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
197
+ }
198
+ return new RegExp(`^${source}$`, 'i');
199
+ }
200
+ /**
201
+ * Walk every folder under the Inbox (recursively) for one account and return the
202
+ * emails matching `filter` — full body included, attachments listed by name but
203
+ * not saved.
204
+ *
205
+ * The filtering happens here rather than in Outlook: `Items.Restrict` is a COM
206
+ * facility with no AppleScript counterpart, so the folder walk indexes each
207
+ * folder in two bulk reads and the subject/date tests run on the index. The
208
+ * observable contract is the same; the cost profile is not, and a `daysBack` of
209
+ * 0 over a large mailbox tree is correspondingly heavier here.
210
+ *
211
+ * `subjectPattern` is applied case-insensitively regardless of the RegExp's own
212
+ * flags, matching PowerShell's `-match`.
213
+ */
214
+ async function searchInboxByFilter(emailAccount, filter = {}, daysBack = 0) {
215
+ const days = Math.max(0, Math.floor(daysBack));
216
+ // Pass 1 — index every folder under the Inbox: path, id, subject, received.
217
+ const indexScript = `on scanFolder(theFolder, prefix, cutoff, useCutoff)
218
+ set out to ""
219
+ tell application "Microsoft Outlook"
220
+ set idList to id of every message of theFolder
221
+ set subjList to subject of every message of theFolder
222
+ try
223
+ set timeList to time received of every message of theFolder
224
+ on error
225
+ set timeList to {}
226
+ end try
227
+ set subs to mail folders of theFolder
228
+ end tell
229
+ set hasTimes to ((count of timeList) is (count of idList))
230
+ repeat with i from 1 to (count of idList)
231
+ set d to missing value
232
+ if hasTimes then set d to item i of timeList
233
+ set keep to true
234
+ if d is missing value then
235
+ -- A folder whose items carry no readable receive time can only be
236
+ -- included when the caller isn't bounding by date; silently dropping
237
+ -- it would look exactly like an empty folder.
238
+ set keep to not useCutoff
239
+ else if useCutoff and d is less than cutoff then
240
+ set keep to false
241
+ end if
242
+ if keep then
243
+ set out to out & ${(0, run_1.asRow)([
244
+ 'prefix',
245
+ '(item i of idList as string)',
246
+ '(item i of subjList)',
247
+ 'my isoDate(d)',
248
+ ])}
249
+ end if
250
+ end repeat
251
+ repeat with f in subs
252
+ set childName to ""
253
+ try
254
+ set childName to (name of f) as string
255
+ end try
256
+ set out to out & my scanFolder(f, prefix & ${run_1.AS_LIST_SEP} & childName, cutoff, useCutoff)
257
+ end repeat
258
+ return out
259
+ end scanFolder
260
+
261
+ tell application "Microsoft Outlook"
262
+ ${(0, scripts_1.accountLookupSnippet)(emailAccount)}
263
+ set rootInbox to inbox of targetAcct
264
+ set rootName to (name of rootInbox) as string
265
+ end tell
266
+ set cutoff to (current date) - (${days} * days)
267
+ return my scanFolder(rootInbox, rootName, cutoff, ${days > 0 ? 'true' : 'false'})`;
268
+ const likeRe = filter.subjectLike ? likePattern(filter.subjectLike) : null;
269
+ // PowerShell's -match is case-insensitive by default, so the pattern is
270
+ // rebuilt with `i` regardless of the flags the caller's RegExp carries.
271
+ const patternRe = filter.subjectPattern
272
+ ? new RegExp(filter.subjectPattern.source, 'i')
273
+ : null;
274
+ const candidates = (0, run_1.splitRecords)(await (0, run_1.runOsaScript)(indexScript, 300000))
275
+ .map(record => {
276
+ const parts = (0, run_1.splitFields)(record);
277
+ const segments = (0, run_1.splitList)((0, run_1.field)(parts, 0));
278
+ return {
279
+ folderPath: (0, scripts_1.macFolderPath)(emailAccount, segments[0] || 'Inbox', segments.slice(1)),
280
+ id: (0, run_1.field)(parts, 1),
281
+ subject: (0, run_1.field)(parts, 2).trim(),
282
+ receivedTime: (0, run_1.field)(parts, 3),
283
+ };
284
+ })
285
+ .filter(candidate => {
286
+ if (!candidate.subject)
287
+ return false;
288
+ if (likeRe && !likeRe.test(candidate.subject))
289
+ return false;
290
+ if (patternRe && !patternRe.test(candidate.subject))
291
+ return false;
292
+ if (filter.excludeReplies && /^(re|fwd?)\s*:/i.test(candidate.subject))
293
+ return false;
294
+ return true;
295
+ });
296
+ if (candidates.length === 0)
297
+ return [];
298
+ // Pass 2 — bodies, senders and attachment names for the survivors only.
299
+ const detailScript = `tell application "Microsoft Outlook"
300
+ set wanted to {${candidates.map(c => c.id).join(', ')}}
301
+ set out to ""
302
+ repeat with k from 1 to (count of wanted)
303
+ set theMsg to missing value
304
+ try
305
+ set theMsg to message id (item k of wanted)
306
+ end try
307
+ if theMsg is not missing value then
308
+ ${(0, scripts_1.senderSnippet)('theMsg', ' ')}
309
+ set attNames to {}
310
+ try
311
+ set attNames to name of every attachment of theMsg
312
+ end try
313
+ set bodyText to ""
314
+ try
315
+ set bodyText to (plain text content of theMsg) as string
316
+ end try
317
+ set out to out & ${(0, run_1.asRow)([
318
+ '(id of theMsg as string)',
319
+ 'sndName',
320
+ 'sndAddr',
321
+ 'my sanitizeList(attNames)',
322
+ 'bodyText',
323
+ ])}
324
+ end if
325
+ end repeat
326
+ return out
327
+ end tell`;
328
+ const details = new Map();
329
+ for (const record of (0, run_1.splitRecords)(await (0, run_1.runOsaScript)(detailScript, 300000))) {
330
+ const parts = (0, run_1.splitFields)(record);
331
+ details.set((0, run_1.field)(parts, 0), {
332
+ senderName: (0, run_1.field)(parts, 1),
333
+ senderEmail: (0, run_1.field)(parts, 2),
334
+ attachmentNames: (0, run_1.splitList)((0, run_1.field)(parts, 3)),
335
+ body: (0, run_1.field)(parts, 4),
336
+ });
337
+ }
338
+ const matches = [];
339
+ for (const candidate of candidates) {
340
+ const detail = details.get(candidate.id);
341
+ if (!detail)
342
+ continue;
343
+ // requireAttachment can only be answered once the attachment names are in
344
+ // hand, so it filters here rather than during the index pass.
345
+ if (filter.requireAttachment && detail.attachmentNames.length === 0)
346
+ continue;
347
+ matches.push({
348
+ entryId: candidate.id,
349
+ storeId: '', // macOS AppleScript has no StoreID equivalent
350
+ subject: candidate.subject,
351
+ senderName: detail.senderName,
352
+ senderEmail: detail.senderEmail,
353
+ receivedTime: candidate.receivedTime,
354
+ body: detail.body,
355
+ attachmentNames: detail.attachmentNames,
356
+ folderPath: candidate.folderPath,
357
+ });
358
+ }
359
+ return matches;
360
+ }
361
+ /**
362
+ * Read the email currently selected (or open) in Outlook — full body,
363
+ * attachments listed by name but not saved.
364
+ *
365
+ * `current messages` covers both cases the Windows reader handles separately
366
+ * (an explorer selection and an open item), so there is no second lookup here.
367
+ */
368
+ async function readSelectedEmail() {
369
+ const script = `tell application "Microsoft Outlook"
370
+ set sel to {}
371
+ try
372
+ set sel to current messages
373
+ end try
374
+ if (count of sel) is 0 then error "No email is selected in Outlook. Open Outlook, select (or open) an email, then try again."
375
+ set theMsg to item 1 of sel
376
+ ${(0, scripts_1.messageDetailSnippet)(true)}
377
+ return ${(0, run_1.asRow)((0, scripts_1.messageDetailFields)(true))}
378
+ end tell`;
379
+ const records = (0, run_1.splitRecords)(await (0, run_1.runOsaScript)(script, 30000));
380
+ if (records.length === 0) {
381
+ throw new errors_1.NotFoundError('email', 'Failed to read the selected Outlook email.');
382
+ }
383
+ const parts = (0, run_1.splitFields)(records[0]);
384
+ return {
385
+ entryId: (0, run_1.field)(parts, scripts_1.MessageDetail.id),
386
+ storeId: '', // macOS AppleScript has no StoreID equivalent
387
+ subject: (0, run_1.field)(parts, scripts_1.MessageDetail.subject).trim(),
388
+ senderName: (0, run_1.field)(parts, scripts_1.MessageDetail.senderName),
389
+ senderEmail: (0, run_1.field)(parts, scripts_1.MessageDetail.senderEmail),
390
+ receivedTime: (0, run_1.field)(parts, scripts_1.MessageDetail.receivedTime),
391
+ body: (0, run_1.field)(parts, scripts_1.MessageDetail.body),
392
+ attachmentNames: (0, run_1.splitList)((0, run_1.field)(parts, scripts_1.MessageDetail.attachmentNames)),
393
+ };
394
+ }
395
+ /** Open an email in Outlook by its message id, and bring Outlook forward. */
396
+ async function openOutlookEmail(entryId) {
397
+ const id = (0, scripts_1.macMessageId)(entryId);
398
+ const script = `
399
+ tell application "Microsoft Outlook"
400
+ ${(0, scripts_1.messageLookupSnippet)(id)}
401
+ open theMsg
402
+ activate
403
+ end tell`;
404
+ await (0, run_1.runOsaScript)(script, 30000);
405
+ }
406
+ //# sourceMappingURL=read.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"read.js","sourceRoot":"","sources":["../../src/mac/read.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,64 @@
1
+ /**
2
+ * Run an AppleScript via a temp file (avoids arg-length and quoting limits).
3
+ *
4
+ * `AS_HANDLERS` is prepended here rather than by each caller — the Windows runner
5
+ * already owns its UTF-8 prelude the same way. It matters more on this side: a
6
+ * script missing a handler fails at COMPILE time for the WHOLE script, with a
7
+ * message pointing nowhere near the omission, so "remember to paste the handlers"
8
+ * was a footgun every new script had to survive.
9
+ *
10
+ * `timeout` overrides the configured default for this one call; see `configure()`
11
+ * for that and for the stdout cap.
12
+ */
13
+ export declare function runOsaScript(source: string, timeout?: number): Promise<string>;
14
+ /** Escape a string for embedding inside an AppleScript double-quoted literal. */
15
+ export declare function asEscape(s: string): string;
16
+ /** AppleScript's boolean literals. */
17
+ export declare function asBool(value: boolean): string;
18
+ export declare const FIELD_SEP = "\u001F";
19
+ export declare const RECORD_SEP = "\u001E";
20
+ export declare const LIST_SEP = "\u001D";
21
+ /** The same three, as AppleScript expressions. */
22
+ export declare const AS_FIELD_SEP = "(character id 31)";
23
+ export declare const AS_RECORD_SEP = "(character id 30)";
24
+ export declare const AS_LIST_SEP = "(character id 29)";
25
+ /**
26
+ * Emit one record: the AppleScript expressions in `fields`, separated and
27
+ * terminated so `splitRecords`/`splitFields` can take them apart again.
28
+ *
29
+ * Every field goes through `sanitize`, which is what makes the framing safe
30
+ * rather than merely unlikely to break. A field holding a LIST must be built
31
+ * with `my sanitizeList(...)`, which cleans the elements instead — `sanitize`
32
+ * deliberately leaves the list separator alone.
33
+ */
34
+ export declare function asRow(fields: readonly string[]): string;
35
+ /**
36
+ * The AppleScript handlers every script here relies on. Called with `my` from
37
+ * inside a `tell` block.
38
+ *
39
+ * `isoDate` produces the zero-padded 'yyyy-MM-dd HH:mm' both platforms' readers
40
+ * return; `sanitize` strips the framing characters; `joinList` and `replaceText`
41
+ * are the text-item-delimiter dance nobody should write twice.
42
+ */
43
+ export declare const AS_HANDLERS = "\non pad2(n)\n set s to (n as integer) as string\n if (length of s) < 2 then set s to \"0\" & s\n return s\nend pad2\n\non isoDate(d)\n if d is missing value then return \"\"\n return (year of d as string) & \"-\" & pad2(month of d as integer) & \"-\" & pad2(day of d) & \" \" & pad2(hours of d) & \":\" & pad2(minutes of d)\nend isoDate\n\non joinList(lst, sep)\n set saved to AppleScript's text item delimiters\n set AppleScript's text item delimiters to sep\n set out to lst as string\n set AppleScript's text item delimiters to saved\n return out\nend joinList\n\non replaceText(t, findWhat, replaceWith)\n set saved to AppleScript's text item delimiters\n set AppleScript's text item delimiters to findWhat\n set parts to text items of t\n set AppleScript's text item delimiters to replaceWith\n set out to parts as string\n set AppleScript's text item delimiters to saved\n return out\nend replaceText\n\n-- Strips the FIELD and RECORD separators only. The LIST separator is left\n-- alone on purpose: a field may legitimately BE a list, and stripping 29 here\n-- collapsed every such field into one run-on string.\non sanitize(v)\n if v is missing value then return \"\"\n set t to v as string\n repeat with codePoint in {30, 31}\n set marker to (character id (codePoint as integer))\n if t contains marker then set t to my replaceText(t, marker, \" \")\n end repeat\n return t\nend sanitize\n\n-- A list field: each element loses all three separators, then they are joined\n-- with the LIST separator that splitList() takes them apart on.\non sanitizeList(lst)\n set cleaned to {}\n repeat with item_ in lst\n set t to my sanitize(item_)\n repeat with codePoint in {29}\n set marker to (character id (codePoint as integer))\n if t contains marker then set t to my replaceText(t, marker, \" \")\n end repeat\n set end of cleaned to t\n end repeat\n return my joinList(cleaned, (character id 29))\nend sanitizeList\n\non insertAboveQuoted(c, ins)\n if c is missing value then return ins\n set c to c as string\n if (length of c) is 0 then return ins\n -- Outlook builds a reply as a document whose own empty paragraph sits inside\n -- WordSection1; inserting straight after that tag puts the new text where the\n -- user's cursor would have been. Anything else falls back to just inside <body>.\n -- 'at' is a reserved AppleScript parameter name, so the cut point cannot be\n -- called that however naturally it reads.\n set cutPoint to my tagEnd(c, \"WordSection1>\")\n if cutPoint is 0 then set cutPoint to my tagEnd(c, \"<body\")\n if cutPoint is 0 then return ins & c\n if cutPoint is (length of c) then return c & ins\n return (text 1 thru cutPoint of c) & ins & (text (cutPoint + 1) thru -1 of c)\nend insertAboveQuoted\n\n-- 'rest' is an AppleScript term (rest of list), so the remainder cannot be\n-- called that: assigning to it compiles and then fails at run time.\non tagEnd(c, marker)\n set ix to offset of marker in c\n if ix is 0 then return 0\n if marker ends with \">\" then return ix + (length of marker) - 1\n set tailText to text ix thru -1 of c\n set gt to offset of \">\" in tailText\n if gt is 0 then return 0\n return ix + gt - 1\nend tagEnd\n";
44
+ /** Split a script's output into records, dropping the trailing empty one. */
45
+ export declare function splitRecords(raw: string): string[];
46
+ /** Split one record into its fields. */
47
+ export declare function splitFields(record: string): string[];
48
+ /** Split one field that carries a list. */
49
+ export declare function splitList(value: string | undefined): string[];
50
+ /** A field by position — a missing field reads as ''. */
51
+ export declare function field(fields: readonly string[], index: number): string;
52
+ /**
53
+ * The fields of a script's ONE summary record — the shape every mutation here
54
+ * returns (counts first, then any per-item failures as further records).
55
+ */
56
+ export declare function summaryFields(raw: string): string[];
57
+ /** A numeric field, defaulting to `fallback` when absent or unparsable. */
58
+ export declare function intField(fields: readonly string[], index: number, fallback?: number): number;
59
+ /**
60
+ * A boolean field. AppleScript renders booleans as the bare words `true`/`false`,
61
+ * so this is the counterpart of `shared/json.ts`'s coercions for the framed
62
+ * output — the Windows side gets those free from ConvertFrom-Json.
63
+ */
64
+ export declare function boolField(fields: readonly string[], index: number): boolean;