Laravel

Run Shell Commands with Laravel's Process Facade

Run Shell Commands with Laravel's Process Facade

Execute external commands with built-in timeouts.

  • 16 Oct, 2026
  • 1 Views

Run Shell Commands with Laravel's Process Facade

Sometimes a Laravel application needs to run an external command, such as generating a PDF, processing an image, or executing a maintenance script.

Instead of using PHP's exec() or shell_exec() directly, Laravel provides the Process facade.

Execute a Command

use Illuminate\Support\Facades\Process;

$result = Process::run('php --version');

if ($result->successful()) {
    $output = $result->output();
}

Laravel returns a process result that lets you inspect whether the command succeeded, its output, and its exit code.

Set a Timeout

External commands can take longer than expected. You can specify how long Laravel should wait:

$result = Process::timeout(30)
    ->run('php artisan about');

Here, the process has a 30-second timeout. Laravel's default process timeout is 60 seconds.

Handle Command Failures

You can make Laravel throw an exception when a command fails:

$result = Process::run('php artisan about')
    ->throw();

If the process exits unsuccessfully, throw() raises an exception rather than letting the failure go unnoticed.

Real-World Example

Imagine you have a script that generates a report:

$result = Process::path(base_path())
    ->timeout(120)
    ->run('php scripts/generate-report.php');

if ($result->failed()) {
    logger()->error('Report generation failed', [
        'error' => $result->errorOutput(),
    ]);
}

This runs the script from your project directory, limits execution time, and logs the error output if it fails.

When Should You Use It?

  • Running external scripts
  • Image or document processing
  • Invoking command-line utilities
  • Integrating tools that don't have PHP libraries
  • Running controlled maintenance tasks

Important Security Note

Never concatenate untrusted user input into shell commands. Validate inputs carefully and prefer fixed commands with controlled arguments.

Also, if a task should run independently of the web request, consider dispatching a queued job instead of running a long process inside a controller.

Share: