0
votes

I am using CakePHP 3.0 framework and need to disable/turn off Stack Trace if exception or error occurs.

I tried solution given on Turn on /off the debug mode for particular controller in cakephp.

If I make change in MyProject\config\app.php file, stack trace are turned off for all controllers but if I set trace = false using following code for a specific controller Error.trace is set to false but stack trace are not disabled.

<?php
namespace App\Shell;

use Cake\Core\Configure;
use Cake\Console\Shell;

Configure::write('Error.trace', false);

class MyClassShell extends Shell {

    public function main() {
        echo 'Error.trace...' . Configure::read('Error.trace'); // output is false
        ...
    }
}
?>

Its weird to see that even if Error.trace is False still stack trace are printed.

Is their any other way to disable Stack Trace in Cakephp 3.0 for a specific controller/shell file instead of setting it from app.php ?

1

1 Answers

2
votes

Error options are only being read once

Like some of the other options, the Error options are not runtime changeable via the Configure class. While these options are not being consumed, the error handler only reads them once at bootstrapping time, and thus changing them at a later point has no effect, see your applications config/bootstrap.php

// ...
(new ConsoleErrorHandler(Configure::read('Error')))->register();
// ...

https://github.com/cakephp/app/blob/3.2.6/config/bootstrap.php#L116-L120

Use a custom error handler

In order to change the error handler behavior at runtime, you'll need to use a custom/extended error handler that supports that, and then either change it directly, or make it read the option dynamically. In order for the former to work (which is the easier approach as it doesn't require reimplementing a bunch of code), you'll have to store a reference to the handler that you can access at a later point.

A basic custom error handler that supports changing options could look something like this (* note that this is all untested example code)

namespace App\Console;

use Cake\Console\ConsoleErrorHandler;

class AppConsoleErrorHandler extends ConsoleErrorHandler
{
    public function setOption($key, $value)
    {
        $this->_options[$key] = $value;
    }
}

A quick and dirty solution would then be to store a reference via Configure, like

use App\Console\AppConsoleErrorHandler;

// ...

if ($isCli) {       
    $handler = new AppConsoleErrorHandler(Configure::read('Error'));
    $handler->register();
    Configure::write('Error.handler', $handler);
} else {
    (new ErrorHandler(Configure::read('Error')))->register();
}

// ...

and then access and reconfigure it in your shell, like

$handler = Configure::read('Error.handler');
$handler->setOption('trace', false);

but don't do that on file level as in your example, do it in the constructor or in the main() method.

See also