We have moved our forum to GitHub Discussions. For questions about Phalcon v3/v4/v5 you can visit here and for Phalcon v6 here.

flash SESSION messages after redirect doesnt show

I have a prepared AccessControll plugin for cheking access to resources and actions, so when i set flash message in plugin and then redirect to the login page the message doesn't show.

I have in access control plugin lines:

if(!$role || !$moduleAcl || !$moduleAcl->isAllowed($role,$controller,$action)){
      $this->flash->warning('Nemáte oprávnění na provedení této akce.');
      if(!$moduleAcl->isAllowed($role, 'index', 'index')){
            $auth = \Core\Auth::logout();
      }
      else {
           return $this->response->redirect($module.'/');
      }
}

In, base controller i have a lines:

if(!$identity)
{          
   return $this->response->redirect('manager/auth/');                      
}

And process is:

  1. Login - check user accross db
  2. Authentication - Loading permissions for the user role
  3. When user is logged in the user is redirected at the main module page ( /module/ ) - index, index but before dispatch it happen 4:
  4. Now the AccessControll plugin check beforeDispatch if the user have permission to access module, when not the identity will be cleared ( session authUser removed ):
protected function removeIdentity()
    {
        $this->identity = null;
        $this->session->remove('authUser');
    }
  1. Then request continue to the main module page ( index ) where is if user is not logged in and doesnt have identity it will be redirected to the auth page:
if(!$role || !$moduleAcl || !$moduleAcl->isAllowed($role,$controller,$action)){
      $this->flash->warning('Nemáte oprávnění na provedení této akce.');
      if(!$moduleAcl->isAllowed($role, 'index', 'index')){
            $auth = \Core\Auth::logout();
      }
      else {
           return $this->response->redirect($module.'/');
      }
}

The flash message is generated at the AccessControll plugin. So why the message doesn't show ?

Thanks for the help.



174

I am use this simple approach in ControllerBase

    public function beforeExecuteRoute(\Phalcon\Mvc\Dispatcher $dispatcher)
    {
        $this->initUser();
    }

    private function initUser()
    {
        $controller = $this->dispatcher->getControllerName();
        $action     = $this->dispatcher->getActionName();
        $user       = $this->session->get('user');
        $loginArea  = (bool) in_array($controller, ['comments']); //put here all the controllers that require login role
        $adminArea  = (bool) in_array($controller, ['admin']); //put here all the controllers that require admin role
        if ($user) {
            if ($adminArea && 'admin' !== $user->role) {
                $this->flashSession->error(_('Your user rights are insufficient to access the requested URL.'));
                $this->dispatcher->forward(['controller' => 'users', 'action' => 'profile']);
            }
        } else {
            if ($loginArea || $adminArea) {
                $this->flashSession->error(_('Please log in to access the requested URL.'));
                $this->dispatcher->forward(['controller' => 'users', 'action' => 'login']);
            }
        }
    }
edited Aug '14

Yes but I have a complicate structure and right for any section, so I must check if you have a section to module/resource and action and if it exactly has some permission to access module.

In my system I have all automated by my releases of AutoRoute plugin and AccessControll plugin :) so it's little bit complicated, but fully automated and configurable.

But I have a problem just with a flash, and forwarding is a not best solution to show other page then redirect.



174

Then use flashSession instead direct flash!

$this->flashSession->error('Login required.');
return $this->response->redirect('users/login');

Mate i have session flash ( did you not seen it in the title ? )

Look my bootstrap:

$di->set('flash', function(){
    $flash = new \Phalcon\Flash\Session(array(
        'error'     => 'alert alert-danger',
        'success'   => 'alert alert-success',
        'notice'    => 'alert alert-info',
        'warning'   => 'alert alert-warning'
    ));    
    return $flash;
});


174

If you use \Phalcon\DI\FactoryDefault() don't rename default services!. service-name-conventions

Put break lines on your code to trace errors (die('run redirect on module')...).

Maybe your code run more than one redirect order and this may be breaking the message output



98.9k
Accepted
answer
  • Check that you have a favicon.ico in public/ (sometimes due to 404 errors flash messages are shown in a parallel request)
  • Try disabling the view $this->view->disable() before redirect
edited Aug '14

@urulab Replaced default flash works too with FactoryDefault it's not significant.

@Pahlcon I have favicon ( on development i have phalcon favicon.ico ) and yes thanks! it's resolved the problem (disable view), but i think, that it will be good to have it implemented in response, response must have exit or something like that for correct run always. :) But still thanks time to rebuild response class :)

edited Aug '14

So solution is:

<?php
namespace Core\Http;

/**
 * Description of Response
 *
 * @author softdream
 */
class Response extends \Phalcon\Http\Response {
    //put your code here

    public function redirect($locationPath = null, $baseUrl = null, $statusCode = null) {
        if($statusCode){
            $this->setStatusHeader($code);
        }

        if(substr($locationPath, 0,1) === '/'){
            $locationPath = substr($locationPath, 1);
        }

        header("Location: ".$baseUrl.'/'.$locationPath);
        exit;
    }

    protected function setStatusHeader($code){
        header("HTTP/1.0 ".$code);
    }

}

And replace default response in bootstrap or index:

$di->set('response',function(){
    return new \Core\Http\Response();
});

It will resolve all problems with throwing session flash messages after redirect :)



25.7k

@Phalcon

sorry to bother you, I want to learn more. I just fixed the session flash issue by disabling the view. My question is under what situation is disabling the view necessary? I couldn't find much info regarding this issue from the doc

edited Feb '17

My messages didnt show up either. And i had to change the following in config/services.php

$di->set('flash', function () {
    return new Flash([
        'error'   => 'alert alert-danger',
        'success' => 'alert alert-success',
        'notice'  => 'alert alert-info',
        'warning' => 'alert alert-warning'
    ]);
});

to:

$di->set('flash', function () {
    return new Phalcon\Flash\Session([
        'error'   => 'alert alert-danger',
        'success' => 'alert alert-success',
        'notice'  => 'alert alert-info',
        'warning' => 'alert alert-warning'
    ]);
});

In the controller I'm using

return $this->dispatcher->forward(["controller" => "client", "action" => "index" ]);

And finally to show them (no proper mark-up yet)

{{ flash.output() }}

I'm learning the framework while building a project management and hour booking system, so it might not be the smartest solution, but for now it works for me.