import React, { useRef, useState, useEffect } from "react"; import { Box, Label, Text, Button, Flex } from "theme-ui"; import { saveAs } from "file-saver"; import * as Comlink from "comlink"; import Modal from "../components/Modal"; import LoadingOverlay from "../components/LoadingOverlay"; import LoadingBar from "../components/LoadingBar"; import Banner from "../components/Banner"; import DatabaseWorker from "worker-loader!../workers/DatabaseWorker"; // eslint-disable-line import/no-webpack-loader-syntax const worker = Comlink.wrap(new DatabaseWorker()); function ImportExportModal({ isOpen, onRequestClose }) { const [isLoading, setIsLoading] = useState(false); const [error, setError] = useState(); const backgroundTaskRunningRef = useRef(false); const fileInputRef = useRef(); function openFileDialog() { if (fileInputRef.current) { fileInputRef.current.click(); } } const loadingProgressRef = useRef(0); function handleDBProgress({ completedRows, totalRows }) { loadingProgressRef.current = completedRows / totalRows; } async function handleImportDatabase(file) { setIsLoading(true); backgroundTaskRunningRef.current = true; try { await worker.importData(file, Comlink.proxy(handleDBProgress)); setIsLoading(false); backgroundTaskRunningRef.current = false; window.location.reload(); } catch (e) { setIsLoading(false); backgroundTaskRunningRef.current = false; if (e.message.startsWith("Max buffer length exceeded")) { setError( new Error( "Max image size exceeded ensure your database doesn't have an image over 100MB" ) ); } else { setError(e); } } } async function handleExportDatabase() { setIsLoading(true); backgroundTaskRunningRef.current = true; try { const blob = await worker.exportData(Comlink.proxy(handleDBProgress)); saveAs(blob, `${new Date().toISOString()}.owlbear`); } catch (e) { setError(e); } setIsLoading(false); backgroundTaskRunningRef.current = false; } useEffect(() => { function handleBeforeUnload(event) { if (backgroundTaskRunningRef.current) { event.returnValue = "Database is still processing, are you sure you want to leave?"; } } window.addEventListener("beforeunload", handleBeforeUnload); return () => { window.removeEventListener("beforeunload", handleBeforeUnload); }; }, []); function handleClose() { if (isLoading) { return; } onRequestClose(); } return ( Importing a database will overwrite your current data. handleImportDatabase(event.target.files[0])} type="file" accept=".owlbear" style={{ display: "none" }} ref={fileInputRef} /> {isLoading && ( )} setError()}> Error: {error && error.message} ); } export default ImportExportModal;