Laravel Concurrency Facade &amp; Process Pools | Mohamed Said       [Skip to content](#main)  [ ![](https://cdn.msaied.com/01KT78WE565VEMM3PSNQAAB0MH.png) Mohamed SaidLaravel Backend Engineer ](https://msaied.com/public) - [Home](https://msaied.com/public)
- [Projects](https://msaied.com/public/projects)
- [Articles](https://msaied.com/public/articles)
- [Certificates](https://msaied.com/public/certificates)
- [About](https://msaied.com/public#about)

           [  Contact](https://msaied.com/public#contact) Menu 

Menu
----

Close 

 - [HomeStart here](https://msaied.com/public)
- [ProjectsCase studies](https://msaied.com/public/projects)
- [ArticlesEngineering notes](https://msaied.com/public/articles)
- [CertificatesCredentials](https://msaied.com/public/certificates)
- [AboutHow I work](https://msaied.com/public#about)
- [ContactGet in touch](https://msaied.com/public#contact)

  [Start a conversation](https://msaied.com/public#contact) [WhatsApp](https://wa.me/201094619204) [Email](mailto:hello@msaied.com) 

 1. [Home](https://msaied.com/public)
2. /
3. [Articles](https://msaied.com/public/articles)
4. /
5. Laravel Concurrency Facade and Process Pools for Parallel Work

 Laravel Concurrency Facade and Process Pools for Parallel Work
===============================================================

 The Concurrency facade and Process pools let Laravel apps run independent tasks in parallel without a queue. Learn when to use each, how to avoid shared-state bugs, and practical patterns for real workloads.

 ![](https://cdn.msaied.com/01M22N44A70A5MC2S599JP0MPH.webp) [Mohamed Said](https://msaied.com/public#person) Published 23 Jun 2026 · Updated 23 Jun 2026 · 4 min read

ShareCopy linkCopied

 ![Laravel Concurrency Facade and Process Pools for Parallel Work](https://cdn.msaied.com/270/db82ee6bc3f93eb77d90dfaf7e731bfd.png) 

  On this page +1. [Why Parallel Execution Matters in a Synchronous Framework](#why-parallel-execution-matters-in-a-synchronous-framework)
2. [The Concurrency Facade](#the-concurrency-facade)
3. [Choosing the Right Driver](#choosing-the-right-driver)
4. [Deferring Work with Concurrency::defer()](#deferring-work-with-codeconcurrencydefercode)
5. [Process Pools for Shell-Level Parallelism](#process-pools-for-shell-level-parallelism)
6. [Timeout and Error Handling](#timeout-and-error-handling)
7. [Common Pitfalls](#common-pitfalls)
8. [Key Takeaways](#key-takeaways)

 Why Parallel Execution Matters in a Synchronous Framework
---------------------------------------------------------

Laravel's default request lifecycle is synchronous. When you need to call three external APIs before returning a response, you pay the latency of each call sequentially. The `Concurrency` facade (introduced in Laravel 11) and the `Process` facade's pool API give you two distinct escape hatches — without reaching for a queue or a dedicated worker.

Understanding *when* to use each is the real skill.

---

The Concurrency Facade
----------------------

`Illuminate\Support\Facades\Concurrency` runs closures in parallel using PHP's `fork` driver (via `ext-pcntl`) or a `fiber` driver. The fork driver is the default in CLI contexts; the fiber driver is safer in long-lived Octane workers.

```php
use Illuminate\Support\Facades\Concurrency;

[$users, $orders, $metrics] = Concurrency::run([
    fn () => User::active()->count(),
    fn () => Order::pendingShipment()->count(),
    fn () => app(MetricsService::class)->summary(),
]);

```

Each closure runs in isolation. With the fork driver, each closure executes in a child process — **no shared memory, no shared Eloquent connections**. Results are serialized back to the parent via a pipe.

### Choosing the Right Driver

```php
// config/concurrency.php (publish with: php artisan vendor:publish)
'default' => env('CONCURRENCY_DRIVER', 'fork'),

```

| Driver | Safe in Octane | Shared DB connection | Overhead | |--------|---------------|----------------------|----------| | `fork` | ⚠️ No (forks worker) | No — child gets copy | ~5–15 ms per fork | | `fiber` | ✅ Yes | Yes — same process | Minimal |

The fiber driver is cooperative, not truly parallel. Use it when tasks are I/O-bound and you control the event loop (e.g., with ReactPHP or Swoole). For CPU-bound or truly independent work, `fork` wins.

### Deferring Work with `Concurrency::defer()`

```php
Concurrency::defer([
    fn () => Cache::put('report:daily', $this->buildReport(), 3600),
    fn () => $this->notifySlack(),
]);
// Returns immediately; tasks run after the response is sent (fork driver only)

```

This is a lightweight alternative to dispatching a job when you don't need retry logic.

---

Process Pools for Shell-Level Parallelism
-----------------------------------------

When the work lives outside PHP — running shell commands, calling CLIs, spawning scripts — the `Process` facade's pool API is the right tool.

```php
use Illuminate\Support\Facades\Process;

$pool = Process::pool(function ($pool) {
    $pool->command('php artisan export:region --region=eu');
    $pool->command('php artisan export:region --region=us');
    $pool->command('php artisan export:region --region=apac');
})->start(function ($type, $output, $key) {
    logger()->info("Process {$key}: {$output}");
});

$results = $pool->wait();

foreach ($results as $key => $result) {
    if ($result->failed()) {
        throw new \RuntimeException("Export {$key} failed: " . $result->errorOutput());
    }
}

```

Process pools are ideal for:

- Running multiple Artisan commands in parallel during a deployment step
- Parallel data exports or imports
- Shelling out to Python/Node scripts alongside PHP work

### Timeout and Error Handling

```php
$pool = Process::pool(function ($pool) {
    $pool->timeout(30)->command('vendor/bin/phpstan analyse src/');
    $pool->timeout(30)->command('vendor/bin/pest --parallel');
})->start();

$results = $pool->wait();

```

Each process in the pool gets its own timeout. A single failure does not kill the pool — inspect each `$result` individually.

---

Common Pitfalls
---------------

**1. Database connections in forked processes.** The fork driver copies the parent's file descriptors. Reconnect inside the closure or use `DB::purge()` at the top of each child.

```php
Concurrency::run([
    function () {
        DB::reconnect(); // safe in forked child
        return Order::count();
    },
]);

```

**2. Serialization limits.** Closures passed to `Concurrency::run()` are serialized with `opis/closure`. Avoid binding large objects; pass IDs and re-query inside.

**3. Octane state leakage.** Never use the fork driver inside an Octane worker. The forked child inherits the entire worker state. Use the fiber driver or dispatch a job instead.

---

Key Takeaways
-------------

- Use `Concurrency::run()` for parallel PHP closures; pick `fork` for isolation, `fiber` for Octane safety.
- Use `Process::pool()` when the parallel work is shell commands or external processes.
- Always reconnect database handles in forked children.
- Avoid passing large objects into closures — pass IDs and hydrate inside.
- `Concurrency::defer()` is a zero-queue fire-and-forget for post-response work.

- [laravel](https://msaied.com/public/articles?search=laravel)
- [concurrency](https://msaied.com/public/articles?search=concurrency)
- [performance](https://msaied.com/public/articles?search=performance)
- [php](https://msaied.com/public/articles?search=php)

 Frequently asked questions 
---------------------------

  Can I use the Concurrency facade inside a Livewire component or Octane request?Use the fiber driver in Octane contexts. The fork driver forks the entire worker process, which corrupts Octane's long-lived state. Set CONCURRENCY\_DRIVER=fiber in your Octane environment, and note that fiber concurrency is cooperative, not truly parallel.

   How does Concurrency::run() differ from dispatching multiple queued jobs?Concurrency::run() blocks until all tasks complete and returns results inline — no queue infrastructure needed. Queued jobs are fire-and-forget with retry logic and Horizon visibility. Use Concurrency for latency-sensitive, in-request parallelism; use queues for durable, retriable background work.

   Is Process::pool() suitable for production use or just local tooling?It is production-ready. Laravel's Process facade wraps Symfony Process, which is battle-tested. Process pools are commonly used in deployment scripts, data pipeline commands, and scheduled tasks that benefit from parallelism without queue overhead.

   ![Mohamed Said](https://cdn.msaied.com/01M22N44A70A5MC2S599JP0MPH.webp)About the author
----------------

[Mohamed Said](https://msaied.com/public#person)Senior Backend Engineer specializing in Laravel, scalable SaaS platforms, APIs, and cloud infrastructure. I build secure, high-performance web applications that help businesses grow.

[About](https://msaied.com/public#about) [GitHub ↗](https://github.com/EG-Mohamed) [LinkedIn ↗](https://www.linkedin.com/in/msaiedm/) [WhatsApp ↗](https://wa.me/201094619204) [Email Address ↗](mailto:hello@msaied.com) [My CV ↗](https://drive.google.com/file/u/0/d/1MF20IPRJyzfy32mhEutjL5EpSls0w2Q8/view)  

   [Previous articleShowcase Your PhpStorm Expertise on LinkedIn with JetBrains' New Plugin](https://msaied.com/public/articles/showcase-your-phpstorm-expertise-on-linkedin-with-jetbrains-new-plugin) [Next articleMonitor and Control Schedules, Queues, and Errors in Laravel with Watchtower](https://msaied.com/public/articles/monitor-and-control-schedules-queues-and-errors-in-laravel-with-watchtower)  

   On this page
-------------

1. [Why Parallel Execution Matters in a Synchronous Framework](#why-parallel-execution-matters-in-a-synchronous-framework)
2. [The Concurrency Facade](#the-concurrency-facade)
3. [Choosing the Right Driver](#choosing-the-right-driver)
4. [Deferring Work with Concurrency::defer()](#deferring-work-with-codeconcurrencydefercode)
5. [Process Pools for Shell-Level Parallelism](#process-pools-for-shell-level-parallelism)
6. [Timeout and Error Handling](#timeout-and-error-handling)
7. [Common Pitfalls](#common-pitfalls)
8. [Key Takeaways](#key-takeaways)

 ###  Have a technical challenge?

 Tell me what you’re building. I reply within two working days.

[Start a conversation](https://msaied.com/public#contact) 

   Related articles
-----------------

 [ ![](https://cdn.msaied.com/745/8744e1be5136b430da52e9fca3ed3964.png)  · 3 min read### Service Container Deep Dive: Contextual Binding, Tagging, and Method Injection

6 Oct 2026 ](https://msaied.com/public/articles/service-container-deep-dive-contextual-binding-tagging-and-method-injection-1) [ ![](https://cdn.msaied.com/743/8998fac3a41451ab3fe1588194e17a43.png) Filament · 3 min read### Securing Filament Plugins with Plumb: Automated Security Scoring for PHP Packages

5 Oct 2026 ](https://msaied.com/public/articles/securing-filament-plugins-with-plumb-automated-security-scoring-for-php-packages) [ ![](https://cdn.msaied.com/742/2d02018669cdeedccb5de2efb898f0ee.png) Filament · 3 min read### Filament v3.3.56 Released: File Hash Names and Livewire Upload Fix

5 Oct 2026 ](https://msaied.com/public/articles/filament-v3356-released-file-hash-names-and-livewire-upload-fix) 

  Have a technical challenge?
----------------------------

Tell me what you’re building. I reply within two working days.

 [Discuss your project ↗](https://msaied.com/public#contact) 

  © 2026 Mohamed Said · Built with Laravel, meant to last.Senior Backend Engineer specializing in Laravel, scalable SaaS platforms, APIs, and cloud infrastructure. I build secure, high-performance web applications that help businesses grow.

 - [Home](https://msaied.com/public)
- [Articles](https://msaied.com/public/articles)
- [Certificates](https://msaied.com/public/certificates)
- [GitHub](https://github.com/EG-Mohamed)
- [LinkedIn](https://www.linkedin.com/in/msaiedm/)
- [WhatsApp](https://wa.me/201094619204)
- [Email Address](mailto:hello@msaied.com)
- [My CV](https://drive.google.com/file/u/0/d/1MF20IPRJyzfy32mhEutjL5EpSls0w2Q8/view)
- [Sitemap](https://msaied.com/public/sitemap.xml)
