У меня реализовано следующим образом:
Есть в БД таблица sessions с полями current_session, long_session, user_id и login_time.
При успешном логине генерируются две случайные строки. Первая записывается в стандартную PHP сессию и будет current_session. Вторая записывается пользователю в куку session, а хеш этой строки будет long_session. user_id - идентификатор пользователя, login_time - время логина.
Проверка, залогинен ли пользователь, выполняется следующим образом:
1. Если у пользователя есть активная PHP сессия, проверяем, активна ли его current_session, если да, то пользователь авторизован.
2. Если у пользователя нет текущей сессии, но установлена кука session, то ищем хеш от неё в базе. Если запись есть и с момента последнего логина прошло меньше указанного количество времени (я использую меньше трёх месяцев), то по user_id берём остальные данные пользователя и создаём текущую сессию, пользователь авторизован.
При logout просто очищаем текущие current_session и long_session. Если нужно разлогинить везде, то очищаем все эти значение по user_id.
Такой подход позволяет строго управлять сессиями с помощью БД, но при этом стандартный механизм PHP сессий позволяет хранить разнообразную информацию, типо csrf токенов, не захламляя базу.