laravel-debugbar
laravel-debugbar copied to clipboard
Ability to add a custom stacktrace parsing method
Hello there,
I use https://github.com/yajra/laravel-datatables package in almost all of my projects.
I currently have a problem of seeing the source of the queries inside my DataTable classes.
For example:
I have a query builder setup inside my UsersDataTable
.
public function query()
{
return User::query();
}
Since this function only starts to bulid the query it doesn't show up in debug_backtrace()
.
For this I've added a solution which allows me to check the "query sender" object and modify how the $frame
was filled.
I've added simple static method to add my custom callables to QueryCollector
, in there I can modify and return the $frame
as I wish in case the $trace['object']
is matching my first parameter $objectType
.
Here is an example DataTable::class
query tracer.
QueryCollector::addCustomFrameParser(DataTable::class, function (object $frame, array $trace) {
// Remove the 'App\' prefix from the namespace
$relativeNamespace = str_replace('App\\', '', $trace['object']::class);
// Convert namespace to a directory path
$directoryPath = str_replace('\\', DIRECTORY_SEPARATOR, $relativeNamespace);
$filePath = app_path($directoryPath) . '.php';
// Get the file path inside the project from the class object
$frame->file = $filePath;
return $frame;
});
After I add this to my AppServiceProvider
, I can simply see the change inside my "Query" tab.
Before:
After:
This way I can simply tell where I built the query and continue debugging/development.
Did you try adding PATH_TO_FILE/DataTablesController.php
to options.db.backtrace_exclude_paths
?
I have a bridge query builder, and I had a similar problem,
I added the file_path
to the backtrace_exclude_paths
and I already got the correct file
https://github.com/barryvdh/laravel-debugbar/blob/03448e59739181179697dd996f581404db4ce7c5/config/debugbar.php#L213
Yes I tried, but since the query is NOT actually sent from the UsersDataTable
PHP's debug_backtrace()
only detects the call from: DataTablesController.php
Also here is how mine looks like usually:
'backtrace_exclude_paths' => [
'/vendor/yajra/laravel-datatables',
'/vendor/staudenmeir',
],
Post Before\After
with backtrace
Maybe there could be a simpler way
Before:
After:
extends UsersDataTable
some yajra class?? or uses some yajra trait?
It extends the DataTable
class from the package.
I think it could be made more native, maybe some "demo minimal app" to find another approach?
I can make a demo next week, the change is actually very minimal anyway.
I actually already pushed a demo to GitHub.
https://github.com/OzanKurt/debugbar-demo
You can simply pull and run with php artisan serve
.
After you install the app you can simply open these two pages:
http://127.0.0.1:8000/?custom_parsing=true http://127.0.0.1:8000/?custom_parsing=false
replace the contents of QueryCollector
and check it out.
This removes a step from the trace, I'm going to try another approach Try #1588
So you suggest adding an extra source to the trace instead of modifying its file...
I'm fine with that approach as well.
One thing to add maybe would be the custom source parsing:
So instead of
if (($trace['class'] ?? null) == 'Yajra\DataTables\Services\DataTable') {
looping through an array of customs would be nicer
foreach (static::$customSourceParsers as $objectType => $customSourceParser) {
if (isset($trace['object']) && is_a($trace['object'], $objectType)) {
QueryCollector::addCustomFrameParser(DataTable::class, function (object $frame, array $trace) { // Remove the 'App' prefix from the namespace $relativeNamespace = str_replace('App\', '', $trace['object']::class);
I try to avoid that, not everyone has the knowledge to do that customization, and not all cases can be solved in that way the way I add it would be ready to use but @barryvdh decides
Why not add both, so people with the knowledge to customize can do it without needing a PR process.
I'm not really sure about this, not seeing this in my own datatables. Don't want to complicate the backtrace too much.