@eui/components 18.2.16-snapshot-1756456305763 → 18.2.16-snapshot-1756489547144
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/docs/js/search/search_index.js +2 -2
- package/docs/miscellaneous/variables.html +499 -71
- package/docs/properties.html +1 -1
- package/esm2022/eui-file-upload/utils/eui-file-upload.validators.mjs +3 -2
- package/esm2022/eui-file-upload/utils/mime-types.mjs +292 -39
- package/eui-file-upload/utils/mime-types.d.ts.map +1 -1
- package/fesm2022/eui-components-eui-file-upload.mjs +293 -39
- package/fesm2022/eui-components-eui-file-upload.mjs.map +1 -1
- package/package.json +9 -9
- package/directives/package.json +0 -3
- package/eui-accordion/package.json +0 -3
- package/eui-alert/package.json +0 -3
- package/eui-autocomplete/package.json +0 -3
- package/eui-avatar/package.json +0 -3
- package/eui-badge/package.json +0 -3
- package/eui-block-content/package.json +0 -3
- package/eui-block-document/package.json +0 -3
- package/eui-breadcrumb/package.json +0 -3
- package/eui-button/package.json +0 -3
- package/eui-button-group/package.json +0 -3
- package/eui-button-v2/package.json +0 -3
- package/eui-card/package.json +0 -3
- package/eui-chip/package.json +0 -3
- package/eui-chip-list/package.json +0 -3
- package/eui-dashboard-button/package.json +0 -3
- package/eui-dashboard-card/package.json +0 -3
- package/eui-date-range-selector/package.json +0 -3
- package/eui-datepicker/package.json +0 -3
- package/eui-dialog/package.json +0 -3
- package/eui-dimmer/package.json +0 -3
- package/eui-disable-content/package.json +0 -3
- package/eui-discussion-thread/package.json +0 -3
- package/eui-dropdown/package.json +0 -3
- package/eui-feedback-message/package.json +0 -3
- package/eui-fieldset/package.json +0 -3
- package/eui-file-upload/package.json +0 -3
- package/eui-growl/package.json +0 -3
- package/eui-icon/package.json +0 -3
- package/eui-icon-button/package.json +0 -3
- package/eui-icon-button-expander/package.json +0 -3
- package/eui-icon-color/package.json +0 -3
- package/eui-icon-input/package.json +0 -3
- package/eui-icon-state/package.json +0 -3
- package/eui-icon-toggle/package.json +0 -3
- package/eui-input-checkbox/package.json +0 -3
- package/eui-input-group/package.json +0 -3
- package/eui-input-number/package.json +0 -3
- package/eui-input-radio/package.json +0 -3
- package/eui-input-text/package.json +0 -3
- package/eui-label/package.json +0 -3
- package/eui-language-selector/package.json +0 -3
- package/eui-list/package.json +0 -3
- package/eui-menu/package.json +0 -3
- package/eui-message-box/package.json +0 -3
- package/eui-navbar/package.json +0 -3
- package/eui-overlay/package.json +0 -3
- package/eui-page/package.json +0 -3
- package/eui-paginator/package.json +0 -3
- package/eui-popover/package.json +0 -3
- package/eui-progress-bar/package.json +0 -3
- package/eui-progress-circle/package.json +0 -3
- package/eui-select/package.json +0 -3
- package/eui-sidebar-menu/package.json +0 -3
- package/eui-skeleton/package.json +0 -3
- package/eui-slide-toggle/package.json +0 -3
- package/eui-split-button/package.json +0 -3
- package/eui-table/package.json +0 -3
- package/eui-table-v2/package.json +0 -3
- package/eui-tabs/package.json +0 -3
- package/eui-textarea/package.json +0 -3
- package/eui-timebar/package.json +0 -3
- package/eui-timeline/package.json +0 -3
- package/eui-timepicker/package.json +0 -3
- package/eui-tree/package.json +0 -3
- package/eui-tree-list/package.json +0 -3
- package/eui-user-profile/package.json +0 -3
- package/eui-wizard/package.json +0 -3
- package/externals/charts/package.json +0 -3
- package/externals/eui-editor/package.json +0 -3
- package/externals/helpers/package.json +0 -3
- package/externals/quill/package.json +0 -3
- package/externals/search/favourite-queries/package.json +0 -3
- package/layout/package.json +0 -3
- package/pipes/package.json +0 -3
- package/shared/package.json +0 -3
- package/validators/package.json +0 -3
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"mime-types.d.ts","sourceRoot":"","sources":["../../../eui-file-upload/utils/mime-types.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,QAAQ,GACd,YAAY,GACZ,WAAW,GACX,WAAW,GACX,YAAY,GACZ,YAAY,GACZ,aAAa,GACb,mBAAmB,GACnB,mBAAmB,GACnB,YAAY,GACZ,WAAW,GACX,YAAY,GACZ,oBAAoB,GACpB,2BAA2B,GAC3B,wBAAwB,GACxB,sBAAsB,GACtB,yBAAyB,GACzB,yCAAyC,GACzC,gDAAgD,GAChD,iDAAiD,GACjD,yEAAyE,GACzE,2EAA2E,GAC3E,mEAAmE,GACnE,iBAAiB,GACjB,kBAAkB,GAClB,mBAAmB,GACnB,8BAA8B,GAC9B,kBAAkB,GAClB,qBAAqB,GACrB,6BAA6B,GAC7B,+BAA+B,GAC/B,WAAW,GACX,YAAY,GACZ,kBAAkB,GAClB,YAAY,GACZ,iBAAiB,GACjB,eAAe,GACf,gBAAgB,GAChB,aAAa,GACb,gBAAgB,GAChB,gBAAgB,GAChB,wBAAwB,GACxB,YAAY,GACZ,YAAY,GACZ,YAAY,GACZ,WAAW,GACX,YAAY,GACZ,WAAW,GACX,WAAW,GACX,iBAAiB,GACjB,cAAc,GACd,WAAW,GACX,eAAe,GACf,WAAW,GACX,iBAAiB,GACjB,mBAAmB,GACnB,0BAA0B,GAC1B,+BAA+B,GAC/B,iBAAiB,GACjB,kBAAkB,GAClB,WAAW,GACX,YAAY,GACZ,+BAA+B,GAC/B,UAAU,GACV,UAAU,GACV,cAAc,GACd,aAAa,GACb,wBAAwB,GACxB,iBAAiB,GACjB,kBAAkB,GAClB,uBAAuB,GACvB,gCAAgC,GAChC,uCAAuC,GACvC,mCAAmC,GACnC,mBAAmB,GACnB,4BAA4B,GAC5B,mBAAmB,GACnB,wBAAwB,GACxB,oBAAoB,GACpB,mBAAmB,GACnB,mBAAmB,GACnB,4BAA4B,GAC5B,iBAAiB,GACjB,YAAY,GACZ,uBAAuB,GACvB,WAAW,GACX,WAAW,GACX,WAAW,GACX,WAAW,GACX,WAAW,GACX,WAAW,GACX,YAAY,GACZ,iBAAiB,GACjB,gCAAgC,GAChC,YAAY,GACZ,qBAAqB,GACrB,YAAY,GACZ,qBAAqB,GACrB,WAAW,GACX,mBAAmB,GACnB,kBAAkB,GAClB,eAAe,GACf,YAAY,GACZ,mBAAmB,GACnB,8BAA8B,GAC9B,aAAa,GACb,wBAAwB,GACxB,aAAa,GACb,YAAY,GACZ,qBAAqB,GACrB,kBAAkB,GAClB,mBAAmB,GACnB,mBAAmB,GACnB,uBAAuB,GACvB,sBAAsB,GACtB,aAAa,GACb,aAAa,GACb,0BAA0B,GAC1B,WAAW,GACX,YAAY,GACZ,aAAa,GACb,YAAY,GACZ,YAAY,GACZ,YAAY,GACZ,8BAA8B,GAC9B,YAAY,GACZ,8BAA8B,GAC9B,2BAA2B,GAC3B,oBAAoB,GACpB,WAAW,GACX,6BAA6B,GAC7B,WAAW,GACX,WAAW,GACX,kBAAkB,GAClB,WAAW,GACX,4BAA4B,GAC5B,eAAe,GACf,uBAAuB,GACvB,qBAAqB,GACrB,mBAAmB,GACnB,oBAAoB,GACpB,8BAA8B,GAC9B,kBAAkB,GAClB,4BAA4B,CAAC;AAEnC,eAAO,MAAM,WAAW,WAAY,UAAU,KAAG,
|
1
|
+
{"version":3,"file":"mime-types.d.ts","sourceRoot":"","sources":["../../../eui-file-upload/utils/mime-types.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,QAAQ,GACd,YAAY,GACZ,WAAW,GACX,WAAW,GACX,YAAY,GACZ,YAAY,GACZ,aAAa,GACb,mBAAmB,GACnB,mBAAmB,GACnB,YAAY,GACZ,WAAW,GACX,YAAY,GACZ,oBAAoB,GACpB,2BAA2B,GAC3B,wBAAwB,GACxB,sBAAsB,GACtB,yBAAyB,GACzB,yCAAyC,GACzC,gDAAgD,GAChD,iDAAiD,GACjD,yEAAyE,GACzE,2EAA2E,GAC3E,mEAAmE,GACnE,iBAAiB,GACjB,kBAAkB,GAClB,mBAAmB,GACnB,8BAA8B,GAC9B,kBAAkB,GAClB,qBAAqB,GACrB,6BAA6B,GAC7B,+BAA+B,GAC/B,WAAW,GACX,YAAY,GACZ,kBAAkB,GAClB,YAAY,GACZ,iBAAiB,GACjB,eAAe,GACf,gBAAgB,GAChB,aAAa,GACb,gBAAgB,GAChB,gBAAgB,GAChB,wBAAwB,GACxB,YAAY,GACZ,YAAY,GACZ,YAAY,GACZ,WAAW,GACX,YAAY,GACZ,WAAW,GACX,WAAW,GACX,iBAAiB,GACjB,cAAc,GACd,WAAW,GACX,eAAe,GACf,WAAW,GACX,iBAAiB,GACjB,mBAAmB,GACnB,0BAA0B,GAC1B,+BAA+B,GAC/B,iBAAiB,GACjB,kBAAkB,GAClB,WAAW,GACX,YAAY,GACZ,+BAA+B,GAC/B,UAAU,GACV,UAAU,GACV,cAAc,GACd,aAAa,GACb,wBAAwB,GACxB,iBAAiB,GACjB,kBAAkB,GAClB,uBAAuB,GACvB,gCAAgC,GAChC,uCAAuC,GACvC,mCAAmC,GACnC,mBAAmB,GACnB,4BAA4B,GAC5B,mBAAmB,GACnB,wBAAwB,GACxB,oBAAoB,GACpB,mBAAmB,GACnB,mBAAmB,GACnB,4BAA4B,GAC5B,iBAAiB,GACjB,YAAY,GACZ,uBAAuB,GACvB,WAAW,GACX,WAAW,GACX,WAAW,GACX,WAAW,GACX,WAAW,GACX,WAAW,GACX,YAAY,GACZ,iBAAiB,GACjB,gCAAgC,GAChC,YAAY,GACZ,qBAAqB,GACrB,YAAY,GACZ,qBAAqB,GACrB,WAAW,GACX,mBAAmB,GACnB,kBAAkB,GAClB,eAAe,GACf,YAAY,GACZ,mBAAmB,GACnB,8BAA8B,GAC9B,aAAa,GACb,wBAAwB,GACxB,aAAa,GACb,YAAY,GACZ,qBAAqB,GACrB,kBAAkB,GAClB,mBAAmB,GACnB,mBAAmB,GACnB,uBAAuB,GACvB,sBAAsB,GACtB,aAAa,GACb,aAAa,GACb,0BAA0B,GAC1B,WAAW,GACX,YAAY,GACZ,aAAa,GACb,YAAY,GACZ,YAAY,GACZ,YAAY,GACZ,8BAA8B,GAC9B,YAAY,GACZ,8BAA8B,GAC9B,2BAA2B,GAC3B,oBAAoB,GACpB,WAAW,GACX,6BAA6B,GAC7B,WAAW,GACX,WAAW,GACX,kBAAkB,GAClB,WAAW,GACX,4BAA4B,GAC5B,eAAe,GACf,uBAAuB,GACvB,qBAAqB,GACrB,mBAAmB,GACnB,oBAAoB,GACpB,8BAA8B,GAC9B,kBAAkB,GAClB,4BAA4B,CAAC;AAEnC,eAAO,MAAM,WAAW,WAAY,UAAU,KAAG,QAkGhD,CAAC"}
|
@@ -615,7 +615,7 @@ const getMimeType = (header) => {
|
|
615
615
|
// convert Uint8Array to hex string
|
616
616
|
const hex = uint8ArrayToHexString(header);
|
617
617
|
// map hex string to mime type
|
618
|
-
if (hex.startsWith('
|
618
|
+
if (hex.startsWith('ffd8ff'))
|
619
619
|
return 'image/jpeg';
|
620
620
|
if (hex.startsWith('89504e47'))
|
621
621
|
return 'image/png';
|
@@ -639,24 +639,10 @@ const getMimeType = (header) => {
|
|
639
639
|
return 'image/vnd.adobe.photoshop';
|
640
640
|
if (hex.startsWith('06054b50'))
|
641
641
|
return 'application/x-indesign';
|
642
|
-
|
643
|
-
|
644
|
-
|
645
|
-
|
646
|
-
if (hex.startsWith('504b0304'))
|
647
|
-
return 'application/vnd.oasis.opendocument.text';
|
648
|
-
if (hex.startsWith('504b0304'))
|
649
|
-
return 'application/vnd.oasis.opendocument.spreadsheet';
|
650
|
-
if (hex.startsWith('504b0304'))
|
651
|
-
return 'application/vnd.oasis.opendocument.presentation';
|
652
|
-
if (hex.startsWith('504b0304'))
|
653
|
-
return 'application/vnd.openxmlformats-officedocument.wordprocessingml.document';
|
654
|
-
if (hex.startsWith('504b0304'))
|
655
|
-
return 'application/vnd.openxmlformats-officedocument.presentationml.presentation';
|
656
|
-
if (hex.startsWith('504b0304'))
|
657
|
-
return 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet';
|
658
|
-
if (hex.startsWith('504b0304'))
|
659
|
-
return 'application/zip';
|
642
|
+
// Handle ZIP-based formats by examining content
|
643
|
+
if (hex.startsWith('504b0304')) {
|
644
|
+
return identifyZipBasedFormat(header);
|
645
|
+
}
|
660
646
|
if (hex.startsWith('7b2274797065223a226a736f6e227d'))
|
661
647
|
return 'application/json';
|
662
648
|
if (hex.startsWith('7573746172'))
|
@@ -688,11 +674,7 @@ const getMimeType = (header) => {
|
|
688
674
|
if (hex.startsWith('0a010301'))
|
689
675
|
return 'audio/qcelp';
|
690
676
|
if (hex.startsWith('3026b2758e66cf11'))
|
691
|
-
return
|
692
|
-
if (hex.startsWith('3026b2758e66cf11'))
|
693
|
-
return 'video/x-ms-asf';
|
694
|
-
if (hex.startsWith('3026b2758e66cf11'))
|
695
|
-
return 'application/vnd.ms-asf';
|
677
|
+
return identifyAsfFormat(header);
|
696
678
|
if (hex.startsWith('000001ba'))
|
697
679
|
return 'video/mpeg';
|
698
680
|
if (hex.startsWith('00000020667479703367'))
|
@@ -704,11 +686,7 @@ const getMimeType = (header) => {
|
|
704
686
|
if (hex.startsWith('4f707573'))
|
705
687
|
return 'audio/opus';
|
706
688
|
if (hex.startsWith('4f676753'))
|
707
|
-
return
|
708
|
-
if (hex.startsWith('4f676753'))
|
709
|
-
return 'audio/ogg';
|
710
|
-
if (hex.startsWith('4f676753'))
|
711
|
-
return 'application/ogg';
|
689
|
+
return identifyOggFormat(header);
|
712
690
|
if (hex.startsWith('664c6143'))
|
713
691
|
return 'audio/x-flac';
|
714
692
|
if (hex.startsWith('4d414320'))
|
@@ -753,8 +731,6 @@ const getMimeType = (header) => {
|
|
753
731
|
return 'application/x-sqlite3';
|
754
732
|
if (hex.startsWith('4e45531a00000001'))
|
755
733
|
return 'application/x-nintendo-nes-rom';
|
756
|
-
if (hex.startsWith('504b0304'))
|
757
|
-
return 'application/x-google-chrome-extension';
|
758
734
|
if (hex.startsWith('4d534346'))
|
759
735
|
return 'application/vnd.ms-cab-compressed';
|
760
736
|
if (hex.startsWith('213c617263683e0a'))
|
@@ -798,13 +774,7 @@ const getMimeType = (header) => {
|
|
798
774
|
if (hex.startsWith('424f4f4b4d4f4249'))
|
799
775
|
return 'application/x-mobipocket-ebook';
|
800
776
|
if (hex.startsWith('667479706174'))
|
801
|
-
return
|
802
|
-
if (hex.startsWith('667479706174'))
|
803
|
-
return 'image/heif-sequence';
|
804
|
-
if (hex.startsWith('667479706174'))
|
805
|
-
return 'image/heic';
|
806
|
-
if (hex.startsWith('667479706174'))
|
807
|
-
return 'image/heic-sequence';
|
777
|
+
return identifyHeifFormat(header);
|
808
778
|
if (hex.startsWith('4b545820'))
|
809
779
|
return 'image/ktx';
|
810
780
|
if (hex.startsWith('4449434d'))
|
@@ -825,9 +795,292 @@ const getMimeType = (header) => {
|
|
825
795
|
return 'audio/vnd.dolby.dd-raw';
|
826
796
|
return null;
|
827
797
|
};
|
798
|
+
const identifyZipBasedFormat = (data) => {
|
799
|
+
try {
|
800
|
+
const fileEntries = extractZipFileList(data);
|
801
|
+
// Chrome extension
|
802
|
+
if (fileEntries.includes('manifest.json')) {
|
803
|
+
return 'application/x-google-chrome-extension';
|
804
|
+
}
|
805
|
+
// EPUB
|
806
|
+
if (fileEntries.includes('META-INF/container.xml') || fileEntries.includes('mimetype')) {
|
807
|
+
return 'application/epub+zip';
|
808
|
+
}
|
809
|
+
// OpenDocument formats
|
810
|
+
if (fileEntries.includes('META-INF/manifest.xml')) {
|
811
|
+
if (fileEntries.some(f => f.endsWith('.odp')))
|
812
|
+
return 'application/vnd.oasis.opendocument.presentation';
|
813
|
+
if (fileEntries.some(f => f.endsWith('.ods')))
|
814
|
+
return 'application/vnd.oasis.opendocument.spreadsheet';
|
815
|
+
if (fileEntries.some(f => f.endsWith('.odt')))
|
816
|
+
return 'application/vnd.oasis.opendocument.text';
|
817
|
+
}
|
818
|
+
// Microsoft Office formats
|
819
|
+
if (fileEntries.includes('[Content_Types].xml')) {
|
820
|
+
if (fileEntries.includes('ppt/presentation.xml'))
|
821
|
+
return 'application/vnd.openxmlformats-officedocument.presentationml.presentation';
|
822
|
+
if (fileEntries.includes('xl/workbook.xml'))
|
823
|
+
return 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet';
|
824
|
+
if (fileEntries.includes('word/document.xml'))
|
825
|
+
return 'application/vnd.openxmlformats-officedocument.wordprocessingml.document';
|
826
|
+
}
|
827
|
+
// Default to generic ZIP
|
828
|
+
return 'application/zip';
|
829
|
+
}
|
830
|
+
catch {
|
831
|
+
return 'application/zip';
|
832
|
+
}
|
833
|
+
};
|
834
|
+
const extractZipFileList = (data) => {
|
835
|
+
// Simplified ZIP parsing - looks for central directory entries
|
836
|
+
const files = [];
|
837
|
+
let offset = 0;
|
838
|
+
while (offset < data.length - 4) {
|
839
|
+
// Look for local file header signature (0x04034b50)
|
840
|
+
if (data[offset] === 0x50 && data[offset + 1] === 0x4b &&
|
841
|
+
data[offset + 2] === 0x03 && data[offset + 3] === 0x04) {
|
842
|
+
const filenameLength = data[offset + 26] | (data[offset + 27] << 8);
|
843
|
+
const extraFieldLength = data[offset + 28] | (data[offset + 29] << 8);
|
844
|
+
if (filenameLength > 0 && offset + 30 + filenameLength <= data.length) {
|
845
|
+
const filename = new TextDecoder().decode(data.slice(offset + 30, offset + 30 + filenameLength));
|
846
|
+
files.push(filename);
|
847
|
+
}
|
848
|
+
offset += 30 + filenameLength + extraFieldLength;
|
849
|
+
}
|
850
|
+
else {
|
851
|
+
offset++;
|
852
|
+
}
|
853
|
+
}
|
854
|
+
return files;
|
855
|
+
};
|
828
856
|
const uint8ArrayToHexString = (uint8Array) => {
|
829
857
|
return Array.prototype.map.call(uint8Array, (byte) => ('00' + byte.toString(16)).slice(-2)).join('');
|
830
858
|
};
|
859
|
+
const identifyAsfFormat = (data) => {
|
860
|
+
// ASF files all start with the same GUID: 3026b2758e66cf11a6d900aa0062ce6c
|
861
|
+
// To distinguish between audio, video, and application ASF, we need to examine
|
862
|
+
// the stream properties in the ASF header
|
863
|
+
try {
|
864
|
+
// Look for stream properties object GUID starting at offset 30
|
865
|
+
// Audio stream properties: b7dc0791a9b711cf8ee600c00c205365
|
866
|
+
// Video stream properties: bc19efc05b4d11cf9b1100aa00bbcb8b
|
867
|
+
if (data.length < 100) {
|
868
|
+
// Not enough data to analyze, default to application
|
869
|
+
return 'application/vnd.ms-asf';
|
870
|
+
}
|
871
|
+
const hex = uint8ArrayToHexString(data);
|
872
|
+
// Look for video stream properties GUID (indicates video content)
|
873
|
+
if (hex.includes('bc19efc05b4d11cf9b1100aa00bbcb8b')) {
|
874
|
+
return 'video/x-ms-asf';
|
875
|
+
}
|
876
|
+
// Look for audio stream properties GUID (indicates audio content)
|
877
|
+
if (hex.includes('b7dc0791a9b711cf8ee600c00c205365')) {
|
878
|
+
return 'audio/x-ms-asf';
|
879
|
+
}
|
880
|
+
// Check for Windows Media Audio/Video codec identifiers
|
881
|
+
// WMA codec: 161 (0xa1) or 162 (0xa2) or 163 (0xa3)
|
882
|
+
// WMV codec: Common values include various Windows Media Video identifiers
|
883
|
+
// Scan through the header for codec information
|
884
|
+
for (let i = 0; i < Math.min(data.length - 4, 1000); i++) {
|
885
|
+
// Look for audio codec indicators
|
886
|
+
if (data[i] === 0xa1 || data[i] === 0xa2 || data[i] === 0xa3) {
|
887
|
+
// Found WMA codec indicator
|
888
|
+
return 'audio/x-ms-asf';
|
889
|
+
}
|
890
|
+
}
|
891
|
+
// Look for common video indicators in the first 1KB
|
892
|
+
const textContent = new TextDecoder('utf-8', { fatal: false }).decode(data.slice(0, Math.min(1000, data.length)));
|
893
|
+
// Check for video-related strings
|
894
|
+
if (textContent.toLowerCase().includes('video') ||
|
895
|
+
textContent.toLowerCase().includes('wmv') ||
|
896
|
+
textContent.toLowerCase().includes('mpeg')) {
|
897
|
+
return 'video/x-ms-asf';
|
898
|
+
}
|
899
|
+
// Check for audio-related strings
|
900
|
+
if (textContent.toLowerCase().includes('audio') ||
|
901
|
+
textContent.toLowerCase().includes('wma') ||
|
902
|
+
textContent.toLowerCase().includes('music')) {
|
903
|
+
return 'audio/x-ms-asf';
|
904
|
+
}
|
905
|
+
// Default to application/vnd.ms-asf if we can't determine the specific type
|
906
|
+
return 'application/vnd.ms-asf';
|
907
|
+
}
|
908
|
+
catch {
|
909
|
+
// If any error occurs during analysis, default to application type
|
910
|
+
return 'application/vnd.ms-asf';
|
911
|
+
}
|
912
|
+
};
|
913
|
+
const identifyHeifFormat = (data) => {
|
914
|
+
// HEIF/HEIC files all start with the same ftyp box signature: 667479706174
|
915
|
+
// To distinguish between formats, we need to examine the brand and compatible brands
|
916
|
+
// in the ftyp (file type) box
|
917
|
+
try {
|
918
|
+
if (data.length < 20) {
|
919
|
+
// Not enough data to analyze, default to HEIF
|
920
|
+
return 'image/heif';
|
921
|
+
}
|
922
|
+
const hex = uint8ArrayToHexString(data);
|
923
|
+
// The ftyp box structure:
|
924
|
+
// Bytes 0-3: Box size (4 bytes)
|
925
|
+
// Bytes 4-7: Box type "ftyp" (4 bytes) - 667479706174
|
926
|
+
// Bytes 8-11: Major brand (4 bytes)
|
927
|
+
// Bytes 12-15: Minor version (4 bytes)
|
928
|
+
// Bytes 16+: Compatible brands (4 bytes each)
|
929
|
+
// Extract major brand (4 bytes starting at offset 8)
|
930
|
+
// Convert to ASCII string for easier comparison
|
931
|
+
const majorBrand = String.fromCharCode(data[8], data[9], data[10], data[11]);
|
932
|
+
// Look for compatible brands in the first 100 bytes
|
933
|
+
const compatibleBrandsHex = hex.substring(32, Math.min(200, hex.length)); // Start after major brand + minor version
|
934
|
+
// HEIC brands: 'heic', 'heix', 'hevc', 'hevx'
|
935
|
+
if (majorBrand === 'heic' ||
|
936
|
+
compatibleBrandsHex.includes('68656963') || // 'heic'
|
937
|
+
compatibleBrandsHex.includes('68656978') || // 'heix'
|
938
|
+
compatibleBrandsHex.includes('68657663') || // 'hevc'
|
939
|
+
compatibleBrandsHex.includes('68657678')) { // 'hevx'
|
940
|
+
// Check for sequence/animation indicators
|
941
|
+
if (compatibleBrandsHex.includes('68657673') || // 'hevs' - HEIC sequence
|
942
|
+
compatibleBrandsHex.includes('6d736631') || // 'msf1' - sequence
|
943
|
+
majorBrand === 'hevs') {
|
944
|
+
return 'image/heic-sequence';
|
945
|
+
}
|
946
|
+
return 'image/heic';
|
947
|
+
}
|
948
|
+
// HEIF brands: 'mif1', 'msf1'
|
949
|
+
if (majorBrand === 'mif1' || majorBrand === 'msf1' ||
|
950
|
+
compatibleBrandsHex.includes('6d696631') || // 'mif1'
|
951
|
+
compatibleBrandsHex.includes('6d736631')) { // 'msf1'
|
952
|
+
// Check for sequence/animation indicators
|
953
|
+
if (majorBrand === 'msf1' ||
|
954
|
+
compatibleBrandsHex.includes('6d736631')) { // 'msf1' - sequence
|
955
|
+
return 'image/heif-sequence';
|
956
|
+
}
|
957
|
+
return 'image/heif';
|
958
|
+
}
|
959
|
+
// Check for specific sequence indicators in the data
|
960
|
+
if (hex.includes('6d736631') || // 'msf1' - multi-image sequence
|
961
|
+
hex.includes('68657673')) { // 'hevs' - HEIC sequence
|
962
|
+
// If we find HEIC-related brands, it's HEIC sequence
|
963
|
+
if (hex.includes('68656963') || hex.includes('68657663')) {
|
964
|
+
return 'image/heic-sequence';
|
965
|
+
}
|
966
|
+
return 'image/heif-sequence';
|
967
|
+
}
|
968
|
+
// If we find HEIC indicators but no sequence, it's single HEIC
|
969
|
+
if (hex.includes('68656963') || // 'heic'
|
970
|
+
hex.includes('68657663') || // 'hevc'
|
971
|
+
hex.includes('68656978') || // 'heix'
|
972
|
+
hex.includes('68657678')) { // 'hevx'
|
973
|
+
return 'image/heic';
|
974
|
+
}
|
975
|
+
// Default to HEIF for any other case
|
976
|
+
return 'image/heif';
|
977
|
+
}
|
978
|
+
catch {
|
979
|
+
// If any error occurs during analysis, default to HEIF
|
980
|
+
return 'image/heif';
|
981
|
+
}
|
982
|
+
};
|
983
|
+
const identifyOggFormat = (data) => {
|
984
|
+
// OGG files all start with "OggS" (4f676753) but can contain different codecs
|
985
|
+
// To distinguish between audio, video, and application OGG, we need to examine
|
986
|
+
// the codec information in the OGG page headers
|
987
|
+
try {
|
988
|
+
if (data.length < 64) {
|
989
|
+
// Not enough data to analyze, default to audio
|
990
|
+
return 'audio/ogg';
|
991
|
+
}
|
992
|
+
const hex = uint8ArrayToHexString(data);
|
993
|
+
// Look for codec identification patterns in the first few hundred bytes
|
994
|
+
// Common video codecs in OGG:
|
995
|
+
// - Theora: "theora" or "\x80theora"
|
996
|
+
// - VP8/VP9: various signatures
|
997
|
+
// - Dirac: "BBCD"
|
998
|
+
// Common audio codecs in OGG:
|
999
|
+
// - Vorbis: "vorbis" or "\x01vorbis"
|
1000
|
+
// - Opus: "OpusHead"
|
1001
|
+
// - FLAC: "fLaC"
|
1002
|
+
// - Speex: "Speex"
|
1003
|
+
// Convert some bytes to text for string matching
|
1004
|
+
const textContent = new TextDecoder('utf-8', { fatal: false }).decode(data.slice(0, Math.min(512, data.length)));
|
1005
|
+
const lowerContent = textContent.toLowerCase();
|
1006
|
+
// Check for video codec indicators first (as they're more specific)
|
1007
|
+
if (lowerContent.includes('theora') ||
|
1008
|
+
hex.includes('8074686f726120') || // "\x80theora "
|
1009
|
+
hex.includes('7468656f7261') || // "theora"
|
1010
|
+
lowerContent.includes('dirac') ||
|
1011
|
+
hex.includes('42424344') || // "BBCD" - Dirac
|
1012
|
+
lowerContent.includes('vp8') ||
|
1013
|
+
lowerContent.includes('vp9')) {
|
1014
|
+
return 'video/ogg';
|
1015
|
+
}
|
1016
|
+
// Check for audio codec indicators
|
1017
|
+
if (lowerContent.includes('vorbis') ||
|
1018
|
+
hex.includes('01766f72626973') || // "\x01vorbis"
|
1019
|
+
hex.includes('766f72626973') || // "vorbis"
|
1020
|
+
lowerContent.includes('opushead') ||
|
1021
|
+
hex.includes('4f7075734865616420') || // "OpusHead "
|
1022
|
+
lowerContent.includes('speex') ||
|
1023
|
+
hex.includes('53706565782020') || // "Speex "
|
1024
|
+
lowerContent.includes('flac') ||
|
1025
|
+
hex.includes('664c6143')) { // "fLaC"
|
1026
|
+
return 'audio/ogg';
|
1027
|
+
}
|
1028
|
+
// Look for OGG stream structure patterns
|
1029
|
+
// OGG pages have a specific structure, look for multiple "OggS" signatures
|
1030
|
+
// which might indicate a complex multimedia container
|
1031
|
+
let oggSCount = 0;
|
1032
|
+
for (let i = 0; i < Math.min(data.length - 4, 1000); i += 4) {
|
1033
|
+
if (data[i] === 0x4f && data[i + 1] === 0x67 &&
|
1034
|
+
data[i + 2] === 0x67 && data[i + 3] === 0x53) {
|
1035
|
+
oggSCount++;
|
1036
|
+
}
|
1037
|
+
}
|
1038
|
+
// Multiple OGG pages might indicate a more complex application format
|
1039
|
+
if (oggSCount > 3) {
|
1040
|
+
// Check if it's likely a multimedia container vs pure audio/video
|
1041
|
+
if (lowerContent.includes('application') ||
|
1042
|
+
lowerContent.includes('metadata') ||
|
1043
|
+
lowerContent.includes('index') ||
|
1044
|
+
(!lowerContent.includes('audio') && !lowerContent.includes('video') &&
|
1045
|
+
!lowerContent.includes('vorbis') && !lowerContent.includes('theora'))) {
|
1046
|
+
return 'application/ogg';
|
1047
|
+
}
|
1048
|
+
}
|
1049
|
+
// Look for file extension hints in metadata (if present)
|
1050
|
+
if (lowerContent.includes('.ogv') || lowerContent.includes('video')) {
|
1051
|
+
return 'video/ogg';
|
1052
|
+
}
|
1053
|
+
if (lowerContent.includes('.oga') || lowerContent.includes('audio') || lowerContent.includes('music')) {
|
1054
|
+
return 'audio/ogg';
|
1055
|
+
}
|
1056
|
+
// Check the OGG page header flags
|
1057
|
+
// Byte 5 in OGG page header contains flags
|
1058
|
+
// If we have enough data, check the stream type
|
1059
|
+
if (data.length > 26) {
|
1060
|
+
const pageHeaderType = data[5];
|
1061
|
+
// Fresh packet start (0x02) often indicates beginning of codec data
|
1062
|
+
if ((pageHeaderType & 0x02) === 0x02) {
|
1063
|
+
// Look at the packet data starting around byte 27
|
1064
|
+
const packetStart = data.slice(27, Math.min(data.length, 50));
|
1065
|
+
const packetHex = uint8ArrayToHexString(packetStart);
|
1066
|
+
// Check for Vorbis identification header
|
1067
|
+
if (packetHex.startsWith('01766f72626973')) {
|
1068
|
+
return 'audio/ogg';
|
1069
|
+
}
|
1070
|
+
// Check for Theora identification header
|
1071
|
+
if (packetHex.startsWith('8074686f726120')) {
|
1072
|
+
return 'video/ogg';
|
1073
|
+
}
|
1074
|
+
}
|
1075
|
+
}
|
1076
|
+
// Default to audio/ogg as it's the most common OGG format
|
1077
|
+
return 'audio/ogg';
|
1078
|
+
}
|
1079
|
+
catch {
|
1080
|
+
// If any error occurs during analysis, default to audio
|
1081
|
+
return 'audio/ogg';
|
1082
|
+
}
|
1083
|
+
};
|
831
1084
|
|
832
1085
|
/**
|
833
1086
|
* @description
|
@@ -957,7 +1210,8 @@ const validateFileMimeType = (file, mimeTypes) => {
|
|
957
1210
|
const reader = new FileReader();
|
958
1211
|
reader.onloadend = () => {
|
959
1212
|
const buffer = reader.result;
|
960
|
-
|
1213
|
+
// Read more bytes to support complex MIME type detection (e.g., ASF format analysis)
|
1214
|
+
const headerBytes = new Uint8Array(buffer).slice(0, Math.min(1024, buffer.byteLength));
|
961
1215
|
const mime = getMimeType(headerBytes);
|
962
1216
|
if (mimeTypes.includes(mime)) {
|
963
1217
|
subscriber.next(null);
|