phpmiddlewareslim-3respect-validation

Slim3 right way to set errors and check is user logged in


I'm a new user of Slim framework, I've a simple Slim 3 application, with sign in and sign up validation. But I'm not really sure if this is the right/best way to set errors and check if user is logged in -In order to redirect it to his account if session user.id exists.

I used a middleware: AuthMiddleware which includes:

class AuthMiddleware
{
protected $container;

public function __construct($container)
{
    $this->container = $container;
}

public function __invoke($request, $response, $next)
{
    if (isset($_SESSION['user.id']) && !empty($_SESSION['user.id'])) {
        return $response->withRedirect($this->container->router->pathFor('user.index'));
    }

    $twig = $this->container->view->getEnvironment();

    if (isset($_SESSION['validation'])) {
        $twig->addGlobal('errors', $_SESSION['validation']['errors']);
        $twig->addGlobal('values', $_SESSION['validation']['values']);
        unset($_SESSION['validation']);
    }

    if (isset($_SESSION['auth.signup.success'])) {
        $twig->addGlobal('auth_signup_success', $_SESSION['auth.signup.success']);
        unset($_SESSION['auth.signup.success']);
    }

    if (isset($_SESSION['auth.signin.failed'])) {
        $twig->addGlobal('auth_signin_failed', $_SESSION['auth.signin.failed']);
        unset($_SESSION['auth.signin.failed']);
    }

    $response = $next($request, $response);

    return $response;
}
}

And I used Twig for my views. Session validation assigned in the validator.php which includes:

class Validator
{
protected $errors = [];
protected $values = [];

public function validate($request, $rules)
{
    foreach ($rules as $field => $rule) {
        $this->values[$field] = $request->getParam($field);
        try {
            $rule->setName(ucfirst($field))->assert($request->getParam($field));
        } catch (NestedValidationException $e) {
            $this->errors[$field] = $e->getMessages()[0];
        }
    }

    if ($this->failed()) {
        $_SESSION['validation'] = [
            'errors' => $this->errors,
            'values' => $this->values,
        ];
    }

    return $this;
}

public function failed()
{
    return !empty($this->errors);
}
}

Using Respect\Validation. Also, is this the right use of Middlewares?

Thanks in advance.


Solution

  • try creating a separate file for the methods, and calling it from the middleware:

    <?php 
        class AuthMiddleware extends Middleware {
            public function __invoke($request, $response, $next) {
                if (!$this->container->auth->check()) {
                    $this->container->flash->addMessage('danger', 'Please sign in to continue.');
                return $response->withRedirect($this->container->router->pathFor('auth.signin'));
                }
                $response = $next($request, $response);
                return $response;
            }
        }
    

    while the Auth class would have those methods to check:

    <?php
        public function check () {
            return isset($_SESSION['user']);
        }
    
        public function user() {
            if (isset($_SESSION['user'])) {
                return User::find($_SESSION['user'])->first();
            } else {
                return false;
            }
        }
    

    Don't forget to include the Auth Class within your $app:

    <?php 
        $container['auth'] = function ($container) {
            return new \App\Auth\Auth();
        };