@memori.ai/memori-react
Version:
[](https://www.npmjs.com/package/@memori.ai/memori-react)  ;
const tslib_1 = require("tslib");
const jsx_runtime_1 = require("react/jsx-runtime");
const react_1 = tslib_1.__importStar(require("react"));
const classnames_1 = tslib_1.__importDefault(require("classnames"));
const Spin_1 = tslib_1.__importDefault(require("../../ui/Spin"));
const Document_1 = require("../../icons/Document");
const Modal_1 = tslib_1.__importDefault(require("../../ui/Modal"));
const constants_1 = require("../../../helpers/constants");
const PDF_JS_VERSION = '3.11.174';
const WORKER_URL = `https://cdnjs.cloudflare.com/ajax/libs/pdf.js/${PDF_JS_VERSION}/pdf.worker.min.js`;
const PDF_JS_URL = `https://cdnjs.cloudflare.com/ajax/libs/pdf.js/${PDF_JS_VERSION}/pdf.min.js`;
const XLSX_URL = 'https://cdn.sheetjs.com/xlsx-0.20.0/package/dist/xlsx.full.min.js';
const UploadDocuments = ({ setDocumentPreviewFiles, maxDocuments, documentPreviewFiles, onLoadingChange, onDocumentError, onValidateFile, onValidatePayloadSize, }) => {
const [isLoading, setIsLoading] = (0, react_1.useState)(false);
const [selectedFile, setSelectedFile] = (0, react_1.useState)(null);
const documentInputRef = (0, react_1.useRef)(null);
(0, react_1.useEffect)(() => {
if (onLoadingChange) {
onLoadingChange(isLoading);
}
}, [isLoading, onLoadingChange]);
const validateDocumentFile = (file) => {
if (onValidateFile) {
return onValidateFile(file);
}
return true;
};
const validatePayloadSize = (newDocuments) => {
if (onValidatePayloadSize) {
return onValidatePayloadSize(newDocuments);
}
return true;
};
const extractTextFromPDF = async (file) => {
console.log('Extracting text from PDF:', file.name);
try {
if (!window.pdfjsLib) {
console.log('Loading PDF.js library...');
await new Promise((resolve, reject) => {
const script = document.createElement('script');
script.src = PDF_JS_URL;
script.onload = () => {
window.pdfjsLib.GlobalWorkerOptions.workerSrc = WORKER_URL;
console.log('PDF.js loaded successfully');
resolve(true);
};
script.onerror = reject;
document.head.appendChild(script);
});
}
const arrayBuffer = await file.arrayBuffer();
const pdf = await window.pdfjsLib.getDocument({ data: arrayBuffer }).promise;
console.log('PDF loaded, pages:', pdf.numPages);
let text = '';
for (let i = 1; i <= pdf.numPages; i++) {
console.log('Processing page', i);
const page = await pdf.getPage(i);
const content = await page.getTextContent();
const pageText = content.items
.filter((item) => item.str && typeof item.str === 'string')
.map((item) => item.str)
.join(' ');
text += pageText + '\n';
}
console.log('PDF text extraction complete');
return text;
}
catch (error) {
console.error('PDF extraction failed:', error);
throw new Error(`PDF extraction failed: ${error instanceof Error ? error.message : 'Unknown error'}`);
}
};
const extractTextFromXLSX = async (file) => {
console.log('Extracting text from XLSX:', file.name);
try {
if (!window.XLSX) {
console.log('Loading XLSX library...');
await new Promise((resolve, reject) => {
const script = document.createElement('script');
script.src = XLSX_URL;
script.onload = resolve;
script.onerror = reject;
document.head.appendChild(script);
});
console.log('XLSX library loaded successfully');
}
const arrayBuffer = await file.arrayBuffer();
const workbook = window.XLSX.read(arrayBuffer, {
type: 'array',
cellFormula: true,
cellNF: true,
cellText: true,
cellDates: true,
});
console.log('XLSX workbook loaded, sheets:', workbook.SheetNames);
let text = '';
for (const sheetName of workbook.SheetNames) {
console.log('Processing sheet:', sheetName);
const worksheet = workbook.Sheets[sheetName];
const data = window.XLSX.utils.sheet_to_json(worksheet, { header: 1, raw: false });
const colWidths = data.reduce((widths, row) => {
row.forEach((cell, i) => {
const cellWidth = (cell || '').toString().length;
widths[i] = Math.max(widths[i] || 0, cellWidth);
});
return widths;
}, []);
const formattedText = data.map((row) => {
return row
.map((cell, i) => {
const cellStr = (cell || '').toString();
return cellStr.padEnd(colWidths[i] + 2);
})
.join('|')
.trim();
});
if (formattedText.length > 0) {
const separator = colWidths
.map((w) => '-'.repeat(w + 2))
.join('+');
formattedText.splice(1, 0, separator);
}
text += `Sheet: ${sheetName}\n${formattedText.join('\n')}\n\n`;
}
console.log('XLSX text extraction complete');
return text;
}
catch (error) {
console.error('XLSX extraction failed:', error);
throw new Error(`XLSX extraction failed: ${error instanceof Error ? error.message : 'Unknown error'}`);
}
};
const processDocumentFile = async (file) => {
var _a;
console.log('Processing document file:', file.name);
const fileExt = ((_a = file.name.split('.').pop()) === null || _a === void 0 ? void 0 : _a.toLowerCase()) || '';
try {
let text = null;
if (fileExt === 'pdf') {
text = await extractTextFromPDF(file);
}
else if (['txt', 'md', 'json', 'csv'].includes(fileExt)) {
text = await file.text();
}
else if (fileExt === 'xlsx') {
text = await extractTextFromXLSX(file);
}
if (text && text.length > constants_1.MAX_DOCUMENT_CONTENT_LENGTH) {
console.warn('Document content exceeds length limit:', text.length, '>', constants_1.MAX_DOCUMENT_CONTENT_LENGTH);
onDocumentError === null || onDocumentError === void 0 ? void 0 : onDocumentError({
message: `File "${file.name}" content exceeds ${constants_1.MAX_DOCUMENT_CONTENT_LENGTH} characters and was truncated`,
severity: 'warning',
});
text = text.substring(0, constants_1.MAX_DOCUMENT_CONTENT_LENGTH) + "\n\n[Content truncated due to size limits]";
}
console.log('Document processing complete');
return text;
}
catch (error) {
console.error('Document processing failed:', error);
throw new Error(`Failed to process "${file.name}": ${error instanceof Error ? error.message : 'Unknown error'}`);
}
};
const handleDocumentUpload = async (e) => {
console.log('Document upload started');
const files = Array.from(e.target.files || []);
if (files.length === 0)
return;
setIsLoading(true);
const processedFiles = [];
for (const file of files) {
console.log('Processing file:', file.name);
if (!validateDocumentFile(file)) {
continue;
}
const fileId = Math.random().toString(36).substr(2, 9);
try {
const text = await processDocumentFile(file);
if (text) {
processedFiles.push({
name: file.name,
id: fileId,
content: text,
mimeType: file.type,
});
}
}
catch (error) {
console.error('File processing error:', error);
onDocumentError === null || onDocumentError === void 0 ? void 0 : onDocumentError({
message: `${error instanceof Error ? error.message : 'Unknown error'}`,
severity: 'error',
});
}
}
if (processedFiles.length > 0) {
console.log('Successfully processed files:', processedFiles.length);
if (!validatePayloadSize(processedFiles)) {
setIsLoading(false);
if (documentInputRef.current) {
documentInputRef.current.value = '';
}
return;
}
const existingDocuments = documentPreviewFiles.filter((file) => file.type === 'document');
const existingImages = documentPreviewFiles.filter((file) => file.type === 'image');
console.log('existingDocuments', existingDocuments);
console.log('processedFiles', processedFiles);
console.log('existingImages', existingImages);
setDocumentPreviewFiles([
...existingDocuments,
...processedFiles.map(file => ({
...file,
type: 'document'
})),
]);
}
console.log('Document upload complete');
setIsLoading(false);
if (documentInputRef.current) {
documentInputRef.current.value = '';
}
};
return ((0, jsx_runtime_1.jsxs)("div", { className: "memori--document-upload-wrapper", children: [(0, jsx_runtime_1.jsx)("input", { ref: documentInputRef, type: "file", accept: ".pdf,.txt,.md,.json,.xlsx,.csv", className: "memori--upload-file-input", onChange: handleDocumentUpload }), (0, jsx_runtime_1.jsx)("button", { className: (0, classnames_1.default)('memori-button', 'memori-button--circle', 'memori-button--icon-only', 'memori-share-button--button', 'memori--conversation-button', 'memori--document-upload-button', { 'memori--error': false }), onClick: () => { var _a; return (_a = documentInputRef.current) === null || _a === void 0 ? void 0 : _a.click(); }, disabled: isLoading || (maxDocuments && documentPreviewFiles.filter((file) => file.type !== 'image').length >= maxDocuments) || false, title: "Upload documents", children: isLoading ? ((0, jsx_runtime_1.jsx)(Spin_1.default, { spinning: true, className: "memori--upload-icon" })) : ((0, jsx_runtime_1.jsx)(react_1.default.Fragment, { children: (0, jsx_runtime_1.jsx)(Document_1.DocumentIcon, { className: "memori--upload-icon" }) })) }), (0, jsx_runtime_1.jsx)(Modal_1.default, { width: "80%", widthMd: "80%", open: !!selectedFile, className: "memori--modal-preview-file", onClose: () => setSelectedFile(null), closable: true, title: selectedFile === null || selectedFile === void 0 ? void 0 : selectedFile.name, children: (0, jsx_runtime_1.jsx)("div", { className: "memori--preview-content", style: {
maxHeight: '70vh',
overflowY: 'auto',
textAlign: 'center',
whiteSpace: 'pre-wrap'
}, children: selectedFile === null || selectedFile === void 0 ? void 0 : selectedFile.content }) })] }));
};
exports.default = UploadDocuments;
//# sourceMappingURL=UploadDocuments.js.map