laravel-debugbar: Debugbar::enable() does not seem to work!

I have the below code in a middleware and disabling debug_bar (if i have it enabled by default) works fine! However if I try the opposite, meaning having the debug bar disabled by default and try to enable it on demand then id does not work.

Any ideas?

P.S. lavavel’s own debug mode works fine like this! gets enable or disabled when i want!

    if ($request->has('disable_debug')) {
        \Config::set('app.debug', false);
        \Debugbar::disable();
    }
    if ($request->has('enable_debug')) {
        \Config::set('app.debug', true);
        \Debugbar::enable();
    }

About this issue

  • Original URL
  • State: closed
  • Created 9 years ago
  • Reactions: 3
  • Comments: 29 (6 by maintainers)

Most upvoted comments

I have a use case where none of these solutions seem to work:

This is what I ended up doing:

  1. Create middleware: /app/Http/Middleware/DebugBar.php:
<?php namespace App\Http\Middleware;

use Closure;

class DebugBar
{
    /**
     * Handle an incoming request.
     *
     * @param  \Illuminate\Http\Request  $request
     * @param  \Closure  $next
     * @return mixed
     */
    public function handle($request, Closure $next)
    {
        app('debugbar')->disable();

        if (auth()->check() && auth()->user()->is_admin) {
            app('debugbar')->enable();
        }

        return $next($request);
    }
}
  1. Add this new middleware to /app/Http/Kernel.php as the last item in the web middleware group.
  2. Important to note here is that the enabled value needs to be null in /config/debugbar.php. Note: I think this still has the issue of the various libraries being loaded on each request, adding a bit of overhead.
  3. Don’t forget to add the appropriate getIsAdminAttribute() method to your user model, if that’s your criteria for enabling debugbar.

To use debugbar in production, you will need to set APP_DEBUG env variable to true while debugging things.

I have found a workaround however I would prefer to do it with middleware!

I figured that in config/laravel debugbar.php I can do something like

      'enabled' => function(){
      if (Illuminate\Support\Facades\Request::has('enable_debug')) { 
          return true; 
      } 
      return config('app.debug');
      }

@unitedworx @mikebronner @lvbeck @GoodJob @emilv To enable debugbar in middleware (when it’s off in config and APP_DEBUG=false):

  1. add this middleware \Barryvdh\Debugbar\Middleware\InjectDebugbar::class after your middleware (which call \Debugbar::enable()) app\Http\Kernel.php:
'web' => [
           ...
            \App\Http\Middleware\DebugbarEnabler::class, // my middleware
            \Barryvdh\Debugbar\Middleware\InjectDebugbar::class,
        ],
  1. create DebugbarEnablerServiceProvider (app\Providers\DebugbarEnablerServiceProvider.php) with this code (which adds web middleware in debugbar css/js and other routes)
public function boot()
    {
        $debugbarRoutes = collect(app('router')->getRoutes()->getRoutesByName())
            ->filter(function ($value, $key) {
                return strpos($key, 'debugbar') !== false;
            });

        foreach ($debugbarRoutes as $route) {
            $action = $route->getAction();
            array_unshift($action['middleware'], 'web');
            $route->setAction($action);
        };
    }
  1. make sure that the config\app.php looks like this (Barryvdh\Debugbar\ServiceProvider must be before DebugbarEnablerServiceProvider)
'providers' => [
	...
    Barryvdh\Debugbar\ServiceProvider::class, // debugbar service provider
    App\Providers\DebugbarEnablerServiceProvider::class, // my service provider
    ...
],

PS. To use debugbar in production, you will need to set APP_DEBUG env variable to false because as written in the documentation:

Once enabled, the collectors are added (and could produce extra overhead), so if you want to use the debugbar in production, disable in the config and only enable when needed.

This method works for activating debugbar for specific IP addresses on production.

I need an advice from people who knows Laravel well, or this my provided way is safe enough. 0.0.0.0 - add your IP you want to activate debugbar

In /config/app.php: 'debug' => env('APP_DEBUG', ($_SERVER['REMOTE_ADDR'] == '0.0.0.0' or $_SERVER['REMOTE_ADDR'] == '0.0.0.0') ? true : false),

In /config/debugbar.php: 'enabled' => null,

In /.env: Remove line “APP_DEBUG=false”

We wanted to enable Debugbar in production and have the following features:

  • Controlled through a cookie, so that admins can toggle Debugbar and then log out to use it as a guest or any other user
  • Config caching should work
  • Route caching should work

