CakePHP 2.0+ custom error views using exceptions - php

I have been reading the following question here: CakePHP 2.0 - How to make custom error pages?
About creating custom views for exception handling in CakePHP 2.0+ and have been using it as a base to start doing the same in my own application hence starting my own question.
However I'm not following the logic. For example how does the Throw NotFoundException know to call the notFound method in the Errors Controller as I don't see any direct relationship in terms of the naming... Unless I'm missing the point?
In any case I'm looking to add 404, 403, and 401 errors and then be able to create custom views and call them using the exception handler throughout my app.
Can anyone shed more light on this? I'm using the latest version of Cake 2.1
So I have the following code:
App::uses('ExceptionRenderer', 'Error');
class AppExceptionRenderer extends ExceptionRenderer {
public function notFound($error) {
$this->controller->redirect(array('controller' => 'errors', 'action' => 'error404'));
}
}
And I want to replace that redirect with rendering a custom error view:
I've tried:
$this->controller->layout = null;
$this->controller->render('/Errors/error404');
But that just shows a blank page... Can anyone help me out as I don't want to do the redirect and would much rather follow conventions and render actual views with the same url when getting errors.
Update: Also noticed that the custom views ONLY get called when exceptions are manually called in the controller, and not for actual errors such as domain.com/garbageurl or something else... So it doesn't seem to be doing what I thought!

Have a look at these files from core Cake:
Cake/Error/ErrorHandler.php
Cake/Error/ExceptionRenderer.php
Here's what's happening:
ErrorHandler::handleException() is your exception handler. It gets called when an exception is thrown.
ErrorHandler::handleException() calls ExceptionRenderer::__construct() (your custom exception renderer must extend ExceptionRenderer) which parses the name of the Exception that was thrown, and from that, sets $this->method.
ErrorHandler::handleException() then calls ExceptionRenderer::render() which uses call_user_func_array() to call the method whose name is $this->method.

I was just looking for the same thing and could not find a neat way to do this using AppExceptionRenderer. It just won't allow you to have separate error403 and error404 template files.
So I just did this in my /app/View/Errors/error400.ctp file instead...
<? if ($error instanceof ForbiddenException) { ?>
<h4>Whoops! The page you attempted to access
requires permissions that you don't have.</h4>
<? } else { ?>
<h4>Whoops! We couldn't find the page you were looking for, sorry!</h4>
<? } ?>

Related

Symfony Throw custom 404 page inside service

I need to throw an Exception inside service
$isLangExist = $this->em->getRepository('TranslationBundle:Language')->findOneBy(array(
'locale' => $this->request->getMasterRequest()->getLocale()
));
if (!$isLangExist) {
throw new createNotFoundException('you are using unavailable langage');
}
but I got this page is not workinc in prod env
how can i show 404 page with createNotFoundException or any another Exception type
thanks
It looks like your code is not correct. I would expect it to look like this:
if (!$isLangExist) {
throw $this->createNotFoundException('you are using unavailable langage');
}
The method is part of the abstract base controller you can use, but it's not mandatory. What should work in cases where you don't extend this controller is:
if (!$isLangExist) {
throw new NotFoundHttpException('you are using unavailable langage');
}
Your problem goes beyond the above code, because you don't throw the exception inside a controller as I expected. You throw it inside a Twig extension. This exception will interrupt rendering, which is why the error is not converted into a 404 exception and instead is treated as a 500 error. Potentially you will see other 500-errors with your extension whenever one of the queries fails, which is probably not what you want. Addressing this issue likely requires rethinking how you use these global twig variables.
You could try moving the templates that use these variables into separate templates being rendered by a dedicated controller using sub requests or ESI:
{{
render(controller(
'AppBundle:Global:_listCategories',
{
'locale': app.request.attributes.get('_locale')
}
))
}}
Another solution might be to set these with null or an error-object whenever something fails and then react to these "alternative" results in your template, which is not what I would prefer.
There are probably many other ways to tackle this. The gist is: rendering error are different than http-exceptions thrown by controllers services. You have to ensure that your templates can either be rendered despite these missing/faulty variables or deal with these missing parameters before rendering the templates, e.g. in an event listener.

error variable in Zend_View (ZF1)

I have a new project to inspect and manage. It is written with ZF1.
There are views, contained in .phtml files which contain following code:
echo $this->partial('error.phtml', array('error'=>$this->error));
My issue is that no business logic, controller code or other application code sets
that error variable explicitly. I am hunting it down and need to figure out if this
error is set by Zend Framework itself.
My main lead is the CallbackHandler.php in Stdlib folder. It seems to be responsible for setting
an error flag to true, when its errorHandler is executed. Problem is that I'm not sure.
My second guess is that it is dead code and if $this->error is simply not used anywhere.
Any guesses ?
It depens on kind of displayed error.
For system errors write something like ErrorController and redirect to error page after handling of exeption(in dev mode you can add displaying of stack traces, etc).
For form validation "errors" there is build-in instruments to display it in forms.

Capture or modify Laravel's error pages?

I'd like to insert a code snippet into Laravel's error pages, but I can't figure out how to modify or capture the output.
This filthy hack seems to work, but the snippet is inserted before any page code.
// In laravel/app/start/global.php
App::error(function (Exception, $exception, $code)
{
echo '<script src="//localhost:35729/livereload.js"></script>';
});
The error pages are in resources/views/errors. You can then simply add whatever you want inside those file by naming them with the status code like 503.blade.php.
You can even make a base error page and the other view extends this one.
You can also take a look at the \App\Exceptions\Handler class in the report method, you can check Exceptions that have been thrown there.

kohana 3.0.12 how to log

i am working on an website on kohana 3.0.12 and i have installed a module that loggs me some errors. All works fine, except that, when i want to effectively log an error, i get an error and i don;t know how to manage it.
Here is the messy code:
public static function handler(Exception $e)
{
// It's a nice time to log :)
Kohana::$log->add(Kohana::ERROR, Kohana_Exception::text($e));
etc code here
well that Kohana_Exception::text($e) causes an exception like: Call to undefined method Kohana_Exception::text() ? i guess it is a framework bug. any idea of how i can solve the problem? (i guess i should use another instance but Kohana_Exception:: but what instance?)
thank you
You get this error because neither Kohana_Exception nor Exception classes don't have text() method. I think the author of the module wanted to write like this:
Kohana::$log->add(Kohana::ERROR, Kohana::exception_text($e));
I belive the exception handling in 3.0 is located in the Kohana class. Try Kohana::exception(), or look in api guide if that isn't it.

stopping page not found errors when controller does not exist

In production mode (minimal errors), when a controller is not found, Zend gives a 404 page not found error. There are a couple of controllers that I don't want this activated for. Even though they don't exist, I don't want the page not found error activated. Is it possible to somehow block that error and give an empty page. I'm guessing, if at all possible, it has to be done at the plugin level since no controller really exists to handle this.
One possible solution would be to check the request object in your errorAction for controller and/or action that threw the exceptions (for non-existing controllers and actions you could also get their names this way). Based on this you could customize the rest of errorAction. For example:
public function errorAction() {
$errors = $this->_getParam('error_handler');
$whatController = $errors->request->getControllerName();
if ('secretController' == $whatController) {
return $this->_redirect('blankErrorPage');
}
// usual rest of errorAction
}

Categories