From 87c79dfdd34c69a7475bf7b271aae030a7fa1a04 Mon Sep 17 00:00:00 2001 From: Avinash Kumar Deepak Date: Sun, 15 Feb 2026 12:02:51 +0530 Subject: [PATCH 1/2] fix: handle localStorage errors in private browsing --- src/component/fileBrowser.jsx | 13 ++++- src/graph-builder/local-storage-manager.js | 68 ++++++++++++++++------ 2 files changed, 62 insertions(+), 19 deletions(-) diff --git a/src/component/fileBrowser.jsx b/src/component/fileBrowser.jsx index 7bf145f..5b80004 100644 --- a/src/component/fileBrowser.jsx +++ b/src/component/fileBrowser.jsx @@ -5,6 +5,7 @@ /* eslint-disable react/state-in-constructor */ import React, { useEffect, useState } from 'react'; import FileBrowser, { FileRenderers, FolderRenderers } from 'react-keyed-file-browser'; +import { toast } from 'react-toastify'; import { readFile, readTextFile } from '../toolbarActions/toolbarFunctions'; import { actionType as T } from '../reducer'; import ConfirmModal from './modals/ConfirmModal'; @@ -33,7 +34,11 @@ const LocalFileBrowser = ({ superState, dispatcher }) => { // const allFiles = window.localStorage.getItem('fileList'); // setFileState({ files: allFiles }); // } - window.localStorage.setItem('fileList', JSON.stringify(fileState)); + try { + window.localStorage.setItem('fileList', JSON.stringify(fileState)); + } catch (e) { + toast.error(e.message); + } }, [fileState]); useEffect(() => { @@ -235,7 +240,11 @@ const LocalFileBrowser = ({ superState, dispatcher }) => { })); setFileState(filesArray); - window.localStorage.setItem('fileList', JSON.stringify(filesArray)); + try { + window.localStorage.setItem('fileList', JSON.stringify(filesArray)); + } catch (e) { + toast.error(e.message); + } if (filesArray.length > 0) { dispatcher({ type: T.SET_DIR_NAME, payload: filesArray[0].key.split('/')[0] }); dispatcher({ type: T.SET_FILE_STATE, payload: filesArray }); diff --git a/src/graph-builder/local-storage-manager.js b/src/graph-builder/local-storage-manager.js index fb21593..2fbc329 100644 --- a/src/graph-builder/local-storage-manager.js +++ b/src/graph-builder/local-storage-manager.js @@ -1,8 +1,37 @@ +import { toast } from 'react-toastify'; + +const lsGet = (key) => { + try { + return window.localStorage.getItem(key); + } catch (e) { + toast.error(e.message); + return null; + } +}; + +const lsSet = (key, value) => { + try { + window.localStorage.setItem(key, value); + } catch (e) { + toast.error(e.message); + } +}; + +const lsRemove = (key) => { + try { + window.localStorage.removeItem(key); + } catch (e) { + toast.error(e.message); + } +}; + const getSet = (ALL_GRAPHS) => { - if (!window.localStorage.getItem(ALL_GRAPHS)) { - window.localStorage.setItem(ALL_GRAPHS, window.btoa(JSON.stringify([]))); + if (!lsGet(ALL_GRAPHS)) { + lsSet(ALL_GRAPHS, window.btoa(JSON.stringify([]))); } - return new Set(JSON.parse(window.atob(window.localStorage.getItem(ALL_GRAPHS)))); + const raw = lsGet(ALL_GRAPHS); + if (!raw) return new Set(); + return new Set(JSON.parse(window.atob(raw))); }; const localStorageManager = { @@ -12,27 +41,28 @@ const localStorageManager = { allgs: getSet(window.btoa('ALL_GRAPHS')), saveAllgs() { - window.localStorage.setItem(this.ALL_GRAPHS, window.btoa(JSON.stringify(Array.from(this.allgs)))); + lsSet(this.ALL_GRAPHS, window.btoa(JSON.stringify(Array.from(this.allgs)))); }, addEmptyIfNot() { - if (!window.localStorage.getItem(this.ALL_GRAPHS)) { - window.localStorage.setItem(this.ALL_GRAPHS, window.btoa(JSON.stringify([]))); + if (!lsGet(this.ALL_GRAPHS)) { + lsSet(this.ALL_GRAPHS, window.btoa(JSON.stringify([]))); } }, get(id) { - if (window.localStorage.getItem(id) === null) return null; - return JSON.parse(window.atob(window.localStorage.getItem(id))); + const raw = lsGet(id); + if (raw === null) return null; + return JSON.parse(window.atob(raw)); }, save(id, graphContent) { this.addGraph(id); const serializedJson = JSON.stringify(graphContent); - window.localStorage.setItem(id, window.btoa(serializedJson)); + lsSet(id, window.btoa(serializedJson)); }, remove(id) { if (this.allgs.delete(id)) this.saveAllgs(); - localStorage.removeItem(id); + lsRemove(id); }, addGraph(id) { if (this.allgs.has(id)) return; @@ -40,26 +70,30 @@ const localStorageManager = { this.saveAllgs(); }, getAllGraphs() { - return JSON.parse(window.atob(window.localStorage.getItem(this.ALL_GRAPHS))); + const raw = lsGet(this.ALL_GRAPHS); + if (!raw) return []; + return JSON.parse(window.atob(raw)); }, addToFront(id) { if (this.allgs.has(id)) return; this.allgs.add(id); - const Garr = JSON.parse(window.atob(window.localStorage.getItem(this.ALL_GRAPHS))); + const raw = lsGet(this.ALL_GRAPHS); + if (!raw) return; + const Garr = JSON.parse(window.atob(raw)); Garr.unshift(id); - window.localStorage.setItem(this.ALL_GRAPHS, window.btoa(JSON.stringify(Garr))); + lsSet(this.ALL_GRAPHS, window.btoa(JSON.stringify(Garr))); }, getAuthorName() { - return localStorage.getItem(this.AUTHOR_NAME) || ''; + return lsGet(this.AUTHOR_NAME) || ''; }, setAuthorName(authorName) { - localStorage.setItem(this.AUTHOR_NAME, authorName); + lsSet(this.AUTHOR_NAME, authorName); }, clearGraph(id) { - window.localStorage.removeItem(id); + lsRemove(id); }, getFileList() { - return localStorage.getItem('fileList') || ''; + return lsGet('fileList') || ''; }, }; export default localStorageManager; From 7445a6db7bc669abb9965d3c2a9c5273900de98f Mon Sep 17 00:00:00 2001 From: Avinash Kumar Deepak Date: Wed, 18 Feb 2026 22:13:00 +0530 Subject: [PATCH 2/2] refactor: rename ls* helpers to localStorageGet/Set/Remove for readability --- src/graph-builder/local-storage-manager.js | 38 +++++++++++----------- 1 file changed, 19 insertions(+), 19 deletions(-) diff --git a/src/graph-builder/local-storage-manager.js b/src/graph-builder/local-storage-manager.js index 2fbc329..1b4a93f 100644 --- a/src/graph-builder/local-storage-manager.js +++ b/src/graph-builder/local-storage-manager.js @@ -1,6 +1,6 @@ import { toast } from 'react-toastify'; -const lsGet = (key) => { +const localStorageGet = (key) => { try { return window.localStorage.getItem(key); } catch (e) { @@ -9,7 +9,7 @@ const lsGet = (key) => { } }; -const lsSet = (key, value) => { +const localStorageSet = (key, value) => { try { window.localStorage.setItem(key, value); } catch (e) { @@ -17,7 +17,7 @@ const lsSet = (key, value) => { } }; -const lsRemove = (key) => { +const localStorageRemove = (key) => { try { window.localStorage.removeItem(key); } catch (e) { @@ -26,10 +26,10 @@ const lsRemove = (key) => { }; const getSet = (ALL_GRAPHS) => { - if (!lsGet(ALL_GRAPHS)) { - lsSet(ALL_GRAPHS, window.btoa(JSON.stringify([]))); + if (!localStorageGet(ALL_GRAPHS)) { + localStorageSet(ALL_GRAPHS, window.btoa(JSON.stringify([]))); } - const raw = lsGet(ALL_GRAPHS); + const raw = localStorageGet(ALL_GRAPHS); if (!raw) return new Set(); return new Set(JSON.parse(window.atob(raw))); }; @@ -41,28 +41,28 @@ const localStorageManager = { allgs: getSet(window.btoa('ALL_GRAPHS')), saveAllgs() { - lsSet(this.ALL_GRAPHS, window.btoa(JSON.stringify(Array.from(this.allgs)))); + localStorageSet(this.ALL_GRAPHS, window.btoa(JSON.stringify(Array.from(this.allgs)))); }, addEmptyIfNot() { - if (!lsGet(this.ALL_GRAPHS)) { - lsSet(this.ALL_GRAPHS, window.btoa(JSON.stringify([]))); + if (!localStorageGet(this.ALL_GRAPHS)) { + localStorageSet(this.ALL_GRAPHS, window.btoa(JSON.stringify([]))); } }, get(id) { - const raw = lsGet(id); + const raw = localStorageGet(id); if (raw === null) return null; return JSON.parse(window.atob(raw)); }, save(id, graphContent) { this.addGraph(id); const serializedJson = JSON.stringify(graphContent); - lsSet(id, window.btoa(serializedJson)); + localStorageSet(id, window.btoa(serializedJson)); }, remove(id) { if (this.allgs.delete(id)) this.saveAllgs(); - lsRemove(id); + localStorageRemove(id); }, addGraph(id) { if (this.allgs.has(id)) return; @@ -70,30 +70,30 @@ const localStorageManager = { this.saveAllgs(); }, getAllGraphs() { - const raw = lsGet(this.ALL_GRAPHS); + const raw = localStorageGet(this.ALL_GRAPHS); if (!raw) return []; return JSON.parse(window.atob(raw)); }, addToFront(id) { if (this.allgs.has(id)) return; this.allgs.add(id); - const raw = lsGet(this.ALL_GRAPHS); + const raw = localStorageGet(this.ALL_GRAPHS); if (!raw) return; const Garr = JSON.parse(window.atob(raw)); Garr.unshift(id); - lsSet(this.ALL_GRAPHS, window.btoa(JSON.stringify(Garr))); + localStorageSet(this.ALL_GRAPHS, window.btoa(JSON.stringify(Garr))); }, getAuthorName() { - return lsGet(this.AUTHOR_NAME) || ''; + return localStorageGet(this.AUTHOR_NAME) || ''; }, setAuthorName(authorName) { - lsSet(this.AUTHOR_NAME, authorName); + localStorageSet(this.AUTHOR_NAME, authorName); }, clearGraph(id) { - lsRemove(id); + localStorageRemove(id); }, getFileList() { - return lsGet('fileList') || ''; + return localStorageGet('fileList') || ''; }, }; export default localStorageManager;