Support for Drupal 7 is ending on 5 January 2025—it’s time to migrate to Drupal 10! Learn about the many benefits of Drupal 10 and find migration tools in our resource center.
Problem/Motivation
If your module is broken during development you can easily end up with an exception being rendered.
Sadly your code also breaks the rendering of that exception page easily, which results in pointless errors.
Proposed resolution
Decouple exception/error rendering from the rest of rendering,
... https://github.com/filp/whoops is pretty cool as it helps you to debug really deep problems.
Remaining tasks
User interface changes
API changes
Comment | File | Size | Author |
---|---|---|---|
#1 | 2376153-1.patch | 8.32 KB | dawehner |
Comments
Comment #1
dawehnerComment #2
Wim LeersThat looks very helpful.
Comment #3
dawehnerComment #4
ryan.armstrong CreditAttribution: ryan.armstrong commentedI can attest that Whoops is VERY helpful at debugging.
Comment #5
dawehner@ryan.armstrong
Do you want to try to research how to properly integrate it into core?
Comment #6
ryan.armstrong CreditAttribution: ryan.armstrong commentedActually yea I can take a look at that. Now that StackPHP is in core we could use the middleware.
Comment #7
Aki Tendo CreditAttribution: Aki Tendo commentedI finally took the time to give this a close look over and I would like to fold this into the Well Formed Errors Initiative. This is too large a change to fold into Drupal 8.0 - the error code is too disparate and needs to be consolidated. I am currently developing an assertion handler to staunch the bleeding of the worst of the super cryptic error and start the practice of adding assert statements into the code.
Whoops would give us a foundation for a unified message output format when in verbose mode. The code I was planning to write has the goal of codifying the error messages themselves and transferring their contents out into YAML files, like this one for a twigextension assertion failure:
This information is not at odds with the stackframe information that Whoops provides.
The incorporation of Whoops into the Well Formed Error Initiative does involve writing extended Handler classes that can load the error codes from the yml files. Also an Assertion Handler based on Whoops handle interface will need to be written as well. But it should work out very well.
Thoughts?
Comment #8
dawehner@Aki Tendo
Its great what you are working on, but please keep in mind that the only way to achieve something are small steps.
Comment #9
Aki Tendo CreditAttribution: Aki Tendo commentedSteps should be no larger or smaller than they need to be. Anyway, I'm getting a bit excited at the possibilities of putting this together. But before a single line of code gets written I need to take the step of drafting the API.
I've finished my first overview of Whoops and I think it will make for a fine error presentation layer. What my current project is about is error composition and error system setup - presentation was in my original plan largely an afterthought because those first two points are kinda massive on their own.
Comment #10
dawehnerOne thing I'd like to see at some point is that in case we render the exception we should not depend on any code in Drupal which could be broken as well.
Using whoops helps with that, because its just whoops, and nothing else.
Comment #11
Crell CreditAttribution: Crell at Palantir.net commentedAnother similar library worth investigating is BooBoo, from The PHP League: http://booboo.thephpleague.com/
(I've not used either one so have no opinion as to their relative quality, just that both exist and deserve evaluation.)
Comment #12
Aki Tendo CreditAttribution: Aki Tendo commentedBoth of these solutions share a problem - they do not lazy load. That is, they must load themselves *entirely* into memory. The Fault System I've devised only loads pointers to the error handling system that don't go over until tripped. I will expand it somehow to do a handoff to a third party library, but neither solution is idea for mainline use because of their overhead.
Comment #13
dawehner@Aki Tendo
Do you think these libraries could be easily made lazy loadable? We don't have to reinvent the wheel here.
Comment #14
Crell CreditAttribution: Crell commentedHow are they not lazy loading? They both use composer for autoloading (so no class has any impact on the system until it's actually used) and their initial setup at least seems fairly cheap. Instantiating an object or two is fairly inexpensive in modern PHP versions. We'd get much more mileage out of eliminating an SQL query than prematurely optimizing here. :-)
Comment #15
Aki Tendo CreditAttribution: Aki Tendo commentedThe moment you invoke a call from the class to set_error_handler or set_exception_handler the class is loaded. I was reminded of this while developing the Fault system. That's the reason a static method in the FaultSetup method was used instead of instantiating the object directly. Instead the object is loaded and instantiated at the last possible moment. I need to study Whoops and BooBoo more to see if they allow for this.
The main error find tool I want is symfony/var-dumper and it's associated Twig extensions. The first version of this patch used dump but that needed to be removed to for the minimal 8.0.x version.
Comment #16
Crell CreditAttribution: Crell commentedAs I said, especially with an opcode cache (which any self-respecting site uses now a days) the performance cost of loading the one file with the class in it is small enough to be negligible. There are WAAAAY bigger fish to fry than that micro-optimization.
Comment #17
Aki Tendo CreditAttribution: Aki Tendo commentedOp code caches don't remove the processing of the instructions - just the compiling of the code. As for the value of such optimization - most bloated software has no one big pig piece causing it to crawl, rather the problem is hundreds to thousands of small wasting actions that have accumulated and were put in place due to that attitude.
Comment #18
dawehnerFair point, @Aki Tendo but do you think it would be a hard problem to make it actually lazy? Isn't it just about wrapping the existing library and load it, if a error/exception appears?
Comment #20
willzyx CreditAttribution: willzyx commentedIf you are intrested I have create a little sandbox module that integrate Whoops library with Drupal 8 https://www.drupal.org/sandbox/willzyx/2751843
Any help/suggestion is really appreciated :)
Comment #21
Aki Tendo CreditAttribution: Aki Tendo commentedI've been away from the code for awhile but I'm ready to dive back in. The ability to allow developers to choose their debugging framework will be a major plus.
My thought is to adjust Drupal not to just use Whoops per se, but any debug framework. Ideally the framework would be loaded by composer, perhaps with a some glue code to make settings the debug suite needs. Also, splitting out the testmode code out of core would be desirable.
I'll turn to this shortly, I have a couple small patches I'd like to get into, I guess 8.3, at this point.
Comment #22
cosmicdreams CreditAttribution: cosmicdreams commentedVery interesting... I had no idea that there was a proliferation of these kind of debug frameworks. Can you list a few? I am having trouble finding the kinds of php libraries that you're talking about
Comment #23
Metal3d CreditAttribution: Metal3d as a volunteer commentedAnd... any way to fix this ? I have the exact error on 8.1.9 version calling "drush cr"...
Comment #25
Aki Tendo CreditAttribution: Aki Tendo as a volunteer commentedI've been giving this some thought recently. I'm starting to sway into the direction that while enabling optional debug handlers might be desirable this is an instance where leveraging community resources to do this in house makes sense. This is why I feel this way:
First, no outside bug handler - whoops, booboo, or what have you - is going to be written with drupal's code base and community in mind. Why is this important? I feel that it would be very useful to leverage the community in helping people find solutions to the problems at hand.
For example - it's one thing to have an assertion fail and give a nice neatly formatted call stack and variable stats. At the end of the day that's all whoops and booboo can do. A drupal specific package could allow us to encode a discussion page into the error object or error string, and link to that discussion in the error message itself. I also wrote a prototype which scanned the class names on the call stack and, again, linked back to the relevant Drupal API pages. This sort of cross referencing is something no outside project will ever be able to do, and to be honest the more detailed call stack examination can be obtained through xDebug anyway.
On a personal note - I've taken a job where I have a single Drupal 8 website to maintain, so I should be able to devote more time to projects now and on a few projects be able to get permission to work them into my paid work schedule.
Comment #26
dawehnerThis is an interesting thought you do. Having error messages pointing to helpful resources is certaintly a huge plus point.
Symfony fullstack is also providing a specific error message, integrating with other components.
From my point of view whoops is more meant as a one solution fits everything, while booboo is really more designed as a library with flexibility in mind.
Maybe I'm wrong.
That sounds really great. Looking forward to further ideas you have!
Comment #31
Chi CreditAttribution: Chi commentedThe main problem with the current way of rendering error messages is that it encourages developers to write sloppy code. Status messages can always be ignored. It's quite common for Drupal sites to send a few PHP notices/warnings to dblog on each page request.
To avoid this we should display error page with well formatted message for all PHP error levels, even for E_DEPRECATED. I think Symfony takes the same approach.
For BC we could add a new error level debug to system.logging configuration.