better-email-mcp 0.1.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.
@@ -0,0 +1,73 @@
1
+ /**
2
+ * IMAP response parser.
3
+ *
4
+ * Handles tagged/untagged responses, parenthesized lists (flags, envelopes,
5
+ * body structures), and RFC 2047 encoded-word decoding.
6
+ */
7
+ export interface ImapResponse {
8
+ tag: string;
9
+ type?: string;
10
+ num?: number;
11
+ text: string;
12
+ }
13
+ export interface ImapAddress {
14
+ name: string;
15
+ email: string;
16
+ }
17
+ export interface ParsedEnvelope {
18
+ date: string;
19
+ subject: string;
20
+ from: ImapAddress[];
21
+ sender: ImapAddress[];
22
+ replyTo: ImapAddress[];
23
+ to: ImapAddress[];
24
+ cc: ImapAddress[];
25
+ bcc: ImapAddress[];
26
+ inReplyTo: string;
27
+ messageId: string;
28
+ }
29
+ export interface ParsedFetch {
30
+ uid?: number;
31
+ flags?: string[];
32
+ envelope?: ParsedEnvelope;
33
+ bodyText?: string;
34
+ }
35
+ export declare function parseResponseLine(line: string): ImapResponse;
36
+ /**
37
+ * Parses an IMAP parenthesized list into a nested array.
38
+ * Handles NIL, quoted strings, literals (as pre-substituted text), and atoms.
39
+ *
40
+ * Example: `(\\Seen \\Flagged)` → ["\\Seen", "\\Flagged"]
41
+ * Example: `("hello" NIL)` → ["hello", null]
42
+ */
43
+ export declare function parseParenList(data: string, startIndex?: number): {
44
+ value: any[];
45
+ endIndex: number;
46
+ };
47
+ /**
48
+ * Parses the data items from a FETCH response.
49
+ * Input: the text after "* N FETCH", e.g. "(UID 42 FLAGS (\\Seen) ENVELOPE (...))"
50
+ */
51
+ export declare function parseFetchResponse(text: string): ParsedFetch;
52
+ /**
53
+ * Parses UIDs from a SEARCH response text.
54
+ * Input: "1 4 9 23" → [1, 4, 9, 23]
55
+ */
56
+ export declare function parseSearchResponse(text: string): number[];
57
+ /**
58
+ * Parses a LIST response line.
59
+ * Format: (flags) "delimiter" "mailbox-name"
60
+ * Input text (after "* LIST"): `(\HasNoChildren) "/" "INBOX"`
61
+ */
62
+ export declare function parseListResponse(text: string): {
63
+ flags: string[];
64
+ delimiter: string;
65
+ name: string;
66
+ } | null;
67
+ /**
68
+ * Decodes RFC 2047 encoded words in a string.
69
+ * Format: =?charset?encoding?encoded-text?=
70
+ * Supports B (base64) and Q (quoted-printable) encodings.
71
+ */
72
+ export declare function decodeRfc2047(input: string): string;
73
+ //# sourceMappingURL=parser.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"parser.d.ts","sourceRoot":"","sources":["../../src/imap/parser.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH,MAAM,WAAW,YAAY;IAC3B,GAAG,EAAE,MAAM,CAAC;IACZ,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;CACd;AAED,MAAM,WAAW,WAAW;IAC1B,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,cAAc;IAC7B,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,EAAE,WAAW,EAAE,CAAC;IACpB,MAAM,EAAE,WAAW,EAAE,CAAC;IACtB,OAAO,EAAE,WAAW,EAAE,CAAC;IACvB,EAAE,EAAE,WAAW,EAAE,CAAC;IAClB,EAAE,EAAE,WAAW,EAAE,CAAC;IAClB,GAAG,EAAE,WAAW,EAAE,CAAC;IACnB,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,WAAW;IAC1B,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,KAAK,CAAC,EAAE,MAAM,EAAE,CAAC;IACjB,QAAQ,CAAC,EAAE,cAAc,CAAC;IAC1B,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAID,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG,YAAY,CA6B5D;AA6BD;;;;;;GAMG;AACH,wBAAgB,cAAc,CAAC,IAAI,EAAE,MAAM,EAAE,UAAU,SAAI,GAAG;IAAE,KAAK,EAAE,GAAG,EAAE,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAA;CAAE,CA2C/F;AAmCD;;;GAGG;AACH,wBAAgB,kBAAkB,CAAC,IAAI,EAAE,MAAM,GAAG,WAAW,CA2E5D;AA2CD;;;GAGG;AACH,wBAAgB,mBAAmB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,EAAE,CAO1D;AAID;;;;GAIG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG;IAAE,KAAK,EAAE,MAAM,EAAE,CAAC;IAAC,SAAS,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CAmC3G;AAID;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAyBnD"}
@@ -0,0 +1,349 @@
1
+ "use strict";
2
+ /**
3
+ * IMAP response parser.
4
+ *
5
+ * Handles tagged/untagged responses, parenthesized lists (flags, envelopes,
6
+ * body structures), and RFC 2047 encoded-word decoding.
7
+ */
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ exports.parseResponseLine = parseResponseLine;
10
+ exports.parseParenList = parseParenList;
11
+ exports.parseFetchResponse = parseFetchResponse;
12
+ exports.parseSearchResponse = parseSearchResponse;
13
+ exports.parseListResponse = parseListResponse;
14
+ exports.decodeRfc2047 = decodeRfc2047;
15
+ // --- Response line parsing ---
16
+ function parseResponseLine(line) {
17
+ // Continuation response
18
+ if (line.startsWith("+ ") || line === "+") {
19
+ return { tag: "+", text: line.substring(2) };
20
+ }
21
+ // Untagged response: * ...
22
+ if (line.startsWith("* ")) {
23
+ return parseUntagged(line.substring(2));
24
+ }
25
+ // Tagged response: A1 OK/NO/BAD ...
26
+ const spaceIdx = line.indexOf(" ");
27
+ if (spaceIdx === -1) {
28
+ return { tag: line, text: "" };
29
+ }
30
+ const tag = line.substring(0, spaceIdx);
31
+ const rest = line.substring(spaceIdx + 1);
32
+ const typeMatch = rest.match(/^(OK|NO|BAD)\b\s*(.*)/i);
33
+ if (typeMatch) {
34
+ return {
35
+ tag,
36
+ type: typeMatch[1].toUpperCase(),
37
+ text: typeMatch[2],
38
+ };
39
+ }
40
+ return { tag, text: rest };
41
+ }
42
+ function parseUntagged(rest) {
43
+ // Check for numeric prefix: "* 5 EXISTS", "* 42 FETCH (...)"
44
+ const numMatch = rest.match(/^(\d+)\s+(\S+)\s*(.*)/);
45
+ if (numMatch) {
46
+ return {
47
+ tag: "*",
48
+ num: parseInt(numMatch[1], 10),
49
+ type: numMatch[2].toUpperCase(),
50
+ text: numMatch[3],
51
+ };
52
+ }
53
+ // Non-numeric: "* OK ...", "* SEARCH 1 4 9", "* LIST ..."
54
+ const typeMatch = rest.match(/^(\S+)\s*(.*)/);
55
+ if (typeMatch) {
56
+ return {
57
+ tag: "*",
58
+ type: typeMatch[1].toUpperCase(),
59
+ text: typeMatch[2],
60
+ };
61
+ }
62
+ return { tag: "*", text: rest };
63
+ }
64
+ // --- Parenthesized list parser ---
65
+ /**
66
+ * Parses an IMAP parenthesized list into a nested array.
67
+ * Handles NIL, quoted strings, literals (as pre-substituted text), and atoms.
68
+ *
69
+ * Example: `(\\Seen \\Flagged)` → ["\\Seen", "\\Flagged"]
70
+ * Example: `("hello" NIL)` → ["hello", null]
71
+ */
72
+ function parseParenList(data, startIndex = 0) {
73
+ const result = [];
74
+ let i = startIndex;
75
+ // Skip leading whitespace
76
+ while (i < data.length && data[i] === " ")
77
+ i++;
78
+ if (data[i] !== "(") {
79
+ throw new Error(`Expected '(' at position ${i}, got '${data[i]}'`);
80
+ }
81
+ i++; // skip opening paren
82
+ while (i < data.length) {
83
+ // Skip whitespace
84
+ while (i < data.length && data[i] === " ")
85
+ i++;
86
+ if (i >= data.length)
87
+ break;
88
+ const ch = data[i];
89
+ if (ch === ")") {
90
+ return { value: result, endIndex: i + 1 };
91
+ }
92
+ if (ch === "(") {
93
+ // Nested list
94
+ const nested = parseParenList(data, i);
95
+ result.push(nested.value);
96
+ i = nested.endIndex;
97
+ }
98
+ else if (ch === '"') {
99
+ // Quoted string
100
+ const { value, endIndex } = parseQuotedString(data, i);
101
+ result.push(value);
102
+ i = endIndex;
103
+ }
104
+ else {
105
+ // Atom or NIL
106
+ const { value, endIndex } = parseAtom(data, i);
107
+ result.push(value === "NIL" ? null : value);
108
+ i = endIndex;
109
+ }
110
+ }
111
+ return { value: result, endIndex: i };
112
+ }
113
+ function parseQuotedString(data, startIndex) {
114
+ let i = startIndex + 1; // skip opening quote
115
+ let result = "";
116
+ while (i < data.length) {
117
+ if (data[i] === "\\") {
118
+ // Escaped character
119
+ i++;
120
+ if (i < data.length) {
121
+ result += data[i];
122
+ i++;
123
+ }
124
+ }
125
+ else if (data[i] === '"') {
126
+ return { value: result, endIndex: i + 1 };
127
+ }
128
+ else {
129
+ result += data[i];
130
+ i++;
131
+ }
132
+ }
133
+ return { value: result, endIndex: i };
134
+ }
135
+ function parseAtom(data, startIndex) {
136
+ let i = startIndex;
137
+ while (i < data.length && data[i] !== " " && data[i] !== ")" && data[i] !== "(") {
138
+ i++;
139
+ }
140
+ return { value: data.substring(startIndex, i), endIndex: i };
141
+ }
142
+ // --- FETCH response parsing ---
143
+ /**
144
+ * Parses the data items from a FETCH response.
145
+ * Input: the text after "* N FETCH", e.g. "(UID 42 FLAGS (\\Seen) ENVELOPE (...))"
146
+ */
147
+ function parseFetchResponse(text) {
148
+ const result = {};
149
+ // Strip outer parens
150
+ const trimmed = text.trim();
151
+ if (!trimmed.startsWith("(") || !trimmed.endsWith(")")) {
152
+ return result;
153
+ }
154
+ const inner = trimmed.substring(1, trimmed.length - 1);
155
+ let i = 0;
156
+ while (i < inner.length) {
157
+ // Skip whitespace
158
+ while (i < inner.length && inner[i] === " ")
159
+ i++;
160
+ if (i >= inner.length)
161
+ break;
162
+ // Read keyword
163
+ const kwStart = i;
164
+ while (i < inner.length && inner[i] !== " " && inner[i] !== "(")
165
+ i++;
166
+ const keyword = inner.substring(kwStart, i).toUpperCase();
167
+ // Skip whitespace
168
+ while (i < inner.length && inner[i] === " ")
169
+ i++;
170
+ if (keyword === "UID") {
171
+ const { value, endIndex } = parseAtom(inner, i);
172
+ result.uid = parseInt(value, 10);
173
+ i = endIndex;
174
+ }
175
+ else if (keyword === "FLAGS") {
176
+ const { value, endIndex } = parseParenList(inner, i);
177
+ result.flags = value;
178
+ i = endIndex;
179
+ }
180
+ else if (keyword === "ENVELOPE") {
181
+ const { value, endIndex } = parseParenList(inner, i);
182
+ result.envelope = mapEnvelopeList(value);
183
+ i = endIndex;
184
+ }
185
+ else if (keyword.startsWith("BODY[")) {
186
+ // Body text: BODY[TEXT] or BODY[1] etc.
187
+ // Value follows as a literal or quoted string
188
+ if (inner[i] === '"') {
189
+ const { value, endIndex } = parseQuotedString(inner, i);
190
+ result.bodyText = value;
191
+ i = endIndex;
192
+ }
193
+ else if (inner[i] === "{") {
194
+ // Literal: {N}\r\n<data> — in our usage, literals are pre-joined by the client
195
+ // so this appears as {N} followed by the data after client processing
196
+ const braceEnd = inner.indexOf("}", i);
197
+ if (braceEnd !== -1) {
198
+ const size = parseInt(inner.substring(i + 1, braceEnd), 10);
199
+ // Data follows after the closing brace (client pre-processes \r\n)
200
+ const dataStart = braceEnd + 1;
201
+ result.bodyText = inner.substring(dataStart, dataStart + size);
202
+ i = dataStart + size;
203
+ }
204
+ }
205
+ else {
206
+ const { value, endIndex } = parseAtom(inner, i);
207
+ result.bodyText = value === "NIL" ? undefined : value;
208
+ i = endIndex;
209
+ }
210
+ }
211
+ else {
212
+ // Skip unknown data item value
213
+ if (i < inner.length && inner[i] === "(") {
214
+ const { endIndex } = parseParenList(inner, i);
215
+ i = endIndex;
216
+ }
217
+ else if (i < inner.length && inner[i] === '"') {
218
+ const { endIndex } = parseQuotedString(inner, i);
219
+ i = endIndex;
220
+ }
221
+ else if (i < inner.length) {
222
+ const { endIndex } = parseAtom(inner, i);
223
+ i = endIndex;
224
+ }
225
+ }
226
+ }
227
+ return result;
228
+ }
229
+ // --- Envelope parsing ---
230
+ /**
231
+ * Maps a parsed parenthesized list (from ENVELOPE) to a ParsedEnvelope.
232
+ * RFC 3501 §7.4.2: (date subject from sender reply-to to cc bcc in-reply-to message-id)
233
+ */
234
+ function mapEnvelopeList(list) {
235
+ return {
236
+ date: typeof list[0] === "string" ? list[0] : "",
237
+ subject: typeof list[1] === "string" ? decodeRfc2047(list[1]) : "",
238
+ from: parseAddressList(list[2]),
239
+ sender: parseAddressList(list[3]),
240
+ replyTo: parseAddressList(list[4]),
241
+ to: parseAddressList(list[5]),
242
+ cc: parseAddressList(list[6]),
243
+ bcc: parseAddressList(list[7]),
244
+ inReplyTo: typeof list[8] === "string" ? list[8] : "",
245
+ messageId: typeof list[9] === "string" ? list[9] : "",
246
+ };
247
+ }
248
+ /**
249
+ * Parses IMAP address list: ((name adl mailbox host) ...)
250
+ * Each address is (personal-name at-domain-list mailbox host)
251
+ * Email = mailbox@host, display name = personal-name
252
+ */
253
+ function parseAddressList(data) {
254
+ if (!Array.isArray(data))
255
+ return [];
256
+ return data
257
+ .filter((addr) => Array.isArray(addr))
258
+ .map((addr) => {
259
+ const name = typeof addr[0] === "string" ? decodeRfc2047(addr[0]) : "";
260
+ const mailbox = typeof addr[2] === "string" ? addr[2] : "";
261
+ const host = typeof addr[3] === "string" ? addr[3] : "";
262
+ const email = host ? `${mailbox}@${host}` : mailbox;
263
+ return { name, email };
264
+ });
265
+ }
266
+ // --- SEARCH response parsing ---
267
+ /**
268
+ * Parses UIDs from a SEARCH response text.
269
+ * Input: "1 4 9 23" → [1, 4, 9, 23]
270
+ */
271
+ function parseSearchResponse(text) {
272
+ if (!text.trim())
273
+ return [];
274
+ return text
275
+ .trim()
276
+ .split(/\s+/)
277
+ .map((s) => parseInt(s, 10))
278
+ .filter((n) => !isNaN(n));
279
+ }
280
+ // --- LIST response parsing ---
281
+ /**
282
+ * Parses a LIST response line.
283
+ * Format: (flags) "delimiter" "mailbox-name"
284
+ * Input text (after "* LIST"): `(\HasNoChildren) "/" "INBOX"`
285
+ */
286
+ function parseListResponse(text) {
287
+ const trimmed = text.trim();
288
+ if (!trimmed.startsWith("("))
289
+ return null;
290
+ // Parse flags
291
+ const { value: flags, endIndex } = parseParenList(trimmed, 0);
292
+ let i = endIndex;
293
+ while (i < trimmed.length && trimmed[i] === " ")
294
+ i++;
295
+ // Parse delimiter (quoted string or NIL)
296
+ let delimiter = "/";
297
+ if (trimmed[i] === '"') {
298
+ const { value, endIndex: dEnd } = parseQuotedString(trimmed, i);
299
+ delimiter = value;
300
+ i = dEnd;
301
+ }
302
+ else {
303
+ const { value, endIndex: dEnd } = parseAtom(trimmed, i);
304
+ delimiter = value === "NIL" ? "" : value;
305
+ i = dEnd;
306
+ }
307
+ while (i < trimmed.length && trimmed[i] === " ")
308
+ i++;
309
+ // Parse mailbox name (quoted string or atom)
310
+ let name = "";
311
+ if (trimmed[i] === '"') {
312
+ const { value } = parseQuotedString(trimmed, i);
313
+ name = value;
314
+ }
315
+ else {
316
+ const { value } = parseAtom(trimmed, i);
317
+ name = value;
318
+ }
319
+ return { flags: flags, delimiter, name };
320
+ }
321
+ // --- RFC 2047 encoded-word decoding ---
322
+ /**
323
+ * Decodes RFC 2047 encoded words in a string.
324
+ * Format: =?charset?encoding?encoded-text?=
325
+ * Supports B (base64) and Q (quoted-printable) encodings.
326
+ */
327
+ function decodeRfc2047(input) {
328
+ if (!input || !input.includes("=?"))
329
+ return input;
330
+ return input.replace(/=\?([^?]+)\?([BbQq])\?([^?]*)\?=/g, (_match, _charset, encoding, encoded) => {
331
+ try {
332
+ if (encoding.toUpperCase() === "B") {
333
+ return Buffer.from(encoded, "base64").toString("utf-8");
334
+ }
335
+ if (encoding.toUpperCase() === "Q") {
336
+ // Quoted-printable: _ = space, =XX = hex byte
337
+ const decoded = encoded
338
+ .replace(/_/g, " ")
339
+ .replace(/=([0-9A-Fa-f]{2})/g, (_m, hex) => String.fromCharCode(parseInt(hex, 16)));
340
+ return Buffer.from(decoded, "binary").toString("utf-8");
341
+ }
342
+ }
343
+ catch {
344
+ // Fall through to return original
345
+ }
346
+ return encoded;
347
+ });
348
+ }
349
+ //# sourceMappingURL=parser.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"parser.js","sourceRoot":"","sources":["../../src/imap/parser.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":""}
package/dist/index.js ADDED
@@ -0,0 +1,70 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ const mcp_js_1 = require("@modelcontextprotocol/sdk/server/mcp.js");
5
+ const stdio_js_1 = require("@modelcontextprotocol/sdk/server/stdio.js");
6
+ const jmap_js_1 = require("./backends/jmap.js");
7
+ const imap_js_1 = require("./backends/imap.js");
8
+ const register_js_1 = require("./tools/register.js");
9
+ function createBackend() {
10
+ const backendType = process.env.EMAIL_BACKEND ?? "jmap";
11
+ if (backendType === "jmap") {
12
+ const token = process.env.JMAP_TOKEN;
13
+ if (!token) {
14
+ throw new Error("JMAP_TOKEN environment variable is required");
15
+ }
16
+ return new jmap_js_1.JmapBackend({
17
+ token,
18
+ sessionUrl: process.env.JMAP_SESSION_URL,
19
+ });
20
+ }
21
+ if (backendType === "imap") {
22
+ const host = process.env.IMAP_HOST;
23
+ const user = process.env.IMAP_USER;
24
+ const password = process.env.IMAP_PASSWORD;
25
+ if (!host || !user || !password) {
26
+ throw new Error("IMAP_HOST, IMAP_USER, and IMAP_PASSWORD environment variables are required");
27
+ }
28
+ let smtpConfig;
29
+ const smtpHost = process.env.SMTP_HOST;
30
+ if (smtpHost) {
31
+ const smtpUser = process.env.SMTP_USER;
32
+ const smtpPassword = process.env.SMTP_PASSWORD;
33
+ if (!smtpUser || !smtpPassword) {
34
+ throw new Error("SMTP_USER and SMTP_PASSWORD are required when SMTP_HOST is set");
35
+ }
36
+ smtpConfig = {
37
+ host: smtpHost,
38
+ port: parseInt(process.env.SMTP_PORT ?? "587", 10),
39
+ user: smtpUser,
40
+ password: smtpPassword,
41
+ tls: process.env.SMTP_TLS !== "false",
42
+ from: process.env.SMTP_FROM,
43
+ };
44
+ }
45
+ return new imap_js_1.ImapBackend({
46
+ host,
47
+ port: parseInt(process.env.IMAP_PORT ?? "993", 10),
48
+ user,
49
+ password,
50
+ tls: process.env.IMAP_TLS !== "false",
51
+ }, smtpConfig);
52
+ }
53
+ throw new Error(`Unknown backend: ${backendType}`);
54
+ }
55
+ const server = new mcp_js_1.McpServer({
56
+ name: "better-email-mcp",
57
+ version: "0.1.0",
58
+ });
59
+ const backend = createBackend();
60
+ (0, register_js_1.registerEmailTools)(server, backend);
61
+ async function main() {
62
+ await backend.connect();
63
+ const transport = new stdio_js_1.StdioServerTransport();
64
+ await server.connect(transport);
65
+ }
66
+ main().catch((err) => {
67
+ console.error("Fatal error:", err);
68
+ process.exit(1);
69
+ });
70
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,39 @@
1
+ /**
2
+ * Minimal SMTP client using Node's built-in net/tls modules.
3
+ * Supports EHLO, AUTH PLAIN, STARTTLS, and message submission.
4
+ */
5
+ export interface SmtpClientConfig {
6
+ host: string;
7
+ port: number;
8
+ tls: boolean;
9
+ }
10
+ export declare class SmtpError extends Error {
11
+ readonly code: string;
12
+ constructor(code: string, message: string);
13
+ }
14
+ export declare class SmtpClient {
15
+ private socket;
16
+ private host;
17
+ private buffer;
18
+ private capabilities;
19
+ private responseResolve;
20
+ private responseReject;
21
+ private responseLines;
22
+ connect(config: SmtpClientConfig): Promise<void>;
23
+ ehlo(hostname: string): Promise<string[]>;
24
+ startTls(): Promise<void>;
25
+ authPlain(user: string, password: string): Promise<void>;
26
+ mailFrom(address: string): Promise<void>;
27
+ rcptTo(address: string): Promise<void>;
28
+ data(content: string): Promise<void>;
29
+ quit(): Promise<void>;
30
+ disconnect(): void;
31
+ private sendCommand;
32
+ private readResponse;
33
+ private writeRaw;
34
+ private onData;
35
+ private processBuffer;
36
+ private handleLine;
37
+ private destroySocket;
38
+ }
39
+ //# sourceMappingURL=client.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../../src/smtp/client.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAKH,MAAM,WAAW,gBAAgB;IAC/B,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,GAAG,EAAE,OAAO,CAAC;CACd;AAED,qBAAa,SAAU,SAAQ,KAAK;aAEhB,IAAI,EAAE,MAAM;gBAAZ,IAAI,EAAE,MAAM,EAC5B,OAAO,EAAE,MAAM;CAKlB;AAgBD,qBAAa,UAAU;IACrB,OAAO,CAAC,MAAM,CAA2C;IACzD,OAAO,CAAC,IAAI,CAAM;IAClB,OAAO,CAAC,MAAM,CAAM;IACpB,OAAO,CAAC,YAAY,CAAgB;IAEpC,OAAO,CAAC,eAAe,CAA+C;IACtE,OAAO,CAAC,cAAc,CAAuC;IAC7D,OAAO,CAAC,aAAa,CAAgB;IAE/B,OAAO,CAAC,MAAM,EAAE,gBAAgB,GAAG,OAAO,CAAC,IAAI,CAAC;IAuDhD,IAAI,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC;IAMzC,QAAQ,IAAI,OAAO,CAAC,IAAI,CAAC;IA+BzB,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAOxD,QAAQ,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAKxC,MAAM,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAKtC,IAAI,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAkBpC,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IAS3B,UAAU,IAAI,IAAI;YAMJ,WAAW;IAYzB,OAAO,CAAC,YAAY;IAsBpB,OAAO,CAAC,QAAQ;IAOhB,OAAO,CAAC,MAAM;IAKd,OAAO,CAAC,aAAa;IAYrB,OAAO,CAAC,UAAU;IAoBlB,OAAO,CAAC,aAAa;CAQtB"}