# Persistence

ActiveJS [Units](/activejs/fundamentals/units.md) can be made persistent by setting a configuration flag to `true`. By default, persistent Units use [`localStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/localStorage) for the persistence. You can change it to any storage API that implements [`Storage`](https://developer.mozilla.org/en-US/docs/Web/API/Storage) interface. e.g.: [`sessionStorage`](https://developer.mozilla.org/en-US/docs/Web/API/Window/sessionStorage)

## Creating a persistent Unit

All that it takes to make a Unit persistent is a flag, and a unique `id`. The `id` is required to identify the Unit and its stored value.

```typescript
// this will throw an error, id is required
const preferencesUnit = new DictUnit({persistent: true});

// this will work
const preferencesUnit = new DictUnit({id: 'preferences', persistent: true});


// update Unit's value
preferencesUnit.set('side', 'dark');
// value in the LocalStorage would become {"side": "dark"}

// refresh the browser window

// check value
console.log(preferencesUnit.value()) // logs {"side": "dark"}
```

Voila! we're done. No manual saving, no manual retrieving.

## Initial value vs persisted value

When you provide an initial value to a persistent Unit, at first instance it gets saved to the persistent storage immediately, but when you refresh the browser window or open a new one, on the second instance the stored value takes precedence over the provided initial value.

```typescript
const preferencesUnit = new DictUnit({
    id: 'preferences', 
    persistent: true,
    initialValue: {earth: 'flat'}
});
// value in the LocalStorage would become {"earth": "flat"}

// set a new preference, which dispatches and saves a new value
preferencesUnit.set('earth', 'oblate ellipsoid');
// now LocalStorage has {"earth": "oblate ellipsoid"}

// now, refresh the browser window

// check value
console.log(preferencesUnit.value()) // logs {"earth": "oblate ellipsoid"}
// the initial value gets ignored
```

## Clearing the persisted value

Persisted value can be cleared in two ways, per Unit, or every Unit in a Storage instance.

* To clear the persisted value of a Unit, you can use `Unit.clearPersistedValue()`
* To clear all Units' persisted values from the default storage, you can use the global function `clearPersistentStorage()`.
* If you want to clear a particular storage you can pass it to the `clearPersistentStorage()` function.\
  **e.g**. `clearPersistentStorage(window.sessionStorage)`&#x20;

```typescript
// taking the Unit from above example, and starting from where we left
console.log(preferencesUnit.value()) // logs {"earth": "oblate ellipsoid"}

// clear the persisted value
preferencesUnit.clearPersistedValue();
// or clearPersistentStorage()
// or clearPersistentStorage(localStorage)

// check value
console.log(preferencesUnit.value()) // logs {"earth": "oblate ellipsoid"}
// because only the persisted value is removed, the Unit's value stays intact

// now, refresh the browser window

// check value
console.log(preferencesUnit.value()) // logs {"earth": "flat"}
// the initial value is used, because we cleared the persisted value
```

## Changing the persistence storage

All Units use the `localStorage` for persistence by default, but it can be changed to `sessionStorage` as well, and you can either change it globally or for a specific Unit.

### Changing storage for one Unit

```typescript
const unit = new DictUnit({
    id: 'session-token', 
    persistent: true, 
    
    // this is how we can change the storage for a Unit
    storage: window.sessionStorage
    // it overrides the default/global storage configuration
});
```

### Changing default storage for every Unit

You can change the default Storage API used by ActiveJS Units through the global [Configuration](/activejs/guides/configuration.md).

```typescript
// set it in global configuration
Configuration.set({storage: window.sessionStorage})
// now all the persistent Units will use SessionStorage
// and the global clearPersistentStorage() will also operate on SessionStorage
```

{% hint style="danger" %}
Be advised that you should only change it once and that too before initializing any persistent Unit.\
Otherwise, some persistent Units will save their values in `LocalStorage` and try to restore it from `SessionStorage`. Also, the global function`clearPersistentStorage()` won't be able to clear persisted values from the other storage, you'll have to manually provide the non-current storage you want to clean up.
{% endhint %}

## Supported data types

It's advised to put only serializable data types in a persistent Unit, otherwise, the information will be lost in serialization done to save it in the LocalStorage. Non-serializable data types like Date, Map, Set, etc. are not supported.

All the data types that support `JSON.stringify` and `JSON.parse` can be used as values.

**Note:** `Date` object works with `JSON.stringify`, however it can't be parsed back to a `Date` object.\
When using the persisted value of the Unit, you'll only get a `string` representation of `Date`, not a `Date` `object`.


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://docs.activejs.dev/activejs/guides/persistence.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
