Subversion-Projekte lars-tiefland.laravel_shop

Revision

Details | Letzte Änderung | Log anzeigen | RSS feed

Revision Autor Zeilennr. Zeile
148 lars 1
<?php
2
 
3
namespace Illuminate\Queue\Middleware;
4
 
5
use Illuminate\Cache\RateLimiter;
6
use Illuminate\Cache\RateLimiting\Unlimited;
7
use Illuminate\Container\Container;
8
use Illuminate\Support\Arr;
9
 
10
class RateLimited
11
{
12
    /**
13
     * The rate limiter instance.
14
     *
15
     * @var \Illuminate\Cache\RateLimiter
16
     */
17
    protected $limiter;
18
 
19
    /**
20
     * The name of the rate limiter.
21
     *
22
     * @var string
23
     */
24
    protected $limiterName;
25
 
26
    /**
27
     * Indicates if the job should be released if the limit is exceeded.
28
     *
29
     * @var bool
30
     */
31
    public $shouldRelease = true;
32
 
33
    /**
34
     * Create a new middleware instance.
35
     *
36
     * @param  string  $limiterName
37
     * @return void
38
     */
39
    public function __construct($limiterName)
40
    {
41
        $this->limiter = Container::getInstance()->make(RateLimiter::class);
42
 
43
        $this->limiterName = $limiterName;
44
    }
45
 
46
    /**
47
     * Process the job.
48
     *
49
     * @param  mixed  $job
50
     * @param  callable  $next
51
     * @return mixed
52
     */
53
    public function handle($job, $next)
54
    {
55
        if (is_null($limiter = $this->limiter->limiter($this->limiterName))) {
56
            return $next($job);
57
        }
58
 
59
        $limiterResponse = $limiter($job);
60
 
61
        if ($limiterResponse instanceof Unlimited) {
62
            return $next($job);
63
        }
64
 
65
        return $this->handleJob(
66
            $job,
67
            $next,
68
            collect(Arr::wrap($limiterResponse))->map(function ($limit) {
69
                return (object) [
70
                    'key' => md5($this->limiterName.$limit->key),
71
                    'maxAttempts' => $limit->maxAttempts,
72
                    'decayMinutes' => $limit->decayMinutes,
73
                ];
74
            })->all()
75
        );
76
    }
77
 
78
    /**
79
     * Handle a rate limited job.
80
     *
81
     * @param  mixed  $job
82
     * @param  callable  $next
83
     * @param  array  $limits
84
     * @return mixed
85
     */
86
    protected function handleJob($job, $next, array $limits)
87
    {
88
        foreach ($limits as $limit) {
89
            if ($this->limiter->tooManyAttempts($limit->key, $limit->maxAttempts)) {
90
                return $this->shouldRelease
91
                        ? $job->release($this->getTimeUntilNextRetry($limit->key))
92
                        : false;
93
            }
94
 
95
            $this->limiter->hit($limit->key, $limit->decayMinutes * 60);
96
        }
97
 
98
        return $next($job);
99
    }
100
 
101
    /**
102
     * Do not release the job back to the queue if the limit is exceeded.
103
     *
104
     * @return $this
105
     */
106
    public function dontRelease()
107
    {
108
        $this->shouldRelease = false;
109
 
110
        return $this;
111
    }
112
 
113
    /**
114
     * Get the number of seconds that should elapse before the job is retried.
115
     *
116
     * @param  string  $key
117
     * @return int
118
     */
119
    protected function getTimeUntilNextRetry($key)
120
    {
121
        return $this->limiter->availableIn($key) + 3;
122
    }
123
 
124
    /**
125
     * Prepare the object for serialization.
126
     *
127
     * @return array
128
     */
129
    public function __sleep()
130
    {
131
        return [
132
            'limiterName',
133
            'shouldRelease',
134
        ];
135
    }
136
 
137
    /**
138
     * Prepare the object after unserialization.
139
     *
140
     * @return void
141
     */
142
    public function __wakeup()
143
    {
144
        $this->limiter = Container::getInstance()->make(RateLimiter::class);
145
    }
146
}