massive/build-bundle
Symfony bundle providing a massive:build command to run tagged build targets. Define virtual targets in config, declare dependencies between targets, and implement builders to execute custom environment/setup steps—ideal for chaining app-specific commands in development.
Install the Package:
composer require massive/build-bundle
For Laravel, ensure compatibility by adding to config/app.php under providers:
Massive\Bundle\BuildBundle\MassiveBuildBundle::class,
Register a Basic Builder:
Create a builder class implementing BuilderInterface:
namespace App\Builders;
use Massive\Bundle\BuildBundle\Build\BuilderInterface;
use Massive\Bundle\BuildBundle\Build\BuilderContext;
class DatabaseBuilder implements BuilderInterface
{
public function getName() { return 'database'; }
public function getDependencies() { return []; }
public function build() { artisan('migrate:fresh'); }
public function setContext(BuilderContext $context) {}
}
Tag the Builder in DI:
In config/services.php (Laravel) or resources/config/services.xml (Symfony):
<service id="app.database_builder" class="App\Builders\DatabaseBuilder">
<tag name="massive_build.builder" />
</service>
Run the Build:
php artisan massive:build database
Automate Laravel Environment Setup:
Define a dev target in config/massive_build.php:
'massive_build' => [
'targets' => [
'dev' => [
'dependencies' => ['database', 'assets', 'fixtures'],
],
],
],
Then run:
php artisan massive:build dev
This executes migrations, compiles assets, and loads fixtures in order.
Dependency Chaining:
FixturesBuilder depends on DatabaseBuilder).--nodeps to skip dependencies for debugging:
php artisan massive:build fixtures --nodeps
Configuration-Driven Targets:
config/massive_build.php to group builders:
'targets' => [
'deploy' => ['database', 'assets', 'cache:clear'],
'test' => ['database:refresh', 'tests:run'],
],
php artisan massive:build deploy
Context Utilization:
BuilderContext:
public function build()
{
$this->context->get('cache')->clear();
}
Laravel Artisan Integration:
Use artisan() helper in builders to run Laravel commands:
public function build() { artisan('queue:work'); }
Symfony Console Commands:
Extend BuildCommand to add project-specific options:
class CustomBuildCommand extends BuildCommand
{
protected function configure()
{
$this->addOption('force', null, InputOption::VALUE_NONE, 'Force rebuild');
}
}
Register in config/services.php:
Massive\Bundle\BuildBundle\Command\BuildCommand::class => App\Commands\CustomBuildCommand::class,
CI/CD Pipelines: Use targets for environment-specific builds:
# .github/workflows/build.yml
jobs:
build:
runs-on: ubuntu-latest
steps:
- run: php artisan massive:build test
Service Container Access: Resolve Laravel services in builders:
public function build()
{
$mailer = $this->context->get('mailer');
$mailer->send(...);
}
Artisan Command Wrapping: Create builders for complex Artisan workflows:
class QueueWorkerBuilder implements BuilderInterface
{
public function build()
{
artisan('queue:work --once');
}
}
Environment Awareness:
Use app()->environment() in builders to conditionally execute steps:
public function build()
{
if (app()->environment('local')) {
artisan('tinker');
}
}
Circular Dependencies:
--nobuild to inspect dependencies:
php artisan massive:build --nobuild
Builder Context Not Injected:
setContext() leads to NullContextException.public function setContext(BuilderContext $context) { $this->context = $context; }
Symfony/Laravel Service Mismatch:
BuilderContext:
$this->context->has('service.id') ? $this->context->get('service.id') : null;
Exit Code Handling:
--keep-exit-code to preserve failure states:
php artisan massive:build --keep-exit-code
Verbose Output: Enable debug mode for detailed logs:
php artisan massive:build --verbose
Builder Isolation:
Test builders in isolation by using --nodeps:
php artisan massive:build mybuilder --nodeps
Dependency Graph:
Visualize dependencies with --nobuild:
php artisan massive:build --nobuild
Output:
+---+----------+--------------------+
| # | Builder | Deps |
+---+----------+--------------------+
| 0 | database | |
| 1 | fixtures | database |
+---+----------+--------------------+
Custom Build Command:
Override BuildCommand to add project-specific logic:
class AppBuildCommand extends BuildCommand
{
protected function execute(InputInterface $input, OutputInterface $output)
{
if ($input->getOption('custom-flag')) {
// Custom logic
}
parent::execute($input, $output);
}
}
Dynamic Builders: Register builders dynamically via events:
use Symfony\Component\HttpKernel\KernelEvents;
use Symfony\Component\EventDispatcher\EventSubscriberInterface;
class BuilderSubscriber implements EventSubscriberInterface
{
public static function getSubscribedEvents()
{
return [KernelEvents::BOOT => 'registerBuilders'];
}
public function registerBuilders()
{
$container->register('dynamic_builder', DynamicBuilder::class)
->addTag('massive_build.builder');
}
}
Builder Factories: Use factories to conditionally create builders:
class BuilderFactory
{
public function create(string $name): BuilderInterface
{
return match ($name) {
'database' => new DatabaseBuilder(),
'assets' => new AssetBuilder(),
default => throw new \RuntimeException("Unknown builder: $name"),
};
}
}
Artisan Command Conflicts:
massive:build may conflict with custom Artisan commands.BuildCommand:
$this->setName('app:build');
Service Provider Registration:
MassiveBuildBundle is loaded before your app’s providers in config/app.php.Laravel Mix Integration:
public function build()
{
artisan('mix');
}
Avoid Heavy Operations:
composer install) block the CLI.--timeout in Symfony.Caching Builders:
$container->register('cached_builder', function () {
return new CachedBuilder($container->get('cache'));
});
Parallelization:
ParallelCommand to run independent builders concurrently (requires custom integration).How can I help you explore Laravel packages today?