Achieving this requires you to jump through a few hoops. You can not just set the APP_DEBUG environment variable because the env helper should only be used in config files when using config caching. Additionally, Debugbar requires a few routes that they add by hooking into the routing engine, which means Debugbar must be enabled when run through CLI.

0. Base config

We have Debugbar disabled by default in config/debugbar.php:

'enabled' => false,

1. Adding policy method

Who should be allowed to toggle Debugbar? Add a policy method for that. Here we chose to add it to our UserPolicy:

public function enableDebugbar(User $user, User $target) {
    return $target->isSuperAdmin();
}

2. Setting the cookie

This one is easy. Add the following route:

public function toggleDebugbar(Request $r) {
    $this->authorize('enableDebugbar', $user); // Check with UserPolicy if you are authorized to do this
    $is = $r->cookie('debugbar_enabled', false);
    if (!$is) {
        $code = Hash::make(implode(':', [
            config('app.key'), // This is secret, so that nobody else can fake this cookie
            date('Ymd'), // Force the cookie to expire tomorrow
            $r->server('REMOTE_ADDR'), // Cookie only valid for current IP
        ]));
        return redirect()->back()->withCookie(
            'debugbar_enabled', $code, 1440
        );
    } else {
        return redirect()->back()->withCookie('debugbar_enabled', null);
    }
}

This cookie must not be encrypted. The reason is that we want to read the cookie before any middlewares later (to enable Debugbar as early as possible). Open app/Http/Middleware/EncryptCookies.php and add the cookie to the $except array:

protected $except = [
    'debugbar_enabled',
];

3. Enabling Debugbar when you have the cookie

We enable Debugbar in AppServiceProvider. For us this is early enough. Add this boot() method to your AppServiceProvider:

function boot(Request $r) {
    // Enable Debugbar if special hashed cookie is set
    $cookie = $r->cookie('debugbar_enabled', false);
    $enabled = false;
    if ($cookie !== false) {
        $matches = Hash::check(implode(':', [
            config('app.key'),
            date('Ymd'),
            $r->server('REMOTE_ADDR'),
        ]), $cookie);

        if ($matches) {
            $enabled = true;
        }
    }

    if ($enabled) {
        $this->app['config']->set('debugbar.enabled', true);
    } else {
        // We have the querylog enabled so that Debugbar can collect data.
        // Disable when we don't need Debugbar
        if (config('app.environment') === 'production') {
            DB::connection()->disableQueryLog();
        }
    }
}

4. Caching Debugbar routes

To cache Debugbar routes we need to make sure it is enabled during route compilation. Debugbar is disabled in production, but we force it to be enabled in Artisan. Add this method to app/Console/Kernel.php:

// Ugly hack to cache Debugbar routes. Always enable Debugbar in
// Console mode. All it does in console mode is to register its
// routes.
public function bootstrap() {
    if (isset($_SERVER['argv']) && isset($_SERVER['argv'][1]) && $_SERVER['argv'][1] === 'route:cache') {
        $new = [];
        foreach ($this->bootstrappers as $boot) {
            if ($boot === 'Illuminate\Foundation\Bootstrap\BootProviders') {
                $new[] = 'App\Console\BootstrapDebugbar';
            }
            $new[] = $boot;
        }
        $this->bootstrappers = $new;
    }
    return parent::bootstrap();
}

Then create a file app/Console/BootstrapDebugbar.php with the following content:

<?php
namespace App\Console;

use Illuminate\Contracts\Config\Repository as Config;
use Illuminate\Foundation\Application;

class BootstrapDebugbar {
    public function bootstrap(Application $app) {
        // Enable Debugbar in Console mode. This bootstrap class is
        // run just before all services providers are booted.
        $app->config->set('debugbar.enabled', true);
    }
}

5. Ready to use!

All you need to do to use Debugbar is to visit the route you created in step 2. We added it to our menu Blade file:

@can('enableDebugbar', $user)
    <li><a href="{{route('admin::debug::toggle-debugbar')}}">Toggle Debugbar</a></li>
@endcan

I have the same issue here, and here’s my way to reillustrate:

  1. open config/debugbar.php setting storage driver to redis
  2. run php artisan config:cache
  3. refresh browser and that cute icon is gone.

But if I ran php artisan config:clear instead of php artisan config:cache , it’ll show up again. So I guess it’s maybe a integration bug with L5.1’s new feature(Config Caching)?