Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.

mihailovskim's avatar

How to retrieve AWS SQS Messages by long pooling on Laravel

Hi guys,

I am implementing the AWS SQS on Laravel application, so I did all good when sending the message to the SQS, so after the third party service is finishing the job, it will create a new message on the AWS SQS and I want to retrieve the data from that message so I can process it on the Laravel Web Application.

The AWS SQS SDK have an example code, so my confusion is where this piece of code should go? It should constantly monitor the specific AWS SQS Queue so if there is new message will retrieve it.

It cannot be Laravel Job cause it will timeout, it is not a route? What it should be, any idea?

AWS SQS PHP SDK

Thanks in advance!

0 likes
7 replies
LaryAI's avatar
LaryAI
AI
Best Answer
Level 58

To implement long polling for AWS SQS in a Laravel application, you can use a combination of Laravel's console commands and the AWS SDK for PHP. This approach allows you to continuously poll the SQS queue without running into timeout issues that you might encounter with HTTP requests.

Here's a step-by-step guide to achieve this:

  1. Install AWS SDK for PHP: First, ensure you have the AWS SDK for PHP installed. You can add it to your Laravel project using Composer:

    composer require aws/aws-sdk-php
    
  2. Create a Console Command: Create a new Artisan command that will handle the long polling. You can generate a new command using the Artisan CLI:

    php artisan make:command PollSQSQueue
    
  3. Implement the Command: Open the newly created command file located at app/Console/Commands/PollSQSQueue.php and implement the logic to poll the SQS queue.

    Here's an example implementation:

    <?php
    
    namespace App\Console\Commands;
    
    use Illuminate\Console\Command;
    use Aws\Sqs\SqsClient;
    use Illuminate\Support\Facades\Log;
    
    class PollSQSQueue extends Command
    {
        protected $signature = 'sqs:poll';
        protected $description = 'Poll the AWS SQS queue for new messages';
    
        protected $sqsClient;
        protected $queueUrl;
    
        public function __construct()
        {
            parent::__construct();
    
            $this->sqsClient = new SqsClient([
                'region'  => env('AWS_DEFAULT_REGION'),
                'version' => 'latest',
                'credentials' => [
                    'key'    => env('AWS_ACCESS_KEY_ID'),
                    'secret' => env('AWS_SECRET_ACCESS_KEY'),
                ],
            ]);
    
            $this->queueUrl = env('AWS_SQS_QUEUE_URL');
        }
    
        public function handle()
        {
            while (true) {
                $result = $this->sqsClient->receiveMessage([
                    'QueueUrl'            => $this->queueUrl,
                    'MaxNumberOfMessages' => 1,
                    'WaitTimeSeconds'     => 20, // Long polling
                ]);
    
                if (!empty($result->get('Messages'))) {
                    foreach ($result->get('Messages') as $message) {
                        // Process the message
                        $this->processMessage($message);
    
                        // Delete the message from the queue
                        $this->sqsClient->deleteMessage([
                            'QueueUrl'      => $this->queueUrl,
                            'ReceiptHandle' => $message['ReceiptHandle'],
                        ]);
                    }
                }
    
                // Sleep for a short period to avoid hitting rate limits
                sleep(5);
            }
        }
    
        protected function processMessage($message)
        {
            // Implement your message processing logic here
            Log::info('Processing message: ' . $message['Body']);
        }
    }
    
  4. Configure Environment Variables: Ensure you have the necessary AWS credentials and SQS queue URL in your .env file:

    AWS_ACCESS_KEY_ID=your-access-key-id
    AWS_SECRET_ACCESS_KEY=your-secret-access-key
    AWS_DEFAULT_REGION=your-region
    AWS_SQS_QUEUE_URL=your-sqs-queue-url
    
  5. Run the Command: You can run the command manually using:

    php artisan sqs:poll
    

    Alternatively, you can set up a supervisor or a similar process manager to keep the command running continuously in the background.

By following these steps, you can continuously poll an AWS SQS queue in a Laravel application without running into timeout issues. The console command will keep running, checking for new messages and processing them as they arrive.

1 like
mihailovskim's avatar

@martinbean yes, I am using the SQS driver for sending the messages to the queue, but this case is more to constantly monitor the queue and to fetch messages from there. A.I. response helped me a lot, so it's simple, just creating command and setting the supervisor to ensure it is always running in background. So "in the command" I am using the SQS driver, to fetch the messages.

martinbean's avatar

@mihailovskim But why? That’s literally what Laravel’s queue component is for. You’re just reinventing the wheel. You’re writing code… to do what Laravel already offers you.

Dispatch a job to a queue, then run a queue worker to process jobs in that queue.

1 like
mihailovskim's avatar

@martinbean Yes that is what I am doing, so my process is next:

  • Creating some message (Laravel App);
  • Send the message to AWS SQS xxx Queue;
  • Python Worker is taking and processing the message (doing the job);
  • Python Worker is creating response message;
  • Python Worker is sending the message to AWS SQS yyy Queue;

So now it the problem, i do not want to check yyy Queue every minute, to see if there is new message created by the Python Worker, but want to implement long polling on the Laravel App (to monitor the yyy Queue).

I am using the Laravel sqs driver in both cases, to send and to retrieve the message, but the logic is in command so it will keep the connection with the SQS active, if that make sense now.

Snapey's avatar

A queue worker can run the job that python has posted. Do you have control over the format of the job so that it can be handled by Laravel?

The Laravel queue system will monitor the queue and execute any jobs it finds on the queue. It is the worker that is doing the 'polling'

2 likes
mihailovskim's avatar

@Snapey , @martinbean it all make sense what are you both saying, I went in different direction and implemented the functionality that already exists... I am still not completely sure how it will end, but will definitely rework this and use the simple solution provided by Laravel framework.

Thank you both!

Please or to participate in this conversation.