Completed
Push — master ( 1183f0...23d94b )
by Anton
01:16
created

src/Job/Repositories/JobFileRepository.php (2 issues)

Labels
Severity

Upgrade to new PHP Analysis Engine

These results are based on our legacy PHP analysis, consider migrating to our new PHP analysis engine instead. Learn more

1
<?php
2
3
/*
4
 * This file is part of Laravel Paket.
5
 *
6
 * (c) Anton Komarev <[email protected]>
7
 *
8
 * For the full copyright and license information, please view the LICENSE
9
 * file that was distributed with this source code.
10
 */
11
12
declare(strict_types=1);
13
14
namespace Cog\Laravel\Paket\Job\Repositories;
15
16
use Cog\Contracts\Paket\Job\Entities\Job as JobContract;
17
use Cog\Contracts\Paket\Job\Repositories\Job as JobRepositoryContract;
18
use Cog\Laravel\Paket\Job\Entities\Job;
19
use Illuminate\Contracts\Filesystem\FileNotFoundException;
20
use Illuminate\Filesystem\Filesystem;
21
use RuntimeException;
22
use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
23
24
final class JobFileRepository implements JobRepositoryContract
25
{
26
    /**
27
     * The filesystem instance.
28
     *
29
     * @var \Illuminate\Filesystem\Filesystem
30
     */
31
    private $files;
32
33
    /**
34
     * The path to store jobs data.
35
     *
36
     * @var string
37
     */
38
    private $storagePath;
39
40
    /**
41
     * Create a new job file repository instance.
42
     *
43
     * @param \Illuminate\Filesystem\Filesystem $files
44
     * @param string $storagePath
45
     */
46
    public function __construct(Filesystem $files, string $storagePath)
47
    {
48
        $this->files = $files;
49
        $this->storagePath = $storagePath;
50
    }
51
52
    public function all(): iterable
53
    {
54
        $index = $this->getIndex();
55
56
        $jobs = [];
57
        foreach ($index as $job) {
58
            $jobs[] = Job::fromArray($job);
59
        }
60
61
        return $jobs;
62
    }
63
64
    public function getById(string $id): JobContract
65
    {
66
        $index = $this->getIndex();
67
68
        foreach ($index as $job) {
69
            if ($job['id'] === $id) {
70
                $job['process']['output'] = $this->getJobProcessOutput($job['id']);
71
72
                return Job::fromArray($job);
73
            }
74
        }
75
76
        throw new NotFoundHttpException("Job with id `{$id}` not found.");
77
    }
78
79
    public function store(JobContract $job): void
80
    {
81
        $index = $this->getIndex();
82
83
        $index[] = $job->toArray();
84
85
        $this->putIndex($index);
86
    }
87
88
    public function changeJobStatus(JobContract $job, string $statusName): void
89
    {
90
        $names = [
91
            'Pending',
92
            'Running',
93
            'Success',
94
            'Failed',
95
        ];
96
97
        if (!in_array($statusName, $names)) {
98
            // TODO: Throw custom exception
99
            throw new RuntimeException('Unknown job status');
100
        }
101
102
        $index = $this->getIndex();
103
104
        foreach ($index as $key => $record) {
105
            if ($record['id'] === $job->getId()) {
106
                $index[$key]['status'] = $statusName;
107
                break;
108
            }
109
        }
110
111
        $this->putIndex($index);
112
    }
113
114
    public function changeJobExitCode(JobContract $job, int $exitCode): void
115
    {
116
        $index = $this->getIndex();
117
118
        foreach ($index as $key => $record) {
119
            if ($record['id'] === $job->getId()) {
120
                $index[$key]['process']['exitCode'] = $exitCode;
121
                break;
122
            }
123
        }
124
125
        $this->putIndex($index);
126
    }
127
128
    private function getIndex(): array
129
    {
130
        try {
131
            return json_decode($this->files->get($this->getIndexFilePath(), $isLocked = true), true);
132
        } catch (FileNotFoundException $exception) {
0 ignored issues
show
The class Illuminate\Contracts\Fil...m\FileNotFoundException does not exist. Did you forget a USE statement, or did you not list all dependencies?

Scrutinizer analyzes your composer.json/composer.lock file if available to determine the classes, and functions that are defined by your dependencies.

It seems like the listed class was neither found in your dependencies, nor was it found in the analyzed files in your repository. If you are using some other form of dependency management, you might want to disable this analysis.

Loading history...
133
            return [];
134
        }
135
    }
136
137
    private function putIndex(iterable $index): void
138
    {
139
        $this->files->put($this->getIndexFilePath(), json_encode($index));
140
    }
141
142
    private function getJobProcessOutput(string $jobId): string
143
    {
144
        $path = sprintf('%s/jobs/%s.log', $this->storagePath, $jobId);
145
146
        try {
147
            return $this->files->get($path);
148
        } catch (FileNotFoundException $exception) {
0 ignored issues
show
The class Illuminate\Contracts\Fil...m\FileNotFoundException does not exist. Did you forget a USE statement, or did you not list all dependencies?

Scrutinizer analyzes your composer.json/composer.lock file if available to determine the classes, and functions that are defined by your dependencies.

It seems like the listed class was neither found in your dependencies, nor was it found in the analyzed files in your repository. If you are using some other form of dependency management, you might want to disable this analysis.

Loading history...
149
            return '';
150
        }
151
    }
152
153
    private function getIndexFilePath(): string
154
    {
155
        return $this->storagePath . '/jobs.json';
156
    }
157
}
158