officeparser 6.0.2 → 6.0.4

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.
@@ -154,8 +154,12 @@ export declare class SimpleRtfParser {
154
154
  * 2. **StyleMap**: RTF uses inline formatting rather than named style definitions.
155
155
  * There is no direct equivalent to DOCX's style.xml.
156
156
  *
157
- * 3. **Endnotes**: RTF uses `\footnote` for both footnotes and endnotes.
158
- * No separate endnote support exists in the format.
157
+ * **Note Support:**
158
+ * RTF supports both footnotes and endnotes using the `\footnote` group.
159
+ * The `\fet` control word distinguishes between them:
160
+ * - `\fet0` = footnotes only (default)
161
+ * - `\fet1` = endnotes only
162
+ * - `\fet2` = both footnotes and endnotes
159
163
  *
160
164
  * @param buffer The file buffer.
161
165
  * @param config The parser configuration.
@@ -276,8 +276,12 @@ exports.SimpleRtfParser = SimpleRtfParser;
276
276
  * 2. **StyleMap**: RTF uses inline formatting rather than named style definitions.
277
277
  * There is no direct equivalent to DOCX's style.xml.
278
278
  *
279
- * 3. **Endnotes**: RTF uses `\footnote` for both footnotes and endnotes.
280
- * No separate endnote support exists in the format.
279
+ * **Note Support:**
280
+ * RTF supports both footnotes and endnotes using the `\footnote` group.
281
+ * The `\fet` control word distinguishes between them:
282
+ * - `\fet0` = footnotes only (default)
283
+ * - `\fet1` = endnotes only
284
+ * - `\fet2` = both footnotes and endnotes
281
285
  *
282
286
  * @param buffer The file buffer.
283
287
  * @param config The parser configuration.
@@ -315,6 +319,14 @@ const parseRtf = async (buffer, config) => {
315
319
  let lastKnownListType;
316
320
  let tableStack = [];
317
321
  let currentFootnoteId = 0;
322
+ // ═══════════════════════════════════════════════════════════════════
323
+ // Note type tracking (footnotes vs endnotes)
324
+ // ═══════════════════════════════════════════════════════════════════
325
+ // RTF uses \fet to distinguish note types:
326
+ // \fet0 = footnotes only (default)
327
+ // \fet1 = endnotes only
328
+ // \fet2 = both footnotes and endnotes
329
+ let fetValue = 0; // Default to footnotes only
318
330
  // Helper to get current table context
319
331
  const getCurrentTable = () => tableStack.length > 0 ? tableStack[tableStack.length - 1] : undefined;
320
332
  // Helper to ensure a table context exists (for top-level tables)
@@ -956,12 +968,26 @@ const parseRtf = async (buffer, config) => {
956
968
  }
957
969
  flushParagraph();
958
970
  currentFootnoteId++;
971
+ // Determine note type based on \fet value
972
+ let noteType = 'footnote';
973
+ if (fetValue === 1) {
974
+ // \fet1 means all notes are endnotes
975
+ noteType = 'endnote';
976
+ }
977
+ else if (fetValue === 2) {
978
+ // \fet2 means both types exist
979
+ // Check for \ftnalt marker to distinguish endnotes from footnotes
980
+ // \footnote\ftnalt indicates an endnote
981
+ const hasFtnalt = node.content.some(child => child.type === 'control' && child.value === 'ftnalt');
982
+ noteType = hasFtnalt ? 'endnote' : 'footnote';
983
+ }
984
+ // fetValue === 0 (default) means footnotes only
959
985
  const noteNode = {
960
986
  type: 'note',
961
987
  children: [],
962
988
  metadata: {
963
989
  noteId: currentFootnoteId.toString(),
964
- noteType: 'footnote'
990
+ noteType: noteType
965
991
  }
966
992
  };
967
993
  notes.push(noteNode);
@@ -1325,6 +1351,15 @@ const parseRtf = async (buffer, config) => {
1325
1351
  formatting.color = colorTable[node.param];
1326
1352
  }
1327
1353
  }
1354
+ // Note type (\fet)
1355
+ else if (node.value === 'fet') {
1356
+ // \fet0 = footnotes only (default)
1357
+ // \fet1 = endnotes only
1358
+ // \fet2 = both footnotes and endnotes
1359
+ if (node.param !== undefined) {
1360
+ fetValue = node.param;
1361
+ }
1362
+ }
1328
1363
  // Background/highlight color (\cb, \highlight, \chcbpat, \cbpat)
1329
1364
  // \chcbpat = character background pattern color (used for shading)
1330
1365
  // \cbpat = paragraph background pattern color
@@ -1529,7 +1564,6 @@ const parseRtf = async (buffer, config) => {
1529
1564
  type: 'rtf',
1530
1565
  metadata: {
1531
1566
  // RTF Limitation: No style map available (RTF uses inline styles)
1532
- // RTF Limitation: No endnote support (uses footnotes for both)
1533
1567
  },
1534
1568
  content: content,
1535
1569
  attachments: attachments,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "officeparser",
3
- "version": "6.0.2",
3
+ "version": "6.0.4",
4
4
  "description": "A robust, strictly-typed Node.js and Browser library for parsing office files (.docx, .pptx, .xlsx, .odt, .odp, .ods, .pdf, .rtf) into structured AST with rich metadata, formatting, and attachment support.",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",
@@ -64,7 +64,7 @@
64
64
  "bugs": {
65
65
  "url": "https://github.com/harshankur/officeParser/issues"
66
66
  },
67
- "homepage": "https://github.com/harshankur/officeParser#readme",
67
+ "homepage": "https://harshankur.github.io/officeParser/",
68
68
  "dependencies": {
69
69
  "@xmldom/xmldom": "^0.8.10",
70
70
  "concat-stream": "^2.0.0",