Weave 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

Pest Plugin Inside Laravel Package

faissaloux/pest-plugin-inside

Pest plugin to run tests from inside your app’s context. Provides helpers to bootstrap Laravel or other frameworks for faster, cleaner integration-style tests without leaving Pest. Simple setup, lightweight, and aimed at improving developer ergonomics.

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup

  1. Install the package via Composer:
    composer require --dev faissaloux/pest-plugin-inside
    
  2. Ensure compatibility with your Pest version (check requirements in the README).
  3. First use case: Validate a single PHP file’s return array for lowercase keys:
    // tests/Feature/LowercaseKeysTest.php
    use Faissaloux\PestPluginInside\Inside;
    
    it('has lowercase keys in config file', function () {
        expect('config/app.php')->toReturnLowercase();
    });
    

Key Starting Points

  • Supported files: PHP, TXT, and stub files (e.g., Blade stubs, migration stubs).
  • Directory scanning: Use expect('path/to/directory')->toReturnLowercase() to validate all files recursively.
  • Depth control: Limit recursion with depth():
    expect('stubs')->toReturnUnique(depth: 1);
    

Implementation Patterns

Common Workflows

1. Enforcing Configuration Standards

Validate Laravel config files, service provider return arrays, or migration stubs:

// tests/Feature/ConfigValidationTest.php
it('enforces lowercase keys in app config', function () {
    expect('config/app.php')->toReturnLowercase()->toReturnStrings();
});

2. Directory-Wide Validation

Scan all PHP files in a directory (e.g., database/migrations) for consistent formatting:

it('validates all migration stubs', function () {
    expect('database/migrations')->toReturnSingleWords()->forbidEmpty();
});

3. Combining Assertions

Chain multiple expectations for complex rules:

it('validates API response stubs', function () {
    expect('stubs/responses')->toReturnLowercase()
                             ->toBeOrdered()
                             ->toReturnUnique();
});

4. Text File Validation

Validate non-PHP files (e.g., .env.example, README.md snippets):

it('ensures README has no empty lines', function () {
    expect('README.md')->forbidEmpty();
});

5. Integration with Pest Plugins

Combine with other Pest plugins (e.g., pest-plugin-laravel) to validate both file content and application behavior:

it('validates config and routes', function () {
    expect('config/routes.php')->toReturnLowercase();
    // ... other Laravel-specific tests
});

Integration Tips

Laravel-Specific Use Cases

  • Migration Files: Validate stub templates in database/migrations:
    it('ensures migration stubs use lowercase columns', function () {
        expect('database/migrations/stubs')->toReturnLowercase();
    });
    
  • Service Providers: Check return arrays in AppServiceProvider:
    it('validates AppServiceProvider bindings', function () {
        expect('app/Providers/AppServiceProvider.php')->toReturnStrings();
    });
    
  • Factories/Models: Validate factory definitions or model constants:
    it('ensures model constants are uppercase', function () {
        expect('app/Models/User.php')->toReturnUppercase();
    });
    

CI/CD Optimization

  • Pre-commit Hooks: Use the plugin in CI to fail fast on formatting issues:
    # .github/workflows/test.yml
    jobs:
      test:
        steps:
          - run: composer test
          - run: composer test -- --filter "file content validation"
    
  • Parallel Testing: Group file validation tests to run in parallel with other suites.

Custom Extensions

  • Extend for Custom Rules: Override the Investigator class to add project-specific validations (see Gotchas for extension points).

Gotchas and Tips

Pitfalls

  1. File Path Resolution:

    • Issue: Relative paths (e.g., config/app.php) are resolved from the test file’s directory, not the project root.
    • Fix: Use absolute paths or base_path():
      expect(base_path('config/app.php'))->toReturnLowercase();
      
  2. Windows Line Endings:

    • Issue: Text file validation may fail on Windows due to \r\n line endings.
    • Fix: Use toReturnStrings() to normalize line breaks or preprocess files in tests.
  3. Nested Array Depth:

    • Issue: Deeply nested arrays may not be fully validated if the plugin’s recursion limit is hit.
    • Fix: Test incrementally or increase recursion depth in the plugin’s source (see extension points).
  4. Case-Sensitive Filesystems:

    • Issue: On case-insensitive filesystems (e.g., macOS), toReturnLowercase() may pass unexpectedly.
    • Fix: Combine with toReturnUnique() or add custom assertions.
  5. Performance:

    • Issue: Scanning large directories (e.g., app/) can slow down test suites.
    • Fix: Limit depth or scope tests to specific directories (e.g., stubs/).

Debugging Tips

  1. Verbose Failures:

    • The plugin highlights the exact file and line where validation fails. Example output:
      Failed asserting that 'config/app.php' returns lowercase values.
      Found non-lowercase: 'CaSe' at line 5.
      
  2. Isolate Tests:

    • Test one file/directory at a time to diagnose issues:
      it('debugs a single file', function () {
          expect('config/app.php')->toReturnLowercase()->dump(); // Show raw content
      });
      
  3. Skip Non-Critical Files:

    • Use depth: 0 to exclude subdirectories temporarily:
      expect('config')->toReturnLowercase(depth: 0);
      

Extension Points

Custom Assertions

Extend the plugin by creating a custom Investigator class:

// app/Extensions/CustomInvestigator.php
namespace App\Extensions;

use Faissaloux\PestPluginInside\Investigator;

class CustomInvestigator extends Investigator
{
    public function toReturnNoDuplicates(): void
    {
        $this->assertNoDuplicates($this->getContent());
    }
}

Register it in Pest.php:

uses(App\Extensions\CustomInvestigator::class)->in('tests');

Preprocessing Files

Override the getContent() method to transform files before validation:

protected function getContent(): array
{
    $content = parent::getContent();
    return array_map('strtolower', $content); // Force lowercase for testing
}

Supported File Types

Add support for new file types (e.g., .env):

// Override in custom Investigator
protected function isSupportedFile(string $path): bool
{
    return parent::isSupportedFile($path) || str_ends_with($path, '.env');
}

Pro Tips

  1. Living Documentation: Use the plugin’s assertions as executable specs for file formats. Example:

    // tests/Feature/StubFormatTest.php
    it('documents expected stub format', function () {
        // This test serves as both validation and documentation.
        expect('stubs/mailables')->toReturnLowercase()
                                 ->toReturnSingleWords()
                                 ->toBeOrdered();
    });
    
  2. Dynamic Paths: Use Laravel’s helpers to generate dynamic paths:

    expect(resource_path('views/emails/*.blade.php'))->toReturnLowercase();
    
  3. Exclude Files: Skip specific files/directories by filtering paths:

    it('validates all except vendor files', function () {
        $files = glob('src/**/*.php');
        foreach ($files as $file) {
            if (str_contains($file, 'vendor')) continue;
            expect($file)->toReturnStrings();
        }
    });
    
  4. Combine with PHPStan: Use the plugin alongside PHPStan to catch both runtime and static analysis issues:

    composer test && composer stan
    
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.
coleus/frame
thtg88/journalism
filagora/filagora-ai-forums
rlacerda83/query-parser
socialdept/atp-orm
cboxdk/laravel-assistant-client
socialdept/atp-resolver
socialdept/tenant-domains
tautvydasr/blade-class-names
socialdept/color-scales
maherelgamil/controller
coleus/widgets
coleus/table
coleus/users
coleus/music
coleus/health
coleus/calendar
coleus/notes
coleus/support
coleus/settings