fix: accept emergency export format in Settings backup restore
The Settings "load from file" button only understood its own sun-catering-backup format. Extend it to also read the caterium-full-export format produced by the browser-console emergency export (localStorage + IndexedDB), so an already-downloaded export file can be restored directly through the UI. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
parent
345ee8e052
commit
26681195b0
@ -464,12 +464,35 @@ window.SUN_LEGACY_CATALOG_V175=[{"id":"1","name":"Фуршетный бокс
|
||||
// ---------------- Backup to/from JSON file ----------------
|
||||
function backupFileState(){const storage={};for(let i=0;i<localStorage.length;i++){const key=localStorage.key(i);if(!key||!key.startsWith('sun'))continue;storage[key]=localStorage.getItem(key);}return {format:'sun-catering-backup',version:1,createdAt:new Date().toISOString(),storage};}
|
||||
function downloadBackupFile(){try{const state=backupFileState();const blob=new Blob([JSON.stringify(state)],{type:'application/json'});const url=URL.createObjectURL(blob);const a=document.createElement('a');a.href=url;a.download=`caterium-backup-${new Date().toISOString().slice(0,19).replace(/[:T]/g,'-')}.json`;document.body.appendChild(a);a.click();a.remove();setTimeout(()=>URL.revokeObjectURL(url),2000);toast('Файл резервной копии скачан.','success');}catch(_){toast('Не удалось создать файл резервной копии.','warn')}}
|
||||
function restoreIdbFromExport(indexedDbDump){
|
||||
function openDb(name){return new Promise((resolve,reject)=>{const req=indexedDB.open(name);req.onsuccess=()=>resolve(req.result);req.onerror=()=>reject(req.error);});}
|
||||
function putRecord(store,record){return new Promise((resolve,reject)=>{let req;try{req=store.put(record);}catch(_){const guessKey=record&&(record.id??record.key??record.path);try{req=store.put(record,guessKey);}catch(e2){reject(e2);return;}}req.onsuccess=()=>resolve();req.onerror=()=>reject(req.error);});}
|
||||
return (async()=>{
|
||||
for(const [dbName,stores] of Object.entries(indexedDbDump||{})){
|
||||
let db;try{db=await openDb(dbName);}catch(_){continue;}
|
||||
for(const [storeName,records] of Object.entries(stores||{})){
|
||||
if(!db.objectStoreNames.contains(storeName))continue;
|
||||
const tx=db.transaction(storeName,'readwrite'),store=tx.objectStore(storeName);
|
||||
for(const record of (records||[])){try{await putRecord(store,record);}catch(_){}}
|
||||
await new Promise(resolve=>{tx.oncomplete=resolve;tx.onerror=resolve;});
|
||||
}
|
||||
db.close();
|
||||
}
|
||||
})();
|
||||
}
|
||||
async function restoreBackupFile(file){
|
||||
let state;
|
||||
try{state=JSON.parse(await file.text());}catch(_){toast('Не удалось прочитать файл — это не JSON.','warn');return;}
|
||||
if(!state||state.format!=='sun-catering-backup'||!state.storage||typeof state.storage!=='object'){toast('Неверный формат файла резервной копии.','warn');return;}
|
||||
const isSettingsFormat=state&&state.format==='sun-catering-backup'&&state.storage&&typeof state.storage==='object';
|
||||
const isFullExport=state&&state.format==='caterium-full-export'&&state.localStorage&&typeof state.localStorage==='object';
|
||||
if(!isSettingsFormat&&!isFullExport){toast('Неверный формат файла резервной копии.','warn');return;}
|
||||
if(!confirm('Загрузить базу из файла? Текущие локальные данные будут заменены содержимым файла.'))return;
|
||||
if(isSettingsFormat){
|
||||
Object.entries(state.storage).forEach(([key,value])=>{if(key.startsWith('sun')){try{localStorage.setItem(key,String(value));}catch(_){}}});
|
||||
}else{
|
||||
Object.entries(state.localStorage).forEach(([key,value])=>{if(key.startsWith('sun')){try{localStorage.setItem(key,String(value));}catch(_){}}});
|
||||
await restoreIdbFromExport(state.indexedDB);
|
||||
}
|
||||
toast('База восстановлена из файла. Перезагрузка…','success');
|
||||
setTimeout(()=>location.reload(),600);
|
||||
}
|
||||
|
||||
Loading…
Reference in New Issue
Block a user