@depup/nodemailer 7.0.12-depup.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 (47) hide show
  1. package/.gitattributes +6 -0
  2. package/.ncurc.js +9 -0
  3. package/.prettierignore +8 -0
  4. package/.prettierrc +12 -0
  5. package/.prettierrc.js +10 -0
  6. package/.release-please-config.json +9 -0
  7. package/CHANGELOG.md +929 -0
  8. package/CODE_OF_CONDUCT.md +76 -0
  9. package/LICENSE +16 -0
  10. package/README.md +86 -0
  11. package/SECURITY.txt +22 -0
  12. package/eslint.config.js +88 -0
  13. package/lib/addressparser/index.js +383 -0
  14. package/lib/base64/index.js +139 -0
  15. package/lib/dkim/index.js +253 -0
  16. package/lib/dkim/message-parser.js +155 -0
  17. package/lib/dkim/relaxed-body.js +154 -0
  18. package/lib/dkim/sign.js +117 -0
  19. package/lib/fetch/cookies.js +281 -0
  20. package/lib/fetch/index.js +280 -0
  21. package/lib/json-transport/index.js +82 -0
  22. package/lib/mail-composer/index.js +629 -0
  23. package/lib/mailer/index.js +441 -0
  24. package/lib/mailer/mail-message.js +316 -0
  25. package/lib/mime-funcs/index.js +625 -0
  26. package/lib/mime-funcs/mime-types.js +2113 -0
  27. package/lib/mime-node/index.js +1316 -0
  28. package/lib/mime-node/last-newline.js +33 -0
  29. package/lib/mime-node/le-unix.js +43 -0
  30. package/lib/mime-node/le-windows.js +52 -0
  31. package/lib/nodemailer.js +157 -0
  32. package/lib/punycode/index.js +460 -0
  33. package/lib/qp/index.js +227 -0
  34. package/lib/sendmail-transport/index.js +210 -0
  35. package/lib/ses-transport/index.js +234 -0
  36. package/lib/shared/index.js +754 -0
  37. package/lib/smtp-connection/data-stream.js +108 -0
  38. package/lib/smtp-connection/http-proxy-client.js +143 -0
  39. package/lib/smtp-connection/index.js +1865 -0
  40. package/lib/smtp-pool/index.js +652 -0
  41. package/lib/smtp-pool/pool-resource.js +259 -0
  42. package/lib/smtp-transport/index.js +421 -0
  43. package/lib/stream-transport/index.js +135 -0
  44. package/lib/well-known/index.js +47 -0
  45. package/lib/well-known/services.json +611 -0
  46. package/lib/xoauth2/index.js +427 -0
  47. package/package.json +47 -0
