@json-to-office/core-docx 0.19.0 → 0.21.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/dist/components/highcharts.d.ts.map +1 -1
- package/dist/components/section.d.ts.map +1 -1
- package/dist/core/cached-render.d.ts.map +1 -1
- package/dist/core/content.d.ts.map +1 -1
- package/dist/core/generator.d.ts +6 -2
- package/dist/core/generator.d.ts.map +1 -1
- package/dist/core/render.d.ts +8 -6
- package/dist/core/render.d.ts.map +1 -1
- package/dist/core/structure.d.ts +2 -2
- package/dist/core/structure.d.ts.map +1 -1
- package/dist/index.js +414 -345
- package/dist/index.js.map +1 -1
- package/dist/plugin/createDocumentGenerator.d.ts +4 -0
- package/dist/plugin/createDocumentGenerator.d.ts.map +1 -1
- package/dist/plugin/example/index.js +394 -287
- package/dist/plugin/example/index.js.map +1 -1
- package/dist/plugin/types.d.ts +4 -0
- package/dist/plugin/types.d.ts.map +1 -1
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/dist/utils/bookmarkRegistry.d.ts +5 -2
- package/dist/utils/bookmarkRegistry.d.ts.map +1 -1
- package/dist/utils/fixFloatingImageIds.d.ts +3 -0
- package/dist/utils/fixFloatingImageIds.d.ts.map +1 -1
- package/dist/utils/generationContext.d.ts +5 -0
- package/dist/utils/generationContext.d.ts.map +1 -0
- package/dist/utils/numberingConfig.d.ts +5 -2
- package/dist/utils/numberingConfig.d.ts.map +1 -1
- package/dist/utils/packageDocument.d.ts +20 -0
- package/dist/utils/packageDocument.d.ts.map +1 -0
- package/dist/utils/placeholderProcessor.d.ts +5 -5
- package/dist/utils/placeholderProcessor.d.ts.map +1 -1
- package/dist/utils/revisionUtils.d.ts +5 -5
- package/dist/utils/revisionUtils.d.ts.map +1 -1
- package/dist/utils/textParser.d.ts +3 -3
- package/dist/utils/textParser.d.ts.map +1 -1
- package/package.json +3 -3
|
@@ -1613,219 +1613,11 @@ var init_docxImagePositioning = __esm({
|
|
|
1613
1613
|
}
|
|
1614
1614
|
});
|
|
1615
1615
|
|
|
1616
|
-
// src/utils/numberingConfig.ts
|
|
1617
|
-
var numberingConfig_exports = {};
|
|
1618
|
-
__export(numberingConfig_exports, {
|
|
1619
|
-
NumberingRegistry: () => NumberingRegistry,
|
|
1620
|
-
createBulletListConfig: () => createBulletListConfig,
|
|
1621
|
-
createNumberedListConfig: () => createNumberedListConfig,
|
|
1622
|
-
createNumberingConfig: () => createNumberingConfig,
|
|
1623
|
-
globalNumberingRegistry: () => globalNumberingRegistry
|
|
1624
|
-
});
|
|
1625
|
-
import { AlignmentType as AlignmentType3, convertInchesToTwip, LevelFormat } from "docx";
|
|
1626
|
-
function getLevelFormat(format2) {
|
|
1627
|
-
if (!format2) return LevelFormat.BULLET;
|
|
1628
|
-
return LEVEL_FORMAT_MAP[format2] || LevelFormat.BULLET;
|
|
1629
|
-
}
|
|
1630
|
-
function getAlignment2(alignment) {
|
|
1631
|
-
if (!alignment) return AlignmentType3.LEFT;
|
|
1632
|
-
return ALIGNMENT_MAP[alignment] || AlignmentType3.LEFT;
|
|
1633
|
-
}
|
|
1634
|
-
function createDefaultLevel(level, format2 = LevelFormat.BULLET, text) {
|
|
1635
|
-
const baseIndent = 0.5 * (level + 1);
|
|
1636
|
-
const hangingIndent = 0.25;
|
|
1637
|
-
return {
|
|
1638
|
-
level,
|
|
1639
|
-
format: format2,
|
|
1640
|
-
text: text || (format2 === LevelFormat.BULLET ? "\u2022" : "%1."),
|
|
1641
|
-
alignment: AlignmentType3.LEFT,
|
|
1642
|
-
style: {
|
|
1643
|
-
paragraph: {
|
|
1644
|
-
indent: {
|
|
1645
|
-
left: convertInchesToTwip(baseIndent),
|
|
1646
|
-
hanging: convertInchesToTwip(hangingIndent)
|
|
1647
|
-
}
|
|
1648
|
-
}
|
|
1649
|
-
}
|
|
1650
|
-
};
|
|
1651
|
-
}
|
|
1652
|
-
function createNumberingConfig(config) {
|
|
1653
|
-
const levels = [];
|
|
1654
|
-
for (const levelConfig of config.levels) {
|
|
1655
|
-
const format2 = getLevelFormat(levelConfig.format);
|
|
1656
|
-
const alignment = getAlignment2(levelConfig.alignment);
|
|
1657
|
-
const text = levelConfig.text || (format2 === LevelFormat.BULLET ? "\u2022" : `%${levelConfig.level + 1}.`);
|
|
1658
|
-
const baseIndent = levelConfig.indent?.left !== void 0 ? levelConfig.indent.left / 72 : 0.5 * (levelConfig.level + 1);
|
|
1659
|
-
const hangingIndent = levelConfig.indent?.hanging !== void 0 ? levelConfig.indent.hanging / 72 : 0.25;
|
|
1660
|
-
const level = {
|
|
1661
|
-
level: levelConfig.level,
|
|
1662
|
-
format: format2,
|
|
1663
|
-
text,
|
|
1664
|
-
alignment,
|
|
1665
|
-
style: {
|
|
1666
|
-
paragraph: {
|
|
1667
|
-
indent: {
|
|
1668
|
-
left: convertInchesToTwip(baseIndent),
|
|
1669
|
-
hanging: convertInchesToTwip(hangingIndent)
|
|
1670
|
-
}
|
|
1671
|
-
}
|
|
1672
|
-
},
|
|
1673
|
-
// Add start number if specified
|
|
1674
|
-
...levelConfig.start !== void 0 && { start: levelConfig.start }
|
|
1675
|
-
};
|
|
1676
|
-
levels.push(level);
|
|
1677
|
-
}
|
|
1678
|
-
return {
|
|
1679
|
-
reference: config.reference,
|
|
1680
|
-
levels
|
|
1681
|
-
};
|
|
1682
|
-
}
|
|
1683
|
-
function createBulletListConfig(reference, bullet = "\u2022") {
|
|
1684
|
-
return {
|
|
1685
|
-
reference,
|
|
1686
|
-
levels: [
|
|
1687
|
-
createDefaultLevel(0, LevelFormat.BULLET, bullet),
|
|
1688
|
-
createDefaultLevel(1, LevelFormat.BULLET, "\u25E6"),
|
|
1689
|
-
createDefaultLevel(2, LevelFormat.BULLET, "\u25AA")
|
|
1690
|
-
]
|
|
1691
|
-
};
|
|
1692
|
-
}
|
|
1693
|
-
function createNumberedListConfig(reference, start = 1) {
|
|
1694
|
-
return {
|
|
1695
|
-
reference,
|
|
1696
|
-
levels: [
|
|
1697
|
-
{ ...createDefaultLevel(0, LevelFormat.DECIMAL, "%1."), start },
|
|
1698
|
-
createDefaultLevel(1, LevelFormat.LOWER_LETTER, "%2."),
|
|
1699
|
-
createDefaultLevel(2, LevelFormat.LOWER_ROMAN, "%3.")
|
|
1700
|
-
]
|
|
1701
|
-
};
|
|
1702
|
-
}
|
|
1703
|
-
var LEVEL_FORMAT_MAP, ALIGNMENT_MAP, NumberingRegistry, globalNumberingRegistry;
|
|
1704
|
-
var init_numberingConfig = __esm({
|
|
1705
|
-
"src/utils/numberingConfig.ts"() {
|
|
1706
|
-
"use strict";
|
|
1707
|
-
LEVEL_FORMAT_MAP = {
|
|
1708
|
-
decimal: LevelFormat.DECIMAL,
|
|
1709
|
-
upperRoman: LevelFormat.UPPER_ROMAN,
|
|
1710
|
-
lowerRoman: LevelFormat.LOWER_ROMAN,
|
|
1711
|
-
upperLetter: LevelFormat.UPPER_LETTER,
|
|
1712
|
-
lowerLetter: LevelFormat.LOWER_LETTER,
|
|
1713
|
-
bullet: LevelFormat.BULLET,
|
|
1714
|
-
ordinal: LevelFormat.ORDINAL,
|
|
1715
|
-
cardinalText: LevelFormat.CARDINAL_TEXT,
|
|
1716
|
-
ordinalText: LevelFormat.ORDINAL_TEXT,
|
|
1717
|
-
hex: LevelFormat.HEX,
|
|
1718
|
-
chicago: LevelFormat.CHICAGO,
|
|
1719
|
-
ideographDigital: LevelFormat.IDEOGRAPH__DIGITAL,
|
|
1720
|
-
japaneseCounting: LevelFormat.JAPANESE_COUNTING,
|
|
1721
|
-
aiueo: LevelFormat.AIUEO,
|
|
1722
|
-
iroha: LevelFormat.IROHA,
|
|
1723
|
-
decimalFullWidth: LevelFormat.DECIMAL_FULL_WIDTH,
|
|
1724
|
-
decimalHalfWidth: LevelFormat.DECIMAL_HALF_WIDTH,
|
|
1725
|
-
japaneseLegal: LevelFormat.JAPANESE_LEGAL,
|
|
1726
|
-
japaneseDigitalTenThousand: LevelFormat.JAPANESE_DIGITAL_TEN_THOUSAND,
|
|
1727
|
-
decimalEnclosedCircle: LevelFormat.DECIMAL_ENCLOSED_CIRCLE,
|
|
1728
|
-
decimalFullWidth2: LevelFormat.DECIMAL_FULL_WIDTH2,
|
|
1729
|
-
aiueoFullWidth: LevelFormat.AIUEO_FULL_WIDTH,
|
|
1730
|
-
irohaFullWidth: LevelFormat.IROHA_FULL_WIDTH,
|
|
1731
|
-
decimalZero: LevelFormat.DECIMAL_ZERO,
|
|
1732
|
-
ganada: LevelFormat.GANADA,
|
|
1733
|
-
chosung: LevelFormat.CHOSUNG,
|
|
1734
|
-
decimalEnclosedFullstop: LevelFormat.DECIMAL_ENCLOSED_FULLSTOP,
|
|
1735
|
-
decimalEnclosedParen: LevelFormat.DECIMAL_ENCLOSED_PARENTHESES,
|
|
1736
|
-
decimalEnclosedCircleChinese: LevelFormat.DECIMAL_ENCLOSED_CIRCLE_CHINESE,
|
|
1737
|
-
ideographEnclosedCircle: LevelFormat.IDEOGRAPH_ENCLOSED_CIRCLE,
|
|
1738
|
-
ideographTraditional: LevelFormat.IDEOGRAPH_TRADITIONAL,
|
|
1739
|
-
ideographZodiac: LevelFormat.IDEOGRAPH_ZODIAC,
|
|
1740
|
-
ideographZodiacTraditional: LevelFormat.IDEOGRAPH_ZODIAC_TRADITIONAL,
|
|
1741
|
-
taiwaneseCounting: LevelFormat.TAIWANESE_COUNTING,
|
|
1742
|
-
ideographLegalTraditional: LevelFormat.IDEOGRAPH_LEGAL_TRADITIONAL,
|
|
1743
|
-
taiwaneseCountingThousand: LevelFormat.TAIWANESE_COUNTING_THOUSAND,
|
|
1744
|
-
taiwaneseDigital: LevelFormat.TAIWANESE_DIGITAL,
|
|
1745
|
-
chineseCounting: LevelFormat.CHINESE_COUNTING,
|
|
1746
|
-
chineseLegalSimplified: LevelFormat.CHINESE_LEGAL_SIMPLIFIED,
|
|
1747
|
-
chineseCountingThousand: LevelFormat.CHINESE_COUNTING_THOUSAND,
|
|
1748
|
-
koreanDigital: LevelFormat.KOREAN_DIGITAL,
|
|
1749
|
-
koreanCounting: LevelFormat.KOREAN_COUNTING,
|
|
1750
|
-
koreanLegal: LevelFormat.KOREAN_LEGAL,
|
|
1751
|
-
koreanDigital2: LevelFormat.KOREAN_DIGITAL2,
|
|
1752
|
-
vietnameseCounting: LevelFormat.VIETNAMESE_COUNTING,
|
|
1753
|
-
russianLower: LevelFormat.RUSSIAN_LOWER,
|
|
1754
|
-
russianUpper: LevelFormat.RUSSIAN_UPPER,
|
|
1755
|
-
none: LevelFormat.NONE,
|
|
1756
|
-
numberInDash: LevelFormat.NUMBER_IN_DASH,
|
|
1757
|
-
hebrew1: LevelFormat.HEBREW1,
|
|
1758
|
-
hebrew2: LevelFormat.HEBREW2,
|
|
1759
|
-
arabicAlpha: LevelFormat.ARABIC_ALPHA,
|
|
1760
|
-
arabicAbjad: LevelFormat.ARABIC_ABJAD,
|
|
1761
|
-
hindiVowels: LevelFormat.HINDI_VOWELS,
|
|
1762
|
-
hindiConsonants: LevelFormat.HINDI_CONSONANTS,
|
|
1763
|
-
hindiNumbers: LevelFormat.HINDI_NUMBERS,
|
|
1764
|
-
hindiCounting: LevelFormat.HINDI_COUNTING,
|
|
1765
|
-
thaiLetters: LevelFormat.THAI_LETTERS,
|
|
1766
|
-
thaiNumbers: LevelFormat.THAI_NUMBERS,
|
|
1767
|
-
thaiCounting: LevelFormat.THAI_COUNTING
|
|
1768
|
-
};
|
|
1769
|
-
ALIGNMENT_MAP = {
|
|
1770
|
-
start: AlignmentType3.START,
|
|
1771
|
-
end: AlignmentType3.END,
|
|
1772
|
-
left: AlignmentType3.LEFT,
|
|
1773
|
-
right: AlignmentType3.RIGHT,
|
|
1774
|
-
center: AlignmentType3.CENTER
|
|
1775
|
-
};
|
|
1776
|
-
NumberingRegistry = class {
|
|
1777
|
-
configs = /* @__PURE__ */ new Map();
|
|
1778
|
-
counter = 0;
|
|
1779
|
-
/**
|
|
1780
|
-
* Register a numbering configuration
|
|
1781
|
-
*/
|
|
1782
|
-
register(config) {
|
|
1783
|
-
const reference = config.reference;
|
|
1784
|
-
this.configs.set(reference, config);
|
|
1785
|
-
return reference;
|
|
1786
|
-
}
|
|
1787
|
-
/**
|
|
1788
|
-
* Generate a unique reference ID
|
|
1789
|
-
*/
|
|
1790
|
-
generateReference(prefix = "list") {
|
|
1791
|
-
return `${prefix}-${++this.counter}`;
|
|
1792
|
-
}
|
|
1793
|
-
/**
|
|
1794
|
-
* Get all registered configurations as an array suitable for INumberingOptions
|
|
1795
|
-
*/
|
|
1796
|
-
getAll() {
|
|
1797
|
-
return Array.from(this.configs.values());
|
|
1798
|
-
}
|
|
1799
|
-
/**
|
|
1800
|
-
* Clear all configurations
|
|
1801
|
-
*/
|
|
1802
|
-
clear() {
|
|
1803
|
-
this.configs.clear();
|
|
1804
|
-
this.counter = 0;
|
|
1805
|
-
}
|
|
1806
|
-
/**
|
|
1807
|
-
* Check if a reference exists
|
|
1808
|
-
*/
|
|
1809
|
-
has(reference) {
|
|
1810
|
-
return this.configs.has(reference);
|
|
1811
|
-
}
|
|
1812
|
-
/**
|
|
1813
|
-
* Get a configuration by reference
|
|
1814
|
-
*/
|
|
1815
|
-
get(reference) {
|
|
1816
|
-
return this.configs.get(reference);
|
|
1817
|
-
}
|
|
1818
|
-
};
|
|
1819
|
-
globalNumberingRegistry = new NumberingRegistry();
|
|
1820
|
-
}
|
|
1821
|
-
});
|
|
1822
|
-
|
|
1823
1616
|
// src/plugin/example/index.ts
|
|
1824
1617
|
import { Packer as Packer2 } from "docx";
|
|
1825
1618
|
|
|
1826
1619
|
// src/plugin/createDocumentGenerator.ts
|
|
1827
1620
|
init_styles();
|
|
1828
|
-
import { Packer } from "docx";
|
|
1829
1621
|
import { applyExportMode, scopedThemeName } from "@json-to-office/shared";
|
|
1830
1622
|
|
|
1831
1623
|
// src/core/fontResolution.ts
|
|
@@ -2192,8 +1984,8 @@ function resolveComponentTree(components, theme) {
|
|
|
2192
1984
|
}
|
|
2193
1985
|
|
|
2194
1986
|
// src/core/structure.ts
|
|
2195
|
-
async function processDocument(document, theme, themeName) {
|
|
2196
|
-
const metadata = createDocumentMetadata(document.props);
|
|
1987
|
+
async function processDocument(document, theme, themeName, generationDate) {
|
|
1988
|
+
const metadata = createDocumentMetadata(document.props, generationDate);
|
|
2197
1989
|
const docDefaults = document.props.componentDefaults;
|
|
2198
1990
|
const mergedComponentDefaults = docDefaults ? mergeWithDefaults2(docDefaults, theme.componentDefaults || {}) : void 0;
|
|
2199
1991
|
const docNoProofWords = document.props.noProofWords;
|
|
@@ -2231,13 +2023,13 @@ async function processDocument(document, theme, themeName) {
|
|
|
2231
2023
|
language: document.props.language
|
|
2232
2024
|
};
|
|
2233
2025
|
}
|
|
2234
|
-
function createDocumentMetadata(props) {
|
|
2026
|
+
function createDocumentMetadata(props, generationDate = /* @__PURE__ */ new Date()) {
|
|
2235
2027
|
return {
|
|
2236
2028
|
title: props.metadata?.title,
|
|
2237
2029
|
subtitle: props.metadata?.subtitle,
|
|
2238
2030
|
author: props.metadata?.author,
|
|
2239
2031
|
company: props.metadata?.company,
|
|
2240
|
-
date: props.metadata?.date ? new Date(props.metadata.date) :
|
|
2032
|
+
date: props.metadata?.date ? new Date(props.metadata.date) : generationDate
|
|
2241
2033
|
};
|
|
2242
2034
|
}
|
|
2243
2035
|
async function extractSections(components, context) {
|
|
@@ -3900,7 +3692,39 @@ function parseTextWithHyperlinks(text, baseStyle = {}, options = {}) {
|
|
|
3900
3692
|
return runs;
|
|
3901
3693
|
}
|
|
3902
3694
|
|
|
3695
|
+
// src/utils/generationContext.ts
|
|
3696
|
+
import { AsyncLocalStorage } from "async_hooks";
|
|
3697
|
+
var generationDateStorage = new AsyncLocalStorage();
|
|
3698
|
+
function runWithGenerationDate(date, callback) {
|
|
3699
|
+
return generationDateStorage.run(date, callback);
|
|
3700
|
+
}
|
|
3701
|
+
function getGenerationDate() {
|
|
3702
|
+
return generationDateStorage.getStore() ?? /* @__PURE__ */ new Date();
|
|
3703
|
+
}
|
|
3704
|
+
|
|
3903
3705
|
// src/utils/placeholderProcessor.ts
|
|
3706
|
+
function styledPlaceholderText(text, context) {
|
|
3707
|
+
return new TextRun2({
|
|
3708
|
+
text,
|
|
3709
|
+
font: context?.style?.font,
|
|
3710
|
+
size: context?.style?.size,
|
|
3711
|
+
color: context?.style?.color,
|
|
3712
|
+
bold: context?.style?.bold,
|
|
3713
|
+
italics: context?.style?.italics,
|
|
3714
|
+
underline: context?.style?.underline,
|
|
3715
|
+
language: context?.style?.language,
|
|
3716
|
+
noProof: context?.style?.noProof
|
|
3717
|
+
});
|
|
3718
|
+
}
|
|
3719
|
+
function placeholderDate(context) {
|
|
3720
|
+
return context?.date ?? getGenerationDate();
|
|
3721
|
+
}
|
|
3722
|
+
function isoDate(date) {
|
|
3723
|
+
return date.toISOString().slice(0, 10);
|
|
3724
|
+
}
|
|
3725
|
+
function isoDateTime(date) {
|
|
3726
|
+
return date.toISOString().replace("T", " ").replace(/\.\d{3}Z$/, "Z");
|
|
3727
|
+
}
|
|
3904
3728
|
var PlaceholderRegistry = class {
|
|
3905
3729
|
static handlers = /* @__PURE__ */ new Map();
|
|
3906
3730
|
/**
|
|
@@ -3956,8 +3780,6 @@ function processTextWithPlaceholders(text, baseStyle = {}, context = {}, noProof
|
|
|
3956
3780
|
const placeholderResult = handler({ ...context, style: baseStyle });
|
|
3957
3781
|
if (Array.isArray(placeholderResult)) {
|
|
3958
3782
|
result.push(...placeholderResult);
|
|
3959
|
-
} else if (placeholderResult instanceof TextRun2) {
|
|
3960
|
-
result.push(placeholderResult);
|
|
3961
3783
|
} else if (typeof placeholderResult === "string") {
|
|
3962
3784
|
result.push(
|
|
3963
3785
|
...createTextRunsWithNewlines2(
|
|
@@ -3966,6 +3788,8 @@ function processTextWithPlaceholders(text, baseStyle = {}, context = {}, noProof
|
|
|
3966
3788
|
noProofWords
|
|
3967
3789
|
)
|
|
3968
3790
|
);
|
|
3791
|
+
} else {
|
|
3792
|
+
result.push(placeholderResult);
|
|
3969
3793
|
}
|
|
3970
3794
|
} else {
|
|
3971
3795
|
result.push(
|
|
@@ -4080,59 +3904,51 @@ function initializeBuiltinPlaceholders() {
|
|
|
4080
3904
|
underline: context?.style?.underline
|
|
4081
3905
|
});
|
|
4082
3906
|
});
|
|
4083
|
-
PlaceholderRegistry.register(
|
|
4084
|
-
|
|
4085
|
-
|
|
4086
|
-
|
|
4087
|
-
|
|
4088
|
-
|
|
4089
|
-
|
|
4090
|
-
|
|
4091
|
-
|
|
4092
|
-
|
|
4093
|
-
|
|
4094
|
-
|
|
4095
|
-
|
|
4096
|
-
|
|
4097
|
-
|
|
4098
|
-
const dateTimeString = now.toLocaleString();
|
|
4099
|
-
return new TextRun2({
|
|
4100
|
-
text: dateTimeString,
|
|
4101
|
-
font: context?.style?.font,
|
|
4102
|
-
size: context?.style?.size,
|
|
4103
|
-
color: context?.style?.color,
|
|
4104
|
-
bold: context?.style?.bold,
|
|
4105
|
-
italics: context?.style?.italics,
|
|
4106
|
-
underline: context?.style?.underline
|
|
4107
|
-
});
|
|
4108
|
-
});
|
|
4109
|
-
PlaceholderRegistry.register("YEAR", (context) => {
|
|
4110
|
-
const year = (/* @__PURE__ */ new Date()).getFullYear().toString();
|
|
4111
|
-
return new TextRun2({
|
|
4112
|
-
text: year,
|
|
4113
|
-
font: context?.style?.font,
|
|
4114
|
-
size: context?.style?.size,
|
|
4115
|
-
color: context?.style?.color,
|
|
4116
|
-
bold: context?.style?.bold,
|
|
4117
|
-
italics: context?.style?.italics,
|
|
4118
|
-
underline: context?.style?.underline
|
|
4119
|
-
});
|
|
4120
|
-
});
|
|
3907
|
+
PlaceholderRegistry.register(
|
|
3908
|
+
"DATE",
|
|
3909
|
+
(context) => styledPlaceholderText(isoDate(placeholderDate(context)), context)
|
|
3910
|
+
);
|
|
3911
|
+
PlaceholderRegistry.register(
|
|
3912
|
+
"DATETIME",
|
|
3913
|
+
(context) => styledPlaceholderText(isoDateTime(placeholderDate(context)), context)
|
|
3914
|
+
);
|
|
3915
|
+
PlaceholderRegistry.register(
|
|
3916
|
+
"YEAR",
|
|
3917
|
+
(context) => styledPlaceholderText(
|
|
3918
|
+
String(placeholderDate(context).getUTCFullYear()),
|
|
3919
|
+
context
|
|
3920
|
+
)
|
|
3921
|
+
);
|
|
4121
3922
|
}
|
|
4122
3923
|
initializeBuiltinPlaceholders();
|
|
4123
3924
|
|
|
4124
3925
|
// src/utils/revisionUtils.ts
|
|
3926
|
+
import { AsyncLocalStorage as AsyncLocalStorage2 } from "async_hooks";
|
|
4125
3927
|
var DEFAULT_REVISION_AUTHOR = "json-to-office";
|
|
4126
3928
|
var DEFAULT_REVISION_DATE = "1970-01-01T00:00:00Z";
|
|
4127
3929
|
var RevisionIdRegistry = class {
|
|
4128
|
-
|
|
3930
|
+
fallbackCounter = 0;
|
|
3931
|
+
scopes = new AsyncLocalStorage2();
|
|
3932
|
+
runScoped(callback) {
|
|
3933
|
+
return this.scopes.run({ counter: 0 }, callback);
|
|
3934
|
+
}
|
|
4129
3935
|
next() {
|
|
4130
|
-
this.
|
|
4131
|
-
|
|
3936
|
+
const state = this.scopes.getStore();
|
|
3937
|
+
if (state) {
|
|
3938
|
+
state.counter += 1;
|
|
3939
|
+
return state.counter;
|
|
3940
|
+
}
|
|
3941
|
+
this.fallbackCounter += 1;
|
|
3942
|
+
return this.fallbackCounter;
|
|
4132
3943
|
}
|
|
4133
3944
|
/** Test-only: deterministic ids for snapshot assertions. */
|
|
4134
3945
|
clear() {
|
|
4135
|
-
|
|
3946
|
+
const state = this.scopes.getStore();
|
|
3947
|
+
if (state) {
|
|
3948
|
+
state.counter = 0;
|
|
3949
|
+
} else {
|
|
3950
|
+
this.fallbackCounter = 0;
|
|
3951
|
+
}
|
|
4136
3952
|
}
|
|
4137
3953
|
};
|
|
4138
3954
|
var globalRevisionIdRegistry = new RevisionIdRegistry();
|
|
@@ -4252,7 +4068,10 @@ function initializeComponentCache(cache) {
|
|
|
4252
4068
|
}
|
|
4253
4069
|
}
|
|
4254
4070
|
async function renderComponentWithCache(component, theme, themeName, context, bypassCache = false) {
|
|
4255
|
-
const forceBypassForType = component.name === "toc" || component.name === "section" || component.name === "visual" ||
|
|
4071
|
+
const forceBypassForType = component.name === "toc" || component.name === "section" || component.name === "visual" || component.name === "heading" || // Both explicit lists and markdown-list paragraphs register numbering in
|
|
4072
|
+
// the current document scope. Cached paragraphs can otherwise reference
|
|
4073
|
+
// definitions that only existed in a previous render.
|
|
4074
|
+
component.name === "list" || component.name === "paragraph" || "id" in component || componentHasRevision(component);
|
|
4256
4075
|
if (!componentCache) {
|
|
4257
4076
|
initializeComponentCache();
|
|
4258
4077
|
}
|
|
@@ -4262,8 +4081,9 @@ async function renderComponentWithCache(component, theme, themeName, context, by
|
|
|
4262
4081
|
const componentProps = JSON.stringify(component.props || {});
|
|
4263
4082
|
const themeHash = createThemeHash(theme);
|
|
4264
4083
|
const contextKey = context?.section ? `${context.section.currentLayout}:${context.section.columnCount}` : "no-section";
|
|
4084
|
+
const generationDateKey = getGenerationDate().toISOString();
|
|
4265
4085
|
const childrenKey = "children" in component && component.children ? `:children:${JSON.stringify(component.children)}` : "";
|
|
4266
|
-
const cacheKey = `component:${component.name}:${themeHash}:${contextKey}:${componentProps}${childrenKey}`;
|
|
4086
|
+
const cacheKey = `component:${component.name}:${themeHash}:${contextKey}:${generationDateKey}:${componentProps}${childrenKey}`;
|
|
4267
4087
|
const cached = await componentCache.get(cacheKey);
|
|
4268
4088
|
if (cached) {
|
|
4269
4089
|
return cached.result;
|
|
@@ -4311,19 +4131,27 @@ init_styles();
|
|
|
4311
4131
|
init_defaults();
|
|
4312
4132
|
|
|
4313
4133
|
// src/utils/bookmarkRegistry.ts
|
|
4134
|
+
import { AsyncLocalStorage as AsyncLocalStorage3 } from "async_hooks";
|
|
4314
4135
|
var BookmarkRegistry = class {
|
|
4315
|
-
|
|
4316
|
-
|
|
4136
|
+
fallback = { bookmarks: /* @__PURE__ */ new Map() };
|
|
4137
|
+
scopes = new AsyncLocalStorage3();
|
|
4138
|
+
get state() {
|
|
4139
|
+
return this.scopes.getStore() ?? this.fallback;
|
|
4140
|
+
}
|
|
4141
|
+
/** Run work with an isolated registry that follows its async call chain. */
|
|
4142
|
+
runScoped(callback) {
|
|
4143
|
+
return this.scopes.run({ bookmarks: /* @__PURE__ */ new Map() }, callback);
|
|
4144
|
+
}
|
|
4317
4145
|
/**
|
|
4318
4146
|
* Register a bookmark
|
|
4319
4147
|
*/
|
|
4320
4148
|
register(id, title, type) {
|
|
4321
|
-
if (this.bookmarks.has(id)) {
|
|
4149
|
+
if (this.state.bookmarks.has(id)) {
|
|
4322
4150
|
console.warn(
|
|
4323
4151
|
`Duplicate bookmark ID: ${id}. Using the latest registration.`
|
|
4324
4152
|
);
|
|
4325
4153
|
}
|
|
4326
|
-
this.bookmarks.set(id, { id, title, type });
|
|
4154
|
+
this.state.bookmarks.set(id, { id, title, type });
|
|
4327
4155
|
}
|
|
4328
4156
|
/**
|
|
4329
4157
|
* Generate a unique bookmark ID from text
|
|
@@ -4333,7 +4161,7 @@ var BookmarkRegistry = class {
|
|
|
4333
4161
|
const baseId = text.toLowerCase().replace(/\s+/g, "-").replace(/[^a-z0-9-]/g, "").substring(0, 40);
|
|
4334
4162
|
let id = baseId;
|
|
4335
4163
|
let attempt = 0;
|
|
4336
|
-
while (this.bookmarks.has(id) && attempt < 100) {
|
|
4164
|
+
while (this.state.bookmarks.has(id) && attempt < 100) {
|
|
4337
4165
|
id = `${baseId}-${++attempt}`;
|
|
4338
4166
|
}
|
|
4339
4167
|
return id;
|
|
@@ -4342,26 +4170,25 @@ var BookmarkRegistry = class {
|
|
|
4342
4170
|
* Check if a bookmark exists
|
|
4343
4171
|
*/
|
|
4344
4172
|
exists(id) {
|
|
4345
|
-
return this.bookmarks.has(id);
|
|
4173
|
+
return this.state.bookmarks.has(id);
|
|
4346
4174
|
}
|
|
4347
4175
|
/**
|
|
4348
4176
|
* Get bookmark info by ID
|
|
4349
4177
|
*/
|
|
4350
4178
|
get(id) {
|
|
4351
|
-
return this.bookmarks.get(id);
|
|
4179
|
+
return this.state.bookmarks.get(id);
|
|
4352
4180
|
}
|
|
4353
4181
|
/**
|
|
4354
4182
|
* Get all registered bookmarks
|
|
4355
4183
|
*/
|
|
4356
4184
|
getAll() {
|
|
4357
|
-
return Array.from(this.bookmarks.values());
|
|
4185
|
+
return Array.from(this.state.bookmarks.values());
|
|
4358
4186
|
}
|
|
4359
4187
|
/**
|
|
4360
4188
|
* Clear all bookmarks
|
|
4361
4189
|
*/
|
|
4362
4190
|
clear() {
|
|
4363
|
-
this.bookmarks.clear();
|
|
4364
|
-
this.counter = 0;
|
|
4191
|
+
this.state.bookmarks.clear();
|
|
4365
4192
|
}
|
|
4366
4193
|
/**
|
|
4367
4194
|
* Validate that all internal hyperlink references exist
|
|
@@ -5649,8 +5476,173 @@ function renderHeadingComponent(component, theme, themeName) {
|
|
|
5649
5476
|
return [header];
|
|
5650
5477
|
}
|
|
5651
5478
|
|
|
5479
|
+
// src/utils/numberingConfig.ts
|
|
5480
|
+
import { AlignmentType as AlignmentType3, convertInchesToTwip, LevelFormat } from "docx";
|
|
5481
|
+
import { AsyncLocalStorage as AsyncLocalStorage4 } from "async_hooks";
|
|
5482
|
+
var LEVEL_FORMAT_MAP = {
|
|
5483
|
+
decimal: LevelFormat.DECIMAL,
|
|
5484
|
+
upperRoman: LevelFormat.UPPER_ROMAN,
|
|
5485
|
+
lowerRoman: LevelFormat.LOWER_ROMAN,
|
|
5486
|
+
upperLetter: LevelFormat.UPPER_LETTER,
|
|
5487
|
+
lowerLetter: LevelFormat.LOWER_LETTER,
|
|
5488
|
+
bullet: LevelFormat.BULLET,
|
|
5489
|
+
ordinal: LevelFormat.ORDINAL,
|
|
5490
|
+
cardinalText: LevelFormat.CARDINAL_TEXT,
|
|
5491
|
+
ordinalText: LevelFormat.ORDINAL_TEXT,
|
|
5492
|
+
hex: LevelFormat.HEX,
|
|
5493
|
+
chicago: LevelFormat.CHICAGO,
|
|
5494
|
+
ideographDigital: LevelFormat.IDEOGRAPH__DIGITAL,
|
|
5495
|
+
japaneseCounting: LevelFormat.JAPANESE_COUNTING,
|
|
5496
|
+
aiueo: LevelFormat.AIUEO,
|
|
5497
|
+
iroha: LevelFormat.IROHA,
|
|
5498
|
+
decimalFullWidth: LevelFormat.DECIMAL_FULL_WIDTH,
|
|
5499
|
+
decimalHalfWidth: LevelFormat.DECIMAL_HALF_WIDTH,
|
|
5500
|
+
japaneseLegal: LevelFormat.JAPANESE_LEGAL,
|
|
5501
|
+
japaneseDigitalTenThousand: LevelFormat.JAPANESE_DIGITAL_TEN_THOUSAND,
|
|
5502
|
+
decimalEnclosedCircle: LevelFormat.DECIMAL_ENCLOSED_CIRCLE,
|
|
5503
|
+
decimalFullWidth2: LevelFormat.DECIMAL_FULL_WIDTH2,
|
|
5504
|
+
aiueoFullWidth: LevelFormat.AIUEO_FULL_WIDTH,
|
|
5505
|
+
irohaFullWidth: LevelFormat.IROHA_FULL_WIDTH,
|
|
5506
|
+
decimalZero: LevelFormat.DECIMAL_ZERO,
|
|
5507
|
+
ganada: LevelFormat.GANADA,
|
|
5508
|
+
chosung: LevelFormat.CHOSUNG,
|
|
5509
|
+
decimalEnclosedFullstop: LevelFormat.DECIMAL_ENCLOSED_FULLSTOP,
|
|
5510
|
+
decimalEnclosedParen: LevelFormat.DECIMAL_ENCLOSED_PARENTHESES,
|
|
5511
|
+
decimalEnclosedCircleChinese: LevelFormat.DECIMAL_ENCLOSED_CIRCLE_CHINESE,
|
|
5512
|
+
ideographEnclosedCircle: LevelFormat.IDEOGRAPH_ENCLOSED_CIRCLE,
|
|
5513
|
+
ideographTraditional: LevelFormat.IDEOGRAPH_TRADITIONAL,
|
|
5514
|
+
ideographZodiac: LevelFormat.IDEOGRAPH_ZODIAC,
|
|
5515
|
+
ideographZodiacTraditional: LevelFormat.IDEOGRAPH_ZODIAC_TRADITIONAL,
|
|
5516
|
+
taiwaneseCounting: LevelFormat.TAIWANESE_COUNTING,
|
|
5517
|
+
ideographLegalTraditional: LevelFormat.IDEOGRAPH_LEGAL_TRADITIONAL,
|
|
5518
|
+
taiwaneseCountingThousand: LevelFormat.TAIWANESE_COUNTING_THOUSAND,
|
|
5519
|
+
taiwaneseDigital: LevelFormat.TAIWANESE_DIGITAL,
|
|
5520
|
+
chineseCounting: LevelFormat.CHINESE_COUNTING,
|
|
5521
|
+
chineseLegalSimplified: LevelFormat.CHINESE_LEGAL_SIMPLIFIED,
|
|
5522
|
+
chineseCountingThousand: LevelFormat.CHINESE_COUNTING_THOUSAND,
|
|
5523
|
+
koreanDigital: LevelFormat.KOREAN_DIGITAL,
|
|
5524
|
+
koreanCounting: LevelFormat.KOREAN_COUNTING,
|
|
5525
|
+
koreanLegal: LevelFormat.KOREAN_LEGAL,
|
|
5526
|
+
koreanDigital2: LevelFormat.KOREAN_DIGITAL2,
|
|
5527
|
+
vietnameseCounting: LevelFormat.VIETNAMESE_COUNTING,
|
|
5528
|
+
russianLower: LevelFormat.RUSSIAN_LOWER,
|
|
5529
|
+
russianUpper: LevelFormat.RUSSIAN_UPPER,
|
|
5530
|
+
none: LevelFormat.NONE,
|
|
5531
|
+
numberInDash: LevelFormat.NUMBER_IN_DASH,
|
|
5532
|
+
hebrew1: LevelFormat.HEBREW1,
|
|
5533
|
+
hebrew2: LevelFormat.HEBREW2,
|
|
5534
|
+
arabicAlpha: LevelFormat.ARABIC_ALPHA,
|
|
5535
|
+
arabicAbjad: LevelFormat.ARABIC_ABJAD,
|
|
5536
|
+
hindiVowels: LevelFormat.HINDI_VOWELS,
|
|
5537
|
+
hindiConsonants: LevelFormat.HINDI_CONSONANTS,
|
|
5538
|
+
hindiNumbers: LevelFormat.HINDI_NUMBERS,
|
|
5539
|
+
hindiCounting: LevelFormat.HINDI_COUNTING,
|
|
5540
|
+
thaiLetters: LevelFormat.THAI_LETTERS,
|
|
5541
|
+
thaiNumbers: LevelFormat.THAI_NUMBERS,
|
|
5542
|
+
thaiCounting: LevelFormat.THAI_COUNTING
|
|
5543
|
+
};
|
|
5544
|
+
var ALIGNMENT_MAP = {
|
|
5545
|
+
start: AlignmentType3.START,
|
|
5546
|
+
end: AlignmentType3.END,
|
|
5547
|
+
left: AlignmentType3.LEFT,
|
|
5548
|
+
right: AlignmentType3.RIGHT,
|
|
5549
|
+
center: AlignmentType3.CENTER
|
|
5550
|
+
};
|
|
5551
|
+
function getLevelFormat(format2) {
|
|
5552
|
+
if (!format2) return LevelFormat.BULLET;
|
|
5553
|
+
return LEVEL_FORMAT_MAP[format2] || LevelFormat.BULLET;
|
|
5554
|
+
}
|
|
5555
|
+
function getAlignment2(alignment) {
|
|
5556
|
+
if (!alignment) return AlignmentType3.LEFT;
|
|
5557
|
+
return ALIGNMENT_MAP[alignment] || AlignmentType3.LEFT;
|
|
5558
|
+
}
|
|
5559
|
+
function createNumberingConfig(config) {
|
|
5560
|
+
const levels = [];
|
|
5561
|
+
for (const levelConfig of config.levels) {
|
|
5562
|
+
const format2 = getLevelFormat(levelConfig.format);
|
|
5563
|
+
const alignment = getAlignment2(levelConfig.alignment);
|
|
5564
|
+
const text = levelConfig.text || (format2 === LevelFormat.BULLET ? "\u2022" : `%${levelConfig.level + 1}.`);
|
|
5565
|
+
const baseIndent = levelConfig.indent?.left !== void 0 ? levelConfig.indent.left / 72 : 0.5 * (levelConfig.level + 1);
|
|
5566
|
+
const hangingIndent = levelConfig.indent?.hanging !== void 0 ? levelConfig.indent.hanging / 72 : 0.25;
|
|
5567
|
+
const level = {
|
|
5568
|
+
level: levelConfig.level,
|
|
5569
|
+
format: format2,
|
|
5570
|
+
text,
|
|
5571
|
+
alignment,
|
|
5572
|
+
style: {
|
|
5573
|
+
paragraph: {
|
|
5574
|
+
indent: {
|
|
5575
|
+
left: convertInchesToTwip(baseIndent),
|
|
5576
|
+
hanging: convertInchesToTwip(hangingIndent)
|
|
5577
|
+
}
|
|
5578
|
+
}
|
|
5579
|
+
},
|
|
5580
|
+
// Add start number if specified
|
|
5581
|
+
...levelConfig.start !== void 0 && { start: levelConfig.start }
|
|
5582
|
+
};
|
|
5583
|
+
levels.push(level);
|
|
5584
|
+
}
|
|
5585
|
+
return {
|
|
5586
|
+
reference: config.reference,
|
|
5587
|
+
levels
|
|
5588
|
+
};
|
|
5589
|
+
}
|
|
5590
|
+
var NumberingRegistry = class {
|
|
5591
|
+
fallback = {
|
|
5592
|
+
configs: /* @__PURE__ */ new Map(),
|
|
5593
|
+
counter: 0
|
|
5594
|
+
};
|
|
5595
|
+
scopes = new AsyncLocalStorage4();
|
|
5596
|
+
get state() {
|
|
5597
|
+
return this.scopes.getStore() ?? this.fallback;
|
|
5598
|
+
}
|
|
5599
|
+
/** Run work with an isolated registry that follows its async call chain. */
|
|
5600
|
+
runScoped(callback) {
|
|
5601
|
+
return this.scopes.run({ configs: /* @__PURE__ */ new Map(), counter: 0 }, callback);
|
|
5602
|
+
}
|
|
5603
|
+
/**
|
|
5604
|
+
* Register a numbering configuration
|
|
5605
|
+
*/
|
|
5606
|
+
register(config) {
|
|
5607
|
+
const reference = config.reference;
|
|
5608
|
+
this.state.configs.set(reference, config);
|
|
5609
|
+
return reference;
|
|
5610
|
+
}
|
|
5611
|
+
/**
|
|
5612
|
+
* Generate a unique reference ID
|
|
5613
|
+
*/
|
|
5614
|
+
generateReference(prefix = "list") {
|
|
5615
|
+
return `${prefix}-${++this.state.counter}`;
|
|
5616
|
+
}
|
|
5617
|
+
/**
|
|
5618
|
+
* Get all registered configurations as an array suitable for INumberingOptions
|
|
5619
|
+
*/
|
|
5620
|
+
getAll() {
|
|
5621
|
+
return Array.from(this.state.configs.values());
|
|
5622
|
+
}
|
|
5623
|
+
/**
|
|
5624
|
+
* Clear all configurations
|
|
5625
|
+
*/
|
|
5626
|
+
clear() {
|
|
5627
|
+
this.state.configs.clear();
|
|
5628
|
+
this.state.counter = 0;
|
|
5629
|
+
}
|
|
5630
|
+
/**
|
|
5631
|
+
* Check if a reference exists
|
|
5632
|
+
*/
|
|
5633
|
+
has(reference) {
|
|
5634
|
+
return this.state.configs.has(reference);
|
|
5635
|
+
}
|
|
5636
|
+
/**
|
|
5637
|
+
* Get a configuration by reference
|
|
5638
|
+
*/
|
|
5639
|
+
get(reference) {
|
|
5640
|
+
return this.state.configs.get(reference);
|
|
5641
|
+
}
|
|
5642
|
+
};
|
|
5643
|
+
var globalNumberingRegistry = new NumberingRegistry();
|
|
5644
|
+
|
|
5652
5645
|
// src/components/paragraph.ts
|
|
5653
|
-
init_numberingConfig();
|
|
5654
5646
|
function parseMarkdownList(text) {
|
|
5655
5647
|
const lines = text.split("\n");
|
|
5656
5648
|
const items = [];
|
|
@@ -5776,7 +5768,6 @@ function renderParagraphComponent(component, theme, themeName) {
|
|
|
5776
5768
|
}
|
|
5777
5769
|
|
|
5778
5770
|
// src/components/list.ts
|
|
5779
|
-
init_numberingConfig();
|
|
5780
5771
|
function createLevelsFromSimplifiedProps(props) {
|
|
5781
5772
|
const levels = [];
|
|
5782
5773
|
let format2;
|
|
@@ -6200,17 +6191,22 @@ async function renderTableComponent(component, theme, themeName) {
|
|
|
6200
6191
|
|
|
6201
6192
|
// src/components/section.ts
|
|
6202
6193
|
import { Paragraph as Paragraph4, BookmarkStart, BookmarkEnd } from "docx";
|
|
6203
|
-
function generateSectionBookmarkId() {
|
|
6204
|
-
const
|
|
6194
|
+
function generateSectionBookmarkId(context) {
|
|
6195
|
+
const custom = context.custom ??= {};
|
|
6196
|
+
const state = custom.sectionBookmarks ??= {
|
|
6197
|
+
next: 1
|
|
6198
|
+
};
|
|
6199
|
+
const ordinal = state.next++;
|
|
6200
|
+
const linkId = 1e6 + ordinal;
|
|
6205
6201
|
return {
|
|
6206
|
-
id: `
|
|
6202
|
+
id: `_NestedSection_${ordinal}`,
|
|
6207
6203
|
linkId
|
|
6208
6204
|
};
|
|
6209
6205
|
}
|
|
6210
6206
|
async function renderSectionComponent(component, theme, themeName, context) {
|
|
6211
6207
|
if (!isSectionComponent(component)) return [];
|
|
6212
6208
|
const elements = [];
|
|
6213
|
-
const { id: sectionBookmarkId, linkId: bookmarkLinkId } = generateSectionBookmarkId();
|
|
6209
|
+
const { id: sectionBookmarkId, linkId: bookmarkLinkId } = generateSectionBookmarkId(context);
|
|
6214
6210
|
elements.push(
|
|
6215
6211
|
new Paragraph4({
|
|
6216
6212
|
children: [new BookmarkStart(sectionBookmarkId, bookmarkLinkId)],
|
|
@@ -6619,9 +6615,23 @@ Cause: ${cause}`
|
|
|
6619
6615
|
height
|
|
6620
6616
|
};
|
|
6621
6617
|
}
|
|
6618
|
+
function withThemeColors(config, theme) {
|
|
6619
|
+
const options = config.options;
|
|
6620
|
+
if (!options || options.colors || !theme?.colors) return config;
|
|
6621
|
+
const palette = [
|
|
6622
|
+
theme.colors.primary,
|
|
6623
|
+
theme.colors.secondary,
|
|
6624
|
+
theme.colors.accent
|
|
6625
|
+
].filter((c) => typeof c === "string" && c.length > 0).map((c) => c.startsWith("#") ? c : `#${c}`);
|
|
6626
|
+
if (palette.length === 0) return config;
|
|
6627
|
+
return {
|
|
6628
|
+
...config,
|
|
6629
|
+
options: { ...config.options, colors: palette }
|
|
6630
|
+
};
|
|
6631
|
+
}
|
|
6622
6632
|
async function renderHighchartsComponent(component, theme, themeName, context) {
|
|
6623
6633
|
if (!isHighchartsComponent(component)) return [];
|
|
6624
|
-
const config = component.props;
|
|
6634
|
+
const config = withThemeColors(component.props, theme);
|
|
6625
6635
|
const chartResult = await generateChart(
|
|
6626
6636
|
config,
|
|
6627
6637
|
context?.services?.highcharts
|
|
@@ -6811,13 +6821,23 @@ function getAlignment3(alignment) {
|
|
|
6811
6821
|
}
|
|
6812
6822
|
}
|
|
6813
6823
|
async function renderDocument(structure, layout, options) {
|
|
6824
|
+
return runWithGenerationDate(
|
|
6825
|
+
structure.metadata.date,
|
|
6826
|
+
() => globalBookmarkRegistry.runScoped(
|
|
6827
|
+
() => globalRevisionIdRegistry.runScoped(
|
|
6828
|
+
() => globalNumberingRegistry.runScoped(
|
|
6829
|
+
() => renderDocumentScoped(structure, layout, options)
|
|
6830
|
+
)
|
|
6831
|
+
)
|
|
6832
|
+
)
|
|
6833
|
+
);
|
|
6834
|
+
}
|
|
6835
|
+
async function renderDocumentScoped(structure, layout, options) {
|
|
6814
6836
|
if (options?.cache) {
|
|
6815
6837
|
initializeComponentCache(options.cache);
|
|
6816
6838
|
} else if (!options?.bypassCache) {
|
|
6817
6839
|
initializeComponentCache();
|
|
6818
6840
|
}
|
|
6819
|
-
const { globalNumberingRegistry: globalNumberingRegistry2 } = await Promise.resolve().then(() => (init_numberingConfig(), numberingConfig_exports));
|
|
6820
|
-
globalNumberingRegistry2.clear();
|
|
6821
6841
|
const sections = [];
|
|
6822
6842
|
const context = createRenderContext(
|
|
6823
6843
|
structure,
|
|
@@ -6874,7 +6894,8 @@ async function renderDocument(structure, layout, options) {
|
|
|
6874
6894
|
structure.themeName,
|
|
6875
6895
|
context,
|
|
6876
6896
|
sectionOrdinal,
|
|
6877
|
-
closeBookmark
|
|
6897
|
+
closeBookmark,
|
|
6898
|
+
options?.bypassCache === true
|
|
6878
6899
|
);
|
|
6879
6900
|
if (layoutSection.isUserSection) {
|
|
6880
6901
|
sectionBookmarkCounter++;
|
|
@@ -6883,7 +6904,7 @@ async function renderDocument(structure, layout, options) {
|
|
|
6883
6904
|
sections.push(rendered);
|
|
6884
6905
|
}
|
|
6885
6906
|
}
|
|
6886
|
-
const numberingConfigs =
|
|
6907
|
+
const numberingConfigs = globalNumberingRegistry.getAll();
|
|
6887
6908
|
return new Document({
|
|
6888
6909
|
styles: createWordStyles(structure.theme, structure.language),
|
|
6889
6910
|
sections,
|
|
@@ -7051,7 +7072,7 @@ async function renderHeaderFooterComponents(components, theme, themeName, contex
|
|
|
7051
7072
|
}
|
|
7052
7073
|
return elements;
|
|
7053
7074
|
}
|
|
7054
|
-
async function renderSection(section, theme, themeName, context, sectionOrdinal, closeBookmark) {
|
|
7075
|
+
async function renderSection(section, theme, themeName, context, sectionOrdinal, closeBookmark, bypassCache = false) {
|
|
7055
7076
|
const elements = [];
|
|
7056
7077
|
const isFirstLayoutOfUserSection = section.isUserSection;
|
|
7057
7078
|
const sharedLinkId = section.belongsToUserSection && sectionOrdinal ? sectionOrdinal : void 0;
|
|
@@ -7089,8 +7110,7 @@ async function renderSection(section, theme, themeName, context, sectionOrdinal,
|
|
|
7089
7110
|
theme,
|
|
7090
7111
|
themeName,
|
|
7091
7112
|
sectionContext,
|
|
7092
|
-
|
|
7093
|
-
// Don't bypass cache
|
|
7113
|
+
bypassCache
|
|
7094
7114
|
);
|
|
7095
7115
|
elements.push(...rendered);
|
|
7096
7116
|
}
|
|
@@ -7259,6 +7279,75 @@ function normalizeDocument(document) {
|
|
|
7259
7279
|
return [normalized];
|
|
7260
7280
|
}
|
|
7261
7281
|
|
|
7282
|
+
// src/utils/packageDocument.ts
|
|
7283
|
+
import AdmZip2 from "adm-zip";
|
|
7284
|
+
import { Packer } from "docx";
|
|
7285
|
+
|
|
7286
|
+
// src/utils/fixFloatingImageIds.ts
|
|
7287
|
+
import AdmZip from "adm-zip";
|
|
7288
|
+
function fixFloatingImageIdsInBuffer(buffer) {
|
|
7289
|
+
const zip = new AdmZip(buffer);
|
|
7290
|
+
const documentEntry = zip.getEntry("word/document.xml");
|
|
7291
|
+
if (!documentEntry) {
|
|
7292
|
+
throw new Error("document.xml not found in DOCX");
|
|
7293
|
+
}
|
|
7294
|
+
let idCounter = 1;
|
|
7295
|
+
const documentXml = documentEntry.getData().toString("utf8").replace(/<wp:docPr\s+id="(\d+)"/g, () => {
|
|
7296
|
+
const newId = idCounter++;
|
|
7297
|
+
return `<wp:docPr id="${newId}"`;
|
|
7298
|
+
});
|
|
7299
|
+
zip.updateFile(documentEntry, Buffer.from(documentXml, "utf8"));
|
|
7300
|
+
return zip.toBuffer();
|
|
7301
|
+
}
|
|
7302
|
+
|
|
7303
|
+
// src/utils/packageDocument.ts
|
|
7304
|
+
var DEFAULT_GENERATION_DATE = /* @__PURE__ */ new Date("2000-01-01T00:00:00.000Z");
|
|
7305
|
+
function resolveGenerationDate(options) {
|
|
7306
|
+
if (options?.generatedAt !== void 0) {
|
|
7307
|
+
const date = new Date(options.generatedAt);
|
|
7308
|
+
if (Number.isNaN(date.getTime())) {
|
|
7309
|
+
throw new RangeError("generatedAt must be a valid date");
|
|
7310
|
+
}
|
|
7311
|
+
if (date.getUTCFullYear() < 1980) {
|
|
7312
|
+
throw new RangeError(
|
|
7313
|
+
"generatedAt must be on or after 1980-01-01 for ZIP compatibility"
|
|
7314
|
+
);
|
|
7315
|
+
}
|
|
7316
|
+
return date;
|
|
7317
|
+
}
|
|
7318
|
+
return options?.deterministic === false ? /* @__PURE__ */ new Date() : new Date(DEFAULT_GENERATION_DATE);
|
|
7319
|
+
}
|
|
7320
|
+
function toDosTime(date) {
|
|
7321
|
+
const dosDate = (date.getUTCFullYear() - 1980 & 127) << 9 | date.getUTCMonth() + 1 << 5 | date.getUTCDate();
|
|
7322
|
+
const dosTime = date.getUTCHours() << 11 | date.getUTCMinutes() << 5 | date.getUTCSeconds() >> 1;
|
|
7323
|
+
return (dosDate << 16 | dosTime) >>> 0;
|
|
7324
|
+
}
|
|
7325
|
+
function canonicalizeDocxBuffer(buffer, generatedAt = DEFAULT_GENERATION_DATE) {
|
|
7326
|
+
const zip = new AdmZip2(buffer);
|
|
7327
|
+
const isoTimestamp = generatedAt.toISOString();
|
|
7328
|
+
const coreProperties = zip.getEntry("docProps/core.xml");
|
|
7329
|
+
if (coreProperties) {
|
|
7330
|
+
const normalized = coreProperties.getData().toString("utf8").replace(
|
|
7331
|
+
/(<dcterms:(?:created|modified)\b[^>]*>)[^<]*(<\/dcterms:(?:created|modified)>)/g,
|
|
7332
|
+
`$1${isoTimestamp}$2`
|
|
7333
|
+
);
|
|
7334
|
+
zip.updateFile(coreProperties, Buffer.from(normalized, "utf8"));
|
|
7335
|
+
}
|
|
7336
|
+
const zipTimestamp = toDosTime(generatedAt);
|
|
7337
|
+
for (const entry of zip.getEntries()) {
|
|
7338
|
+
entry.header.timeval = zipTimestamp;
|
|
7339
|
+
}
|
|
7340
|
+
return zip.toBuffer();
|
|
7341
|
+
}
|
|
7342
|
+
async function packageDocument(document, options) {
|
|
7343
|
+
const packed = await Packer.toBuffer(document);
|
|
7344
|
+
const fixed = fixFloatingImageIdsInBuffer(packed);
|
|
7345
|
+
if (options?.deterministic === false) {
|
|
7346
|
+
return fixed;
|
|
7347
|
+
}
|
|
7348
|
+
return canonicalizeDocxBuffer(fixed, resolveGenerationDate(options));
|
|
7349
|
+
}
|
|
7350
|
+
|
|
7262
7351
|
// src/plugin/createDocumentGenerator.ts
|
|
7263
7352
|
function createBuilderImpl(state) {
|
|
7264
7353
|
const componentMap = new Map(state.components.map((c) => [c.name, c]));
|
|
@@ -7414,7 +7503,10 @@ function createBuilderImpl(state) {
|
|
|
7414
7503
|
debug: state.debug,
|
|
7415
7504
|
enableCache: state.enableCache,
|
|
7416
7505
|
services: state.services,
|
|
7417
|
-
fonts: state.fonts
|
|
7506
|
+
fonts: state.fonts,
|
|
7507
|
+
validation: state.validation,
|
|
7508
|
+
deterministic: state.deterministic,
|
|
7509
|
+
generatedAt: state.generatedAt
|
|
7418
7510
|
};
|
|
7419
7511
|
return createBuilderImpl(
|
|
7420
7512
|
newState
|
|
@@ -7506,10 +7598,20 @@ function createBuilderImpl(state) {
|
|
|
7506
7598
|
};
|
|
7507
7599
|
const [modedDoc] = normalizeDocument(processedDocument);
|
|
7508
7600
|
await resolveDocumentFonts(modedDoc, modedTheme, state.fonts, warnings);
|
|
7509
|
-
const
|
|
7601
|
+
const packageOptions = {
|
|
7602
|
+
deterministic: options?.deterministic ?? state.deterministic,
|
|
7603
|
+
generatedAt: options?.generatedAt ?? state.generatedAt
|
|
7604
|
+
};
|
|
7605
|
+
const structure = await processDocument(
|
|
7606
|
+
modedDoc,
|
|
7607
|
+
modedTheme,
|
|
7608
|
+
themeName,
|
|
7609
|
+
resolveGenerationDate(packageOptions)
|
|
7610
|
+
);
|
|
7510
7611
|
const layout = applyLayout(structure.sections, modedTheme, themeName);
|
|
7511
7612
|
const generatedDocument = await renderDocument(structure, layout, {
|
|
7512
|
-
services: state.services
|
|
7613
|
+
services: state.services,
|
|
7614
|
+
bypassCache: !state.enableCache
|
|
7513
7615
|
});
|
|
7514
7616
|
const preservedDefinition = preserveSet ? {
|
|
7515
7617
|
...mode.doc,
|
|
@@ -7535,7 +7637,10 @@ function createBuilderImpl(state) {
|
|
|
7535
7637
|
standardDefinition,
|
|
7536
7638
|
preservedDefinition
|
|
7537
7639
|
} = await generate(document, options);
|
|
7538
|
-
const buffer = await
|
|
7640
|
+
const buffer = await packageDocument(doc, {
|
|
7641
|
+
deterministic: options?.deterministic ?? state.deterministic,
|
|
7642
|
+
generatedAt: options?.generatedAt ?? state.generatedAt
|
|
7643
|
+
});
|
|
7539
7644
|
return { buffer, warnings, standardDefinition, preservedDefinition };
|
|
7540
7645
|
}
|
|
7541
7646
|
async function generateFile(document, outputPath, options) {
|
|
@@ -7634,7 +7739,9 @@ function createDocumentGenerator(options) {
|
|
|
7634
7739
|
enableCache: options.enableCache ?? false,
|
|
7635
7740
|
services: options.services,
|
|
7636
7741
|
fonts: options.fonts,
|
|
7637
|
-
validation: options.validation
|
|
7742
|
+
validation: options.validation,
|
|
7743
|
+
deterministic: options.deterministic ?? true,
|
|
7744
|
+
generatedAt: options.generatedAt
|
|
7638
7745
|
};
|
|
7639
7746
|
return createBuilderImpl(initialState);
|
|
7640
7747
|
}
|