Completed
Push — master ( 2f0980...94c998 )
by Matthew
33:32 queued 29:55
created

PruneCommand   A

Complexity

Total Complexity 31

Size/Duplication

Total Lines 218
Duplicated Lines 0 %

Test Coverage

Coverage 93.69%

Importance

Changes 3
Bugs 1 Features 0
Metric Value
eloc 110
c 3
b 1
f 0
dl 0
loc 218
ccs 104
cts 111
cp 0.9369
rs 9.92
wmc 31

12 Methods

Rating   Name   Duplication   Size   Complexity  
A setJobManager() 0 2 1
A getIntervalTime() 0 18 4
A setRunManager() 0 2 1
A pruneOlderThan() 0 22 4
A configure() 0 7 1
A pruneOldJobs() 0 19 4
A getInterval() 0 17 4
A setJobTimingManager() 0 2 1
A pruneExceptionJobs() 0 5 1
A execute() 0 20 4
A executeOlder() 0 16 3
A executeStalledOther() 0 17 3
1
<?php
2
3
namespace Dtc\QueueBundle\Command;
4
5
use Dtc\QueueBundle\Exception\UnsupportedException;
6
use Dtc\QueueBundle\Manager\JobManagerInterface;
7
use Dtc\QueueBundle\Manager\JobTimingManager;
8
use Dtc\QueueBundle\Manager\RunManager;
9
use Dtc\QueueBundle\Util\Util;
10
use Symfony\Component\Console\Command\Command;
11
use Symfony\Component\Console\Input\InputArgument;
12
use Symfony\Component\Console\Input\InputInterface;
13
use Symfony\Component\Console\Input\InputOption;
14
use Symfony\Component\Console\Output\OutputInterface;
15
16
class PruneCommand extends Command
17
{
18
    const OLDER_MESSAGE = '<int>[d|m|y|h|i|s] Specify how old the jobs should (defaults to timestamp unless a quantifier is specified [d_ays, m_onths, y_years, h_ours, i_minutes, s_econds';
19
20
    /** @var JobManagerInterface */
21
    private $jobManager;
22
23
    /** @var RunManager */
24
    private $runManager;
25
26
    /** @var JobTimingManager */
27
    private $jobTimingManager;
28
29 5
    protected function configure()
30
    {
31
        $this
32 5
        ->setName('dtc:queue:prune')
33 5
        ->setDescription('Prune jobs')
34 5
        ->addArgument('type', InputArgument::REQUIRED, '<stalled|stalled_runs|exception|expired|old|old_runs|old_job_timings> Prune stalled, exception, expired, or old jobs')
35 5
            ->addOption('older', null, InputOption::VALUE_REQUIRED, self::OLDER_MESSAGE);
36 5
    }
37
38 5
    public function setJobManager($jobManager) {
39 5
        $this->jobManager = $jobManager;
40 5
    }
41
42 5
    public function setRunManager($runManager) {
43 5
        $this->runManager = $runManager;
44 5
    }
45
46 5
    public function setJobTimingManager($jobTimingManager) {
47 5
        $this->jobTimingManager = $jobTimingManager;
48 5
    }
49
50 5
    protected function execute(InputInterface $input, OutputInterface $output)
51
    {
52 5
        $type = $input->getArgument('type');
53 5
        switch ($type) {
54 5
            case 'erroneous':
55
                $output->writeln("(Warning): 'erroneous' is deprecated, please use 'exception' instead");
56
                $this->pruneExceptionJobs($output);
57
                break;
58 5
            case 'exception':
59 1
                $this->pruneExceptionJobs($output);
60 1
                break;
61 4
            case 'expired':
62 1
                $count = $this->jobManager->pruneExpiredJobs();
63 1
                $output->writeln("$count Expired Job(s) pruned");
64 1
                break;
65
            default:
66 3
                return $this->executeStalledOther($input, $output);
67
        }
68
69 2
        return 0;
70
    }
71
72 1
    protected function pruneExceptionJobs(OutputInterface $output)
73
    {
74
        // @TODO: move this to dependency injection.
75 1
        $count = $this->jobManager->pruneExceptionJobs();
76 1
        $output->writeln("$count Job(s) with status 'exception' pruned");
77 1
    }
78
79 3
    public function executeStalledOther(InputInterface $input, OutputInterface $output)
80
    {
81 3
        $type = $input->getArgument('type');
82 3
        switch ($type) {
83 3
            case 'stalled':
84 1
                $count = $this->jobManager->pruneStalledJobs();
0 ignored issues
show
Bug introduced by
The method pruneStalledJobs() does not exist on Dtc\QueueBundle\Manager\JobManagerInterface. It seems like you code against a sub-type of Dtc\QueueBundle\Manager\JobManagerInterface such as Dtc\QueueBundle\Manager\StallableJobManager. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

84
                /** @scrutinizer ignore-call */ 
85
                $count = $this->jobManager->pruneStalledJobs();
Loading history...
85 1
                $output->writeln("$count Stalled Job(s) pruned");
86 1
                break;
87 2
            case 'stalled_runs':
88 1
                $count = $this->runManager->pruneStalledRuns();
89 1
                $output->writeln("$count Stalled Job(s) pruned");
90 1
                break;
91
            default:
92 1
                return $this->executeOlder($input, $output);
93
        }
94
95 2
        return 0;
96
    }
97
98 1
    public function executeOlder(InputInterface $input, OutputInterface $output)
99
    {
100 1
        $older = $input->getOption('older');
101 1
        $type = $input->getArgument('type');
102 1
        if (!$older) {
103 1
            $output->writeln('<error>--older must be specified</error>');
104
105 1
            return 1;
106
        }
107 1
        if (!preg_match("/(\d+)([d|m|y|h|i|s]){0,1}$/", $older, $matches)) {
108 1
            $output->writeln('<error>Wrong format for --older</error>');
109
110 1
            return 1;
111
        }
112
113 1
        return $this->pruneOldJobs($matches, $type, $output);
0 ignored issues
show
Bug introduced by
It seems like $type can also be of type string[]; however, parameter $type of Dtc\QueueBundle\Command\...Command::pruneOldJobs() does only seem to accept string, maybe add an additional type check? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

113
        return $this->pruneOldJobs($matches, /** @scrutinizer ignore-type */ $type, $output);
Loading history...
114
    }
115
116
    /**
117
     * @param string[]        $matches
118
     * @param string          $type
119
     * @param OutputInterface $output
120
     *
121
     * @return int
122
     *
123
     * @throws \Exception
124
     */
125 1
    protected function pruneOldJobs(array $matches, $type, OutputInterface $output)
126
    {
127 1
        $durationOrTimestamp = intval($matches[1]);
128 1
        $modifier = isset($matches[2]) ? $matches[2] : null;
129
130 1
        if (!$durationOrTimestamp) {
131
            $output->writeln('<error>No duration or timestamp passed in.</error>');
132
133
            return 1;
134
        }
135 1
        $olderThan = Util::getMicrotimeDateTime();
136 1
        if (null === $modifier) {
137 1
            $olderThan->setTimestamp($durationOrTimestamp);
138
        } else {
139 1
            $interval = $this->getInterval($modifier, $durationOrTimestamp);
140 1
            $olderThan->sub($interval);
141
        }
142
143 1
        return $this->pruneOlderThan($type, $olderThan, $output);
144
    }
145
146
    /**
147
     * @param string          $type
148
     * @param \DateTime       $olderThan
149
     * @param OutputInterface $output
150
     *
151
     * @return int
152
     *
153
     * @throws UnsupportedException
154
     */
155 1
    protected function pruneOlderThan($type, \DateTime $olderThan, OutputInterface $output)
156
    {
157 1
        $typeName = null;
158 1
        switch ($type) {
159 1
            case 'old':
160 1
                $count = $this->jobManager->pruneArchivedJobs($olderThan);
161 1
                $typeName = 'Job';
162 1
                break;
163 1
            case 'old_runs':
164 1
                $count = $this->runManager->pruneArchivedRuns($olderThan);
165 1
                $typeName = 'Run';
166 1
                break;
167 1
            case 'old_job_timings':
168 1
                $count = $this->jobTimingManager->pruneJobTimings($olderThan);
169 1
                $typeName = 'Job Timing';
170 1
                break;
171
            default:
172
                throw new UnsupportedException("Unknown type $type");
173
        }
174 1
        $output->writeln("$count Archived $typeName(s) pruned");
175
176 1
        return 0;
177
    }
178
179
    /**
180
     * Returns the date interval based on the modifier and the duration.
181
     *
182
     * @param string $modifier
183
     * @param int    $duration
184
     *
185
     * @return \DateInterval
186
     *
187
     * @throws UnsupportedException
188
     */
189 1
    protected function getInterval($modifier, $duration)
190
    {
191 1
        switch ($modifier) {
192 1
            case 'd':
193 1
                $interval = new \DateInterval("P${duration}D");
194 1
                break;
195 1
            case 'm':
196 1
                $interval = new \DateInterval("P${duration}M");
197
                break;
198
            case 'y':
199
                $interval = new \DateInterval("P${duration}Y");
200 1
                break;
201
            default:
202 1
                $interval = $this->getIntervalTime($modifier, $duration);
203
        }
204
205 1
        return $interval;
206
    }
207
208
    /**
209
     * @param string $modifier
210
     * @param int    $duration
211
     *
212
     * @return \DateInterval
213
     *
214
     * @throws UnsupportedException
215
     */
216
    protected function getIntervalTime($modifier, $duration)
217
    {
218 1
        switch ($modifier) {
219 1
            case 'h':
220 1
                $interval = new \DateInterval("PT${duration}H");
221 1
                break;
222 1
            case 'i':
223 1
                $seconds = $duration * 60;
224 1
                $interval = new \DateInterval("PT${seconds}S");
225 1
                break;
226 1
            case 's':
227 1
                $interval = new \DateInterval("PT${duration}S");
228 1
                break;
229
            default:
230
                throw new UnsupportedException("Unknown duration modifier: $modifier");
231
        }
232
233 1
        return $interval;
234
    }
235
}
236