@@ -0,0 +1,316 @@
1
+ 'use strict';
2
+
3
+ const shared = require('../shared');
4
+ const MimeNode = require('../mime-node');
5
+ const mimeFuncs = require('../mime-funcs');
6
+
7
+ class MailMessage {
8
+ constructor(mailer, data) {
9
+ this.mailer = mailer;
10
+ this.data = {};
11
+ this.message = null;
12
+
13
+ data = data || {};
14
+ let options = mailer.options || {};
15
+ let defaults = mailer._defaults || {};
16
+
17
+ Object.keys(data).forEach(key => {
18
+ this.data[key] = data[key];
19
+ });
20
+
21
+ this.data.headers = this.data.headers || {};
22
+
23
+ // apply defaults
24
+ Object.keys(defaults).forEach(key => {
25
+ if (!(key in this.data)) {
26
+ this.data[key] = defaults[key];
27
+ } else if (key === 'headers') {
28
+ // headers is a special case. Allow setting individual default headers
29
+ Object.keys(defaults.headers).forEach(key => {
30
+ if (!(key in this.data.headers)) {
31
+ this.data.headers[key] = defaults.headers[key];
32
+ }
33
+ });
34
+ }
35
+ });
36
+
37
+ // force specific keys from transporter options
38
+ ['disableFileAccess', 'disableUrlAccess', 'normalizeHeaderKey'].forEach(key => {
39
+ if (key in options) {
40
+ this.data[key] = options[key];
41
+ }
42
+ });
43
+ }
44
+
45
+ resolveContent(...args) {
46
+ return shared.resolveContent(...args);
47
+ }
48
+
49
+ resolveAll(callback) {
50
+ let keys = [
51
+ [this.data, 'html'],
52
+ [this.data, 'text'],
53
+ [this.data, 'watchHtml'],
54
+ [this.data, 'amp'],
55
+ [this.data, 'icalEvent']
56
+ ];
57
+
58
+ if (this.data.alternatives && this.data.alternatives.length) {
59
+ this.data.alternatives.forEach((alternative, i) => {
60
+ keys.push([this.data.alternatives, i]);
61
+ });
62
+ }
63
+
64
+ if (this.data.attachments && this.data.attachments.length) {
65
+ this.data.attachments.forEach((attachment, i) => {
66
+ if (!attachment.filename) {
67
+ attachment.filename =
68
+ (attachment.path || attachment.href || '').split('/').pop().split('?').shift() || 'attachment-' + (i + 1);
69
+ if (attachment.filename.indexOf('.') < 0) {
70
+ attachment.filename += '.' + mimeFuncs.detectExtension(attachment.contentType);
71
+ }
72
+ }
73
+
74
+ if (!attachment.contentType) {
75
+ attachment.contentType = mimeFuncs.detectMimeType(attachment.filename || attachment.path || attachment.href || 'bin');
76
+ }
77
+
78
+ keys.push([this.data.attachments, i]);
79
+ });
80
+ }
81
+
82
+ let mimeNode = new MimeNode();
83
+
84
+ let addressKeys = ['from', 'to', 'cc', 'bcc', 'sender', 'replyTo'];
85
+
86
+ addressKeys.forEach(address => {
87
+ let value;
88
+ if (this.message) {
89
+ value = [].concat(mimeNode._parseAddresses(this.message.getHeader(address === 'replyTo' ? 'reply-to' : address)) || []);
90
+ } else if (this.data[address]) {
91
+ value = [].concat(mimeNode._parseAddresses(this.data[address]) || []);
92
+ }
93
+ if (value && value.length) {
94
+ this.data[address] = value;
95
+ } else if (address in this.data) {
96
+ this.data[address] = null;
97
+ }
98
+ });
99
+
100
+ let singleKeys = ['from', 'sender'];
101
+ singleKeys.forEach(address => {
102
+ if (this.data[address]) {
103
+ this.data[address] = this.data[address].shift();
104
+ }
105
+ });
106
+
107
+ let pos = 0;
108
+ let resolveNext = () => {
109
+ if (pos >= keys.length) {
110
+ return callback(null, this.data);
111
+ }
112
+ let args = keys[pos++];
113
+ if (!args[0] || !args[0][args[1]]) {
114
+ return resolveNext();
115
+ }
116
+ shared.resolveContent(...args, (err, value) => {
117
+ if (err) {
118
+ return callback(err);
119
+ }
120
+
121
+ let node = {
122
+ content: value
123
+ };
124
+ if (args[0][args[1]] && typeof args[0][args[1]] === 'object' && !Buffer.isBuffer(args[0][args[1]])) {
125
+ Object.keys(args[0][args[1]]).forEach(key => {
126
+ if (!(key in node) && !['content', 'path', 'href', 'raw'].includes(key)) {
127
+ node[key] = args[0][args[1]][key];
128
+ }
129
+ });
130
+ }
131
+
132
+ args[0][args[1]] = node;
133
+ resolveNext();
134
+ });
135
+ };
136
+
137
+ setImmediate(() => resolveNext());
138
+ }
139
+
140
+ normalize(callback) {
141
+ let envelope = this.data.envelope || this.message.getEnvelope();
142
+ let messageId = this.message.messageId();
143
+
144
+ this.resolveAll((err, data) => {
145
+ if (err) {
146
+ return callback(err);
147
+ }
148
+
149
+ data.envelope = envelope;
150
+ data.messageId = messageId;
151
+
152
+ ['html', 'text', 'watchHtml', 'amp'].forEach(key => {
153
+ if (data[key] && data[key].content) {
154
+ if (typeof data[key].content === 'string') {
155
+ data[key] = data[key].content;
156
+ } else if (Buffer.isBuffer(data[key].content)) {
157
+ data[key] = data[key].content.toString();
158
+ }
159
+ }
160
+ });
161
+
162
+ if (data.icalEvent && Buffer.isBuffer(data.icalEvent.content)) {
163
+ data.icalEvent.content = data.icalEvent.content.toString('base64');
164
+ data.icalEvent.encoding = 'base64';
165
+ }
166
+
167
+ if (data.alternatives && data.alternatives.length) {
168
+ data.alternatives.forEach(alternative => {
169
+ if (alternative && alternative.content && Buffer.isBuffer(alternative.content)) {
170
+ alternative.content = alternative.content.toString('base64');
171
+ alternative.encoding = 'base64';
172
+ }
173
+ });
174
+ }
175
+
176
+ if (data.attachments && data.attachments.length) {
177
+ data.attachments.forEach(attachment => {
178
+ if (attachment && attachment.content && Buffer.isBuffer(attachment.content)) {
179
+ attachment.content = attachment.content.toString('base64');
180
+ attachment.encoding = 'base64';
181
+ }
182
+ });
183
+ }
184
+
185
+ data.normalizedHeaders = {};
186
+ Object.keys(data.headers || {}).forEach(key => {
187
+ let value = [].concat(data.headers[key] || []).shift();
188
+ value = (value && value.value) || value;
189
+ if (value) {
190
+ if (['references', 'in-reply-to', 'message-id', 'content-id'].includes(key)) {
191
+ value = this.message._encodeHeaderValue(key, value);
192
+ }
193
+ data.normalizedHeaders[key] = value;
194
+ }
195
+ });
196
+
197
+ if (data.list && typeof data.list === 'object') {
198
+ let listHeaders = this._getListHeaders(data.list);
199
+ listHeaders.forEach(entry => {
200
+ data.normalizedHeaders[entry.key] = entry.value.map(val => (val && val.value) || val).join(', ');
201
+ });
202
+ }
203
+
204
+ if (data.references) {
205
+ data.normalizedHeaders.references = this.message._encodeHeaderValue('references', data.references);
206
+ }
207
+
208
+ if (data.inReplyTo) {
209
+ data.normalizedHeaders['in-reply-to'] = this.message._encodeHeaderValue('in-reply-to', data.inReplyTo);
210
+ }
211
+
212
+ return callback(null, data);
213
+ });
214
+ }
215
+
216
+ setMailerHeader() {
217
+ if (!this.message || !this.data.xMailer) {
218
+ return;
219
+ }
220
+ this.message.setHeader('X-Mailer', this.data.xMailer);
221
+ }
222
+
223
+ setPriorityHeaders() {
224
+ if (!this.message || !this.data.priority) {
225
+ return;
226
+ }
227
+ switch ((this.data.priority || '').toString().toLowerCase()) {
228
+ case 'high':
229
+ this.message.setHeader('X-Priority', '1 (Highest)');
230
+ this.message.setHeader('X-MSMail-Priority', 'High');
231
+ this.message.setHeader('Importance', 'High');
232
+ break;
233
+ case 'low':
234
+ this.message.setHeader('X-Priority', '5 (Lowest)');
235
+ this.message.setHeader('X-MSMail-Priority', 'Low');
236
+ this.message.setHeader('Importance', 'Low');
237
+ break;
238
+ default:
239
+ // do not add anything, since all messages are 'Normal' by default
240
+ }
241
+ }
242
+
243
+ setListHeaders() {
244
+ if (!this.message || !this.data.list || typeof this.data.list !== 'object') {
245
+ return;
246
+ }
247
+ // add optional List-* headers
248
+ if (this.data.list && typeof this.data.list === 'object') {
249
+ this._getListHeaders(this.data.list).forEach(listHeader => {
250
+ listHeader.value.forEach(value => {
251
+ this.message.addHeader(listHeader.key, value);
252
+ });
253
+ });
254
+ }
255
+ }
256
+
257
+ _getListHeaders(listData) {
258
+ // make sure an url looks like <protocol:url>
259
+ return Object.keys(listData).map(key => ({
260
+ key: 'list-' + key.toLowerCase().trim(),
261
+ value: [].concat(listData[key] || []).map(value => ({
262
+ prepared: true,
263
+ foldLines: true,
264
+ value: []
265
+ .concat(value || [])
266
+ .map(value => {
267
+ if (typeof value === 'string') {
268
+ value = {
269
+ url: value
270
+ };
271
+ }
272
+
273
+ if (value && value.url) {
274
+ if (key.toLowerCase().trim() === 'id') {
275
+ // List-ID: "comment" <domain>
276
+ let comment = value.comment || '';
277
+ if (mimeFuncs.isPlainText(comment)) {
278
+ comment = '"' + comment + '"';
279
+ } else {
280
+ comment = mimeFuncs.encodeWord(comment);
281
+ }
282
+
283
+ return (value.comment ? comment + ' ' : '') + this._formatListUrl(value.url).replace(/^<[^:]+\/{,2}/, '');
284
+ }
285
+
286
+ // List-*: <http://domain> (comment)
287
+ let comment = value.comment || '';
288
+ if (!mimeFuncs.isPlainText(comment)) {
289
+ comment = mimeFuncs.encodeWord(comment);
290
+ }
291
+
292
+ return this._formatListUrl(value.url) + (value.comment ? ' (' + comment + ')' : '');
293
+ }
294
+
295
+ return '';
296
+ })
297
+ .filter(value => value)
298
+ .join(', ')
299
+ }))
300
+ }));
301
+ }
302
+
303
+ _formatListUrl(url) {
304
+ url = url.replace(/[\s<]+|[\s>]+/g, '');
305
+ if (/^(https?|mailto|ftp):/.test(url)) {
306
+ return '<' + url + '>';
307
+ }
308
+ if (/^[^@]+@[^@]+$/.test(url)) {
309
+ return '<mailto:' + url + '>';
310
+ }
311
+
312
+ return '<http://' + url + '>';
313
+ }
314
+ }
315
+
316
+ module.exports = MailMessage;