cve fixes
This commit is contained in:
@@ -3,6 +3,7 @@ import JSZip from "jszip";
|
||||
import { INITIAL_DATA } from "../constants/index.js";
|
||||
import { STANDAARD_THEMA } from "../constants/themas.js";
|
||||
import { migrateData, loadFromStorage, saveToStorage } from "../utils/storage.js";
|
||||
import { bouwHtmlExport, leesHtmlBackup } from "../utils/htmlExport.js";
|
||||
import { useTheme } from "../hooks/useTheme.js";
|
||||
|
||||
const AppContext = createContext(null);
|
||||
@@ -168,17 +169,43 @@ export function AppProvider({ children }) {
|
||||
if (saveTimer.current) clearTimeout(saveTimer.current);
|
||||
};
|
||||
|
||||
// ── Backup / restore ──────────────────────────────────────────
|
||||
// ── Backup / restore / export ─────────────────────────────────
|
||||
const downloadZip = async (zip, bestandsnaam) => {
|
||||
const blob = await zip.generateAsync({ type: "blob", compression: "DEFLATE" });
|
||||
const url = URL.createObjectURL(blob);
|
||||
const a = document.createElement("a");
|
||||
a.href = url;
|
||||
a.download = bestandsnaam;
|
||||
a.click();
|
||||
URL.revokeObjectURL(url);
|
||||
};
|
||||
|
||||
const doBackup = async () => {
|
||||
const zip = new JSZip();
|
||||
const datum = new Date().toISOString().slice(0, 10);
|
||||
zip.file("data.json", JSON.stringify({ ...data, evVoortgang: evRows, evVoortgangHistory }, null, 2));
|
||||
zip.file("meta.json", JSON.stringify({ versie: 1, datum, app: "vibefinance", gebruiker: currentUser?.email }, null, 2));
|
||||
const blob = await zip.generateAsync({ type: "blob", compression: "DEFLATE" });
|
||||
await downloadZip(zip, `vibefinance_backup_${datum}.zip`);
|
||||
};
|
||||
|
||||
/**
|
||||
* Export naar één zelfdragende HTML-pagina: leesbaar zonder de app, en met de
|
||||
* ruwe data ingebakken zodat `doRestore` hem ook weer terug kan zetten.
|
||||
*/
|
||||
const doExport = () => {
|
||||
const datum = new Date().toISOString().slice(0, 10);
|
||||
const html = bouwHtmlExport({
|
||||
cats, schuldBlokken, evRows, evVoortgangHistory, schuldHistory,
|
||||
totEV, totSchuld, doel: ev?.doel || 0,
|
||||
initieleSchuld: schuld?.initieleSchuld || 0,
|
||||
gebruiker: currentUser?.email || "",
|
||||
ruweData: { ...data, evVoortgang: evRows, evVoortgangHistory },
|
||||
});
|
||||
const blob = new Blob([html], { type: "text/html;charset=utf-8" });
|
||||
const url = URL.createObjectURL(blob);
|
||||
const a = document.createElement("a");
|
||||
a.href = url;
|
||||
a.download = `vibefinance_backup_${datum}.zip`;
|
||||
a.download = `vibefinance_${datum}.html`;
|
||||
a.click();
|
||||
URL.revokeObjectURL(url);
|
||||
};
|
||||
@@ -186,15 +213,25 @@ export function AppProvider({ children }) {
|
||||
const doRestore = () => {
|
||||
const input = document.createElement("input");
|
||||
input.type = "file";
|
||||
input.accept = ".zip";
|
||||
input.accept = ".zip,.html";
|
||||
input.onchange = async (e) => {
|
||||
const file = e.target.files[0];
|
||||
if (!file) return;
|
||||
try {
|
||||
const zip = await JSZip.loadAsync(file);
|
||||
const entry = zip.file("data.json");
|
||||
if (!entry) throw new Error("Geen data.json gevonden in backup.");
|
||||
const parsed = JSON.parse(await entry.async("string"));
|
||||
// Twee soorten bestanden met dezelfde inhoud: de backup-ZIP met
|
||||
// `data.json`, en de geëxporteerde HTML-pagina met hetzelfde JSON in
|
||||
// een script-blok. Zonder dit tweede pad is de belofte onderaan die
|
||||
// pagina — "hiermee kun je herstellen" — niet waar te maken.
|
||||
let parsed;
|
||||
if (file.name.toLowerCase().endsWith(".html")) {
|
||||
parsed = leesHtmlBackup(await file.text());
|
||||
if (!parsed) throw new Error("Deze HTML-pagina bevat geen VibeFinance-gegevens.");
|
||||
} else {
|
||||
const zip = await JSZip.loadAsync(file);
|
||||
const entry = zip.file("data.json");
|
||||
if (!entry) throw new Error("Geen data.json gevonden in backup.");
|
||||
parsed = JSON.parse(await entry.async("string"));
|
||||
}
|
||||
const migrated = migrateData({ eigenVermogen: parsed.eigenVermogen, schuld: parsed.schuld });
|
||||
const newEvRows = parsed.evVoortgang || [];
|
||||
const newEvVH = parsed.evVoortgangHistory || [];
|
||||
@@ -229,7 +266,7 @@ export function AppProvider({ children }) {
|
||||
evRows, setEvRows,
|
||||
evVoortgangHistory, setEvVoortgangHistory,
|
||||
users, setUsers,
|
||||
doBackup, doRestore,
|
||||
doBackup, doRestore, doExport,
|
||||
}}>
|
||||
{children}
|
||||
</AppContext.Provider>
|
||||
|
||||
Reference in New Issue
Block a user