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

Dependency Injection Laravel Package

draw/dependency-injection

Add-ons for Symfony DependencyInjection to simplify integrating subcomponents into a main bundle. Provides Integration classes and traits to auto-register integrations, load enabled configuration, and prepend container configuration when components are installed.

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Steps

  1. Installation:

    composer require draw/dependency-injection
    

    Add the package to your composer.json dependencies.

  2. First Use Case:

    • Use the IntegrationTrait in your bundle’s DependencyInjection extension to integrate subcomponents.
    • Example: Extend a base bundle (e.g., DrawFrameworkExtraBundle) by integrating smaller components (e.g., MyComponent, MyOtherComponent).
  3. Key Files to Review:

    • IntegrationTrait (for bundle integration logic).
    • ExtendableExtensionTrait (for extending Symfony’s ContainerBuilder).
    • Component-specific integration classes (e.g., MyComponentIntegration).

Implementation Patterns

Core Workflow

  1. Define Component Integrations:

    • In your main bundle’s DependencyInjection extension, list subcomponent integrations in provideExtensionClasses().
    • Example:
      protected function provideExtensionClasses(): array {
          return [
              MyComponentIntegration::class,
              MyOtherComponentIntegration::class,
          ];
      }
      
  2. Automatic Registration:

    • Call registerDefaultIntegrations() in the bundle’s constructor to auto-load integrations.
    • The trait handles instantiation and validation of integration classes.
  3. Configuration Handling:

    • Use loadIntegrations() to process subcomponent configs only if enabled: true.
    • Example YAML:
      example_my_bundle:
          my_component:
              enabled: true
              # Component-specific config
      
  4. Service Prepending:

    • Use prependIntegrations() to modify the container before your bundle’s services are loaded.
    • Example:
      public function prepend(ContainerBuilder $container): void {
          $this->prependIntegrations($container, 'example_my_bundle');
      }
      

Integration Tips

  • Modular Bundles: Ideal for splitting large bundles into smaller, reusable components (e.g., AuthBundle, CacheBundle).
  • Conditional Loading: Disable components via YAML (enabled: false) to avoid conflicts or reduce overhead.
  • Configuration Inheritance: Subcomponents can extend the main bundle’s configuration by overriding getConfiguration().

Gotchas and Tips

Pitfalls

  1. Circular Dependencies:

    • If subcomponents depend on each other, ensure prependIntegrations() order matches dependency resolution.
    • Fix: Explicitly order integrations in provideExtensionClasses().
  2. Missing Integration Classes:

    • The trait silently skips non-existent classes. Verify with:
      if (!class_exists(MyComponentIntegration::class)) {
          throw new \RuntimeException('Integration class missing!');
      }
      
  3. Configuration Overrides:

    • Subcomponent configs merge with the main bundle’s config. Use parent::load() carefully to avoid overwrites.
  4. Namespace Collisions:

    • Ensure subcomponent integration classes have unique namespaces (e.g., Example\Component\Auth\DependencyInjection\AuthIntegration).

Debugging

  • Check Loaded Integrations:
    var_dump($this->integrations); // Inspect registered integrations in `load()`.
    
  • Enable Debug Mode: Symfony’s ContainerBuilder logs service modifications. Use:
    $container->setDebug(true);
    

Extension Points

  1. Custom Integration Logic:

    • Override loadIntegrations() to add pre/post-processing (e.g., validation).
    protected function loadIntegrations(array $configs, ContainerBuilder $container): array {
        $config = parent::loadIntegrations($configs, $container);
        // Custom logic here
        return $config;
    }
    
  2. Dynamic Component Discovery:

    • Use Composer\Autoload\ClassLoader to auto-discover integrations in provideExtensionClasses():
    $loader = new \Composer\Autoload\ClassLoader();
    $loader->addPsr4('Example\Component\\', __DIR__.'/../../../vendor');
    $integrationClasses = $loader->findFiles('*Integration');
    
  3. Environment-Specific Configs:

    • Load integrations conditionally based on environment variables:
    if ($_ENV['APP_ENV'] === 'prod') {
        $this->integrations[] = new ProdOptimizationIntegration();
    }
    
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.
yandex/translate-api
voku/simple_html_dom
league/flysystem-vfs
bkwld/upchuck
filament/spatie-laravel-tags-plugin
capell-app/block-library
axium/identity
cetria/laravel-dummy-models
cetria/reflection-helper
agropredict/sso-auth-bundle
evolvestudio/spam-protection
datacore/hub-sdk
develia/commons
cuci/prototurk-sdk
cuci/prototurk-sdk-symfony
develia/geo-bundle
dreamzy/livewire-charts
touchestate-sdk/php-sdk
22h/doctrine-garbage-collection-bundle
agtp/agtp-php