Skip to content
This repository was archived by the owner on Sep 14, 2023. It is now read-only.
This repository was archived by the owner on Sep 14, 2023. It is now read-only.

Bootstrapping an Atom from localStorage... how to? #295

Description

@gremo

I'm new to React and this library, so my question may be a bit silly.

I'm using React hooks like useState, useReducer and dispatch inside components and using custom helper functions. For a small app like mine, this is overkill.

I need to persist the state into the local storage, but I don't know to do this using this library. Using React state management, I would use a custom hook like this:

import React from 'react';

/**
 * @param {string} storageKey
 * @param {*} initialState
 * @param {number} expiration
 */
export const useStateWithLocalStorage = (storageKey, initialState, expiration) => {
  const [value, setValue] = React.useState(() => {
    const value = localStorage.getItem(storageKey);
    if (null === value || 'undefined' === typeof value) {
      return initialState;
    }

    const expiration = parseInt(localStorage.getItem(`${storageKey}_expire`));
    if (!isNaN(expiration) && Math.floor(Date.now() / 1000) > expiration) {
      localStorage.removeItem(`${storageKey}_expire`);

      return initialState;
    }

    if ('{' === value[0] || '[' === value[0]) {
      return JSON.parse(value);
    }

    return value;
  });

  React.useEffect(() => {
    localStorage.setItem(storageKey, null !== value && 'object' === typeof value ? JSON.stringify(value) : value);

    if (expiration > 0) {
      const existingExpiration = localStorage.getItem(`${storageKey}_expire`);
      if (null === existingExpiration || 'undefined' === typeof existingExpiration) {
        localStorage.setItem(`${storageKey}_expire`, Math.floor(Date.now() / 1000) + expiration);
      }
    }
  }, [storageKey, value, expiration]);

  return [value, setValue];
};

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions