Builder

/laravel-agent:service:make

Create a service class or action with proper patterns

Overview

The /service:make command generates service classes or single-purpose actions following Laravel best practices. It supports native actions with a single execute() method, or can integrate with the Laravel Actions package to create actions that run as controllers, jobs, listeners, or commands.

Usage

/laravel-agent:service:make <Name> [type] [specification]

Examples

# Create a service class with multiple methods
/laravel-agent:service:make OrderProcessor

# Create a native action with single execute() method
/laravel-agent:service:make SendWelcomeEmail action

# Create Laravel Actions that can run as controller and job
/laravel-agent:service:make CreateOrder action:controller,job

# Create with specification
/laravel-agent:service:make ProcessPayment with Stripe integration

Service Types

Choose the right type for your use case:

Type Description Use Case
service Service class with multiple methods (default) Complex business logic with multiple operations
action Native action with single execute() method Single-purpose operation, simple and focused
action:controller Laravel Actions running as controller HTTP request handling with action pattern
action:job Laravel Actions running as queued job Background processing, async operations
action:listener Laravel Actions running as event listener Event-driven responses
action:command Laravel Actions running as artisan command CLI operations and scheduled tasks
action:all Laravel Actions with all contexts Maximum flexibility across all contexts

What Gets Created

Depending on the type, the command creates:

Type Location Components
service app/Services/ Service class, interface, tests
action app/Actions/{Domain}/ Native action class with execute(), tests
action:* app/Actions/{Domain}/ Laravel Actions class with traits, tests

Domain Organization

The command prompts you to organize services and actions by domain:

  • Orders - Order processing, fulfillment logic
  • Users - User management, authentication
  • Products - Product catalog, inventory
  • Payments - Payment processing, refunds
  • Notifications - Email, SMS, push notifications
  • Custom - Any domain-specific to your application

Generated Service Example

For /laravel-agent:service:make OrderProcessor:

<?php

namespace App\Services;

class OrderProcessorService
{
    public function processOrder(array $orderData): array
    {
        // Validate order data
        $this->validateOrder($orderData);

        // Calculate totals
        $totals = $this->calculateTotals($orderData);

        // Process payment
        $payment = $this->processPayment($totals);

        // Create order record
        return $this->createOrder($orderData, $payment);
    }

    protected function validateOrder(array $data): void
    {
        // Validation logic
    }

    protected function calculateTotals(array $data): array
    {
        // Calculation logic
    }

    protected function processPayment(array $totals): array
    {
        // Payment processing
    }

    protected function createOrder(array $data, array $payment): array
    {
        // Order creation
    }
}

Generated Native Action Example

For /laravel-agent:service:make SendWelcomeEmail action:

<?php

namespace App\Actions\Notifications;

use App\Models\User;
use Illuminate\Support\Facades\Mail;

class SendWelcomeEmailAction
{
    public function execute(User $user): void
    {
        Mail::to($user->email)->send(
            new WelcomeEmail($user)
        );
    }
}

Generated Laravel Actions Example

For /laravel-agent:service:make CreateOrder action:controller,job:

<?php

namespace App\Actions\Orders;

use App\Models\Order;
use Lorisleiva\Actions\Concerns\AsAction;

class CreateOrder
{
    use AsAction;

    public function handle(array $orderData): Order
    {
        // Create order logic
        return Order::create($orderData);
    }

    // As Controller
    public function asController(StoreOrderRequest $request)
    {
        $order = $this->handle($request->validated());

        return new OrderResource($order);
    }

    // As Job
    public function jobQueue(): string
    {
        return 'orders';
    }

    public function jobRetryAfter(): int
    {
        return 60;
    }
}

Usage Patterns

How to use the generated services and actions:

Service Class Usage

<?php

// Dependency injection
public function __construct(
    private OrderProcessorService $orderProcessor
) {}

// Direct usage
$result = $this->orderProcessor->processOrder($orderData);

// Via container
$result = app(OrderProcessorService::class)->processOrder($orderData);

Native Action Usage

<?php

// Dependency injection
public function __construct(
    private SendWelcomeEmailAction $sendWelcomeEmail
) {}

// Execute the action
$this->sendWelcomeEmail->execute($user);

// Via container
app(SendWelcomeEmailAction::class)->execute($user);

Laravel Actions Usage

<?php

// Direct call
$order = CreateOrder::run($orderData);

// Dispatch as job
CreateOrder::dispatch($orderData);

// Run as controller (auto-routed)
Route::post('/orders', CreateOrder::class);

// Listen to events
Event::listen(OrderCreated::class, CreateOrder::class);

Laravel Actions Integration

The command detects if lorisleiva/laravel-actions is installed by running:

composer show lorisleiva/laravel-actions

If detected, you can use action:* types to leverage Laravel Actions traits:

  • AsController - Handle HTTP requests
  • AsJob - Run as queued job
  • AsListener - Listen to events
  • AsCommand - Run as artisan command

Testing Generated Code

The command generates corresponding test files with basic test coverage:

# Run tests for specific service/action
vendor/bin/pest --filter=OrderProcessor
vendor/bin/pest --filter=SendWelcomeEmail
vendor/bin/pest --filter=CreateOrder

Best Practices

  1. Single Responsibility - Each service/action should do one thing well
  2. Use Actions for Single Operations - Prefer actions over services for focused tasks
  3. Domain Organization - Group related actions by domain (Orders, Users, etc.)
  4. Service for Coordination - Use services when orchestrating multiple actions
  5. Dependency Injection - Always inject dependencies in constructor
  6. Type Hints - Use strict typing for parameters and return values
  7. Test Coverage - Write tests for all public methods

When to Use Each Type

Use Service Classes When:

  • You need multiple related methods
  • Coordinating multiple actions or operations
  • Complex business logic with internal state
  • Need to share private helper methods

Use Native Actions When:

  • Single, focused operation
  • Simple input/output transformation
  • No need for Laravel Actions features
  • Want lightweight, straightforward code

Use Laravel Actions When:

  • Same logic needs to run in multiple contexts
  • Want to dispatch as job, handle as controller, etc.
  • Need built-in validation and authorization
  • Want to reduce boilerplate code

Related Agent

This command uses the laravel-service-builder agent.

See Also