Weave Code
Code Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Testbench Dusk Laravel Package

orchestra/testbench-dusk

Helper for testing Laravel packages with Laravel Dusk. Provides a Testbench-based setup to run browser tests in a package development workflow, maintained under the Orchestra namespace with ongoing support and community contributions.

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup

  1. Install Dependencies Add to your package's composer.json:

    "require-dev": {
        "orchestra/testbench-dusk": "^11.0",
        "laravel/dusk": "^8.5",
        "phpunit/phpunit": "^12.0"
    }
    

    Run composer update in your package directory.

  2. Configure Dusk Publish the Dusk config (if using Laravel Dusk):

    php artisan vendor:publish --provider="Laravel\Dusk\DuskServiceProvider" --tag="dusk-config"
    

    Ensure DUSK_BROWSER is set in .env.testing (e.g., chrome).

  3. First Test Case Create a test class extending Orchestra\Testbench\DuskTestCase:

    use Orchestra\Testbench\DuskTestCase;
    
    class ExampleDuskTest extends DuskTestCase
    {
        public function test_example()
        {
            $this->browse(function ($browser) {
                $browser->visit('/')
                        ->assertSee('Welcome');
            });
        }
    }
    

    Run tests with:

    phpunit
    
  4. Package Integration Use withPackage() to load your package in tests:

    protected function getPackageProviders($app)
    {
        return ['YourPackage\\ServiceProvider'];
    }
    

Implementation Patterns

Core Workflows

  1. Isolated Package Testing

    • Use beforeServingApplication() to mock dependencies or configure the app:
      protected function beforeServingApplication($app)
      {
          $app['config']->set('your-package.key', 'value');
      }
      
    • Reset state with afterServingApplication():
      protected function afterServingApplication($app)
      {
          $app['config']->set('your-package.key', null);
      }
      
  2. Dusk-Specific Helpers

    • Browser Management: Leverage Dusk’s built-in methods (e.g., click(), assertPathIs(), pause(5000)).
    • Package-Specific Assertions: Create custom assertions for package features:
      $browser->assertSeeInPackageView('your-package::partial', 'Expected Text');
      
  3. Test Data Setup

    • Use create() or factory() from Testbench to seed test data:
      $this->browse(function ($browser) use ($user) {
          $browser->loginAs($user)
                  ->visit('/dashboard');
      });
      
  4. Cross-Browser Testing

    • Configure multiple browsers in phpunit.xml:
      <env name="DUSK_BROWSER" value="chrome|firefox"/>
      
  5. CI/CD Integration

    • Use DUSK_HEADLESS=true in CI for faster tests:
      DUSK_HEADLESS=true phpunit --filter=DuskTest
      

Integration Tips

  1. Testbench + Dusk Synergy

    • Combine Testbench’s migrate() and artisan() with Dusk’s browser interactions:
      $this->artisan('migrate:fresh')
          ->browse(function ($browser) {
              $browser->visit('/admin')
                      ->assertPathIs('/admin');
          });
      
  2. Package-Specific Dusk Commands

    • Extend Dusk’s Browser class for package-specific actions:
      namespace YourPackage\Dusk;
      
      use Laravel\Dusk\Browser;
      
      class PackageBrowser extends Browser
      {
          public function triggerPackageAction()
          {
              $this->click('@package-button');
          }
      }
      
  3. Mocking External Services

    • Use Testbench’s Mockery or Http::fake() within Dusk tests:
      $this->browse(function ($browser) {
          Http::fake([
              'api.example.com/*' => Http::response('Mocked', 200),
          ]);
          $browser->visit('/api-dependent-page');
      });
      
  4. Parallel Testing

    • Split Dusk tests across CI workers using PHPUnit’s --group flag:
      phpunit --group=auth --parallel
      

Gotchas and Tips

