Атрибут onstorage тега <body>
Описание
Атрибут onstorage позволяет задать JavaScript-код, который выполняется при изменении данных в локальном хранилище (localStorage или sessionStorage) в других вкладках того же домена. Это мощный механизм для синхронизации состояния между разными вкладками приложения.
<body onstorage="handleStorageChange(event)">
<div id="user-prefs">
Текущая тема: <span id="theme-display">светлая</span>
</div>
<script>
function handleStorageChange(event) {
if (event.key === 'theme') {
// Обновляем тему при изменении в другой вкладке
document.getElementById('theme-display').textContent = event.newValue;
applyTheme(event.newValue);
}
}
function applyTheme(theme) {
document.body.className = theme === 'dark' ? 'dark-theme' : 'light-theme';
}
// Инициализация при загрузке
const savedTheme = localStorage.getItem('theme') || 'light';
applyTheme(savedTheme);
</script>
</body>
Свойства события storage:
| Свойство | Описание |
|---|---|
key |
Ключ измененного элемента (null при очистке хранилища) |
oldValue |
Предыдущее значение (null при добавлении) |
newValue |
Новое значение (null при удалении) |
url |
URL документа, где произошло изменение |
storageArea |
Ссылка на localStorage или sessionStorage |
Рекомендации по использованию:
- Используйте для синхронизации состояния между вкладками
- Обрабатывайте только нужные ключи (проверяйте event.key)
- Для сложных данных используйте JSON.parse/stringify
- Сочетайте с debounce для частых обновлений
- Тестируйте в разных браузерах
Практический пример с корзиной покупок:
<body onstorage="syncCart(event)">
<div id="cart"></div>
<script>
function syncCart(event) {
if (event.key === 'shopping-cart') {
const cart = JSON.parse(event.newValue || '[]');
renderCart(cart);
}
}
function renderCart(items) {
const cartDiv = document.getElementById('cart');
cartDiv.innerHTML = items.length
? `В корзине: ${items.length} товаров`
: 'Корзина пуста';
}
function addToCart(product) {
const cart = JSON.parse(localStorage.getItem('shopping-cart') || '[]');
cart.push(product);
localStorage.setItem('shopping-cart', JSON.stringify(cart));
}
// Инициализация
syncCart({key: 'shopping-cart', newValue: localStorage.getItem('shopping-cart')});
</script>
</body>
Важные замечания:
- Событие не срабатывает в той же вкладке, где произошли изменения
- Для sessionStorage работает только в рамках одного окна браузера
- Размер хранилища ограничен (~5MB)
- В приватном режиме могут быть ограничения
- Не все браузеры поддерживают одинаково
Оптимизация производительности:
- Минимизируйте объем сохраняемых данных
- Используйте сжатие для больших структур
- Избегайте частых обновлений (debounce)
- Для сложных состояний используйте IndexedDB
- Очищайте устаревшие данные
Примечание: Для современных приложений с сложными требованиями к синхронизации между вкладками рекомендуется использовать BroadcastChannel API или SharedWorker, которые предоставляют более гибкие возможности коммуникации.