Authentification

River fournit un service Auth complet pour gérer connexion, déconnexion, vérification et contrôle d'accès par rôle.

Service Auth

Le service River\Auth est enregistré par Auth_provider. Il est automatiquement partagé avec les templates ($auth).

use River\Auth;

class My_ctrl extends Controller {
    public function __construct(
        private Auth $auth,
        // ...
    ){}

    public function dashboard() {
        $user = $this->auth->user();      // Utilisateur courant (object ou null)
        $id   = $this->auth->id();        // ID de l'utilisateur
    }
}

Connexion

// Tentative avec email/password
if ($this->auth->attempt($email, $password)) {
    return $this->auth->redirect_intended('/dashboard');
}

// Connexion manuelle (après vérification externe)
$this->auth->login($user);

Déconnexion

$this->auth->logout();

Vérification

$this->auth->check();   // true si connecté
$this->auth->guest();   // true si non connecté
$this->auth->user();    // object|null
$this->auth->id();      // int|null

Inscription

$id = $this->auth->register($email, $password, [
    'name' => 'John',
    'role' => 'user'
]);

User Checker

Par défaut, attempt() connecte n'importe quel utilisateur dont les credentials sont valides, et user() recharge n'importe quel utilisateur dont l'ID est en session. Un compte mis en corbeille ou désactivé après la connexion reste donc actif jusqu'à expiration de session.

Le user checker est un callable configurable qui reçoit l'objet $user et retourne true pour autoriser, false pour bloquer. Il est appelé :

Configuration dans config.php :

'auth' => [
    // Bloquer les comptes en corbeille (status = -1) ou désactivés
    'user_checker' => fn($user) => ($user->status ?? 0) >= 0,
],

River n'impose aucune colonne — la logique est entièrement dans votre callable :

// Bloquer les comptes non vérifiés
'user_checker' => fn($user) => (bool) $user->email_verified_at,

// Plusieurs conditions
'user_checker' => fn($user) => $user->active && !$user->banned,

Note : Sans user_checker, le comportement est identique à avant — aucune régression.

Middleware d'authentification

Configuration

Deux clés dans config.php contrôlent le comportement des middlewares d'auth pour les utilisateurs non connectés :

'auth' => [
    'login_url'       => getenv('LOGIN_URL') ?: '/login',
    'unauth_behavior' => getenv('UNAUTH_BEHAVIOR') ?: 'redirect', // redirect | 403 | 404
],
unauth_behaviorEffet
redirectRedirige vers login_url et mémorise l'URL demandée (défaut, rétrocompatible)
403Retourne une page "Accès restreint" sans révéler l'URL de login
404Fausse page introuvable — ne révèle pas l'existence de la route

Note : Sans ces clés, le comportement est identique à avant — aucune régression.

Auth_middleware

Protège les routes qui nécessitent un utilisateur connecté.

use River\Middleware\Auth_middleware;

$router->get('dashboard', 'Dashboard::index')
       ->middleware(Auth_middleware::class);

Guest_middleware

Protège les routes réservées aux visiteurs (login, register). Redirige vers / si déjà connecté.

use River\Middleware\Guest_middleware;

$router->get('login', 'Auth_ctrl::login_form')
       ->middleware(Guest_middleware::class);

Role_middleware

Protège les routes par rôle. Accepte un ou plusieurs rôles en paramètres (logique OR).

use River\Middleware\Role_middleware;

// Un seul rôle
$router->get('admin', 'Admin::index')
       ->middleware(Role_middleware::class . ':admin');

// Plusieurs rôles (admin OU sysadmin)
$router->get('admin', 'Admin::index')
       ->middleware(Role_middleware::class . ':admin,sysadmin');

Comportement :

Groupe avec Role_middleware

$router->group([
    'prefix' => 'admin',
    'middleware' => Role_middleware::class . ':admin,sysadmin'
], function($r) {
    $r->get('users', 'Admin\Users_ctrl::index');
    $r->get('settings', 'Admin\Settings_ctrl::index');
});

Rôles dans les vues

$auth est automatiquement partagé dans tous les templates via Auth_provider::boot().

// Dans un template ($auth via extract(), pas $this->auth)
<?php if ($auth->check()): ?>
    Bonjour <?= $this->e($auth->user()->name) ?>
<?php endif ?>

<?php if ($auth->has_role('admin')): ?>
    <a href="/admin">Administration</a>
<?php endif ?>

<?php if ($auth->is_admin()): ?>
    <!-- Raccourci pour has_role('admin') -->
<?php endif ?>

Note : Dans les templates, les données partagées sont des variables directes ($auth), pas des propriétés de $this. Utilisez $this->e(), $this->url() uniquement pour les helpers de Template.

Intended URL

Quand un utilisateur non connecté est redirigé vers /login, l'URL d'origine est mémorisée en session. Après le login, redirigez-le vers cette URL :

// Dans le controller de login
if ($this->auth->attempt($email, $password)) {
    return $this->auth->redirect_intended('/dashboard');
}
// redirect_intended() renvoie vers l'URL mémorisée, ou /dashboard par défaut