postal-mime 2.1.2 → 2.2.1
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/CHANGELOG.md +14 -0
- package/LICENSE.txt +1 -1
- package/README.md +21 -21
- package/package.json +2 -2
- package/postal-mime.d.ts +1 -0
- package/src/postal-mime.js +23 -15
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,19 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## [2.2.1](https://github.com/postalsys/postal-mime/compare/v2.2.0...v2.2.1) (2024-03-31)
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
### Bug Fixes
|
|
7
|
+
|
|
8
|
+
* **parser:** Reply-To value must be an array, not a single address object ([280bd8d](https://github.com/postalsys/postal-mime/commit/280bd8dc1626315e1a43f35641415453c434716e))
|
|
9
|
+
|
|
10
|
+
## [2.2.0](https://github.com/postalsys/postal-mime/compare/v2.1.2...v2.2.0) (2024-03-26)
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
### Features
|
|
14
|
+
|
|
15
|
+
* **interface:** Added statis parse() method to simplify usage (`await PostalMime.parse(email)`) ([c2faa27](https://github.com/postalsys/postal-mime/commit/c2faa276520d6551df640abe008986eebc6d99d3))
|
|
16
|
+
|
|
3
17
|
## [2.1.2](https://github.com/postalsys/postal-mime/compare/v2.1.1...v2.1.2) (2024-02-29)
|
|
4
18
|
|
|
5
19
|
|
package/LICENSE.txt
CHANGED
package/README.md
CHANGED
|
@@ -1,12 +1,15 @@
|
|
|
1
1
|
# postal-mime
|
|
2
2
|
|
|
3
|
-
Email parser for browser environments.
|
|
3
|
+
Email parser for browser and serverless environments.
|
|
4
4
|
|
|
5
|
-
PostalMime can be run in the main web thread or from Web Workers.
|
|
5
|
+
PostalMime can be run in the main web thread or from Web Workers. It can also used in serverless functions.
|
|
6
|
+
|
|
7
|
+
> [!TIP]
|
|
8
|
+
> PostalMime is developed by the makers of **[EmailEngine](https://emailengine.app/?utm_source=github&utm_campaign=imapflow&utm_medium=readme-link)** – a self-hosted email gateway that allows making **REST requests against IMAP and SMTP servers**. EmailEngine also sends webhooks whenever something changes on the registered accounts.
|
|
6
9
|
|
|
7
10
|
## Source
|
|
8
11
|
|
|
9
|
-
|
|
12
|
+
The source code is available from [Github](https://github.com/postalsys/postal-mime).
|
|
10
13
|
|
|
11
14
|
## Demo
|
|
12
15
|
|
|
@@ -14,7 +17,7 @@ See this [example](https://kreata.ee/postal-mime/example/).
|
|
|
14
17
|
|
|
15
18
|
## Usage
|
|
16
19
|
|
|
17
|
-
First install the module from npm:
|
|
20
|
+
First, install the module from npm:
|
|
18
21
|
|
|
19
22
|
```
|
|
20
23
|
$ npm install postal-mime
|
|
@@ -26,7 +29,7 @@ next import the PostalMime class into your script:
|
|
|
26
29
|
import PostalMime from './node_modules/postal-mime/src/postal-mime.js';
|
|
27
30
|
```
|
|
28
31
|
|
|
29
|
-
or when using from a Node.js app
|
|
32
|
+
or when using from a Node.js app or in a serverless function:
|
|
30
33
|
|
|
31
34
|
```js
|
|
32
35
|
import PostalMime from 'postal-mime';
|
|
@@ -34,15 +37,14 @@ import PostalMime from 'postal-mime';
|
|
|
34
37
|
|
|
35
38
|
### Promises
|
|
36
39
|
|
|
37
|
-
|
|
40
|
+
PostalMime methods use Promises, so you need to wait using `await` or wait for the `then()` method to fire until you get the response.
|
|
38
41
|
|
|
39
42
|
#### Browser
|
|
40
43
|
|
|
41
44
|
```js
|
|
42
45
|
import PostalMime from './node_modules/postal-mime/src/postal-mime.js';
|
|
43
46
|
|
|
44
|
-
const
|
|
45
|
-
const email = await parser.parse(`Subject: My awesome email 🤓
|
|
47
|
+
const email = await PostalMime.parse(`Subject: My awesome email 🤓
|
|
46
48
|
Content-Type: text/html; charset=utf-8
|
|
47
49
|
|
|
48
50
|
<p>Hello world 😵💫</p>`);
|
|
@@ -58,8 +60,7 @@ It is pretty much the same as in the browser.
|
|
|
58
60
|
import PostalMime from 'postal-mime';
|
|
59
61
|
import util from 'node:util';
|
|
60
62
|
|
|
61
|
-
const
|
|
62
|
-
const email = await parser.parse(`Subject: My awesome email 🤓
|
|
63
|
+
const email = await PostalMime.parse(`Subject: My awesome email 🤓
|
|
63
64
|
Content-Type: text/html; charset=utf-8
|
|
64
65
|
|
|
65
66
|
<p>Hello world 😵💫</p>`);
|
|
@@ -76,8 +77,7 @@ import PostalMime from 'postal-mime';
|
|
|
76
77
|
|
|
77
78
|
export default {
|
|
78
79
|
async email(message, env, ctx) {
|
|
79
|
-
const
|
|
80
|
-
const email = await parser.parse(message.raw);
|
|
80
|
+
const email = await PostalMime.parse(message.raw);
|
|
81
81
|
|
|
82
82
|
console.log('Subject: ', email.subject);
|
|
83
83
|
console.log('HTML: ', email.html);
|
|
@@ -86,28 +86,28 @@ export default {
|
|
|
86
86
|
};
|
|
87
87
|
```
|
|
88
88
|
|
|
89
|
-
####
|
|
89
|
+
#### PostalMime.parse()
|
|
90
|
+
|
|
91
|
+
`parse(email)` is a static class method to parse emails
|
|
90
92
|
|
|
91
93
|
```js
|
|
92
|
-
|
|
94
|
+
PostalMime.parse(email) -> Promise
|
|
93
95
|
```
|
|
94
96
|
|
|
95
97
|
Where
|
|
96
98
|
|
|
97
|
-
- **email** is the rfc822 formatted email. Either a string, an ArrayBuffer, a Blob object
|
|
98
|
-
|
|
99
|
-
> **NB** you can call `parse()` only once. If you need to parse another message, create a new _PostalMime_ object.
|
|
99
|
+
- **email** is the rfc822 formatted email. Either a string, an ArrayBuffer/Uint8Array value, a Blob object, a Node.js Buffer, or a [ReadableStream](https://developer.mozilla.org/en-US/docs/Web/API/ReadableStream)
|
|
100
100
|
|
|
101
101
|
This method parses an email message into a structured object with the following properties:
|
|
102
102
|
|
|
103
103
|
- **headers** is an array of headers in the same order as found from the message (topmost headers first).
|
|
104
104
|
- **headers[].key** is lowercase key of the header line, eg. `"dkim-signature"`
|
|
105
105
|
- **headers[].value** is the unprocessed value of the header line
|
|
106
|
-
- **from**, **sender
|
|
106
|
+
- **from**, **sender** includes a processed object for the corresponding headers
|
|
107
107
|
- **from.name** is decoded name (empty string if not set)
|
|
108
108
|
- **from.address** is the email address
|
|
109
109
|
- **deliveredTo**, **returnPath** is the email address from the corresponding header
|
|
110
|
-
- **to**, **cc**, **bcc** includes an array of processed objects for the corresponding headers
|
|
110
|
+
- **to**, **cc**, **bcc**, **replyTo** includes an array of processed objects for the corresponding headers
|
|
111
111
|
- **to[].name** is decoded name (empty string if not set)
|
|
112
112
|
- **to[].address** is the email address
|
|
113
113
|
- **subject** is the email subject line
|
|
@@ -121,10 +121,10 @@ This method parses an email message into a structured object with the following
|
|
|
121
121
|
- **attachment[].disposition** is either "attachment", "inline" or `null` if disposition was not provided
|
|
122
122
|
- **attachment[].related** is a boolean value that indicats if this attachment should be treated as embedded image
|
|
123
123
|
- **attachment[].contentId** is the ID from Content-ID header
|
|
124
|
-
- **attachment[].content** is an
|
|
124
|
+
- **attachment[].content** is an Uint8Array value that contains the attachment file
|
|
125
125
|
|
|
126
126
|
## License
|
|
127
127
|
|
|
128
|
-
© 2021-
|
|
128
|
+
© 2021-2024 Andris Reinman
|
|
129
129
|
|
|
130
130
|
`postal-mime` is licensed under the **MIT No Attribution license**
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "postal-mime",
|
|
3
|
-
"version": "2.1
|
|
3
|
+
"version": "2.2.1",
|
|
4
4
|
"description": "Email parser for browser environments",
|
|
5
5
|
"main": "./src/postal-mime.js",
|
|
6
6
|
"exports": {
|
|
@@ -27,7 +27,7 @@
|
|
|
27
27
|
"author": "Andris Reinman",
|
|
28
28
|
"license": "MIT-0",
|
|
29
29
|
"devDependencies": {
|
|
30
|
-
"@types/node": "20.11.
|
|
30
|
+
"@types/node": "20.11.30",
|
|
31
31
|
"cross-blob": "3.0.2",
|
|
32
32
|
"cross-env": "7.0.3",
|
|
33
33
|
"eslint": "8.57.0",
|
package/postal-mime.d.ts
CHANGED
package/src/postal-mime.js
CHANGED
|
@@ -4,6 +4,11 @@ import addressParser from './address-parser.js';
|
|
|
4
4
|
import { decodeWords, textEncoder, blobToArrayBuffer } from './decode-strings.js';
|
|
5
5
|
|
|
6
6
|
export default class PostalMime {
|
|
7
|
+
static parse(buf) {
|
|
8
|
+
const parser = new PostalMime();
|
|
9
|
+
return parser.parse(buf);
|
|
10
|
+
}
|
|
11
|
+
|
|
7
12
|
constructor() {
|
|
8
13
|
this.root = this.currentNode = new MimeNode({
|
|
9
14
|
postalMime: this
|
|
@@ -353,32 +358,33 @@ export default class PostalMime {
|
|
|
353
358
|
|
|
354
359
|
await this.processNodeTree();
|
|
355
360
|
|
|
356
|
-
|
|
361
|
+
const message = {
|
|
357
362
|
headers: this.root.headers.map(entry => ({ key: entry.key, value: entry.value })).reverse()
|
|
358
363
|
};
|
|
359
364
|
|
|
360
|
-
for (
|
|
361
|
-
|
|
365
|
+
for (const key of ['from', 'sender']) {
|
|
366
|
+
const addressHeader = this.root.headers.find(line => line.key === key);
|
|
362
367
|
if (addressHeader && addressHeader.value) {
|
|
363
|
-
|
|
368
|
+
const addresses = addressParser(addressHeader.value);
|
|
364
369
|
if (addresses && addresses.length) {
|
|
365
|
-
message[key
|
|
370
|
+
message[key] = addresses[0];
|
|
366
371
|
}
|
|
367
372
|
}
|
|
368
373
|
}
|
|
369
374
|
|
|
370
|
-
for (
|
|
371
|
-
|
|
375
|
+
for (const key of ['delivered-to', 'return-path']) {
|
|
376
|
+
const addressHeader = this.root.headers.find(line => line.key === key);
|
|
372
377
|
if (addressHeader && addressHeader.value) {
|
|
373
|
-
|
|
378
|
+
const addresses = addressParser(addressHeader.value);
|
|
374
379
|
if (addresses && addresses.length && addresses[0].address) {
|
|
375
|
-
|
|
380
|
+
const camelKey = key.replace(/\-(.)/g, (o, c) => c.toUpperCase());
|
|
381
|
+
message[camelKey] = addresses[0].address;
|
|
376
382
|
}
|
|
377
383
|
}
|
|
378
384
|
}
|
|
379
385
|
|
|
380
|
-
for (
|
|
381
|
-
|
|
386
|
+
for (const key of ['to', 'cc', 'bcc', 'reply-to']) {
|
|
387
|
+
const addressHeaders = this.root.headers.filter(line => line.key === key);
|
|
382
388
|
let addresses = [];
|
|
383
389
|
|
|
384
390
|
addressHeaders
|
|
@@ -387,14 +393,16 @@ export default class PostalMime {
|
|
|
387
393
|
.forEach(parsed => (addresses = addresses.concat(parsed || [])));
|
|
388
394
|
|
|
389
395
|
if (addresses && addresses.length) {
|
|
390
|
-
|
|
396
|
+
const camelKey = key.replace(/\-(.)/g, (o, c) => c.toUpperCase());
|
|
397
|
+
message[camelKey] = addresses;
|
|
391
398
|
}
|
|
392
399
|
}
|
|
393
400
|
|
|
394
|
-
for (
|
|
395
|
-
|
|
401
|
+
for (const key of ['subject', 'message-id', 'in-reply-to', 'references']) {
|
|
402
|
+
const header = this.root.headers.find(line => line.key === key);
|
|
396
403
|
if (header && header.value) {
|
|
397
|
-
|
|
404
|
+
const camelKey = key.replace(/\-(.)/g, (o, c) => c.toUpperCase());
|
|
405
|
+
message[camelKey] = decodeWords(header.value);
|
|
398
406
|
}
|
|
399
407
|
}
|
|
400
408
|
|