zele 0.3.16 → 0.3.20
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +155 -36
- package/dist/api-utils.d.ts +14 -0
- package/dist/api-utils.js +20 -0
- package/dist/api-utils.js.map +1 -1
- package/dist/auth.d.ts +71 -9
- package/dist/auth.js +186 -10
- package/dist/auth.js.map +1 -1
- package/dist/cli-types.d.ts +4 -0
- package/dist/cli-types.js +6 -0
- package/dist/cli-types.js.map +1 -0
- package/dist/cli.js +1 -5
- package/dist/cli.js.map +1 -1
- package/dist/commands/attachment.d.ts +2 -2
- package/dist/commands/attachment.js +2 -0
- package/dist/commands/attachment.js.map +1 -1
- package/dist/commands/auth-cmd.d.ts +2 -2
- package/dist/commands/auth-cmd.js +104 -6
- package/dist/commands/auth-cmd.js.map +1 -1
- package/dist/commands/calendar.d.ts +2 -2
- package/dist/commands/calendar.js.map +1 -1
- package/dist/commands/draft.d.ts +2 -2
- package/dist/commands/draft.js +58 -4
- package/dist/commands/draft.js.map +1 -1
- package/dist/commands/filter.d.ts +2 -2
- package/dist/commands/filter.js +7 -2
- package/dist/commands/filter.js.map +1 -1
- package/dist/commands/label.d.ts +2 -2
- package/dist/commands/label.js +19 -9
- package/dist/commands/label.js.map +1 -1
- package/dist/commands/mail-actions.d.ts +2 -2
- package/dist/commands/mail-actions.js +290 -1
- package/dist/commands/mail-actions.js.map +1 -1
- package/dist/commands/mail.d.ts +2 -2
- package/dist/commands/mail.js +90 -23
- package/dist/commands/mail.js.map +1 -1
- package/dist/commands/profile.d.ts +2 -2
- package/dist/commands/profile.js +25 -18
- package/dist/commands/profile.js.map +1 -1
- package/dist/commands/watch.d.ts +2 -2
- package/dist/commands/watch.js.map +1 -1
- package/dist/db.js +24 -0
- package/dist/db.js.map +1 -1
- package/dist/generated/internal/class.js +2 -2
- package/dist/generated/internal/class.js.map +1 -1
- package/dist/generated/internal/prismaNamespace.d.ts +2 -0
- package/dist/generated/internal/prismaNamespace.js +2 -0
- package/dist/generated/internal/prismaNamespace.js.map +1 -1
- package/dist/generated/internal/prismaNamespaceBrowser.d.ts +2 -0
- package/dist/generated/internal/prismaNamespaceBrowser.js +2 -0
- package/dist/generated/internal/prismaNamespaceBrowser.js.map +1 -1
- package/dist/generated/models/Account.d.ts +97 -1
- package/dist/gmail-client.d.ts +73 -3
- package/dist/gmail-client.js +165 -5
- package/dist/gmail-client.js.map +1 -1
- package/dist/imap-smtp-client.d.ts +306 -0
- package/dist/imap-smtp-client.js +1349 -0
- package/dist/imap-smtp-client.js.map +1 -0
- package/dist/mail-tui.js.map +1 -1
- package/dist/unsubscribe.d.ts +76 -0
- package/dist/unsubscribe.js +224 -0
- package/dist/unsubscribe.js.map +1 -0
- package/package.json +6 -3
- package/schema.prisma +7 -5
- package/skills/zele/SKILL.md +26 -96
- package/src/api-utils.ts +20 -0
- package/src/auth.ts +282 -14
- package/src/cli-types.ts +8 -0
- package/src/cli.ts +2 -7
- package/src/commands/attachment.ts +3 -2
- package/src/commands/auth-cmd.ts +114 -8
- package/src/commands/calendar.ts +2 -2
- package/src/commands/draft.ts +65 -6
- package/src/commands/filter.ts +11 -5
- package/src/commands/label.ts +24 -13
- package/src/commands/mail-actions.ts +317 -5
- package/src/commands/mail.ts +97 -25
- package/src/commands/profile.ts +29 -19
- package/src/commands/watch.ts +2 -2
- package/src/db.ts +28 -0
- package/src/generated/internal/class.ts +2 -2
- package/src/generated/internal/prismaNamespace.ts +2 -0
- package/src/generated/internal/prismaNamespaceBrowser.ts +2 -0
- package/src/generated/models/Account.ts +97 -1
- package/src/gmail-client.test.ts +155 -2
- package/src/gmail-client.ts +258 -6
- package/src/imap-smtp-client.ts +1560 -0
- package/src/mail-tui.tsx +2 -1
- package/src/schema.sql +2 -0
- package/src/unsubscribe.test.ts +487 -0
- package/src/unsubscribe.ts +255 -0
|
@@ -0,0 +1,306 @@
|
|
|
1
|
+
import { AuthError, ApiError, UnsupportedError, EmptyThreadError, NotFoundError } from './api-utils.js';
|
|
2
|
+
import type { AccountId, ImapSmtpCredentials } from './auth.js';
|
|
3
|
+
import type { ThreadListResult, ThreadResult, ParsedMessage, WatchEvent, Sender } from './gmail-client.js';
|
|
4
|
+
export declare class ImapSmtpClient {
|
|
5
|
+
private imapCreds;
|
|
6
|
+
private smtpCreds;
|
|
7
|
+
private account;
|
|
8
|
+
private smtpTransporter;
|
|
9
|
+
constructor({ credentials, account }: {
|
|
10
|
+
credentials: ImapSmtpCredentials;
|
|
11
|
+
account: AccountId;
|
|
12
|
+
});
|
|
13
|
+
private createImapClient;
|
|
14
|
+
/**
|
|
15
|
+
* Resolve a zele folder name (inbox, sent, trash, etc.) to the actual IMAP
|
|
16
|
+
* mailbox path by checking RFC 6154 specialUse attributes first, then
|
|
17
|
+
* falling back to common mailbox name variants.
|
|
18
|
+
*/
|
|
19
|
+
private resolveMailboxPath;
|
|
20
|
+
/** Run an IMAP operation with auto-connect/logout.
|
|
21
|
+
* The entire callback is wrapped in imapBoundary so any IMAP error
|
|
22
|
+
* (getMailboxLock, search, fetch, etc.) becomes an error value. */
|
|
23
|
+
private withImap;
|
|
24
|
+
private getSmtpTransporter;
|
|
25
|
+
listThreads({ query, folder, maxResults, labelIds, pageToken, }?: {
|
|
26
|
+
query?: string;
|
|
27
|
+
folder?: string;
|
|
28
|
+
maxResults?: number;
|
|
29
|
+
labelIds?: string[];
|
|
30
|
+
pageToken?: string;
|
|
31
|
+
}): Promise<ThreadListResult | AuthError | ApiError>;
|
|
32
|
+
getThread({ threadId }: {
|
|
33
|
+
threadId: string;
|
|
34
|
+
}): Promise<ThreadResult>;
|
|
35
|
+
getMessage({ messageId }: {
|
|
36
|
+
messageId: string;
|
|
37
|
+
}): Promise<ParsedMessage | AuthError | ApiError>;
|
|
38
|
+
getRawMessage({ messageId }: {
|
|
39
|
+
messageId: string;
|
|
40
|
+
}): Promise<string | NotFoundError | AuthError | ApiError>;
|
|
41
|
+
sendMessage({ to, subject, body, cc, bcc, inReplyTo, references, attachments, }: {
|
|
42
|
+
to: Array<{
|
|
43
|
+
name?: string;
|
|
44
|
+
email: string;
|
|
45
|
+
}>;
|
|
46
|
+
subject: string;
|
|
47
|
+
body: string;
|
|
48
|
+
cc?: Array<{
|
|
49
|
+
name?: string;
|
|
50
|
+
email: string;
|
|
51
|
+
}>;
|
|
52
|
+
bcc?: Array<{
|
|
53
|
+
name?: string;
|
|
54
|
+
email: string;
|
|
55
|
+
}>;
|
|
56
|
+
threadId?: string;
|
|
57
|
+
inReplyTo?: string;
|
|
58
|
+
references?: string;
|
|
59
|
+
attachments?: Array<{
|
|
60
|
+
filename: string;
|
|
61
|
+
mimeType: string;
|
|
62
|
+
content: Buffer;
|
|
63
|
+
}>;
|
|
64
|
+
fromEmail?: string;
|
|
65
|
+
}): Promise<{
|
|
66
|
+
id: string;
|
|
67
|
+
threadId: string;
|
|
68
|
+
labelIds: string[];
|
|
69
|
+
} | UnsupportedError | AuthError | ApiError>;
|
|
70
|
+
replyToThread({ threadId, body, replyAll, cc, fromEmail, }: {
|
|
71
|
+
threadId: string;
|
|
72
|
+
body: string;
|
|
73
|
+
replyAll?: boolean;
|
|
74
|
+
cc?: Array<{
|
|
75
|
+
email: string;
|
|
76
|
+
}>;
|
|
77
|
+
fromEmail?: string;
|
|
78
|
+
}): Promise<EmptyThreadError | UnsupportedError | AuthError | ApiError | {
|
|
79
|
+
id: string;
|
|
80
|
+
threadId: string;
|
|
81
|
+
labelIds: string[];
|
|
82
|
+
}>;
|
|
83
|
+
forwardThread({ threadId, to, body, fromEmail, }: {
|
|
84
|
+
threadId: string;
|
|
85
|
+
to: Array<{
|
|
86
|
+
email: string;
|
|
87
|
+
}>;
|
|
88
|
+
body?: string;
|
|
89
|
+
fromEmail?: string;
|
|
90
|
+
}): Promise<EmptyThreadError | UnsupportedError | AuthError | ApiError | {
|
|
91
|
+
id: string;
|
|
92
|
+
threadId: string;
|
|
93
|
+
labelIds: string[];
|
|
94
|
+
}>;
|
|
95
|
+
star({ threadIds }: {
|
|
96
|
+
threadIds: string[];
|
|
97
|
+
}): Promise<void | AuthError | ApiError>;
|
|
98
|
+
unstar({ threadIds }: {
|
|
99
|
+
threadIds: string[];
|
|
100
|
+
}): Promise<void | AuthError | ApiError>;
|
|
101
|
+
markAsRead({ threadIds }: {
|
|
102
|
+
threadIds: string[];
|
|
103
|
+
}): Promise<void | AuthError | ApiError>;
|
|
104
|
+
markAsUnread({ threadIds }: {
|
|
105
|
+
threadIds: string[];
|
|
106
|
+
}): Promise<void | AuthError | ApiError>;
|
|
107
|
+
trash({ threadId }: {
|
|
108
|
+
threadId: string;
|
|
109
|
+
}): Promise<void | AuthError | ApiError>;
|
|
110
|
+
untrash({ threadId }: {
|
|
111
|
+
threadId: string;
|
|
112
|
+
}): Promise<void | AuthError | ApiError>;
|
|
113
|
+
archive({ threadIds }: {
|
|
114
|
+
threadIds: string[];
|
|
115
|
+
}): Promise<void | AuthError | ApiError>;
|
|
116
|
+
markAsSpam({ threadIds }: {
|
|
117
|
+
threadIds: string[];
|
|
118
|
+
}): Promise<void | AuthError | ApiError>;
|
|
119
|
+
unmarkSpam({ threadIds }: {
|
|
120
|
+
threadIds: string[];
|
|
121
|
+
}): Promise<void | AuthError | ApiError>;
|
|
122
|
+
trashAllSpam(): Promise<{
|
|
123
|
+
count: number;
|
|
124
|
+
} | AuthError | ApiError>;
|
|
125
|
+
listLabels(): Promise<UnsupportedError>;
|
|
126
|
+
modifyLabels(_opts: {
|
|
127
|
+
threadIds: string[];
|
|
128
|
+
addLabelIds: string[];
|
|
129
|
+
removeLabelIds: string[];
|
|
130
|
+
}): Promise<UnsupportedError>;
|
|
131
|
+
getProfile(): Promise<{
|
|
132
|
+
emailAddress: string;
|
|
133
|
+
messagesTotal: number;
|
|
134
|
+
threadsTotal: number;
|
|
135
|
+
historyId: string;
|
|
136
|
+
} | AuthError | ApiError>;
|
|
137
|
+
getEmailAliases(): Promise<Array<{
|
|
138
|
+
email: string;
|
|
139
|
+
name?: string;
|
|
140
|
+
primary: boolean;
|
|
141
|
+
}> | AuthError | ApiError>;
|
|
142
|
+
getAttachment({ messageId, attachmentId }: {
|
|
143
|
+
messageId: string;
|
|
144
|
+
attachmentId: string;
|
|
145
|
+
}): Promise<string | NotFoundError | AuthError | ApiError>;
|
|
146
|
+
watchInbox({ folder, intervalMs, query, once, }?: {
|
|
147
|
+
folder?: string;
|
|
148
|
+
intervalMs?: number;
|
|
149
|
+
query?: string;
|
|
150
|
+
once?: boolean;
|
|
151
|
+
}): AsyncGenerator<WatchEvent>;
|
|
152
|
+
listDrafts({ query, maxResults, pageToken, }?: {
|
|
153
|
+
query?: string;
|
|
154
|
+
maxResults?: number;
|
|
155
|
+
pageToken?: string;
|
|
156
|
+
}): Promise<{
|
|
157
|
+
drafts: Array<{
|
|
158
|
+
id: string;
|
|
159
|
+
subject: string;
|
|
160
|
+
to: string[];
|
|
161
|
+
date: string;
|
|
162
|
+
}>;
|
|
163
|
+
nextPageToken: string | null;
|
|
164
|
+
} | AuthError | ApiError>;
|
|
165
|
+
createDraft({ to, subject, body, cc, bcc, threadId, fromEmail, }: {
|
|
166
|
+
to: Array<{
|
|
167
|
+
name?: string;
|
|
168
|
+
email: string;
|
|
169
|
+
}>;
|
|
170
|
+
subject: string;
|
|
171
|
+
body: string;
|
|
172
|
+
cc?: Array<{
|
|
173
|
+
name?: string;
|
|
174
|
+
email: string;
|
|
175
|
+
}>;
|
|
176
|
+
bcc?: Array<{
|
|
177
|
+
name?: string;
|
|
178
|
+
email: string;
|
|
179
|
+
}>;
|
|
180
|
+
threadId?: string;
|
|
181
|
+
fromEmail?: string;
|
|
182
|
+
attachments?: Array<{
|
|
183
|
+
filename: string;
|
|
184
|
+
mimeType: string;
|
|
185
|
+
content: Buffer;
|
|
186
|
+
}>;
|
|
187
|
+
}): Promise<{
|
|
188
|
+
id: string;
|
|
189
|
+
message: {
|
|
190
|
+
id: string;
|
|
191
|
+
};
|
|
192
|
+
threadId: string;
|
|
193
|
+
}>;
|
|
194
|
+
getDraft({ draftId }: {
|
|
195
|
+
draftId: string;
|
|
196
|
+
}): Promise<{
|
|
197
|
+
id: string;
|
|
198
|
+
message: ParsedMessage;
|
|
199
|
+
to: Sender[];
|
|
200
|
+
cc: Sender[];
|
|
201
|
+
bcc: Sender[];
|
|
202
|
+
}>;
|
|
203
|
+
sendDraft({ draftId }: {
|
|
204
|
+
draftId: string;
|
|
205
|
+
}): Promise<AuthError | ApiError | UnsupportedError | {
|
|
206
|
+
id: string;
|
|
207
|
+
threadId: string;
|
|
208
|
+
labelIds: string[];
|
|
209
|
+
}>;
|
|
210
|
+
deleteDraft({ draftId }: {
|
|
211
|
+
draftId: string;
|
|
212
|
+
}): Promise<void | AuthError | ApiError>;
|
|
213
|
+
/**
|
|
214
|
+
* Update an existing draft. IMAP has no native update — we delete the old
|
|
215
|
+
* draft and APPEND a new message to the Drafts folder.
|
|
216
|
+
*/
|
|
217
|
+
updateDraft({ draftId, to, subject, body, cc, bcc, fromEmail, }: {
|
|
218
|
+
draftId: string;
|
|
219
|
+
to: Array<{
|
|
220
|
+
name?: string;
|
|
221
|
+
email: string;
|
|
222
|
+
}>;
|
|
223
|
+
subject: string;
|
|
224
|
+
body: string;
|
|
225
|
+
cc?: Array<{
|
|
226
|
+
name?: string;
|
|
227
|
+
email: string;
|
|
228
|
+
}>;
|
|
229
|
+
bcc?: Array<{
|
|
230
|
+
name?: string;
|
|
231
|
+
email: string;
|
|
232
|
+
}>;
|
|
233
|
+
threadId?: string;
|
|
234
|
+
fromEmail?: string;
|
|
235
|
+
attachments?: Array<{
|
|
236
|
+
filename: string;
|
|
237
|
+
mimeType: string;
|
|
238
|
+
content: Buffer;
|
|
239
|
+
}>;
|
|
240
|
+
}): Promise<AuthError | ApiError | {
|
|
241
|
+
id: string;
|
|
242
|
+
message: {
|
|
243
|
+
id: string;
|
|
244
|
+
};
|
|
245
|
+
threadId: string;
|
|
246
|
+
}>;
|
|
247
|
+
/**
|
|
248
|
+
* Create a draft reply to a thread. Resolves reply-to, reply-all CCs,
|
|
249
|
+
* and sets In-Reply-To/References headers, then appends to Drafts.
|
|
250
|
+
*/
|
|
251
|
+
createDraftReply({ threadId, body, replyAll, cc, fromEmail, }: {
|
|
252
|
+
threadId: string;
|
|
253
|
+
body: string;
|
|
254
|
+
replyAll?: boolean;
|
|
255
|
+
cc?: Array<{
|
|
256
|
+
email: string;
|
|
257
|
+
}>;
|
|
258
|
+
fromEmail?: string;
|
|
259
|
+
}): Promise<EmptyThreadError | AuthError | ApiError | {
|
|
260
|
+
id: string;
|
|
261
|
+
message: {
|
|
262
|
+
id: string;
|
|
263
|
+
};
|
|
264
|
+
threadId: string;
|
|
265
|
+
}>;
|
|
266
|
+
/**
|
|
267
|
+
* Create a draft forwarding a thread. Builds the forwarded-message body
|
|
268
|
+
* and appends to Drafts folder.
|
|
269
|
+
*/
|
|
270
|
+
createDraftForward({ threadId, to, body, fromEmail, }: {
|
|
271
|
+
threadId: string;
|
|
272
|
+
to: Array<{
|
|
273
|
+
email: string;
|
|
274
|
+
}>;
|
|
275
|
+
body?: string;
|
|
276
|
+
fromEmail?: string;
|
|
277
|
+
}): Promise<EmptyThreadError | AuthError | ApiError | {
|
|
278
|
+
id: string;
|
|
279
|
+
message: {
|
|
280
|
+
id: string;
|
|
281
|
+
};
|
|
282
|
+
threadId: string;
|
|
283
|
+
}>;
|
|
284
|
+
listFolders(): Promise<Array<{
|
|
285
|
+
name: string;
|
|
286
|
+
path: string;
|
|
287
|
+
specialUse?: string;
|
|
288
|
+
flags: string[];
|
|
289
|
+
}> | AuthError | ApiError>;
|
|
290
|
+
invalidateThreads(_threadIds: string[]): Promise<void>;
|
|
291
|
+
invalidateThread(_threadId: string): Promise<void>;
|
|
292
|
+
/** Modify IMAP flags on messages. Groups by folder for efficiency. */
|
|
293
|
+
private modifyFlags;
|
|
294
|
+
/** Check if a message has attachments from its bodyStructure. */
|
|
295
|
+
private hasAttachments;
|
|
296
|
+
/** Parse an imapflow FetchMessageObject into our ParsedMessage type. */
|
|
297
|
+
private parseImapMessage;
|
|
298
|
+
/** Extract body text from raw RFC 2822 source. */
|
|
299
|
+
private extractBodyFromSource;
|
|
300
|
+
private parseBody;
|
|
301
|
+
private parseMultipart;
|
|
302
|
+
private decodeTransferEncoding;
|
|
303
|
+
private getHeader;
|
|
304
|
+
/** Recursively collect attachment metadata from bodyStructure. */
|
|
305
|
+
private collectAttachments;
|
|
306
|
+
}
|