1
votes

Comment exécuter un seul travail à la fois dans la même file d'attente laravel?

J'ai un service saas qui fonctionne avec l'API. Il a des limites, donc j'ai besoin d'un seul compte utilisateur pour faire une seule demande à la fois.

Pour cela, je fais la queue avec OnQueue($user->name);

puis dans handle () faire le travail ...

Je n'ai besoin que d'un seul travail peut être exécuté dans la file d'attente des utilisateurs. Dans le même temps peut être exécuté seulement différentes files d'attente 1 travail par 1 file d'attente.

J'utilise la connexion redis.

Voici ma classe de travail:

$accounts = Accounts::select(['id', 'login', 'hashtag_filter', 'concurency_filter'])->whereNotNull('hashtag_filter')->get();
        foreach ($accounts as $acc) {
            doFollowing::dispatch($acc)->onQueue($acc->login);
        }


0 commentaires

3 Réponses :


1
votes

Vous pouvez limiter numprocs par file d'attente dans votre configuration Supervisor ou Horizon.

Si vous ne créez qu'un seul agent de file d'attente par utilisateur, je pense que vous obtiendrez le comportement souhaité.


1 commentaires

Cela fonctionnera bien lorsque les utilisateurs sont ~ 100, mais que faire si les utilisateurs 10k? Aussi comme je l'ai dit - le nom de la file d'attente est le nom d'utilisateur. Dans votre variante, j'ai toujours besoin de modifier la configuration du superviseur?



1
votes

Utilisez le package de composition mxl / laravel-queue-rate-limit .

Il vous permet de noter les tâches Laravel limitées sur une file d'attente spécifique sans utiliser de pilote tiers tel que Redis .

  1. Installez-le avec:

    SomeJob::dispatch()->onQueue('mail');
    SomeJob::dispatch()->onQueue('mail');
    SomeJob::dispatch()->onQueue('mail');
    SomeJob::dispatch();
    
  2. Ce package est compatible avec Laravel 5.5+ et utilise la fonctionnalité [auto-discovery] [1] pour ajouter MichaelLedin \ LaravelQueueRateLimit \ QueueServiceProvider :: class aux fournisseurs.

  3. Ajouter les paramètres de limite de débit (x nombre de travaux par y secondes) à config / queue.php :

    $ php artisan queue:work --queue mail,default
    

    Ces paramètres permettent d'exécuter 1 tâche toutes les 5 secondes sur la file d'attente mail . Assurez-vous que le pilote de file d'attente par défaut (propriété default dans config / queue.php ) est défini sur n'importe quelle valeur sauf sync .

  4. Exécutez le gestionnaire de file d'attente avec l'option --queue mail :

    $ php artisan queue:work --queue mail
    

    Vous pouvez exécuter un worker sur plusieurs files d'attente, mais seules les files d'attente référencées dans le paramètre rateLimit seront limitées au débit:

    'rateLimit' => [
        'mail' => [
            'allows' => 1, // number of jobs
            'every' => 5 // time interval in seconds
        ]
    ]
    

    Les travaux de la file d'attente default seront exécutés sans limitation de débit.

  5. Mettre en file d'attente des tâches pour tester la limitation du débit:

    $ composer require mxl/laravel-queue-rate-limit:^1.0
    


1 commentaires

J'ai un nom de file d'attente dynamique car c'est une file d'attente par utilisateur - je ne peux pas toujours modifier la configuration pour chaque utilisateur. De plus, je ne demande pas la limite de temps, je veux exécuter simultanément un seul travail dans la même file d'attente - peu importe, ce sera 1 par minute ou 100



2
votes

Vous pouvez utiliser la limitation de débit intégrée de Laravel pour cela (notez que cela nécessite Redis).

Dans votre travail:

Redis::funnel('process-name')->limit(1)->then(function () {
    // Your job logic here
});

Notez que si vous ne le faites pas fournissez un deuxième rappel à alors, il lancera une exception s'il ne peut pas obtenir le verrou (ce qui entraînera l'échec de votre travail)

Si vous utilisez Laravel 6 ou supérieur, vous pouvez également choisir de le faire dans un middleware de jobs, plutôt que dans le job lui-même (pratique si vous avez plusieurs jobs qui partagent le même verrou)

Plus d'informations sur la limitation de débit de Laravel: https://laravel.com/docs/5.8/queues#rate-limiting


0 commentaires