quản lý session webman

Ví dụ

<?php
namespace app\controller;

use support\Request;

class UserController
{
    public function hello(Request $request)
    {
        $name = $request->get('name');
        $session = $request->session();
        $session->set('name', $name);
        return response('hello ' . $session->get('name'));
    }
}

Bằng cách sử dụng $request->session(); để có được một instance của Workerman\Protocols\Http\Session, sử dụng các phương thức của instance để thêm, sửa đổi hoặc xóa dữ liệu session.

Lưu ý: Đối tượng session sẽ tự động lưu trữ dữ liệu session khi bị hủy, vì vậy không nên lưu trữ đối tượng trả về từ $request->session() trong mảng toàn cục hoặc thành viên lớp để tránh việc session không được lưu trữ.

Lấy tất cả dữ liệu session

$session = $request->session();
$all = $session->all();

Trả về một mảng. Nếu không có dữ liệu session nào, sẽ trả về một mảng rỗng.

Lấy một giá trị trong session

$session = $request->session();
$name = $session->get('name');

Nếu dữ liệu không tồn tại, sẽ trả về null.

Bạn cũng có thể truyền một giá trị mặc định cho tham số thứ hai của phương thức get, nếu không tìm thấy giá trị tương ứng trong mảng session thì sẽ trả về giá trị mặc định. Ví dụ:

$session = $request->session();
$name = $session->get('name', 'tom');

Lưu trữ session

Khi lưu trữ một mục dữ liệu thì sử dụng phương thức set.

$session = $request->session();
$session->set('name', 'tom');

set không trả về giá trị, dữ liệu session sẽ tự động được lưu khi đối tượng session bị hủy.

Khi lưu trữ nhiều giá trị sử dụng phương thức put.

$session = $request->session();
$session->put(['name' => 'tom', 'age' => 12]);

Tương tự, put cũng không trả về giá trị.

Xóa dữ liệu session

Khi cần xóa một hay nhiều dữ liệu session, sử dụng phương thức forget.

$session = $request->session();
// Xóa một mục
$session->forget('name');
// Xóa nhiều mục
$session->forget(['name', 'age']);

Ngoài ra, hệ thống cung cấp phương thức delete, khác với phương thức forget là delete chỉ có thể xóa một mục.

$session = $request->session();
// Tương đương với $session->forget('name');
$session->delete('name');

Lấy và xóa một giá trị trong session

$session = $request->session();
$name = $session->pull('name');

Kết quả tương đương với đoạn mã sau

$session = $request->session();
$value = $session->get($name);
$session->delete($name);

Nếu session tương ứng không tồn tại, sẽ trả về null.

Xóa tất cả dữ liệu session

$request->session()->flush();

Không có giá trị trả về, dữ liệu session sẽ tự động bị xóa khỏi lưu trữ khi đối tượng session bị hủy.

Kiểm tra xem dữ liệu session tương ứng có tồn tại không

$session = $request->session();
$has = $session->has('name');

Nếu session không tồn tại hoặc giá trị session tương ứng là null, sẽ trả về false, ngược lại sẽ trả về true.

$session = $request->session();
$has = $session->exists('name');

Đoạn mã trên cũng dùng để kiểm tra xem dữ liệu session có tồn tại hay không, sự khác biệt là khi giá trị session tương ứng là null, cũng sẽ trả về true.

Hàm trợ giúp session()

webman cung cấp hàm trợ giúp session() để thực hiện các chức năng tương tự.

// Lấy instance session
$session = session();
// Tương đương với
$session = $request->session();

// Lấy một giá trị
$value = session('key', 'default');
// Tương đương với
$value = session()->get('key', 'default');
// Tương đương với
$value = $request->session()->get('key', 'default');

// Gán giá trị cho session
session(['key1'=>'value1', 'key2' => 'value2']);
// Tương đương với
session()->put(['key1'=>'value1', 'key2' => 'value2']);
// Tương đương với
$request->session()->put(['key1'=>'value1', 'key2' => 'value2']);

Tập tin cấu hình

Tập tin cấu hình session nằm tại config/session.php, nội dung tương tự như sau:

use Webman\Session\FileSessionHandler;
use Webman\Session\RedisSessionHandler;
use Webman\Session\RedisClusterSessionHandler;

return [
    // FileSessionHandler::class hoặc RedisSessionHandler::class hoặc RedisClusterSessionHandler::class 
    'handler' => FileSessionHandler::class,

    // Nếu handler là FileSessionHandler::class thì giá trị là file,
    // Nếu handler là RedisSessionHandler::class thì giá trị là redis
    // Nếu handler là RedisClusterSessionHandler::class thì giá trị là redis_cluster tức là redis cluster
    'type'    => 'file',

    // Các handler khác nhau sẽ sử dụng cấu hình khác nhau
    'config' => [
        // Cấu hình khi type là file
        'file' => [
            'save_path' => runtime_path() . '/sessions',
        ],
        // Cấu hình khi type là redis
        'redis' => [
            'host'      => '127.0.0.1',
            'port'      => 6379,
            'auth'      => '',
            'timeout'   => 2,
            'database'  => '',
            'prefix'    => 'redis_session_',
        ],
        'redis_cluster' => [
            'host'    => ['127.0.0.1:7000', '127.0.0.1:7001', '127.0.0.1:7001'],
            'timeout' => 2,
            'auth'    => '',
            'prefix'  => 'redis_session_',
        ]

    ],

    'session_name' => 'PHPSID', // tên cookie để lưu trữ session_id
    'auto_update_timestamp' => false,  // có tự động làm mới session hay không, mặc định là tắt
    'lifetime' => 7*24*60*60,          // thời gian hết hạn của session
    'cookie_lifetime' => 365*24*60*60, // thời gian hết hạn của cookie lưu trữ session_id
    'cookie_path' => '/',              // đường dẫn cookie lưu trữ session_id
    'domain' => '',                    // tên miền cookie lưu trữ session_id
    'http_only' => true,               // có bật httpOnly không, mặc định là bật
    'secure' => false,                 // chỉ bật session trong https, mặc định là tắt
    'same_site' => '',                 // dùng để ngăn chặn tấn công CSRF và theo dõi người dùng, giá trị có thể là strict/lax/none
    'gc_probability' => [1, 1000],     // xác suất thu hồi session
];

Liên quan đến bảo mật

Khi sử dụng session, không khuyến khích lưu trữ trực tiếp đối tượng instance của lớp, đặc biệt là các đối tượng lớp không thể kiểm soát, vì việc giải mã có thể gây ra rủi ro tiềm ẩn.