Pitfalls

  1. Headless Mode Quirks

    • Issue: Tests may fail in headless mode due to missing visual cues (e.g., assertSee for dynamic content).
    • Fix: Use pause(5000) or waitFor() for critical interactions:
      $browser->waitFor('.loader', 10)->assertMissing('.loader');
      
  2. Browser Driver Conflicts

    • Issue: ChromeDriver/FirefoxDriver version mismatches cause tests to hang.
    • Fix: Pin versions in composer.json or use Laravel’s dusk:driver command to auto-download:
      php artisan dusk:driver
      
  3. State Persistence

    • Issue: Shared state (e.g., sessions) between tests can cause flakiness.
    • Fix: Use refresh() or withoutMiddleware() for isolated tests:
      $this->browse(function ($browser) {
          $browser->withoutMiddleware()->visit('/');
      });
      
  4. Package Loading Order

    • Issue: Tests fail if package providers aren’t loaded before Dusk boots.
    • Fix: Ensure getPackageProviders() returns all required providers, including Laravel’s DuskServiceProvider.
  5. Deprecated Methods

    • Issue: tweakApplication() is deprecated; use beforeServingApplication() instead.
    • Fix: Update tests to use the new lifecycle methods (see release notes).

Debugging Tips

  1. Visual Debugging

    • Enable Dusk’s screenshot on failure:
      $this->browse(function ($browser) {
          $browser->screenshot('debug-failed-test');
      });
      
    • Configure in phpunit.xml:
      <env name="DUSK_SCREENSHOTS" value="true"/>
      
  2. Log Output

    • Capture browser logs for debugging:
      $browser->driver->manage()->logs('browser')->get('available');
      
  3. Slow Tests

    • Profile test execution with Xdebug or --stop-on-failure:
      phpunit --stop-on-failure --verbose
      

Extension Points

  1. Custom Dusk Traits

    • Create reusable traits for package-specific Dusk logic:
      trait PackageDuskTrait
      {
          protected function loginAsPackageAdmin($browser)
          {
              $browser->visit('/login')
                      ->type('email', 'admin@example.com')
                      ->type('password', 'password')
                      ->press('Login');
          }
      }
      
  2. Dusk Service Providers

    • Extend Laravel’s DuskServiceProvider to register package-specific Dusk commands or macros:
      namespace YourPackage\Dusk;
      
      use Laravel\Dusk\DuskServiceProvider as BaseProvider;
      
      class DuskServiceProvider extends BaseProvider
      {
          public function boot()
          {
              $this->macro('assertPackageFeature', function () {
                  // Custom assertion logic
              });
          }
      }
      
  3. Test Data Factories

    • Use Testbench’s create() with Dusk for consistent test data:
      $user = create(User::class, ['email' => 'test@example.com']);
      $this->browse(function ($browser) use ($user) {
          $browser->loginAs($user);
      });
      
  4. Environment-Specific Config

    • Override Dusk settings per environment (e.g., DUSK_TIMEOUT):
      if (app()->environment('testing')) {
          $this->browse(function ($browser) {
              $browser->driver->manage()->timeouts()->implicitWait(2);
          });
      }
      

Pro Tips

  • Test Isolation: Use refresh() or withoutMiddleware() to avoid test pollution.
  • Performance: Run Dusk tests in CI with --group=dusk and cache dependencies.
  • Documentation: Add @dusk tags to test methods for clarity:
    /**
     * @dusk Tests the package's admin dashboard.
     */
    public function test_admin_dashboard() { ... }
    
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
hamzi/corewatch
minionfactory/raw-hydrator
hexters/coinpayment
rjcodes/rjcms
act-training/laravel-permissions-manager
alimarchal/laravel-chart-of-accounts
babenkoivan/elastic-scout-driver
mkwebdesign/filament-watchdog-v5
renatomarinho/laravel-page-speed
zedmagdy/filament-business-hours
renatovdemoura/blade-elements-ui
devgeek/beacon-admin
benjamin-rqt/data-watcher-bundle
atriumphp/atrium
sandermuller/package-boost-laravel
sandermuller/boost-skills
redaxo/core
yusufgenc/filament-api-forge
l3aro/rating-star-for-filament
leek/filament-subtenant-scope