@mikkelscheike/email-provider-links 1.7.0 → 1.8.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/README.md +106 -99
- package/dist/alias-detection.d.ts +30 -47
- package/dist/alias-detection.js +29 -104
- package/dist/api.d.ts +172 -0
- package/dist/api.js +439 -0
- package/dist/concurrent-dns.d.ts +130 -0
- package/dist/concurrent-dns.js +403 -0
- package/dist/index.d.ts +45 -353
- package/dist/index.js +65 -596
- package/dist/loader.d.ts +44 -0
- package/dist/loader.js +155 -0
- package/dist/schema.d.ts +66 -0
- package/dist/schema.js +73 -0
- package/dist/security/hash-verifier.js +2 -2
- package/package.json +2 -2
- package/providers/emailproviders.json +530 -479
package/dist/index.d.ts
CHANGED
|
@@ -1,374 +1,66 @@
|
|
|
1
1
|
/**
|
|
2
2
|
* Email Provider Links
|
|
3
3
|
*
|
|
4
|
-
* A
|
|
5
|
-
*
|
|
6
|
-
*
|
|
7
|
-
*
|
|
8
|
-
*
|
|
9
|
-
*
|
|
10
|
-
*
|
|
11
|
-
* @
|
|
12
|
-
|
|
13
|
-
/**
|
|
14
|
-
* Simple rate limiter to prevent excessive DNS queries.
|
|
15
|
-
* Tracks request timestamps and enforces a maximum number of requests per time window.
|
|
4
|
+
* A clean, modern email provider detection library with:
|
|
5
|
+
* - 93+ verified email providers covering 180+ domains
|
|
6
|
+
* - Concurrent DNS detection for business domains
|
|
7
|
+
* - Zero runtime dependencies
|
|
8
|
+
* - Comprehensive error handling
|
|
9
|
+
* - Email alias normalization
|
|
10
|
+
*
|
|
11
|
+
* @author Email Provider Links Team
|
|
12
|
+
* @license MIT
|
|
16
13
|
*/
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
* Checks if a request is allowed under the current rate limit.
|
|
24
|
-
* @returns true if request is allowed, false if rate limited
|
|
25
|
-
*/
|
|
26
|
-
isAllowed(): boolean;
|
|
27
|
-
/**
|
|
28
|
-
* Gets the current number of requests in the window.
|
|
29
|
-
*/
|
|
30
|
-
getCurrentCount(): number;
|
|
31
|
-
/**
|
|
32
|
-
* Gets the time until the rate limit resets (when oldest request expires).
|
|
33
|
-
* @returns milliseconds until reset, or 0 if not rate limited
|
|
34
|
-
*/
|
|
35
|
-
getTimeUntilReset(): number;
|
|
36
|
-
}
|
|
14
|
+
export { getEmailProvider, getEmailProviderSync, getEmailProviderFast, normalizeEmail, emailsMatch, Config } from './api';
|
|
15
|
+
export type { EmailProvider, EmailProviderResult } from './api';
|
|
16
|
+
export { loadProviders } from './loader';
|
|
17
|
+
export { detectProviderConcurrent } from './concurrent-dns';
|
|
18
|
+
export type { ConcurrentDNSConfig, ConcurrentDNSResult } from './concurrent-dns';
|
|
19
|
+
import { getEmailProvider, getEmailProviderSync, getEmailProviderFast, normalizeEmail, emailsMatch } from './api';
|
|
37
20
|
/**
|
|
38
|
-
*
|
|
39
|
-
*
|
|
40
|
-
* @interface EmailProvider
|
|
41
|
-
* @example
|
|
42
|
-
* ```typescript
|
|
43
|
-
* {
|
|
44
|
-
* companyProvider: "Gmail",
|
|
45
|
-
* loginUrl: "https://mail.google.com/mail/",
|
|
46
|
-
* domains: ["gmail.com", "googlemail.com"],
|
|
47
|
-
* customDomainDetection: {
|
|
48
|
-
* mxPatterns: ["aspmx.l.google.com"],
|
|
49
|
-
* txtPatterns: ["v=spf1 include:_spf.google.com"]
|
|
50
|
-
* }
|
|
51
|
-
* }
|
|
52
|
-
* ```
|
|
21
|
+
* Get list of all supported email providers
|
|
22
|
+
* @returns Array of all email providers in the database
|
|
53
23
|
*/
|
|
54
|
-
export
|
|
55
|
-
/** Human-readable name of the email provider company */
|
|
56
|
-
companyProvider: string;
|
|
57
|
-
/** Direct URL to the provider's login/webmail page */
|
|
58
|
-
loginUrl: string;
|
|
59
|
-
/** Array of email domains this provider handles (e.g., ['gmail.com', 'googlemail.com']) */
|
|
60
|
-
domains: string[];
|
|
61
|
-
/** Optional DNS-based detection patterns for custom business domains */
|
|
62
|
-
customDomainDetection?: {
|
|
63
|
-
/** MX record patterns to match against (e.g., ['aspmx.l.google.com']) */
|
|
64
|
-
mxPatterns?: string[];
|
|
65
|
-
/** TXT record patterns to match against (e.g., ['v=spf1 include:_spf.google.com']) */
|
|
66
|
-
txtPatterns?: string[];
|
|
67
|
-
};
|
|
68
|
-
}
|
|
24
|
+
export declare function getSupportedProviders(): import("./api").EmailProvider[];
|
|
69
25
|
/**
|
|
70
|
-
*
|
|
71
|
-
*
|
|
72
|
-
* @
|
|
73
|
-
* @example
|
|
74
|
-
* ```typescript
|
|
75
|
-
* {
|
|
76
|
-
* provider: { companyProvider: "Gmail", loginUrl: "https://mail.google.com/mail/", domains: ["gmail.com"] },
|
|
77
|
-
* email: "user@gmail.com",
|
|
78
|
-
* loginUrl: "https://mail.google.com/mail/",
|
|
79
|
-
* detectionMethod: "domain_match"
|
|
80
|
-
* }
|
|
81
|
-
* ```
|
|
82
|
-
*/
|
|
83
|
-
export interface EmailProviderResult {
|
|
84
|
-
/** The detected email provider, or null if not found/behind proxy */
|
|
85
|
-
provider: EmailProvider | null;
|
|
86
|
-
/** The original email address that was analyzed */
|
|
87
|
-
email: string;
|
|
88
|
-
/** Direct URL to the email provider's login page, or null if unknown */
|
|
89
|
-
loginUrl: string | null;
|
|
90
|
-
/** Method used to detect the provider */
|
|
91
|
-
detectionMethod?: 'domain_match' | 'mx_record' | 'txt_record' | 'proxy_detected';
|
|
92
|
-
/** If a proxy service was detected, which service (e.g., 'Cloudflare') */
|
|
93
|
-
proxyService?: string;
|
|
94
|
-
}
|
|
95
|
-
/**
|
|
96
|
-
* Result object returned by DNS-based provider detection.
|
|
97
|
-
*
|
|
98
|
-
* @interface DNSDetectionResult
|
|
99
|
-
* @example
|
|
100
|
-
* ```typescript
|
|
101
|
-
* {
|
|
102
|
-
* provider: { companyProvider: "Google Workspace", ... },
|
|
103
|
-
* detectionMethod: "mx_record",
|
|
104
|
-
* proxyService: undefined
|
|
105
|
-
* }
|
|
106
|
-
* ```
|
|
107
|
-
*/
|
|
108
|
-
export interface DNSDetectionResult {
|
|
109
|
-
/** The detected email provider, or null if not found/behind proxy */
|
|
110
|
-
provider: EmailProvider | null;
|
|
111
|
-
/** Method used for DNS-based detection */
|
|
112
|
-
detectionMethod: 'mx_record' | 'txt_record' | 'proxy_detected' | null;
|
|
113
|
-
/** If a proxy service was detected, which service (e.g., 'Cloudflare') */
|
|
114
|
-
proxyService?: string;
|
|
115
|
-
}
|
|
116
|
-
/**
|
|
117
|
-
* Validates if a string is a valid email address using a basic regex pattern.
|
|
118
|
-
*
|
|
119
|
-
* @param email - The string to validate as an email address
|
|
120
|
-
* @returns true if the string matches basic email format, false otherwise
|
|
121
|
-
*
|
|
122
|
-
* @example
|
|
123
|
-
* ```typescript
|
|
124
|
-
* isValidEmail('user@gmail.com'); // true
|
|
125
|
-
* isValidEmail('invalid-email'); // false
|
|
126
|
-
* isValidEmail('user@domain'); // false
|
|
127
|
-
* ```
|
|
128
|
-
*
|
|
129
|
-
* @remarks
|
|
130
|
-
* This uses a simple regex pattern that covers most common email formats.
|
|
131
|
-
* It may not catch all edge cases defined in RFC 5322, but works for
|
|
132
|
-
* standard email addresses.
|
|
26
|
+
* Check if an email provider is supported
|
|
27
|
+
* @param email - Email address to check
|
|
28
|
+
* @returns true if the provider is supported
|
|
133
29
|
*/
|
|
134
|
-
export declare function
|
|
30
|
+
export declare function isEmailProviderSupported(email: string): boolean;
|
|
135
31
|
/**
|
|
136
|
-
*
|
|
137
|
-
*
|
|
138
|
-
* @
|
|
139
|
-
* @returns The domain in lowercase, or null if the email is invalid
|
|
140
|
-
*
|
|
141
|
-
* @example
|
|
142
|
-
* ```typescript
|
|
143
|
-
* extractDomain('user@Gmail.com'); // 'gmail.com'
|
|
144
|
-
* extractDomain('test@yahoo.co.uk'); // 'yahoo.co.uk'
|
|
145
|
-
* extractDomain('invalid-email'); // null
|
|
146
|
-
* ```
|
|
147
|
-
*
|
|
148
|
-
* @remarks
|
|
149
|
-
* The domain is automatically normalized to lowercase for consistent matching.
|
|
32
|
+
* Extract domain from email address
|
|
33
|
+
* @param email - Email address
|
|
34
|
+
* @returns Domain portion or null if invalid
|
|
150
35
|
*/
|
|
151
36
|
export declare function extractDomain(email: string): string | null;
|
|
152
37
|
/**
|
|
153
|
-
*
|
|
154
|
-
*
|
|
155
|
-
*
|
|
156
|
-
* @param domain - The email domain to look up (e.g., 'gmail.com')
|
|
157
|
-
* @returns The matching EmailProvider object, or null if not found
|
|
158
|
-
*
|
|
159
|
-
* @example
|
|
160
|
-
* ```typescript
|
|
161
|
-
* const provider = findEmailProvider('gmail.com');
|
|
162
|
-
* console.log(provider?.companyProvider); // 'Gmail'
|
|
163
|
-
* console.log(provider?.loginUrl); // 'https://mail.google.com/mail/'
|
|
164
|
-
* ```
|
|
165
|
-
*
|
|
166
|
-
* @remarks
|
|
167
|
-
* This function performs a case-insensitive O(1) lookup using a pre-built Map.
|
|
168
|
-
* It only checks the predefined JSON database, not DNS records.
|
|
169
|
-
* Performance optimized from O(n*m) to O(1) where n=providers, m=domains per provider.
|
|
38
|
+
* Validate email format
|
|
39
|
+
* @param email - Email address to validate
|
|
40
|
+
* @returns true if valid format
|
|
170
41
|
*/
|
|
171
|
-
export declare function
|
|
172
|
-
/**
|
|
173
|
-
* Gets email provider information and login URL for a given email address.
|
|
174
|
-
* This is the basic/synchronous version that only checks predefined domains.
|
|
175
|
-
*
|
|
176
|
-
* @param email - The email address to analyze
|
|
177
|
-
* @returns EmailProviderResult containing provider info and login URL
|
|
178
|
-
*
|
|
179
|
-
* @example
|
|
180
|
-
* ```typescript
|
|
181
|
-
* const result = getEmailProviderLink('user@gmail.com');
|
|
182
|
-
* console.log(result.loginUrl); // 'https://mail.google.com/mail/'
|
|
183
|
-
* console.log(result.provider?.companyProvider); // 'Gmail'
|
|
184
|
-
* ```
|
|
185
|
-
*
|
|
186
|
-
* @remarks
|
|
187
|
-
* This function only checks against the predefined JSON database of known domains.
|
|
188
|
-
* It will NOT detect business domains that use major email providers (e.g.,
|
|
189
|
-
* mycompany.com using Google Workspace). For comprehensive detection including
|
|
190
|
-
* business domains, use {@link getEmailProviderLinkWithDNS} instead.
|
|
191
|
-
*
|
|
192
|
-
* **Limitations:**
|
|
193
|
-
* - Only synchronous operation (no DNS lookups)
|
|
194
|
-
* - Limited to domains in the JSON database
|
|
195
|
-
* - Won't detect custom business domains
|
|
196
|
-
* - No proxy service detection
|
|
197
|
-
*/
|
|
198
|
-
export declare function getEmailProviderLink(email: string): EmailProviderResult;
|
|
199
|
-
/**
|
|
200
|
-
* Returns an array of all supported email providers.
|
|
201
|
-
*
|
|
202
|
-
* @returns A copy of the EMAIL_PROVIDERS array
|
|
203
|
-
*
|
|
204
|
-
* @example
|
|
205
|
-
* ```typescript
|
|
206
|
-
* const providers = getSupportedProviders();
|
|
207
|
-
* console.log(providers.length); // 55+
|
|
208
|
-
* console.log(providers[0].companyProvider); // 'Gmail'
|
|
209
|
-
* ```
|
|
210
|
-
*
|
|
211
|
-
* @remarks
|
|
212
|
-
* Returns a shallow copy to prevent external modification of the internal
|
|
213
|
-
* providers array. The returned array includes both consumer email providers
|
|
214
|
-
* (gmail.com, yahoo.com) and business email providers with DNS detection patterns.
|
|
215
|
-
*/
|
|
216
|
-
export declare function getSupportedProviders(): EmailProvider[];
|
|
217
|
-
/**
|
|
218
|
-
* Checks if an email address uses a supported email provider.
|
|
219
|
-
*
|
|
220
|
-
* @param email - The email address to check
|
|
221
|
-
* @returns true if the provider is supported, false otherwise
|
|
222
|
-
*
|
|
223
|
-
* @example
|
|
224
|
-
* ```typescript
|
|
225
|
-
* isEmailProviderSupported('user@gmail.com'); // true
|
|
226
|
-
* isEmailProviderSupported('user@unknown.com'); // false
|
|
227
|
-
* ```
|
|
228
|
-
*
|
|
229
|
-
* @remarks
|
|
230
|
-
* This is a convenience function that uses {@link getEmailProviderLink} internally.
|
|
231
|
-
* It only checks predefined domains, not DNS-based detection. For business
|
|
232
|
-
* domain support checking, you would need to use {@link getEmailProviderLinkWithDNS}.
|
|
233
|
-
*/
|
|
234
|
-
export declare function isEmailProviderSupported(email: string): boolean;
|
|
235
|
-
/**
|
|
236
|
-
* Performs DNS-based detection for custom business domains using MX and TXT record analysis.
|
|
237
|
-
* This function is used internally by {@link getEmailProviderLinkWithDNS} but can also be
|
|
238
|
-
* called directly to analyze domain email configuration.
|
|
239
|
-
*
|
|
240
|
-
* @param domain - The domain to analyze (e.g., 'mycompany.com')
|
|
241
|
-
* @param timeoutMs - Optional timeout for DNS queries in milliseconds (default: 5000ms)
|
|
242
|
-
* @returns Promise resolving to DNSDetectionResult with provider info or proxy detection
|
|
243
|
-
*
|
|
244
|
-
* @example
|
|
245
|
-
* ```typescript
|
|
246
|
-
* const result = await detectProviderByDNS('microsoft.com');
|
|
247
|
-
* console.log(result.provider?.companyProvider); // 'Microsoft 365 (Business)'
|
|
248
|
-
* console.log(result.detectionMethod); // 'mx_record'
|
|
249
|
-
* ```
|
|
250
|
-
*
|
|
251
|
-
* @remarks
|
|
252
|
-
* **Detection Algorithm:**
|
|
253
|
-
* 1. Checks rate limiting (max 10 requests per minute)
|
|
254
|
-
* 2. Performs MX record lookup for the domain
|
|
255
|
-
* 3. Checks if MX records match known proxy services (Cloudflare, etc.)
|
|
256
|
-
* 4. If proxy detected, returns null provider with proxy info
|
|
257
|
-
* 5. Otherwise, matches MX records against business email provider patterns
|
|
258
|
-
* 6. If no MX match, falls back to TXT record analysis (SPF records, etc.)
|
|
259
|
-
* 7. Returns the first matching provider or null if none found
|
|
260
|
-
*
|
|
261
|
-
* **Rate Limiting:**
|
|
262
|
-
* - Maximum 10 DNS requests per 60-second window
|
|
263
|
-
* - Rate limit exceeded returns error with retry information
|
|
264
|
-
* - Prevents abuse and excessive DNS queries
|
|
265
|
-
*
|
|
266
|
-
* **Provider Patterns Checked:**
|
|
267
|
-
* - Google Workspace: aspmx.l.google.com, aspmx2.googlemail.com, etc.
|
|
268
|
-
* - Microsoft 365: *.protection.outlook.com, *.outlook.com
|
|
269
|
-
* - ProtonMail: mail.protonmail.ch, mailsec.protonmail.ch
|
|
270
|
-
* - FastMail: *.messagingengine.com
|
|
271
|
-
* - And many others...
|
|
272
|
-
*
|
|
273
|
-
* **Error Handling:**
|
|
274
|
-
* DNS lookup failures are caught and the function gracefully falls back
|
|
275
|
-
* to the next detection method or returns null if all methods fail.
|
|
276
|
-
*/
|
|
277
|
-
export declare function detectProviderByDNS(domain: string, timeoutMs?: number): Promise<DNSDetectionResult>;
|
|
42
|
+
export declare function isValidEmail(email: string): boolean;
|
|
278
43
|
/**
|
|
279
|
-
*
|
|
280
|
-
* This is the recommended function for most use cases as it provides comprehensive
|
|
281
|
-
* detection coverage including business domains and proxy services.
|
|
282
|
-
*
|
|
283
|
-
* @param email - The email address to analyze
|
|
284
|
-
* @param timeoutMs - Optional timeout for DNS queries in milliseconds (default: 5000ms)
|
|
285
|
-
* @returns Promise resolving to EmailProviderResult with provider info and detection method
|
|
286
|
-
*
|
|
287
|
-
* @example
|
|
288
|
-
* ```typescript
|
|
289
|
-
* // Consumer email (fast domain match)
|
|
290
|
-
* const gmail = await getEmailProviderLinkWithDNS('user@gmail.com');
|
|
291
|
-
* console.log(gmail.provider?.companyProvider); // 'Gmail'
|
|
292
|
-
* console.log(gmail.detectionMethod); // 'domain_match'
|
|
293
|
-
*
|
|
294
|
-
* // Business domain (DNS detection)
|
|
295
|
-
* const business = await getEmailProviderLinkWithDNS('user@mycompany.com');
|
|
296
|
-
* console.log(business.provider?.companyProvider); // 'Google Workspace' (if detected)
|
|
297
|
-
* console.log(business.detectionMethod); // 'mx_record'
|
|
298
|
-
*
|
|
299
|
-
* // Proxied domain (proxy detection)
|
|
300
|
-
* const proxied = await getEmailProviderLinkWithDNS('user@proxied-domain.com');
|
|
301
|
-
* console.log(proxied.provider); // null
|
|
302
|
-
* console.log(proxied.proxyService); // 'Cloudflare'
|
|
303
|
-
* console.log(proxied.detectionMethod); // 'proxy_detected'
|
|
304
|
-
* ```
|
|
305
|
-
*
|
|
306
|
-
* @remarks
|
|
307
|
-
* **Detection Hierarchy (in order):**
|
|
308
|
-
* 1. **Domain Match**: Fast lookup against predefined domains (gmail.com, yahoo.com, etc.)
|
|
309
|
-
* 2. **DNS MX Records**: Analyzes mail exchange records for business email providers
|
|
310
|
-
* 3. **DNS TXT Records**: Checks SPF and verification records as fallback
|
|
311
|
-
* 4. **Proxy Detection**: Identifies when domains are behind CDN/proxy services
|
|
312
|
-
*
|
|
313
|
-
* **Supported Detection Cases:**
|
|
314
|
-
* - ✅ Consumer emails: gmail.com, yahoo.com, outlook.com, etc.
|
|
315
|
-
* - ✅ Business domains: Google Workspace, Microsoft 365, ProtonMail Business, etc.
|
|
316
|
-
* - ✅ Proxy services: Cloudflare, CloudFront, Fastly, etc.
|
|
317
|
-
* - ✅ International providers: QQ Mail, NetEase, Yandex, etc.
|
|
318
|
-
*
|
|
319
|
-
* **Performance:**
|
|
320
|
-
* - Fast for known consumer domains (synchronous JSON lookup)
|
|
321
|
-
* - Additional DNS lookup time for unknown domains (~100-500ms)
|
|
322
|
-
* - Graceful degradation if DNS lookups fail
|
|
323
|
-
*
|
|
324
|
-
* **Error Handling:**
|
|
325
|
-
* - Invalid email addresses return null provider
|
|
326
|
-
* - DNS lookup failures are caught and don't throw errors
|
|
327
|
-
* - Network timeouts gracefully fall back to null detection
|
|
328
|
-
*
|
|
329
|
-
* **Use Cases:**
|
|
330
|
-
* - Password reset flows ("Check your Gmail inbox")
|
|
331
|
-
* - Login form enhancements (direct links to email providers)
|
|
332
|
-
* - Email client detection for support purposes
|
|
333
|
-
* - Business domain analysis for enterprise features
|
|
44
|
+
* Library metadata
|
|
334
45
|
*/
|
|
335
|
-
export declare
|
|
46
|
+
export declare const PROVIDER_COUNT = 93;
|
|
47
|
+
export declare const DOMAIN_COUNT = 178;
|
|
336
48
|
/**
|
|
337
|
-
*
|
|
338
|
-
* @public
|
|
49
|
+
* Default export for convenience
|
|
339
50
|
*/
|
|
340
|
-
export declare const RateLimit: {
|
|
341
|
-
MAX_REQUESTS: number;
|
|
342
|
-
WINDOW_MS: number;
|
|
343
|
-
SimpleRateLimiter: typeof SimpleRateLimiter;
|
|
344
|
-
/**
|
|
345
|
-
* Gets the current rate limiter instance for inspection or testing.
|
|
346
|
-
* @internal
|
|
347
|
-
*/
|
|
348
|
-
getCurrentLimiter: () => SimpleRateLimiter;
|
|
349
|
-
};
|
|
350
|
-
export * from './alias-detection';
|
|
351
|
-
export * from './security/url-validator';
|
|
352
|
-
export * from './security/hash-verifier';
|
|
353
|
-
export * from './security/secure-loader';
|
|
354
51
|
declare const _default: {
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
|
|
358
|
-
|
|
359
|
-
|
|
360
|
-
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
WINDOW_MS: number;
|
|
366
|
-
SimpleRateLimiter: typeof SimpleRateLimiter;
|
|
367
|
-
/**
|
|
368
|
-
* Gets the current rate limiter instance for inspection or testing.
|
|
369
|
-
* @internal
|
|
370
|
-
*/
|
|
371
|
-
getCurrentLimiter: () => SimpleRateLimiter;
|
|
52
|
+
getEmailProvider: typeof getEmailProvider;
|
|
53
|
+
getEmailProviderSync: typeof getEmailProviderSync;
|
|
54
|
+
getEmailProviderFast: typeof getEmailProviderFast;
|
|
55
|
+
normalizeEmail: typeof normalizeEmail;
|
|
56
|
+
emailsMatch: typeof emailsMatch;
|
|
57
|
+
Config: {
|
|
58
|
+
readonly DEFAULT_DNS_TIMEOUT: 5000;
|
|
59
|
+
readonly MAX_DNS_REQUESTS_PER_MINUTE: 10;
|
|
60
|
+
readonly SUPPORTED_PROVIDERS_COUNT: 93;
|
|
61
|
+
readonly SUPPORTED_DOMAINS_COUNT: 180;
|
|
372
62
|
};
|
|
63
|
+
PROVIDER_COUNT: number;
|
|
64
|
+
DOMAIN_COUNT: number;
|
|
373
65
|
};
|
|
374
66
|
export default _default;
|