pst-extractor 1.10.0 → 1.12.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.
@@ -16,7 +16,7 @@ export declare class PSTDescriptorItem {
16
16
  * @param {PSTFile} pstFile
17
17
  * @memberof PSTDescriptorItem
18
18
  */
19
- constructor(data: Buffer, offset: number, pstFile: PSTFile);
19
+ constructor(data: Buffer, offset: number, pstFile: PSTFile, entryType: number);
20
20
  /**
21
21
  * Get a node input stream from the offset index and read into a buffer.
22
22
  * @returns {Buffer}
@@ -25,7 +25,7 @@ class PSTDescriptorItem {
25
25
  * @param {PSTFile} pstFile
26
26
  * @memberof PSTDescriptorItem
27
27
  */
28
- constructor(data, offset, pstFile) {
28
+ constructor(data, offset, pstFile, entryType) {
29
29
  this.dataBlockData = null;
30
30
  this.dataBlockOffsets = [];
31
31
  this._pstFile = pstFile;
@@ -33,15 +33,25 @@ class PSTDescriptorItem {
33
33
  this._descriptorIdentifier = PSTUtil_class_1.PSTUtil.convertLittleEndianBytesToLong(data, offset, offset + 4).toNumber();
34
34
  this._offsetIndexIdentifier =
35
35
  PSTUtil_class_1.PSTUtil.convertLittleEndianBytesToLong(data, offset + 4, offset + 8).toNumber() & 0xfffffffe;
36
- this._subNodeOffsetIndexIdentifier =
37
- PSTUtil_class_1.PSTUtil.convertLittleEndianBytesToLong(data, offset + 8, offset + 12).toNumber() & 0xfffffffe;
36
+ if (entryType == PSTFile_class_1.PSTFile.SLBLOCK_ENTRY) {
37
+ this._subNodeOffsetIndexIdentifier =
38
+ PSTUtil_class_1.PSTUtil.convertLittleEndianBytesToLong(data, offset + 8, offset + 12).toNumber() & 0xfffffffe;
39
+ }
40
+ else {
41
+ this._subNodeOffsetIndexIdentifier = 0;
42
+ }
38
43
  }
39
44
  else {
40
45
  this._descriptorIdentifier = PSTUtil_class_1.PSTUtil.convertLittleEndianBytesToLong(data, offset, offset + 4).toNumber();
41
46
  this._offsetIndexIdentifier =
42
47
  PSTUtil_class_1.PSTUtil.convertLittleEndianBytesToLong(data, offset + 8, offset + 16).toNumber() & 0xfffffffe;
43
- this._subNodeOffsetIndexIdentifier =
44
- PSTUtil_class_1.PSTUtil.convertLittleEndianBytesToLong(data, offset + 16, offset + 24).toNumber() & 0xfffffffe;
48
+ if (entryType == PSTFile_class_1.PSTFile.SLBLOCK_ENTRY) {
49
+ this._subNodeOffsetIndexIdentifier =
50
+ PSTUtil_class_1.PSTUtil.convertLittleEndianBytesToLong(data, offset + 16, offset + 24).toNumber() & 0xfffffffe;
51
+ }
52
+ else {
53
+ this._subNodeOffsetIndexIdentifier = 0;
54
+ }
45
55
  }
46
56
  }
47
57
  /**
@@ -24,6 +24,8 @@ export declare class PSTFile {
24
24
  static PS_MAPI: number;
25
25
  static PSETID_AirSync: number;
26
26
  static PSETID_Sharing: number;
27
+ static SLBLOCK_ENTRY: number;
28
+ static SIBLOCK_ENTRY: number;
27
29
  private guidMap;
28
30
  private _encryptionType;
29
31
  get encryptionType(): number;
@@ -15,13 +15,23 @@ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (
15
15
  }) : function(o, v) {
16
16
  o["default"] = v;
17
17
  });
18
- var __importStar = (this && this.__importStar) || function (mod) {
19
- if (mod && mod.__esModule) return mod;
20
- var result = {};
21
- if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
22
- __setModuleDefault(result, mod);
23
- return result;
24
- };
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
25
35
  var __importDefault = (this && this.__importDefault) || function (mod) {
26
36
  return (mod && mod.__esModule) ? mod : { "default": mod };
27
37
  };
@@ -218,10 +228,12 @@ class PSTFile {
218
228
  // identifier is a string
219
229
  // key is byte offset into the String stream in which the string name of the property is stored.
220
230
  const len = PSTUtil_class_1.PSTUtil.convertLittleEndianBytesToLong(stringNameToIdByte, key, key + 4).toNumber();
221
- const keyByteValue = Buffer.alloc(len);
222
- PSTUtil_class_1.PSTUtil.arraycopy(stringNameToIdByte, key + 4, keyByteValue, 0, keyByteValue.length);
223
- propId += 0x8000;
224
- PSTFile.nodeMap.setId(keyByteValue.toString('utf16le').replace(/\0/g, ''), propId);
231
+ if (len > 0 && len <= stringNameToIdByte.length) {
232
+ const keyByteValue = Buffer.alloc(len);
233
+ PSTUtil_class_1.PSTUtil.arraycopy(stringNameToIdByte, key + 4, keyByteValue, 0, keyByteValue.length);
234
+ propId += 0x8000;
235
+ PSTFile.nodeMap.setId(keyByteValue.toString('utf16le').replace(/\0/g, ''), propId);
236
+ }
225
237
  }
226
238
  }
227
239
  }
@@ -590,6 +602,11 @@ class PSTFile {
590
602
  throw new Error('PSTFile::getPSTDescriptorItems Unable to process descriptor node, bad signature: ' +
591
603
  sig);
592
604
  }
605
+ // NID nodes defines in subnode can be either SLBLOCK (0) or SIBLOCK_ENTRY (1)
606
+ const blockType = inputStream.read();
607
+ if ((blockType !== PSTFile.SLBLOCK_ENTRY) && (blockType !== PSTFile.SIBLOCK_ENTRY)) {
608
+ throw new Error("Unable to process descriptor node, unknown BLOCK type: " + blockType);
609
+ }
593
610
  const output = new Map();
594
611
  const numberOfItems = inputStream.seekAndReadLong(long_1.default.fromValue(2), 2);
595
612
  let offset;
@@ -603,13 +620,31 @@ class PSTFile {
603
620
  inputStream.seek(long_1.default.ZERO);
604
621
  inputStream.readCompletely(data);
605
622
  for (let x = 0; x < numberOfItems.toNumber(); x++) {
606
- const item = new PSTDescriptorItem_class_1.PSTDescriptorItem(data, offset, this);
607
- output.set(item.descriptorIdentifier, item);
623
+ const item = new PSTDescriptorItem_class_1.PSTDescriptorItem(data, offset, this, blockType);
624
+ if (blockType == PSTFile.SLBLOCK_ENTRY) {
625
+ output.set(item.descriptorIdentifier, item);
626
+ }
627
+ else {
628
+ const subItems = this.getPSTDescriptorItems(long_1.default.fromNumber(item.offsetIndexIdentifier));
629
+ subItems.forEach((value, key) => {
630
+ output.set(key, value);
631
+ });
632
+ }
608
633
  if (this._pstFileType === PSTFile.PST_TYPE_ANSI) {
609
- offset += 12;
634
+ if (blockType === PSTFile.SLBLOCK_ENTRY) {
635
+ offset += 12;
636
+ }
637
+ else {
638
+ offset += 8;
639
+ }
610
640
  }
611
641
  else {
612
- offset += 24;
642
+ if (blockType === PSTFile.SLBLOCK_ENTRY) {
643
+ offset += 24;
644
+ }
645
+ else {
646
+ offset += 16;
647
+ }
613
648
  }
614
649
  }
615
650
  return output;
@@ -814,5 +849,7 @@ PSTFile.PSETID_UnifiedMessaging = 11;
814
849
  PSTFile.PS_MAPI = 12;
815
850
  PSTFile.PSETID_AirSync = 13;
816
851
  PSTFile.PSETID_Sharing = 14;
852
+ PSTFile.SLBLOCK_ENTRY = 0;
853
+ PSTFile.SIBLOCK_ENTRY = 1;
817
854
  // node tree maps
818
855
  PSTFile.nodeMap = new NodeMap_class_1.NodeMap();
@@ -15,13 +15,23 @@ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (
15
15
  }) : function(o, v) {
16
16
  o["default"] = v;
17
17
  });
18
- var __importStar = (this && this.__importStar) || function (mod) {
19
- if (mod && mod.__esModule) return mod;
20
- var result = {};
21
- if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
22
- __setModuleDefault(result, mod);
23
- return result;
24
- };
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
25
35
  var __importDefault = (this && this.__importDefault) || function (mod) {
26
36
  return (mod && mod.__esModule) ? mod : { "default": mod };
27
37
  };
@@ -178,15 +178,17 @@ class PSTTable7C extends PSTTable_class_1.PSTTable {
178
178
  currentItem.set(item.entryType.toNumber(), item);
179
179
  let col = 0;
180
180
  if (this.overrideCol > -1) {
181
- col = this.overrideCol - 1;
181
+ col = this.overrideCol;
182
182
  }
183
- while (col < this.numColumns - 1) {
184
- col++;
183
+ while (col < this.numColumns) {
185
184
  // Does this column exist for this row?
186
185
  const bitIndex = Math.trunc(this.columnDescriptors[col].iBit / 8);
187
186
  const bit = this.columnDescriptors[col].iBit % 8;
188
- if (bitIndex >= bitmap.length || (bitmap[bitIndex] & (1 << bit)) == 0) {
187
+ // https://learn.microsoft.com/en-us/openspecs/office_file_formats/ms-pst/c48fa6b4-bfd4-49d7-80f8-8718bc4bcddc
188
+ if (bitIndex >= bitmap.length ||
189
+ (bitmap[bitIndex] & (1 << (7 - bit))) == 0) {
189
190
  // Column doesn't exist
191
+ col++;
190
192
  continue;
191
193
  }
192
194
  item = new PSTTableItem_class_1.PSTTableItem();
@@ -248,6 +250,7 @@ class PSTTable7C extends PSTTable_class_1.PSTTable {
248
250
  }
249
251
  break;
250
252
  }
253
+ col++;
251
254
  currentItem.set(item.entryType.toNumber(), item);
252
255
  }
253
256
  itemList[dataSetNumber] = currentItem;
@@ -101,10 +101,8 @@ class PSTUtil {
101
101
  }
102
102
  }
103
103
  catch (err) {
104
- console.error('PSTUtil::createJavascriptString Unable to decode string\n' + err);
105
- throw err;
104
+ return iconv_lite_1.default.decode(data, 'utf8').toString();
106
105
  }
107
- return '';
108
106
  }
109
107
  /**
110
108
  * Copy from one array to another
@@ -6,12 +6,12 @@
6
6
  "pst-extractor": "link:.."
7
7
  },
8
8
  "devDependencies": {
9
- "@types/node": "^20.14.10",
10
- "eslint-config-prettier": "^9.1.0",
11
- "eslint-plugin-prettier": "^5.1.3",
12
- "prettier": "^3.3.3",
9
+ "@types/node": "^22.10.7",
10
+ "eslint-config-prettier": "^10.0.1",
11
+ "eslint-plugin-prettier": "^5.2.2",
12
+ "prettier": "^3.4.2",
13
13
  "ts-node": "^10.9.2",
14
- "typescript": "^5.5.3"
14
+ "typescript": "^5.7.3"
15
15
  },
16
16
  "scripts": {
17
17
  "start": "ts-node test-min.ts",