read-email-mcp 1.0.0 → 2.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.
- package/LICENSE +21 -21
- package/README.md +153 -34
- package/dist/accounts-cli.d.ts +1 -0
- package/dist/accounts-cli.js +518 -0
- package/dist/accounts-cli.js.map +1 -0
- package/dist/config.d.ts +30 -2
- package/dist/config.js +219 -15
- package/dist/config.js.map +1 -1
- package/dist/imap-discovery.d.ts +52 -0
- package/dist/imap-discovery.js +207 -0
- package/dist/imap-discovery.js.map +1 -0
- package/dist/imap.d.ts +41 -5
- package/dist/imap.js +332 -64
- package/dist/imap.js.map +1 -1
- package/dist/index.js +28 -8
- package/dist/index.js.map +1 -1
- package/dist/providers.d.ts +12 -0
- package/dist/providers.js +122 -0
- package/dist/providers.js.map +1 -0
- package/dist/server.d.ts +3 -6
- package/dist/server.js +10 -8
- package/dist/server.js.map +1 -1
- package/dist/store.d.ts +31 -2
- package/dist/store.js +300 -153
- package/dist/store.js.map +1 -1
- package/dist/tools.d.ts +189 -174
- package/dist/tools.js +714 -60
- package/dist/tools.js.map +1 -1
- package/dist/types.d.ts +44 -1
- package/docs/production-readiness.md +84 -70
- package/package.json +10 -9
- package/scripts/smoke-mcp.mjs +8 -1
package/dist/config.js
CHANGED
|
@@ -1,8 +1,13 @@
|
|
|
1
1
|
import crypto from "node:crypto";
|
|
2
|
+
import { execSync } from "node:child_process";
|
|
3
|
+
import fs from "node:fs";
|
|
2
4
|
import os from "node:os";
|
|
3
5
|
import path from "node:path";
|
|
6
|
+
import { detectProvider, findProvider, PROVIDER_PRESETS } from "./providers.js";
|
|
4
7
|
export const DEFAULT_IMAP_PORT = 993;
|
|
5
8
|
export const DEFAULT_IMAP_SECURE = true;
|
|
9
|
+
export const DEFAULT_ACCOUNTS_FILENAME = "accounts.json";
|
|
10
|
+
export const DEFAULT_ENV_FILENAME = ".env";
|
|
6
11
|
export function hashAccount(email) {
|
|
7
12
|
return crypto
|
|
8
13
|
.createHash("sha256")
|
|
@@ -10,8 +15,64 @@ export function hashAccount(email) {
|
|
|
10
15
|
.digest("hex")
|
|
11
16
|
.slice(0, 16);
|
|
12
17
|
}
|
|
18
|
+
export function defaultAccountsPath(baseDir) {
|
|
19
|
+
return path.join(baseDir, DEFAULT_ACCOUNTS_FILENAME);
|
|
20
|
+
}
|
|
13
21
|
export function loadConfig(env = process.env, options = {}) {
|
|
14
22
|
const args = options.args ?? process.argv.slice(2);
|
|
23
|
+
const baseDir = options.dataDir ?? path.join(os.homedir(), ".read-email-mcp");
|
|
24
|
+
loadEnvFiles(env, args, baseDir);
|
|
25
|
+
const explicitAccountsFile = getArgValue(args, "--accounts") ?? env.ACCOUNTS_FILE;
|
|
26
|
+
const legacyEmail = getArgValue(args, "--email") ?? env.EMAIL;
|
|
27
|
+
const defaultFile = defaultAccountsPath(baseDir);
|
|
28
|
+
const accountsFile = explicitAccountsFile ?? (!legacyEmail && fs.existsSync(defaultFile) ? defaultFile : undefined);
|
|
29
|
+
const accounts = accountsFile
|
|
30
|
+
? loadAccountsFile(accountsFile, env, baseDir)
|
|
31
|
+
: [loadSingleAccount(env, args, baseDir)];
|
|
32
|
+
assertUniqueAccounts(accounts);
|
|
33
|
+
return { accounts, baseDir };
|
|
34
|
+
}
|
|
35
|
+
function loadEnvFiles(env, args, baseDir) {
|
|
36
|
+
const explicit = getArgValue(args, "--env-file") ?? env.ENV_FILE;
|
|
37
|
+
if (explicit) {
|
|
38
|
+
applyEnvFile(path.resolve(explicit), env, true);
|
|
39
|
+
return;
|
|
40
|
+
}
|
|
41
|
+
applyEnvFile(path.join(process.cwd(), DEFAULT_ENV_FILENAME), env, false);
|
|
42
|
+
applyEnvFile(path.join(baseDir, DEFAULT_ENV_FILENAME), env, false);
|
|
43
|
+
}
|
|
44
|
+
function applyEnvFile(filePath, env, required) {
|
|
45
|
+
let contents;
|
|
46
|
+
try {
|
|
47
|
+
contents = fs.readFileSync(filePath, "utf8");
|
|
48
|
+
}
|
|
49
|
+
catch (error) {
|
|
50
|
+
if (required) {
|
|
51
|
+
throw new Error(`Could not read env file ${filePath}: ${error instanceof Error ? error.message : String(error)}`);
|
|
52
|
+
}
|
|
53
|
+
return;
|
|
54
|
+
}
|
|
55
|
+
for (const line of contents.split(/\r?\n/)) {
|
|
56
|
+
const trimmed = line.trim();
|
|
57
|
+
if (!trimmed || trimmed.startsWith("#")) {
|
|
58
|
+
continue;
|
|
59
|
+
}
|
|
60
|
+
const match = /^(?:export\s+)?([A-Za-z_][A-Za-z0-9_.]*)\s*=\s*(.*)$/.exec(trimmed);
|
|
61
|
+
if (!match) {
|
|
62
|
+
continue;
|
|
63
|
+
}
|
|
64
|
+
const key = match[1];
|
|
65
|
+
let value = match[2].trim();
|
|
66
|
+
const quote = value[0];
|
|
67
|
+
if ((quote === '"' || quote === "'") && value.endsWith(quote) && value.length >= 2) {
|
|
68
|
+
value = value.slice(1, -1);
|
|
69
|
+
}
|
|
70
|
+
if (env[key] === undefined) {
|
|
71
|
+
env[key] = value;
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
function loadSingleAccount(env, args, baseDir) {
|
|
15
76
|
const argEmail = getArgValue(args, "--email");
|
|
16
77
|
const argPassword = getArgValue(args, "--password");
|
|
17
78
|
const argImapHost = getArgValue(args, "--imap-host");
|
|
@@ -26,39 +87,182 @@ export function loadConfig(env = process.env, options = {}) {
|
|
|
26
87
|
if (!password) {
|
|
27
88
|
throw new Error("Missing required credential: provide --password or PASSWORD");
|
|
28
89
|
}
|
|
29
|
-
const
|
|
90
|
+
const detected = detectProvider(email);
|
|
91
|
+
const host = (argImapHost ?? env.IMAP_HOST)?.trim() ?? detected?.imapHost;
|
|
30
92
|
if (!host) {
|
|
31
|
-
throw new Error(
|
|
93
|
+
throw new Error(`Missing required IMAP setting: provide --imap-host or IMAP_HOST (for example imap.gmail.com). ` +
|
|
94
|
+
`No provider preset matched the domain of ${email}.`);
|
|
32
95
|
}
|
|
33
|
-
const port = parsePort(argImapPort ?? env.IMAP_PORT ?? DEFAULT_IMAP_PORT);
|
|
34
|
-
const secure = parseBoolean(argImapSecure ?? env.IMAP_SECURE, DEFAULT_IMAP_SECURE);
|
|
96
|
+
const port = parsePort(argImapPort ?? env.IMAP_PORT ?? detected?.imapPort ?? DEFAULT_IMAP_PORT);
|
|
97
|
+
const secure = parseBoolean(argImapSecure ?? env.IMAP_SECURE, detected?.imapSecure ?? DEFAULT_IMAP_SECURE);
|
|
35
98
|
const customImapUser = argImapUser ?? env.IMAP_USER;
|
|
36
99
|
const authUser = customImapUser && customImapUser.trim() ? customImapUser.trim() : email;
|
|
37
|
-
const
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
100
|
+
const tlsRejectUnauthorized = parseBoolean(env.IMAP_TLS_REJECT_UNAUTHORIZED, true);
|
|
101
|
+
return buildAccountConfig({
|
|
102
|
+
name: email,
|
|
103
|
+
email,
|
|
104
|
+
password,
|
|
105
|
+
host,
|
|
106
|
+
port,
|
|
107
|
+
secure,
|
|
108
|
+
authUser,
|
|
109
|
+
baseDir,
|
|
110
|
+
provider: detectProvider(email)?.id ?? null,
|
|
111
|
+
groups: [],
|
|
112
|
+
tlsRejectUnauthorized
|
|
113
|
+
});
|
|
114
|
+
}
|
|
115
|
+
function loadAccountsFile(filePath, env, baseDir) {
|
|
116
|
+
const resolved = path.resolve(filePath);
|
|
117
|
+
let parsed;
|
|
118
|
+
try {
|
|
119
|
+
parsed = JSON.parse(fs.readFileSync(resolved, "utf8"));
|
|
120
|
+
}
|
|
121
|
+
catch (error) {
|
|
122
|
+
throw new Error(`Could not read accounts file ${resolved}: ${error instanceof Error ? error.message : String(error)}`);
|
|
123
|
+
}
|
|
124
|
+
if (!Array.isArray(parsed.accounts) || parsed.accounts.length === 0) {
|
|
125
|
+
throw new Error(`Accounts file ${resolved} must contain a non-empty "accounts" array`);
|
|
126
|
+
}
|
|
127
|
+
return parsed.accounts.map((entry, index) => {
|
|
128
|
+
const label = entry.name ?? entry.email ?? `account #${index + 1}`;
|
|
129
|
+
const email = entry.email?.trim().toLowerCase();
|
|
130
|
+
if (!email) {
|
|
131
|
+
throw new Error(`Accounts file ${resolved}: ${label} is missing "email"`);
|
|
132
|
+
}
|
|
133
|
+
const preset = resolvePreset(entry, resolved, label);
|
|
134
|
+
const password = resolvePassword(entry, env, resolved, label);
|
|
135
|
+
const host = entry.imapHost?.trim() ?? preset?.imapHost;
|
|
136
|
+
if (!host) {
|
|
137
|
+
throw new Error(`Accounts file ${resolved}: ${label} is missing "imapHost" and no provider preset matched ` +
|
|
138
|
+
`(set "provider" to one of: ${PROVIDER_PRESETS.map((p) => p.id).join(", ")}, or provide "imapHost")`);
|
|
139
|
+
}
|
|
140
|
+
const port = parsePort(entry.imapPort ?? preset?.imapPort ?? DEFAULT_IMAP_PORT);
|
|
141
|
+
const secure = typeof entry.imapSecure === "boolean"
|
|
142
|
+
? entry.imapSecure
|
|
143
|
+
: parseBoolean(entry.imapSecure, preset?.imapSecure ?? DEFAULT_IMAP_SECURE);
|
|
144
|
+
const authUser = entry.imapUser?.trim() ? entry.imapUser.trim() : email;
|
|
145
|
+
const tlsRejectUnauthorized = typeof entry.imapTlsRejectUnauthorized === "boolean"
|
|
146
|
+
? entry.imapTlsRejectUnauthorized
|
|
147
|
+
: parseBoolean(entry.imapTlsRejectUnauthorized, true);
|
|
148
|
+
return buildAccountConfig({
|
|
149
|
+
name: entry.name?.trim() || email,
|
|
42
150
|
email,
|
|
43
|
-
|
|
44
|
-
},
|
|
45
|
-
imap: {
|
|
151
|
+
password,
|
|
46
152
|
host,
|
|
47
153
|
port,
|
|
48
154
|
secure,
|
|
155
|
+
authUser,
|
|
156
|
+
baseDir,
|
|
157
|
+
provider: preset?.id ?? null,
|
|
158
|
+
groups: normalizeGroups(entry.groups),
|
|
159
|
+
tlsRejectUnauthorized
|
|
160
|
+
});
|
|
161
|
+
});
|
|
162
|
+
}
|
|
163
|
+
function resolvePreset(entry, filePath, label) {
|
|
164
|
+
if (entry.provider) {
|
|
165
|
+
const preset = findProvider(entry.provider);
|
|
166
|
+
if (!preset) {
|
|
167
|
+
throw new Error(`Accounts file ${filePath}: ${label} has unknown provider "${entry.provider}". ` +
|
|
168
|
+
`Known providers: ${PROVIDER_PRESETS.map((p) => p.id).join(", ")}`);
|
|
169
|
+
}
|
|
170
|
+
return preset;
|
|
171
|
+
}
|
|
172
|
+
return detectProvider(entry.email ?? "");
|
|
173
|
+
}
|
|
174
|
+
function normalizeGroups(groups) {
|
|
175
|
+
if (!Array.isArray(groups)) {
|
|
176
|
+
return [];
|
|
177
|
+
}
|
|
178
|
+
return [...new Set(groups.map((group) => String(group).trim().toLowerCase()).filter(Boolean))];
|
|
179
|
+
}
|
|
180
|
+
export function resolvePassword(entry, env, filePath, label) {
|
|
181
|
+
if (entry.passwordEnv) {
|
|
182
|
+
const password = env[entry.passwordEnv];
|
|
183
|
+
if (!password) {
|
|
184
|
+
throw new Error(`Accounts file ${filePath}: ${label} references passwordEnv "${entry.passwordEnv}" but that environment variable is not set`);
|
|
185
|
+
}
|
|
186
|
+
return password;
|
|
187
|
+
}
|
|
188
|
+
if (entry.passwordCommand) {
|
|
189
|
+
return runPasswordCommand(entry.passwordCommand, filePath, label);
|
|
190
|
+
}
|
|
191
|
+
if (entry.password) {
|
|
192
|
+
return entry.password;
|
|
193
|
+
}
|
|
194
|
+
throw new Error(`Accounts file ${filePath}: ${label} needs one of "passwordEnv" (env var name), ` +
|
|
195
|
+
`"passwordCommand" (shell command that prints the password), or "password" (inline, discouraged)`);
|
|
196
|
+
}
|
|
197
|
+
function runPasswordCommand(command, filePath, label) {
|
|
198
|
+
let output;
|
|
199
|
+
try {
|
|
200
|
+
output = execSync(command, {
|
|
201
|
+
encoding: "utf8",
|
|
202
|
+
timeout: 15_000,
|
|
203
|
+
windowsHide: true,
|
|
204
|
+
stdio: ["ignore", "pipe", "pipe"],
|
|
205
|
+
maxBuffer: 64 * 1024
|
|
206
|
+
});
|
|
207
|
+
}
|
|
208
|
+
catch (error) {
|
|
209
|
+
throw new Error(`Accounts file ${filePath}: ${label} passwordCommand failed: ` +
|
|
210
|
+
`${error instanceof Error ? error.message : String(error)}`);
|
|
211
|
+
}
|
|
212
|
+
const password = output
|
|
213
|
+
.split(/\r?\n/)
|
|
214
|
+
.map((line) => line.trim())
|
|
215
|
+
.find((line) => line.length > 0);
|
|
216
|
+
if (!password) {
|
|
217
|
+
throw new Error(`Accounts file ${filePath}: ${label} passwordCommand produced no output`);
|
|
218
|
+
}
|
|
219
|
+
return password;
|
|
220
|
+
}
|
|
221
|
+
function buildAccountConfig(input) {
|
|
222
|
+
const accountHash = hashAccount(input.email);
|
|
223
|
+
const accountDir = path.join(input.baseDir, accountHash);
|
|
224
|
+
return {
|
|
225
|
+
account: {
|
|
226
|
+
name: input.name,
|
|
227
|
+
email: input.email,
|
|
228
|
+
accountHash,
|
|
229
|
+
provider: input.provider,
|
|
230
|
+
groups: input.groups
|
|
231
|
+
},
|
|
232
|
+
imap: {
|
|
233
|
+
host: input.host,
|
|
234
|
+
port: input.port,
|
|
235
|
+
secure: input.secure,
|
|
236
|
+
...(input.tlsRejectUnauthorized ? {} : { tls: { rejectUnauthorized: false } }),
|
|
49
237
|
auth: {
|
|
50
|
-
user: authUser,
|
|
51
|
-
pass: password
|
|
238
|
+
user: input.authUser,
|
|
239
|
+
pass: input.password
|
|
52
240
|
}
|
|
53
241
|
},
|
|
54
242
|
storage: {
|
|
55
|
-
baseDir,
|
|
243
|
+
baseDir: input.baseDir,
|
|
56
244
|
accountDir,
|
|
57
245
|
databasePath: path.join(accountDir, "emails.sqlite"),
|
|
58
246
|
rawDir: path.join(accountDir, "raw")
|
|
59
247
|
}
|
|
60
248
|
};
|
|
61
249
|
}
|
|
250
|
+
function assertUniqueAccounts(accounts) {
|
|
251
|
+
const names = new Set();
|
|
252
|
+
const emails = new Set();
|
|
253
|
+
for (const account of accounts) {
|
|
254
|
+
const name = account.account.name.toLowerCase();
|
|
255
|
+
const email = account.account.email;
|
|
256
|
+
if (names.has(name)) {
|
|
257
|
+
throw new Error(`Duplicate account name "${account.account.name}" — account names must be unique`);
|
|
258
|
+
}
|
|
259
|
+
if (emails.has(email)) {
|
|
260
|
+
throw new Error(`Duplicate account email "${email}" — each account needs a distinct email address`);
|
|
261
|
+
}
|
|
262
|
+
names.add(name);
|
|
263
|
+
emails.add(email);
|
|
264
|
+
}
|
|
265
|
+
}
|
|
62
266
|
function parsePort(value) {
|
|
63
267
|
if (value === undefined || value === "") {
|
|
64
268
|
return DEFAULT_IMAP_PORT;
|
package/dist/config.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
import { type ProviderPreset } from "./providers.js";
|
|
2
|
+
export interface DiscoveredImap {
|
|
3
|
+
host: string;
|
|
4
|
+
port: number;
|
|
5
|
+
secure: boolean;
|
|
6
|
+
user: string | null;
|
|
7
|
+
providerId: string | null;
|
|
8
|
+
source: "autoconfig" | "dns-srv" | "mx" | "guess";
|
|
9
|
+
}
|
|
10
|
+
export interface DiscoveryDeps {
|
|
11
|
+
resolveSrv: (name: string) => Promise<Array<{
|
|
12
|
+
name: string;
|
|
13
|
+
port: number;
|
|
14
|
+
priority: number;
|
|
15
|
+
weight: number;
|
|
16
|
+
}>>;
|
|
17
|
+
resolveMx: (domain: string) => Promise<Array<{
|
|
18
|
+
exchange: string;
|
|
19
|
+
priority: number;
|
|
20
|
+
}>>;
|
|
21
|
+
fetchText: (url: string) => Promise<string>;
|
|
22
|
+
probeTcp: (host: string, port: number) => Promise<boolean>;
|
|
23
|
+
lookupProvider: (id: string) => ProviderPreset | null;
|
|
24
|
+
}
|
|
25
|
+
/**
|
|
26
|
+
* Parse a Mozilla autoconfig XML document for the first IMAP incomingServer
|
|
27
|
+
* block. Returns null when no usable IMAP section is present.
|
|
28
|
+
*/
|
|
29
|
+
export declare function parseAutoconfigXml(xml: string, email: string): {
|
|
30
|
+
host: string;
|
|
31
|
+
port: number;
|
|
32
|
+
secure: boolean;
|
|
33
|
+
user: string | null;
|
|
34
|
+
} | null;
|
|
35
|
+
/**
|
|
36
|
+
* Infer a known provider from a domain's MX records. Returns the preset when
|
|
37
|
+
* the mail is actually hosted by Gmail, Microsoft 365, etc.
|
|
38
|
+
*/
|
|
39
|
+
export declare function inferProviderFromMx(mxHosts: string[], lookupProvider?: (id: string) => ProviderPreset | null): ProviderPreset | null;
|
|
40
|
+
/**
|
|
41
|
+
* Best-effort IMAP settings discovery for an email address whose domain has no
|
|
42
|
+
* preset. Order: Mozilla autoconfig, DNS SRV (RFC 6186), MX-based provider
|
|
43
|
+
* inference, then probing imap./mail. hostnames. Returns null on total failure.
|
|
44
|
+
* Never throws — every step fails soft.
|
|
45
|
+
*/
|
|
46
|
+
export declare function discoverImapSettings(email: string, deps?: Partial<DiscoveryDeps>): Promise<DiscoveredImap | null>;
|
|
47
|
+
/**
|
|
48
|
+
* True when an IMAP/TLS failure looks like a self-signed or otherwise
|
|
49
|
+
* unverifiable certificate — the case where imapTlsRejectUnauthorized: false
|
|
50
|
+
* is the fix.
|
|
51
|
+
*/
|
|
52
|
+
export declare function isSelfSignedCertError(message: string): boolean;
|
|
@@ -0,0 +1,207 @@
|
|
|
1
|
+
import dns from "node:dns/promises";
|
|
2
|
+
import net from "node:net";
|
|
3
|
+
import { findProvider } from "./providers.js";
|
|
4
|
+
const DISCOVERY_TIMEOUT_MS = 3_000;
|
|
5
|
+
const PROBE_TIMEOUT_MS = 2_500;
|
|
6
|
+
// MX hostname suffixes that reveal the real provider behind a custom domain
|
|
7
|
+
// (e.g. a company domain hosted on Google Workspace or Microsoft 365).
|
|
8
|
+
const MX_PROVIDER_SUFFIXES = [
|
|
9
|
+
{ suffix: ".google.com", provider: "gmail" },
|
|
10
|
+
{ suffix: ".googlemail.com", provider: "gmail" },
|
|
11
|
+
{ suffix: ".outlook.com", provider: "outlook" },
|
|
12
|
+
{ suffix: ".protection.outlook.com", provider: "outlook" },
|
|
13
|
+
{ suffix: ".yahoodns.net", provider: "yahoo" },
|
|
14
|
+
{ suffix: ".aol.com", provider: "aol" },
|
|
15
|
+
{ suffix: ".mail.icloud.com", provider: "icloud" },
|
|
16
|
+
{ suffix: ".icloud.com", provider: "icloud" },
|
|
17
|
+
{ suffix: ".messagingengine.com", provider: "fastmail" },
|
|
18
|
+
{ suffix: ".zoho.com", provider: "zoho" },
|
|
19
|
+
{ suffix: ".zoho.eu", provider: "zoho" },
|
|
20
|
+
{ suffix: ".gmx.net", provider: "gmx" },
|
|
21
|
+
{ suffix: ".gmx.com", provider: "gmx" },
|
|
22
|
+
{ suffix: ".protonmail.ch", provider: "proton" },
|
|
23
|
+
{ suffix: ".protonmail.com", provider: "proton" },
|
|
24
|
+
{ suffix: ".yandex.net", provider: "yandex" },
|
|
25
|
+
{ suffix: ".yandex.ru", provider: "yandex" },
|
|
26
|
+
{ suffix: ".mail.com", provider: "mailcom" }
|
|
27
|
+
];
|
|
28
|
+
function defaultDeps() {
|
|
29
|
+
return {
|
|
30
|
+
resolveSrv: (name) => dns.resolveSrv(name),
|
|
31
|
+
resolveMx: (domain) => dns.resolveMx(domain),
|
|
32
|
+
fetchText: async (url) => {
|
|
33
|
+
const response = await fetch(url, {
|
|
34
|
+
signal: AbortSignal.timeout(DISCOVERY_TIMEOUT_MS),
|
|
35
|
+
redirect: "follow"
|
|
36
|
+
});
|
|
37
|
+
if (!response.ok) {
|
|
38
|
+
throw new Error(`HTTP ${response.status}`);
|
|
39
|
+
}
|
|
40
|
+
return response.text();
|
|
41
|
+
},
|
|
42
|
+
probeTcp: (host, port) => new Promise((resolve) => {
|
|
43
|
+
const socket = net.connect({ host, port, timeout: PROBE_TIMEOUT_MS });
|
|
44
|
+
socket.once("connect", () => {
|
|
45
|
+
socket.destroy();
|
|
46
|
+
resolve(true);
|
|
47
|
+
});
|
|
48
|
+
socket.once("timeout", () => {
|
|
49
|
+
socket.destroy();
|
|
50
|
+
resolve(false);
|
|
51
|
+
});
|
|
52
|
+
socket.once("error", () => resolve(false));
|
|
53
|
+
}),
|
|
54
|
+
lookupProvider: findProvider
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
function withTimeout(promise, ms) {
|
|
58
|
+
return Promise.race([
|
|
59
|
+
promise,
|
|
60
|
+
new Promise((_resolve, reject) => setTimeout(() => reject(new Error("timed out")), ms))
|
|
61
|
+
]);
|
|
62
|
+
}
|
|
63
|
+
/**
|
|
64
|
+
* Parse a Mozilla autoconfig XML document for the first IMAP incomingServer
|
|
65
|
+
* block. Returns null when no usable IMAP section is present.
|
|
66
|
+
*/
|
|
67
|
+
export function parseAutoconfigXml(xml, email) {
|
|
68
|
+
const serverBlock = /<incomingServer\s+type="imap"[^>]*>([\s\S]*?)<\/incomingServer>/i.exec(xml) ??
|
|
69
|
+
// Some files omit the type attribute ordering or use single quotes.
|
|
70
|
+
/<incomingServer[^>]*type=["']imap["'][^>]*>([\s\S]*?)<\/incomingServer>/i.exec(xml);
|
|
71
|
+
if (!serverBlock) {
|
|
72
|
+
return null;
|
|
73
|
+
}
|
|
74
|
+
const block = serverBlock[1];
|
|
75
|
+
const text = (tag) => new RegExp(`<${tag}>([^<]+)</${tag}>`, "i").exec(block)?.[1]?.trim() ?? null;
|
|
76
|
+
const host = text("hostname");
|
|
77
|
+
if (!host) {
|
|
78
|
+
return null;
|
|
79
|
+
}
|
|
80
|
+
const port = Number(text("port") ?? "993");
|
|
81
|
+
const socketType = (text("socketType") ?? "SSL").toUpperCase();
|
|
82
|
+
const secure = socketType !== "STARTTLS" && socketType !== "PLAIN";
|
|
83
|
+
const rawUser = text("username");
|
|
84
|
+
const localpart = email.split("@")[0] ?? email;
|
|
85
|
+
const user = rawUser === null || rawUser === "%EMAILADDRESS%"
|
|
86
|
+
? null // null means "use the full email address" (the default)
|
|
87
|
+
: rawUser === "%EMAILLOCALPART%"
|
|
88
|
+
? localpart
|
|
89
|
+
: rawUser.replace(/%EMAILADDRESS%/g, email).replace(/%EMAILLOCALPART%/g, localpart);
|
|
90
|
+
return { host, port: Number.isInteger(port) && port > 0 ? port : 993, secure, user };
|
|
91
|
+
}
|
|
92
|
+
/**
|
|
93
|
+
* Infer a known provider from a domain's MX records. Returns the preset when
|
|
94
|
+
* the mail is actually hosted by Gmail, Microsoft 365, etc.
|
|
95
|
+
*/
|
|
96
|
+
export function inferProviderFromMx(mxHosts, lookupProvider = findProvider) {
|
|
97
|
+
for (const host of mxHosts) {
|
|
98
|
+
const normalized = host.trim().toLowerCase().replace(/\.$/, "");
|
|
99
|
+
for (const { suffix, provider } of MX_PROVIDER_SUFFIXES) {
|
|
100
|
+
if (normalized.endsWith(suffix) || normalized === suffix.slice(1)) {
|
|
101
|
+
return lookupProvider(provider);
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
return null;
|
|
106
|
+
}
|
|
107
|
+
/**
|
|
108
|
+
* Best-effort IMAP settings discovery for an email address whose domain has no
|
|
109
|
+
* preset. Order: Mozilla autoconfig, DNS SRV (RFC 6186), MX-based provider
|
|
110
|
+
* inference, then probing imap./mail. hostnames. Returns null on total failure.
|
|
111
|
+
* Never throws — every step fails soft.
|
|
112
|
+
*/
|
|
113
|
+
export async function discoverImapSettings(email, deps = {}) {
|
|
114
|
+
const domain = email.split("@")[1]?.trim().toLowerCase();
|
|
115
|
+
if (!domain) {
|
|
116
|
+
return null;
|
|
117
|
+
}
|
|
118
|
+
const { resolveSrv, resolveMx, fetchText, probeTcp, lookupProvider } = { ...defaultDeps(), ...deps };
|
|
119
|
+
// 1. Mozilla autoconfig (what Thunderbird uses; cPanel/Dovecot publish it).
|
|
120
|
+
const autoconfigUrls = [
|
|
121
|
+
`https://autoconfig.${domain}/mail/config-v1.3.xml?emailaddress=${encodeURIComponent(email)}`,
|
|
122
|
+
`https://${domain}/.well-known/autoconfig/mail/config-v1.3.xml`,
|
|
123
|
+
`https://autoconfig.thunderbird.net/v1.3/${domain}`
|
|
124
|
+
];
|
|
125
|
+
for (const url of autoconfigUrls) {
|
|
126
|
+
try {
|
|
127
|
+
const xml = await fetchText(url);
|
|
128
|
+
const parsed = parseAutoconfigXml(xml, email);
|
|
129
|
+
if (parsed) {
|
|
130
|
+
return { ...parsed, providerId: null, source: "autoconfig" };
|
|
131
|
+
}
|
|
132
|
+
}
|
|
133
|
+
catch {
|
|
134
|
+
// try the next URL
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
// 2. DNS SRV (RFC 6186): _imaps._tcp for TLS, _imap._tcp for STARTTLS.
|
|
138
|
+
const srvAttempts = [
|
|
139
|
+
{ name: `_imaps._tcp.${domain}`, secure: true },
|
|
140
|
+
{ name: `_imap._tcp.${domain}`, secure: false }
|
|
141
|
+
];
|
|
142
|
+
for (const attempt of srvAttempts) {
|
|
143
|
+
try {
|
|
144
|
+
const records = await withTimeout(resolveSrv(attempt.name), DISCOVERY_TIMEOUT_MS);
|
|
145
|
+
const best = records
|
|
146
|
+
.slice()
|
|
147
|
+
.sort((a, b) => a.priority - b.priority || b.weight - a.weight)[0];
|
|
148
|
+
if (best?.name && best.name !== ".") {
|
|
149
|
+
return {
|
|
150
|
+
host: best.name.replace(/\.$/, ""),
|
|
151
|
+
port: best.port,
|
|
152
|
+
secure: attempt.secure,
|
|
153
|
+
user: null,
|
|
154
|
+
providerId: null,
|
|
155
|
+
source: "dns-srv"
|
|
156
|
+
};
|
|
157
|
+
}
|
|
158
|
+
}
|
|
159
|
+
catch {
|
|
160
|
+
// no SRV record — continue
|
|
161
|
+
}
|
|
162
|
+
}
|
|
163
|
+
// 3. MX inference: a custom domain hosted on Google Workspace/M365 still
|
|
164
|
+
// answers IMAP via the provider's servers.
|
|
165
|
+
try {
|
|
166
|
+
const mxRecords = await withTimeout(resolveMx(domain), DISCOVERY_TIMEOUT_MS);
|
|
167
|
+
const preset = inferProviderFromMx(mxRecords.map((record) => record.exchange), lookupProvider);
|
|
168
|
+
if (preset) {
|
|
169
|
+
return {
|
|
170
|
+
host: preset.imapHost,
|
|
171
|
+
port: preset.imapPort,
|
|
172
|
+
secure: preset.imapSecure,
|
|
173
|
+
user: null,
|
|
174
|
+
providerId: preset.id,
|
|
175
|
+
source: "mx"
|
|
176
|
+
};
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
catch {
|
|
180
|
+
// no MX — continue
|
|
181
|
+
}
|
|
182
|
+
// 4. Guess-and-probe: imap./mail. subdomains on the standard ports.
|
|
183
|
+
const candidates = [
|
|
184
|
+
{ host: `imap.${domain}`, port: 993, secure: true },
|
|
185
|
+
{ host: `mail.${domain}`, port: 993, secure: true },
|
|
186
|
+
{ host: `imap.${domain}`, port: 143, secure: false },
|
|
187
|
+
{ host: `mail.${domain}`, port: 143, secure: false }
|
|
188
|
+
];
|
|
189
|
+
const probes = await Promise.all(candidates.map(async (candidate) => ({
|
|
190
|
+
candidate,
|
|
191
|
+
open: await probeTcp(candidate.host, candidate.port)
|
|
192
|
+
})));
|
|
193
|
+
const hit = probes.find((probe) => probe.open)?.candidate;
|
|
194
|
+
if (hit) {
|
|
195
|
+
return { host: hit.host, port: hit.port, secure: hit.secure, user: null, providerId: null, source: "guess" };
|
|
196
|
+
}
|
|
197
|
+
return null;
|
|
198
|
+
}
|
|
199
|
+
/**
|
|
200
|
+
* True when an IMAP/TLS failure looks like a self-signed or otherwise
|
|
201
|
+
* unverifiable certificate — the case where imapTlsRejectUnauthorized: false
|
|
202
|
+
* is the fix.
|
|
203
|
+
*/
|
|
204
|
+
export function isSelfSignedCertError(message) {
|
|
205
|
+
return /self[- ]signed|DEPTH_ZERO_SELF_SIGNED|SELF_SIGNED_CERT_IN_CHAIN|UNABLE_TO_VERIFY_LEAF|unable to verify|certificate verify|CERT_HAS_EXPIRED|ERR_TLS_CERT/i.test(message);
|
|
206
|
+
}
|
|
207
|
+
//# sourceMappingURL=imap-discovery.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"imap-discovery.js","sourceRoot":"","sources":["../src/imap-discovery.ts"],"names":[],"mappings":"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"}
|
package/dist/imap.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { AccountConfig } from "./config.js";
|
|
2
2
|
import type { EmailStore } from "./store.js";
|
|
3
|
-
import type { SyncResultRecord } from "./types.js";
|
|
3
|
+
import type { ImapSearchCriteria, SyncResultRecord } from "./types.js";
|
|
4
4
|
export interface ImapMailboxInfo {
|
|
5
5
|
path: string;
|
|
6
6
|
delimiter?: string;
|
|
@@ -8,7 +8,7 @@ export interface ImapMailboxInfo {
|
|
|
8
8
|
}
|
|
9
9
|
export interface ImapFetchMessage {
|
|
10
10
|
uid: number;
|
|
11
|
-
source
|
|
11
|
+
source?: Buffer | Uint8Array | string;
|
|
12
12
|
internalDate?: Date | string;
|
|
13
13
|
flags?: Iterable<string>;
|
|
14
14
|
size?: number;
|
|
@@ -33,28 +33,64 @@ export interface ImapClientLike {
|
|
|
33
33
|
release(): void;
|
|
34
34
|
}>;
|
|
35
35
|
fetch(range: string, query?: unknown, options?: unknown): AsyncIterable<ImapFetchMessage>;
|
|
36
|
+
search?(query: Record<string, unknown>, options?: {
|
|
37
|
+
uid?: boolean;
|
|
38
|
+
}): Promise<number[] | false | Iterable<number>> | AsyncIterable<number> | Iterable<number>;
|
|
36
39
|
}
|
|
37
|
-
export type ImapClientFactory = (config:
|
|
40
|
+
export type ImapClientFactory = (config: AccountConfig["imap"]) => ImapClientLike;
|
|
38
41
|
export interface EmailSyncServiceOptions {
|
|
39
|
-
imap:
|
|
42
|
+
imap: AccountConfig["imap"];
|
|
40
43
|
rawDir: string;
|
|
41
44
|
store: EmailStore;
|
|
42
45
|
clientFactory?: ImapClientFactory;
|
|
43
46
|
}
|
|
44
47
|
export interface SyncOptions {
|
|
45
48
|
mailbox?: string;
|
|
49
|
+
mailboxes?: string[];
|
|
50
|
+
excludeMailboxes?: string[];
|
|
51
|
+
excludeFlags?: string[];
|
|
46
52
|
limit?: number;
|
|
47
53
|
since?: string;
|
|
54
|
+
uids?: string;
|
|
55
|
+
search?: ImapSearchCriteria;
|
|
56
|
+
refreshFlags?: boolean;
|
|
57
|
+
pruneExpunged?: boolean;
|
|
58
|
+
resetMailbox?: boolean;
|
|
59
|
+
}
|
|
60
|
+
export interface MailboxSyncError {
|
|
61
|
+
mailbox: string;
|
|
62
|
+
message: string;
|
|
63
|
+
}
|
|
64
|
+
export interface ConnectivityResult {
|
|
65
|
+
ok: boolean;
|
|
66
|
+
host: string;
|
|
67
|
+
mailboxCount: number;
|
|
68
|
+
mailboxes: string[];
|
|
69
|
+
error?: string;
|
|
48
70
|
}
|
|
49
71
|
export interface SyncResult extends SyncResultRecord {
|
|
72
|
+
mode: "incremental" | "targeted";
|
|
50
73
|
mailboxes: string[];
|
|
74
|
+
refreshedFlags: number;
|
|
75
|
+
prunedMessages: number;
|
|
76
|
+
errors: MailboxSyncError[];
|
|
51
77
|
}
|
|
52
78
|
export declare class EmailSyncService {
|
|
53
79
|
private readonly options;
|
|
54
80
|
private readonly clientFactory;
|
|
55
81
|
constructor(options: EmailSyncServiceOptions);
|
|
82
|
+
check(): Promise<ConnectivityResult>;
|
|
56
83
|
sync(syncOptions?: SyncOptions): Promise<SyncResult>;
|
|
84
|
+
private buildResult;
|
|
57
85
|
private selectMailboxes;
|
|
58
86
|
private syncMailbox;
|
|
87
|
+
private syncIncremental;
|
|
88
|
+
private syncTargeted;
|
|
89
|
+
private resolveTargetUids;
|
|
90
|
+
private runServerSideSearch;
|
|
91
|
+
private ingestFetched;
|
|
92
|
+
private refreshMailboxFlags;
|
|
59
93
|
private writeRawEmail;
|
|
94
|
+
private removeRawFiles;
|
|
60
95
|
}
|
|
96
|
+
export declare function checkConnectivity(imap: AccountConfig["imap"], clientFactory?: ImapClientFactory): Promise<ConnectivityResult>;
|