implement sessionAtom function (same api as persistenAtom, just used sessionStorage instead of localStorage)

This commit is contained in:
Kaspars 2024-05-07 11:40:09 +02:00
parent b69b9c37cd
commit 6249631a72

View file

@ -1,5 +1,5 @@
import { atom } from 'nanostores'; import {atom, onMount} from 'nanostores';
import { persistentAtom, setPersistentEngine, windowPersistentEvents } from '@nanostores/persistent'; import { persistentAtom, windowPersistentEvents } from '@nanostores/persistent';
import { useStore } from '@nanostores/react'; import { useStore } from '@nanostores/react';
import { logger } from '@strudel/core'; import { logger } from '@strudel/core';
import { nanoid } from 'nanoid'; import { nanoid } from 'nanoid';
@ -21,14 +21,58 @@ export const patternFilterName = {
user: 'user', user: 'user',
}; };
export let sessionAtom = persistentAtom;
if (typeof sessionStorage !== 'undefined') { if (typeof sessionStorage !== 'undefined') {
// NB: this switches storageEngine of all persistent atoms const identity = a => a;
// ideally we would switch the engine per atom const eventsEngine = windowPersistentEvents;
// (like in this abandoned pr: https://github.com/nanostores/persistent/pull/30) sessionAtom = (name, initial = undefined, opts = {}) => {
setPersistentEngine(sessionStorage, windowPersistentEvents); let encode = opts.encode || identity
let decode = opts.decode || identity
let store = atom(initial)
let set = store.set
store.set = newValue => {
if (typeof newValue === 'undefined') {
delete sessionStorage[name]
} else {
sessionStorage[name] = encode(newValue)
}
set(newValue)
} }
export let $viewingPatternData = persistentAtom( function listener(e) {
if (e.key === name) {
if (e.newValue === null) {
set(undefined)
} else {
set(decode(e.newValue))
}
} else if (!sessionStorage[name]) {
set(undefined)
}
}
function restore() {
store.set(sessionStorage[name] ? decode(sessionStorage[name]) : initial)
}
onMount(store, () => {
restore()
if (opts.listen !== false) {
eventsEngine.addEventListener(name, listener, restore)
return () => {
eventsEngine.removeEventListener(name, listener, restore)
}
}
})
return store
}
}
export let $viewingPatternData = sessionAtom(
'viewingPatternData', 'viewingPatternData',
{ {
id: '', id: '',
@ -75,7 +119,7 @@ export async function loadDBPatterns() {
} }
// reason: https://github.com/tidalcycles/strudel/issues/857 // reason: https://github.com/tidalcycles/strudel/issues/857
const $activePattern = persistentAtom('activePattern', '', { listen: false }); const $activePattern = sessionAtom('activePattern', '', { listen: false });
export function setActivePattern(key) { export function setActivePattern(key) {
$activePattern.set(key); $activePattern.set(key);