Сессии и контексты в Node.js

Контекст запроса без middleware и без AsyncLocalStorage. Объект Client сопровождает каждый запрос; сессия живёт в Map по token.

Что это

Классический способ хранить «контекст текущего запроса»:

  • Express + middlewarereq.user, req.session через цепочку обработчиков.
  • AsyncLocalStorage (ALS) — невидимое хранилище, привязанное к асинхронной цепочке.

Подход Metarhia/Impress — явный объект Client (или Channel/Context), который пробрасывается в API-функции как первый аргумент. Без middleware, без ALS.

API / Пример

class Client {
  constructor(req, res) {
    this.req = req;
    this.res = res;
    this.token = null;
    this.session = null;
    this.cookies = {};
    this.parseCookies;
    this.session = Session.restore(this.cookies.token);
  }

  setCookie(name, value, opts = {}) { /* ... */ }
  sendCookie { /* res.setHeader('Set-Cookie', this.preparedCookie) */ }
}

// В роуте
http.createServer((req, res) => {
  const client = new Client(req, res);
  res.on('finish', () => client.session?.save);
  routing[req.url](client);  // явная передача контекста
});

Архитектура (Metarhia)

Channel  ─ хранит connection / request / response
Client   ─ token, session, cookies — пробрасывается в API
Session  ─ Map<token, sessionData> — в памяти + persist в БД
Context  ─ Proxy на client + counter / events / data
  • API-функции получают context (или client) явно.
  • context.client.emit('event', data) для отправки событий.
  • Через Proxy можно инжектить контекст в data автоматически.
  • Сохранение сессии — на finish или пачкой по таймеру.

Производительность / Подводные камни

  • ALS делает магию — трудно отлаживать; явный client понятнее.
  • Middleware-цепочка дорогая — много функций на каждый запрос. Явный передача — один вызов.
  • Cookie парсится один раз в конструкторе клиента.
  • Token в Cookie с HttpOnly — защита от XSS-кражи.
  • Сессия в Map — быстро, но не переживает рестарт. Persist через БД или Redis.
  • Контекст видит только нужное пользователю — приватные поля скрываются через Proxy/класс.

🎓 Источники

  • 🎓 Sessions and contexts on Node.js and the Metarhia tech stack · 2021-02-05

    • Тезисы: сессии без middleware и без ALS; контекст с ссылкой на client; Proxy на data для инжекта контекста; channel хранит request/response; коллекции sessions = Map<token> и channels; видно только необходимое.
    • Цитата: «Async/continuation local storage в данном случае совершенно лишние понятия.»
  • 🎓 HTTP сессии и cookies на чистом Node.js · 2019-03-14

    • Тезисы: Client сопровождает каждый запрос; парсинг cookie из req.headers.cookie; setCookie/sendCookie/deleteCookie; флаг httpOnly защищает от XSS; сохранение сессии на res.on('finish').

См. также