@extend-ai/react-xlsx 0.15.0 → 0.15.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/dist/index.cjs CHANGED
@@ -6801,6 +6801,204 @@ function cloneArrayBufferForTransfer(buffer) {
6801
6801
  return buffer.slice(0);
6802
6802
  }
6803
6803
 
6804
+ // src/zip-entry-names.ts
6805
+ var BACKSLASH_BYTE = 92;
6806
+ var FORWARD_SLASH_BYTE = 47;
6807
+ var END_OF_CENTRAL_DIRECTORY_SIGNATURE = 101010256;
6808
+ var CENTRAL_FILE_HEADER_SIGNATURE = 33639248;
6809
+ var LOCAL_FILE_HEADER_SIGNATURE = 67324752;
6810
+ var END_OF_CENTRAL_DIRECTORY_LENGTH = 22;
6811
+ var CENTRAL_FILE_HEADER_LENGTH = 46;
6812
+ var LOCAL_FILE_HEADER_LENGTH = 30;
6813
+ var MAX_ZIP_COMMENT_LENGTH = 65535;
6814
+ var ZIP16_SENTINEL = 65535;
6815
+ var ZIP32_SENTINEL = 4294967295;
6816
+ function findEndOfCentralDirectoryOffset(view) {
6817
+ const firstPossibleOffset = Math.max(
6818
+ 0,
6819
+ view.byteLength - END_OF_CENTRAL_DIRECTORY_LENGTH - MAX_ZIP_COMMENT_LENGTH
6820
+ );
6821
+ for (let offset = view.byteLength - END_OF_CENTRAL_DIRECTORY_LENGTH; offset >= firstPossibleOffset; offset -= 1) {
6822
+ if (view.getUint32(offset, true) !== END_OF_CENTRAL_DIRECTORY_SIGNATURE) {
6823
+ continue;
6824
+ }
6825
+ const commentLength = view.getUint16(offset + 20, true);
6826
+ if (offset + END_OF_CENTRAL_DIRECTORY_LENGTH + commentLength === view.byteLength) {
6827
+ return offset;
6828
+ }
6829
+ }
6830
+ return null;
6831
+ }
6832
+ function readCentralDirectoryInfo(view) {
6833
+ if (view.byteLength < END_OF_CENTRAL_DIRECTORY_LENGTH) {
6834
+ return null;
6835
+ }
6836
+ const endOfCentralDirectoryOffset = findEndOfCentralDirectoryOffset(view);
6837
+ if (endOfCentralDirectoryOffset === null) {
6838
+ return null;
6839
+ }
6840
+ const diskNumber = view.getUint16(endOfCentralDirectoryOffset + 4, true);
6841
+ const centralDirectoryDiskNumber = view.getUint16(endOfCentralDirectoryOffset + 6, true);
6842
+ const entriesOnDisk = view.getUint16(endOfCentralDirectoryOffset + 8, true);
6843
+ const entryCount = view.getUint16(endOfCentralDirectoryOffset + 10, true);
6844
+ const centralDirectorySize = view.getUint32(endOfCentralDirectoryOffset + 12, true);
6845
+ const centralDirectoryOffset = view.getUint32(endOfCentralDirectoryOffset + 16, true);
6846
+ if (diskNumber !== 0 || centralDirectoryDiskNumber !== 0 || entriesOnDisk !== entryCount || entryCount === ZIP16_SENTINEL || centralDirectorySize === ZIP32_SENTINEL || centralDirectoryOffset === ZIP32_SENTINEL) {
6847
+ return null;
6848
+ }
6849
+ const centralDirectoryEndOffset = centralDirectoryOffset + centralDirectorySize;
6850
+ if (centralDirectoryOffset > endOfCentralDirectoryOffset || centralDirectoryEndOffset > endOfCentralDirectoryOffset || centralDirectoryEndOffset > view.byteLength) {
6851
+ return null;
6852
+ }
6853
+ return {
6854
+ endOffset: centralDirectoryEndOffset,
6855
+ entryCount,
6856
+ offset: centralDirectoryOffset
6857
+ };
6858
+ }
6859
+ function readCentralDirectoryEntry(view, centralDirectoryEndOffset, offset) {
6860
+ if (offset < 0 || offset + CENTRAL_FILE_HEADER_LENGTH > centralDirectoryEndOffset || offset + CENTRAL_FILE_HEADER_LENGTH > view.byteLength || view.getUint32(offset, true) !== CENTRAL_FILE_HEADER_SIGNATURE) {
6861
+ return null;
6862
+ }
6863
+ const nameLength = view.getUint16(offset + 28, true);
6864
+ const extraLength = view.getUint16(offset + 30, true);
6865
+ const commentLength = view.getUint16(offset + 32, true);
6866
+ const nameStart = offset + CENTRAL_FILE_HEADER_LENGTH;
6867
+ const nameEnd = nameStart + nameLength;
6868
+ const nextOffset = nameEnd + extraLength + commentLength;
6869
+ if (nameEnd > centralDirectoryEndOffset || nextOffset > centralDirectoryEndOffset) {
6870
+ return null;
6871
+ }
6872
+ return {
6873
+ diskNumberStart: view.getUint16(offset + 34, true),
6874
+ localHeaderOffset: view.getUint32(offset + 42, true),
6875
+ nameEnd,
6876
+ nameStart,
6877
+ nextOffset
6878
+ };
6879
+ }
6880
+ function entryNameUsesBackslash(bytes, entry) {
6881
+ for (let cursor = entry.nameStart; cursor < entry.nameEnd; cursor += 1) {
6882
+ if (bytes[cursor] === BACKSLASH_BYTE) {
6883
+ return true;
6884
+ }
6885
+ }
6886
+ return false;
6887
+ }
6888
+ function centralDirectoryUsesBackslashSeparators(bytes, view, centralDirectory) {
6889
+ let offset = centralDirectory.offset;
6890
+ for (let index = 0; index < centralDirectory.entryCount; index += 1) {
6891
+ const entry = readCentralDirectoryEntry(view, centralDirectory.endOffset, offset);
6892
+ if (!entry) {
6893
+ return null;
6894
+ }
6895
+ if (entryNameUsesBackslash(bytes, entry)) {
6896
+ return true;
6897
+ }
6898
+ offset = entry.nextOffset;
6899
+ }
6900
+ return false;
6901
+ }
6902
+ function normalizedEntryNameKey(bytes, entry) {
6903
+ let key = "";
6904
+ for (let cursor = entry.nameStart; cursor < entry.nameEnd; cursor += 1) {
6905
+ const byte = bytes[cursor] === BACKSLASH_BYTE ? FORWARD_SLASH_BYTE : bytes[cursor];
6906
+ key += String.fromCharCode(byte);
6907
+ }
6908
+ return key;
6909
+ }
6910
+ function validateEntryNamePatches(bytes, view, centralDirectory) {
6911
+ const normalizedNames = /* @__PURE__ */ new Set();
6912
+ const localHeaderOffsets = /* @__PURE__ */ new Set();
6913
+ let offset = centralDirectory.offset;
6914
+ for (let index = 0; index < centralDirectory.entryCount; index += 1) {
6915
+ const entry = readCentralDirectoryEntry(view, centralDirectory.endOffset, offset);
6916
+ if (!entry || entry.diskNumberStart !== 0 || entry.localHeaderOffset === ZIP32_SENTINEL || entry.localHeaderOffset + LOCAL_FILE_HEADER_LENGTH > centralDirectory.offset || localHeaderOffsets.has(entry.localHeaderOffset)) {
6917
+ return false;
6918
+ }
6919
+ localHeaderOffsets.add(entry.localHeaderOffset);
6920
+ const normalizedName = normalizedEntryNameKey(bytes, entry);
6921
+ if (normalizedNames.has(normalizedName)) {
6922
+ return false;
6923
+ }
6924
+ normalizedNames.add(normalizedName);
6925
+ if (!entryNameUsesBackslash(bytes, entry)) {
6926
+ offset = entry.nextOffset;
6927
+ continue;
6928
+ }
6929
+ if (view.getUint32(entry.localHeaderOffset, true) !== LOCAL_FILE_HEADER_SIGNATURE) {
6930
+ return false;
6931
+ }
6932
+ const localNameLength = view.getUint16(entry.localHeaderOffset + 26, true);
6933
+ const localNameStart = entry.localHeaderOffset + LOCAL_FILE_HEADER_LENGTH;
6934
+ const localNameEnd = localNameStart + localNameLength;
6935
+ if (localNameLength !== entry.nameEnd - entry.nameStart || localNameEnd > centralDirectory.offset) {
6936
+ return false;
6937
+ }
6938
+ for (let nameIndex = 0; nameIndex < localNameLength; nameIndex += 1) {
6939
+ const centralNameOffset = entry.nameStart + nameIndex;
6940
+ const localNameOffset = localNameStart + nameIndex;
6941
+ if (bytes[centralNameOffset] !== bytes[localNameOffset]) {
6942
+ return false;
6943
+ }
6944
+ }
6945
+ offset = entry.nextOffset;
6946
+ }
6947
+ return true;
6948
+ }
6949
+ function patchEntryNameSeparators(bytes, view, centralDirectory) {
6950
+ let offset = centralDirectory.offset;
6951
+ for (let index = 0; index < centralDirectory.entryCount; index += 1) {
6952
+ const entry = readCentralDirectoryEntry(view, centralDirectory.endOffset, offset);
6953
+ if (!entry) {
6954
+ return;
6955
+ }
6956
+ if (entryNameUsesBackslash(bytes, entry)) {
6957
+ const localNameStart = entry.localHeaderOffset + LOCAL_FILE_HEADER_LENGTH;
6958
+ for (let nameIndex = 0; nameIndex < entry.nameEnd - entry.nameStart; nameIndex += 1) {
6959
+ const centralNameOffset = entry.nameStart + nameIndex;
6960
+ if (bytes[centralNameOffset] === BACKSLASH_BYTE) {
6961
+ bytes[centralNameOffset] = FORWARD_SLASH_BYTE;
6962
+ bytes[localNameStart + nameIndex] = FORWARD_SLASH_BYTE;
6963
+ }
6964
+ }
6965
+ }
6966
+ offset = entry.nextOffset;
6967
+ }
6968
+ }
6969
+ function normalizeZipEntryNames(bytes) {
6970
+ const view = new DataView(bytes.buffer, bytes.byteOffset, bytes.byteLength);
6971
+ const centralDirectory = readCentralDirectoryInfo(view);
6972
+ if (!centralDirectory || centralDirectoryUsesBackslashSeparators(bytes, view, centralDirectory) !== true) {
6973
+ return bytes;
6974
+ }
6975
+ if (!validateEntryNamePatches(bytes, view, centralDirectory)) {
6976
+ return bytes;
6977
+ }
6978
+ const normalizedBytes = new Uint8Array(bytes.byteLength);
6979
+ normalizedBytes.set(bytes);
6980
+ const normalizedView = new DataView(
6981
+ normalizedBytes.buffer,
6982
+ normalizedBytes.byteOffset,
6983
+ normalizedBytes.byteLength
6984
+ );
6985
+ patchEntryNameSeparators(normalizedBytes, normalizedView, centralDirectory);
6986
+ return normalizedBytes;
6987
+ }
6988
+ function normalizeWorkbookArrayBuffer(buffer) {
6989
+ const bytes = new Uint8Array(buffer);
6990
+ const normalizedBytes = normalizeZipEntryNames(bytes);
6991
+ if (normalizedBytes === bytes) {
6992
+ return buffer;
6993
+ }
6994
+ if (normalizedBytes.byteOffset === 0 && normalizedBytes.byteLength === normalizedBytes.buffer.byteLength && normalizedBytes.buffer instanceof ArrayBuffer) {
6995
+ return normalizedBytes.buffer;
6996
+ }
6997
+ const normalizedBuffer = new ArrayBuffer(normalizedBytes.byteLength);
6998
+ new Uint8Array(normalizedBuffer).set(normalizedBytes);
6999
+ return normalizedBuffer;
7000
+ }
7001
+
6804
7002
  // src/controller.tsx
6805
7003
  var FORMULA_COUNT_THRESHOLD = 1e3;
6806
7004
  var DEFAULT_ROW_HEIGHT = 24;
@@ -8444,6 +8642,7 @@ function useXlsxViewerController(options) {
8444
8642
  if (maxFileSizeBytes > 0 && buffer.byteLength > maxFileSizeBytes) {
8445
8643
  throw new XlsxFileSizeLimitExceededError(buffer.byteLength, maxFileSizeBytes);
8446
8644
  }
8645
+ buffer = normalizeWorkbookArrayBuffer(buffer);
8447
8646
  const preflight = preflightWorkbookBuffer(buffer);
8448
8647
  if (preflight?.tooLarge) {
8449
8648
  throw createWorkbookTooLargeError(preflight);