---
title: "Laravel application synchronization with Redis | Roundly"
description: "Connect two Laravel applications through one Redis instance and synchronize data with queued jobs — connection config, job classes and workers."
url: https://roundly-consulting.com/blog/laravel-application-synchronization-with-redis
language: en
---

[All articles](https://roundly-consulting.com/blog.md)

Laravel· 6 June 2023· Updated 12 June 2026

# Laravel application synchronization with Redis

![Laravel application synchronization with Redis — Roundly Consulting](https://roundly-consulting.com/images/blog/laravel-application-synchronization-with-redis.webp)

When two Laravel applications need to exchange data, the reflex is to build an HTTP API between them. There is a lighter option: point both applications at one shared Redis instance and let Laravel's queue system carry the messages. One side dispatches a job, the other processes it — retries, backoff and monitoring come for free with the queue worker.

This guide configures a dedicated Redis connection in both applications, defines a matching job class on each side, and starts the worker that processes synchronization jobs. A custom key prefix keeps the shared queue isolated from each application's default queues.

## 1\. Configuring the Redis connection

In both applications, open config/database.php and add a connection named sync under the redis array. The prefix option is the important part: Laravel prefixes Redis keys per application by default, so two applications would read and write different keys even on the same server. Setting the same explicit prefix on both sides makes them see the same queue.

```php
'connections' => [
    // Other connections...

    'sync' => [
        'url' => env('SYNC_REDIS_URL'),
        'host' => env('SYNC_REDIS_HOST', '127.0.0.1'),
        'port' => env('SYNC_REDIS_PORT', '6379'),
        'password' => env('SYNC_REDIS_PASSWORD', null),
        'database' => env('SYNC_REDIS_DB', '1'),
        'options' => [
            'prefix' => env('SYNC_REDIS_PREFIX', 'app_sync_')
        ],
    ],
],
```

Point SYNC\_REDIS\_HOST, SYNC\_REDIS\_PORT and SYNC\_REDIS\_PASSWORD at the Redis server both applications share.

## 2\. The synchronization job

### Source application

The source application only dispatches — it never runs the job. Its job class therefore needs the right name, the same public properties as the destination's class, and the sync connection. The handle method stays empty:

```php
class SynchronizeItem implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;

    public function __construct(public array $data)
    {
        $this->onConnection('sync');
    }

    public function handle(): void
    {
        // Definition only — processing happens in the destination application.
    }
}
```

### Destination application

The destination application defines the same class — same name, same constructor signature — and implements handle to actually process the payload:

```php
class SynchronizeItem implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;

    public function __construct(public array $data)
    {
        $this->onConnection('sync');
    }

    public function handle(): void
    {
        // Route the payload by type — e.g. dispatch a domain event.
        match($this->data['type']) {
            SynchronizationType::Transaction->value => $this->processTransaction(),
        };
    }

    protected function processTransaction(): void
    {
        TransactionSynchronized::dispatch($this->data);
    }
}
```

The class names and property shapes must match exactly — the queue serializes the job by class name, so a mismatch surfaces as a failed job on the destination side.

## 3\. Dispatching

From the source application, dispatch the job like any other Laravel job. It lands on the shared Redis queue instead of the local one:

```php
SynchronizeItem::dispatch([
    'type' => 'Transaction',
    'item' => [
        'currency' => 'EUR',
        'amountInCents' => 150_000,
    ],
]);
```

## 4\. The queue worker

On the destination side, register the sync queue connection in config/queue.php so a worker can listen to it:

```php
'connections' => [
    // Other connections...

    'sync' => [
        'driver' => 'redis',
        'connection' => 'sync', // Connection defined in database.php
        'queue' => env('SYNC_REDIS_QUEUE', 'default'),
        'retry_after' => 90,
        'block_for' => null,
        'after_commit' => false,
    ],
]
```

Then start the worker (under Supervisor or systemd in production):

```bash
php artisan queue:work sync
```

The worker listens to the default queue on the sync connection and processes every job the source application dispatches.

## Conclusion

Two Laravel applications now exchange data through one Redis instance with nothing but the queue primitives Laravel already ships: a shared connection, a matching job class on each side, and a worker. The custom key prefix keeps the synchronization queue isolated from each application's own jobs, and failed-job handling, retries and horizon-style monitoring all apply as usual.

Designing reliable integrations between systems — queues, APIs, webhooks, sync jobs — is everyday work in our [API and system integration services](https://roundly-consulting.com/services/api-systems.md). If your applications still exchange data by CSV export, talk to us.

## Want this working in your company?

Tell us what you're trying to automate or build — we'll reply with a concrete proposal within 48 hours.

[Get a quote in 48 hours](https://roundly-consulting.com/contact.md) [See use cases](https://roundly-consulting.com/use-cases.md)
