@justybase/spreadsheet-tasks 3.0.0 → 3.1.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/CHANGELOG.md +26 -0
- package/README.md +11 -0
- package/browser/browser-spreadsheet.js +35 -20
- package/browser/justybase-spreadsheet.min.js +11 -11
- package/dist/cjs/index.d.ts +28 -3
- package/dist/cjs/index.js +89 -40
- package/dist/cjs/index.js.map +1 -1
- package/dist/esm/index.js +87 -40
- package/dist/esm/index.js.map +1 -1
- package/package.json +2 -2
package/dist/cjs/index.js
CHANGED
|
@@ -57,6 +57,7 @@ __export(index_exports, {
|
|
|
57
57
|
convertXlsbToXlsx: () => convertXlsbToXlsx,
|
|
58
58
|
convertXlsxToXlsb: () => convertXlsxToXlsb,
|
|
59
59
|
defaultColWidth: () => defaultColWidth,
|
|
60
|
+
escapeXlsxText: () => escapeXlsxText,
|
|
60
61
|
escapeXmlText: () => escapeXmlText,
|
|
61
62
|
getFormat: () => getFormat,
|
|
62
63
|
initColWidths: () => initColWidths,
|
|
@@ -67,6 +68,7 @@ __export(index_exports, {
|
|
|
67
68
|
sanitizeSheetName: () => sanitizeSheetName,
|
|
68
69
|
trimTrailingEmptyRows: () => trimTrailingEmptyRows,
|
|
69
70
|
unescapeXml: () => unescapeXml,
|
|
71
|
+
unescapeXmlText: () => unescapeXmlText,
|
|
70
72
|
unwrapCell: () => unwrapCell,
|
|
71
73
|
updateColWidthsFromRows: () => updateColWidthsFromRows
|
|
72
74
|
});
|
|
@@ -322,6 +324,16 @@ function defaultColWidth(width, floor = false) {
|
|
|
322
324
|
}
|
|
323
325
|
return 10;
|
|
324
326
|
}
|
|
327
|
+
function cellRefAttr(col, prevCol, colRef, rowNum) {
|
|
328
|
+
return col === prevCol + 1 ? "" : ` r="${colRef}${rowNum}"`;
|
|
329
|
+
}
|
|
330
|
+
var DEFAULT_COMPRESSION_LEVEL = 6;
|
|
331
|
+
function assertCompressionLevel(level) {
|
|
332
|
+
if (!Number.isInteger(level) || level < 0 || level > 9) {
|
|
333
|
+
throw new RangeError(`compressionLevel must be an integer from 0 to 9, got ${level}`);
|
|
334
|
+
}
|
|
335
|
+
return level;
|
|
336
|
+
}
|
|
325
337
|
|
|
326
338
|
// src/ExcelReaderAbstract.ts
|
|
327
339
|
var ExcelReaderAbstract = class {
|
|
@@ -619,10 +631,10 @@ function stripInvalidControlChars(str) {
|
|
|
619
631
|
return out;
|
|
620
632
|
}
|
|
621
633
|
function escapeXmlText(str) {
|
|
622
|
-
if (
|
|
634
|
+
if (!/[&<>"'\r]/.test(str) && !hasInvalidControlChars(str)) {
|
|
623
635
|
return str;
|
|
624
636
|
}
|
|
625
|
-
let out = str.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """).replace(/'/g, "'");
|
|
637
|
+
let out = str.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """).replace(/'/g, "'").replace(/\r/g, " ");
|
|
626
638
|
if (hasInvalidControlChars(out)) {
|
|
627
639
|
out = stripInvalidControlChars(out);
|
|
628
640
|
}
|
|
@@ -659,6 +671,14 @@ function unescapeXml(str) {
|
|
|
659
671
|
}
|
|
660
672
|
});
|
|
661
673
|
}
|
|
674
|
+
function escapeXlsxText(str) {
|
|
675
|
+
return escapeXmlText(str.replace(/_x([0-9A-Fa-f]{4})_/g, "_x005F_x$1_"));
|
|
676
|
+
}
|
|
677
|
+
function unescapeXmlText(str) {
|
|
678
|
+
if (!str) return str;
|
|
679
|
+
const text = unescapeXml(str.indexOf("\r") === -1 ? str : str.replace(/\r\n?/g, "\n"));
|
|
680
|
+
return text.indexOf("_x") === -1 ? text : text.replace(/_x([0-9A-Fa-f]{4})_/g, (_match, hex) => String.fromCharCode(parseInt(hex, 16)));
|
|
681
|
+
}
|
|
662
682
|
function parseTagAttributes(tag) {
|
|
663
683
|
const attrs = {};
|
|
664
684
|
const re = /([A-Za-z_][\w.:-]*)\s*=\s*("([^"]*)"|'([^']*)')/g;
|
|
@@ -725,7 +745,7 @@ function parseSharedStringsXml(xml) {
|
|
|
725
745
|
while ((textMatch = textRegex.exec(content)) !== null) {
|
|
726
746
|
value += textMatch[1];
|
|
727
747
|
}
|
|
728
|
-
result.push(
|
|
748
|
+
result.push(unescapeXmlText(value));
|
|
729
749
|
}
|
|
730
750
|
return result;
|
|
731
751
|
}
|
|
@@ -1410,7 +1430,7 @@ var XlsxReader = class extends ExcelReaderAbstract {
|
|
|
1410
1430
|
}
|
|
1411
1431
|
let finalVal = null;
|
|
1412
1432
|
if (inlineVals !== null) {
|
|
1413
|
-
finalVal =
|
|
1433
|
+
finalVal = unescapeXmlText(inlineVals.join(""));
|
|
1414
1434
|
} else if (val !== null) {
|
|
1415
1435
|
if (type === "s") {
|
|
1416
1436
|
const idx = parseInt(val, 10);
|
|
@@ -1418,13 +1438,13 @@ var XlsxReader = class extends ExcelReaderAbstract {
|
|
|
1418
1438
|
} else if (type === "b") {
|
|
1419
1439
|
finalVal = val === "1" || val === "true";
|
|
1420
1440
|
} else if (type === "inlineStr") {
|
|
1421
|
-
finalVal =
|
|
1441
|
+
finalVal = unescapeXmlText(val);
|
|
1422
1442
|
} else if (type === "str") {
|
|
1423
|
-
finalVal =
|
|
1443
|
+
finalVal = unescapeXmlText(val);
|
|
1424
1444
|
} else if (type === "e") {
|
|
1425
1445
|
finalVal = unescapeXml(val);
|
|
1426
1446
|
} else if (type === "d") {
|
|
1427
|
-
finalVal = parseIsoDateUtc(val) ??
|
|
1447
|
+
finalVal = parseIsoDateUtc(val) ?? unescapeXmlText(val);
|
|
1428
1448
|
} else if (type === "n" || type === "") {
|
|
1429
1449
|
finalVal = parseFloat(val);
|
|
1430
1450
|
if (styleIndex > 0 && this.xfIdToNumFmtId) {
|
|
@@ -1531,7 +1551,11 @@ var XlsbWriter = class _XlsbWriter {
|
|
|
1531
1551
|
/**
|
|
1532
1552
|
* @param filePath Destination `.xlsb` path on disk.
|
|
1533
1553
|
*/
|
|
1534
|
-
|
|
1554
|
+
/**
|
|
1555
|
+
* @param filePath Destination `.xlsb` path on disk.
|
|
1556
|
+
* @param options.compressionLevel Deflate level 0-9 (default 6).
|
|
1557
|
+
*/
|
|
1558
|
+
constructor(filePath, options = {}) {
|
|
1535
1559
|
this._outputError = null;
|
|
1536
1560
|
this._finalized = false;
|
|
1537
1561
|
this.sheetCount = 0;
|
|
@@ -1544,6 +1568,7 @@ var XlsbWriter = class _XlsbWriter {
|
|
|
1544
1568
|
this._nextXfIdx = 4;
|
|
1545
1569
|
this._stFmtRecords = /* @__PURE__ */ new Map();
|
|
1546
1570
|
this.stream = new StreamingSheetState();
|
|
1571
|
+
const compressionLevel = assertCompressionLevel(options.compressionLevel ?? DEFAULT_COMPRESSION_LEVEL);
|
|
1547
1572
|
this._targetPath = path2.resolve(filePath);
|
|
1548
1573
|
fs.mkdirSync(path2.dirname(this._targetPath), { recursive: true });
|
|
1549
1574
|
this._tempPath = path2.join(
|
|
@@ -1554,7 +1579,7 @@ var XlsbWriter = class _XlsbWriter {
|
|
|
1554
1579
|
this.output.on("error", (err) => {
|
|
1555
1580
|
this._outputError = err;
|
|
1556
1581
|
});
|
|
1557
|
-
this.archive = (0, import_archiver.default)("zip");
|
|
1582
|
+
this.archive = (0, import_archiver.default)("zip", { zlib: { level: compressionLevel } });
|
|
1558
1583
|
this.archive.on("error", (err) => {
|
|
1559
1584
|
this._outputError = err;
|
|
1560
1585
|
});
|
|
@@ -4004,7 +4029,11 @@ var XlsxWriter = class {
|
|
|
4004
4029
|
/**
|
|
4005
4030
|
* @param filePath Destination `.xlsx` path on disk.
|
|
4006
4031
|
*/
|
|
4007
|
-
|
|
4032
|
+
/**
|
|
4033
|
+
* @param filePath Destination `.xlsx` path on disk.
|
|
4034
|
+
* @param options.compressionLevel Deflate level 0-9 (default 6).
|
|
4035
|
+
*/
|
|
4036
|
+
constructor(filePath, options = {}) {
|
|
4008
4037
|
this._outputError = null;
|
|
4009
4038
|
this._finalized = false;
|
|
4010
4039
|
this.sheetCount = 0;
|
|
@@ -4020,6 +4049,7 @@ var XlsxWriter = class {
|
|
|
4020
4049
|
this._nextXfIndex = 4;
|
|
4021
4050
|
this.stream = new StreamingSheetState();
|
|
4022
4051
|
this.currentColLetters = [];
|
|
4052
|
+
const compressionLevel = assertCompressionLevel(options.compressionLevel ?? DEFAULT_COMPRESSION_LEVEL);
|
|
4023
4053
|
this._targetPath = path3.resolve(filePath);
|
|
4024
4054
|
fs2.mkdirSync(path3.dirname(this._targetPath), { recursive: true });
|
|
4025
4055
|
this._tempPath = path3.join(
|
|
@@ -4030,7 +4060,7 @@ var XlsxWriter = class {
|
|
|
4030
4060
|
this.output.on("error", (err) => {
|
|
4031
4061
|
this._outputError = err;
|
|
4032
4062
|
});
|
|
4033
|
-
this.archive = (0, import_archiver2.default)("zip");
|
|
4063
|
+
this.archive = (0, import_archiver2.default)("zip", { zlib: { level: compressionLevel } });
|
|
4034
4064
|
this.archive.on("error", (err) => {
|
|
4035
4065
|
this._outputError = err;
|
|
4036
4066
|
});
|
|
@@ -4075,7 +4105,7 @@ var XlsxWriter = class {
|
|
|
4075
4105
|
_needsEscape(str) {
|
|
4076
4106
|
for (let i = 0; i < str.length; i++) {
|
|
4077
4107
|
const c = str.charCodeAt(i);
|
|
4078
|
-
if (c === 38 || c === 60 || c === 62 || c === 34 || c === 39 || c >= 0 && c <= 8 || c === 11 || c === 12 || c >= 14 && c <= 31) {
|
|
4108
|
+
if (c === 38 || c === 60 || c === 62 || c === 34 || c === 39 || c === 13 || c >= 0 && c <= 8 || c === 11 || c === 12 || c >= 14 && c <= 31) {
|
|
4079
4109
|
return true;
|
|
4080
4110
|
}
|
|
4081
4111
|
}
|
|
@@ -4083,8 +4113,9 @@ var XlsxWriter = class {
|
|
|
4083
4113
|
}
|
|
4084
4114
|
_escape(str) {
|
|
4085
4115
|
if (typeof str !== "string") return str;
|
|
4116
|
+
str = str.replace(/_x([0-9A-Fa-f]{4})_/g, "_x005F_x$1_");
|
|
4086
4117
|
if (!this._needsEscape(str)) return str;
|
|
4087
|
-
return str.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """).replace(/'/g, "'").replace(/[\x00-\x08\x0b\x0c\x0e-\x1f]/g, "");
|
|
4118
|
+
return str.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">").replace(/"/g, """).replace(/'/g, "'").replace(/\r/g, " ").replace(/[\x00-\x08\x0b\x0c\x0e-\x1f]/g, "");
|
|
4088
4119
|
}
|
|
4089
4120
|
/**
|
|
4090
4121
|
* Start streaming a sheet. Call `writeRow` for each row, then `endSheet`.
|
|
@@ -4137,7 +4168,7 @@ var XlsxWriter = class {
|
|
|
4137
4168
|
this.stream.rowNum++;
|
|
4138
4169
|
bigBuf.writeString(`<row r="${this.stream.rowNum}">`);
|
|
4139
4170
|
for (let c = 0; c < headers.length; c++) {
|
|
4140
|
-
this._writeStringCell(bigBuf, headers[c],
|
|
4171
|
+
this._writeStringCell(bigBuf, headers[c], "", 3);
|
|
4141
4172
|
}
|
|
4142
4173
|
bigBuf.writeString("</row>");
|
|
4143
4174
|
}
|
|
@@ -4153,6 +4184,7 @@ var XlsxWriter = class {
|
|
|
4153
4184
|
this.stream.rowNum++;
|
|
4154
4185
|
assertRowCount(this.stream.rowNum);
|
|
4155
4186
|
bigBuf.writeString(`<row r="${this.stream.rowNum}">`);
|
|
4187
|
+
let prevCol = -1;
|
|
4156
4188
|
for (let c = 0; c < row.length; c++) {
|
|
4157
4189
|
const raw = row[c];
|
|
4158
4190
|
if (raw === null || raw === void 0) continue;
|
|
@@ -4160,27 +4192,28 @@ var XlsxWriter = class {
|
|
|
4160
4192
|
const val = fmtString !== null ? unwrapCell(raw) : raw;
|
|
4161
4193
|
const xfIdx = fmtString !== null ? this._registerFormat(fmtString) : -1;
|
|
4162
4194
|
const styleAttr = xfIdx >= 0 ? ` s="${xfIdx}"` : "";
|
|
4163
|
-
const
|
|
4195
|
+
const ref = cellRefAttr(c, prevCol, this.currentColLetters[c], this.stream.rowNum);
|
|
4196
|
+
prevCol = c;
|
|
4164
4197
|
if (typeof val === "number") {
|
|
4165
4198
|
if (Number.isFinite(val)) {
|
|
4166
|
-
bigBuf.writeString(`<c
|
|
4199
|
+
bigBuf.writeString(`<c${ref}${styleAttr}><v>${val}</v></c>`);
|
|
4167
4200
|
} else {
|
|
4168
|
-
this._writeStringCell(bigBuf, val.toString(),
|
|
4201
|
+
this._writeStringCell(bigBuf, val.toString(), ref, xfIdx >= 0 ? xfIdx : void 0);
|
|
4169
4202
|
}
|
|
4170
4203
|
} else if (typeof val === "bigint") {
|
|
4171
|
-
this._writeStringCell(bigBuf, val.toString(),
|
|
4204
|
+
this._writeStringCell(bigBuf, val.toString(), ref, xfIdx >= 0 ? xfIdx : void 0);
|
|
4172
4205
|
} else if (typeof val === "boolean") {
|
|
4173
|
-
bigBuf.writeString(`<c
|
|
4206
|
+
bigBuf.writeString(`<c${ref} t="b"${styleAttr}><v>${val ? 1 : 0}</v></c>`);
|
|
4174
4207
|
} else if (val instanceof Date) {
|
|
4175
4208
|
const oaDate = this._toOADate(val);
|
|
4176
4209
|
if (Number.isFinite(oaDate)) {
|
|
4177
4210
|
const finalStyle = xfIdx >= 0 ? xfIdx : 1;
|
|
4178
|
-
bigBuf.writeString(`<c
|
|
4211
|
+
bigBuf.writeString(`<c${ref} s="${finalStyle}"><v>${oaDate}</v></c>`);
|
|
4179
4212
|
} else {
|
|
4180
|
-
this._writeStringCell(bigBuf, val.toString(),
|
|
4213
|
+
this._writeStringCell(bigBuf, val.toString(), ref, xfIdx >= 0 ? xfIdx : void 0);
|
|
4181
4214
|
}
|
|
4182
4215
|
} else if (val !== null && val !== void 0) {
|
|
4183
|
-
this._writeStringCell(bigBuf, val.toString(),
|
|
4216
|
+
this._writeStringCell(bigBuf, val.toString(), ref, xfIdx >= 0 ? xfIdx : void 0);
|
|
4184
4217
|
}
|
|
4185
4218
|
}
|
|
4186
4219
|
bigBuf.writeString("</row>");
|
|
@@ -4266,7 +4299,7 @@ var XlsxWriter = class {
|
|
|
4266
4299
|
rowNum++;
|
|
4267
4300
|
bigBuf.writeString(`<row r="${rowNum}">`);
|
|
4268
4301
|
for (let c = 0; c < headers.length; c++) {
|
|
4269
|
-
this._writeStringCell(bigBuf, headers[c],
|
|
4302
|
+
this._writeStringCell(bigBuf, headers[c], "", 3);
|
|
4270
4303
|
}
|
|
4271
4304
|
bigBuf.writeString("</row>");
|
|
4272
4305
|
}
|
|
@@ -4274,6 +4307,7 @@ var XlsxWriter = class {
|
|
|
4274
4307
|
rowNum++;
|
|
4275
4308
|
bigBuf.writeString(`<row r="${rowNum}">`);
|
|
4276
4309
|
const row = rows[r];
|
|
4310
|
+
let prevCol = -1;
|
|
4277
4311
|
for (let c = 0; c < row.length; c++) {
|
|
4278
4312
|
const raw = row[c];
|
|
4279
4313
|
if (raw === null || raw === void 0) continue;
|
|
@@ -4281,27 +4315,28 @@ var XlsxWriter = class {
|
|
|
4281
4315
|
const val = fmtString !== null ? unwrapCell(raw) : raw;
|
|
4282
4316
|
const xfIdx = fmtString !== null ? this._registerFormat(fmtString) : -1;
|
|
4283
4317
|
const styleAttr = xfIdx >= 0 ? ` s="${xfIdx}"` : "";
|
|
4284
|
-
const
|
|
4318
|
+
const ref = cellRefAttr(c, prevCol, colLetters[c], rowNum);
|
|
4319
|
+
prevCol = c;
|
|
4285
4320
|
if (typeof val === "number") {
|
|
4286
4321
|
if (Number.isFinite(val)) {
|
|
4287
|
-
bigBuf.writeString(`<c
|
|
4322
|
+
bigBuf.writeString(`<c${ref}${styleAttr}><v>${val}</v></c>`);
|
|
4288
4323
|
} else {
|
|
4289
|
-
this._writeStringCell(bigBuf, val.toString(),
|
|
4324
|
+
this._writeStringCell(bigBuf, val.toString(), ref, xfIdx >= 0 ? xfIdx : void 0);
|
|
4290
4325
|
}
|
|
4291
4326
|
} else if (typeof val === "bigint") {
|
|
4292
|
-
this._writeStringCell(bigBuf, val.toString(),
|
|
4327
|
+
this._writeStringCell(bigBuf, val.toString(), ref, xfIdx >= 0 ? xfIdx : void 0);
|
|
4293
4328
|
} else if (typeof val === "boolean") {
|
|
4294
|
-
bigBuf.writeString(`<c
|
|
4329
|
+
bigBuf.writeString(`<c${ref} t="b"${styleAttr}><v>${val ? 1 : 0}</v></c>`);
|
|
4295
4330
|
} else if (val instanceof Date) {
|
|
4296
4331
|
const oaDate = this._toOADate(val);
|
|
4297
4332
|
if (Number.isFinite(oaDate)) {
|
|
4298
4333
|
const finalStyle = xfIdx >= 0 ? xfIdx : 1;
|
|
4299
|
-
bigBuf.writeString(`<c
|
|
4334
|
+
bigBuf.writeString(`<c${ref} s="${finalStyle}"><v>${oaDate}</v></c>`);
|
|
4300
4335
|
} else {
|
|
4301
|
-
this._writeStringCell(bigBuf, val.toString(),
|
|
4336
|
+
this._writeStringCell(bigBuf, val.toString(), ref, xfIdx >= 0 ? xfIdx : void 0);
|
|
4302
4337
|
}
|
|
4303
4338
|
} else if (val !== null && val !== void 0) {
|
|
4304
|
-
this._writeStringCell(bigBuf, val.toString(),
|
|
4339
|
+
this._writeStringCell(bigBuf, val.toString(), ref, xfIdx >= 0 ? xfIdx : void 0);
|
|
4305
4340
|
}
|
|
4306
4341
|
}
|
|
4307
4342
|
bigBuf.writeString("</row>");
|
|
@@ -4320,7 +4355,8 @@ var XlsxWriter = class {
|
|
|
4320
4355
|
name: this.sheetList[this.sheetCount - 1].pathInArchive
|
|
4321
4356
|
});
|
|
4322
4357
|
}
|
|
4323
|
-
|
|
4358
|
+
/** `ref` is the cell's `r` attribute from `cellRefAttr`, or '' when omitted. */
|
|
4359
|
+
_writeStringCell(bigBuf, val, ref, styleOverride) {
|
|
4324
4360
|
assertCellTextLength(val);
|
|
4325
4361
|
let index = this.sstMap.get(val);
|
|
4326
4362
|
if (index === void 0) {
|
|
@@ -4330,7 +4366,7 @@ var XlsxWriter = class {
|
|
|
4330
4366
|
}
|
|
4331
4367
|
this.sstCntAll++;
|
|
4332
4368
|
const styleAttr = styleOverride !== void 0 ? ` s="${styleOverride}"` : "";
|
|
4333
|
-
bigBuf.writeString(`<c
|
|
4369
|
+
bigBuf.writeString(`<c${ref} t="s"${styleAttr}><v>${index}</v></c>`);
|
|
4334
4370
|
}
|
|
4335
4371
|
_registerFormat(fmtString) {
|
|
4336
4372
|
if (this._formatXfMap.has(fmtString)) {
|
|
@@ -4738,7 +4774,7 @@ async function writeAdmZipStreaming(zip, stagedParts, destinationPath) {
|
|
|
4738
4774
|
} catch {
|
|
4739
4775
|
}
|
|
4740
4776
|
});
|
|
4741
|
-
archive = (0, import_archiver3.default)("zip");
|
|
4777
|
+
archive = (0, import_archiver3.default)("zip", { zlib: { level: DEFAULT_COMPRESSION_LEVEL } });
|
|
4742
4778
|
archive.on("error", (err) => {
|
|
4743
4779
|
outputError = err;
|
|
4744
4780
|
});
|
|
@@ -5247,7 +5283,7 @@ var XlsxUpdater = class _XlsxUpdater {
|
|
|
5247
5283
|
throw new Error("XlsxUpdater: sharedStrings.xml has no closing sst element.");
|
|
5248
5284
|
}
|
|
5249
5285
|
const appended = this.sharedStringsPending.map((txt) => {
|
|
5250
|
-
const clean =
|
|
5286
|
+
const clean = escapeXlsxText(txt);
|
|
5251
5287
|
const preserve = clean.length > 0 && (clean[0] === " " || clean[clean.length - 1] === " " || /[\t\n\r]/.test(clean));
|
|
5252
5288
|
const tAttr = preserve ? ' xml:space="preserve"' : "";
|
|
5253
5289
|
return `<${prefix}si><${prefix}t${tAttr}>${clean}</${prefix}t></${prefix}si>`;
|
|
@@ -5270,14 +5306,25 @@ var XlsxUpdater = class _XlsxUpdater {
|
|
|
5270
5306
|
const sdEnd = sheetXml.indexOf("</sheetData>", sdStart);
|
|
5271
5307
|
if (sdEnd === -1) return { dataStyles: /* @__PURE__ */ new Map(), headerStyles };
|
|
5272
5308
|
const region = sheetXml.substring(sdStart, sdEnd);
|
|
5273
|
-
const cellRe = /<c\b[^>]*>/g;
|
|
5309
|
+
const cellRe = /<row\b[^>]*>|<c\b[^>]*>/g;
|
|
5274
5310
|
let m;
|
|
5311
|
+
let row = 0;
|
|
5312
|
+
let nextCol = 0;
|
|
5275
5313
|
while ((m = cellRe.exec(region)) !== null) {
|
|
5276
5314
|
const tag = m[0];
|
|
5315
|
+
if (tag.startsWith("<row")) {
|
|
5316
|
+
const rowAttr = /\br="(\d+)"/.exec(tag);
|
|
5317
|
+
row = rowAttr ? parseInt(rowAttr[1], 10) : row + 1;
|
|
5318
|
+
nextCol = 0;
|
|
5319
|
+
continue;
|
|
5320
|
+
}
|
|
5277
5321
|
const rMatch = /r="([A-Z]+)(\d+)"/.exec(tag);
|
|
5278
|
-
|
|
5279
|
-
|
|
5280
|
-
|
|
5322
|
+
let col = nextCol;
|
|
5323
|
+
if (rMatch) {
|
|
5324
|
+
col = columnLetterToIndex(rMatch[1]);
|
|
5325
|
+
row = parseInt(rMatch[2], 10);
|
|
5326
|
+
}
|
|
5327
|
+
nextCol = col + 1;
|
|
5281
5328
|
const sMatch = /s="(\d+)"/.exec(tag);
|
|
5282
5329
|
if (!sMatch) continue;
|
|
5283
5330
|
const s = parseInt(sMatch[1], 10);
|
|
@@ -5398,7 +5445,7 @@ var XlsxUpdater = class _XlsxUpdater {
|
|
|
5398
5445
|
const colRef = columnIndexToLetter(col);
|
|
5399
5446
|
const styleAttr = style > 0 ? ` s="${style}"` : "";
|
|
5400
5447
|
if (this.sharedStringsXml === null) {
|
|
5401
|
-
const clean =
|
|
5448
|
+
const clean = escapeXlsxText(text);
|
|
5402
5449
|
const preserve = clean.length > 0 && (clean[0] === " " || clean[clean.length - 1] === " " || /[\t\n\r]/.test(clean));
|
|
5403
5450
|
const tAttr = preserve ? ' xml:space="preserve"' : "";
|
|
5404
5451
|
return `<c r="${colRef}${rowNum}" t="inlineStr"${styleAttr}><is><t${tAttr}>${clean}</t></is></c>`;
|
|
@@ -6938,6 +6985,7 @@ function convertXlsxToXlsb(inputPath, outputPath, options) {
|
|
|
6938
6985
|
convertXlsbToXlsx,
|
|
6939
6986
|
convertXlsxToXlsb,
|
|
6940
6987
|
defaultColWidth,
|
|
6988
|
+
escapeXlsxText,
|
|
6941
6989
|
escapeXmlText,
|
|
6942
6990
|
getFormat,
|
|
6943
6991
|
initColWidths,
|
|
@@ -6948,6 +6996,7 @@ function convertXlsxToXlsb(inputPath, outputPath, options) {
|
|
|
6948
6996
|
sanitizeSheetName,
|
|
6949
6997
|
trimTrailingEmptyRows,
|
|
6950
6998
|
unescapeXml,
|
|
6999
|
+
unescapeXmlText,
|
|
6951
7000
|
unwrapCell,
|
|
6952
7001
|
updateColWidthsFromRows
|
|
6953
7002
|
});
|