1 | <?php |
||||
2 | |||||
3 | namespace Cerbero\ConsoleTasker\Console\Printers; |
||||
4 | |||||
5 | use Cerbero\ConsoleTasker\RollbackScope; |
||||
6 | use Cerbero\ConsoleTasker\Summary; |
||||
7 | use Cerbero\ConsoleTasker\Tasks\AbstractFilesManipulatorTask; |
||||
8 | use Cerbero\ConsoleTasker\Tasks\AbstractTask; |
||||
9 | use Illuminate\Console\Concerns\InteractsWithIO; |
||||
10 | use Illuminate\Console\OutputStyle; |
||||
11 | |||||
12 | /** |
||||
13 | * The default printer. |
||||
14 | * |
||||
15 | */ |
||||
16 | class DefaultPrinter implements PrinterInterface |
||||
17 | { |
||||
18 | use InteractsWithIO; |
||||
19 | |||||
20 | /** |
||||
21 | * The loading mark. |
||||
22 | * |
||||
23 | * @var string |
||||
24 | */ |
||||
25 | protected const LOADING_MARK = '⏳'; |
||||
26 | |||||
27 | /** |
||||
28 | * The success mark. |
||||
29 | * |
||||
30 | * @var string |
||||
31 | */ |
||||
32 | protected const SUCCESS_MARK = '✔'; |
||||
33 | |||||
34 | /** |
||||
35 | * The failure mark. |
||||
36 | * |
||||
37 | * @var string |
||||
38 | */ |
||||
39 | protected const FAILURE_MARK = '✖'; |
||||
40 | |||||
41 | /** |
||||
42 | * The failure mark. |
||||
43 | * |
||||
44 | * @var string |
||||
45 | */ |
||||
46 | protected const SKIPPED_MARK = '⏩'; |
||||
47 | |||||
48 | /** |
||||
49 | * The console output. |
||||
50 | * |
||||
51 | * @var OutputStyle |
||||
52 | */ |
||||
53 | protected $output; |
||||
54 | |||||
55 | /** |
||||
56 | * Instantiate the class. |
||||
57 | * |
||||
58 | * @param OutputStyle $output |
||||
59 | */ |
||||
60 | public function __construct(OutputStyle $output) |
||||
61 | { |
||||
62 | $this->output = $output; |
||||
63 | } |
||||
64 | |||||
65 | /** |
||||
66 | * Print the execution of the given task |
||||
67 | * |
||||
68 | * @param AbstractTask $task |
||||
69 | * @param callable $callback |
||||
70 | * @return void |
||||
71 | */ |
||||
72 | public function printRunningTask(AbstractTask $task, callable $callback): void |
||||
73 | { |
||||
74 | $purpose = ucfirst($task->getPurpose()); |
||||
75 | |||||
76 | $this->output->write("{$purpose}: " . static::LOADING_MARK); |
||||
77 | |||||
78 | $callback($task); |
||||
79 | |||||
80 | if ($task->shouldRun()) { |
||||
81 | $result = $task->succeeded() ? $this->formatTaskSuccess($task) : $this->formatTaskFailure($task); |
||||
82 | } else { |
||||
83 | $result = $this->formatTaskSkipping($task); |
||||
84 | } |
||||
85 | |||||
86 | if ($this->output->isDecorated()) { |
||||
87 | $this->output->write("\033[2K\r"); // it deletes the line |
||||
88 | } else { |
||||
89 | $this->newLine(); |
||||
90 | } |
||||
91 | |||||
92 | $this->output->writeln("{$purpose}: {$result}"); |
||||
93 | } |
||||
94 | |||||
95 | /** |
||||
96 | * Format the success message of the given task |
||||
97 | * |
||||
98 | * @param AbstractTask $task |
||||
99 | * @return string |
||||
100 | */ |
||||
101 | protected function formatTaskSuccess(AbstractTask $task): string |
||||
102 | { |
||||
103 | return '<info>' . static::SUCCESS_MARK . '</info>'; |
||||
104 | } |
||||
105 | |||||
106 | /** |
||||
107 | * Format the failure message of the given task |
||||
108 | * |
||||
109 | * @param AbstractTask $task |
||||
110 | * @return string |
||||
111 | */ |
||||
112 | protected function formatTaskFailure(AbstractTask $task): string |
||||
113 | { |
||||
114 | return sprintf('<fg=red;bg=default>%s %s</>', static::FAILURE_MARK, $task->getError()); |
||||
115 | } |
||||
116 | |||||
117 | /** |
||||
118 | * Format the skipping message of the given task |
||||
119 | * |
||||
120 | * @param AbstractTask $task |
||||
121 | * @return string |
||||
122 | */ |
||||
123 | protected function formatTaskSkipping(AbstractTask $task): string |
||||
124 | { |
||||
125 | $reason = $task->getSkippingReason(); |
||||
0 ignored issues
–
show
|
|||||
126 | $text = $reason ? "skipped because $reason" : 'skipped'; |
||||
0 ignored issues
–
show
|
|||||
127 | |||||
128 | return sprintf('<fg=yellow;bg=default>%s %s</>', static::SKIPPED_MARK, $text); |
||||
129 | } |
||||
130 | |||||
131 | /** |
||||
132 | * Print the tasks summary |
||||
133 | * |
||||
134 | * @return void |
||||
135 | */ |
||||
136 | public function printSummary(): void |
||||
137 | { |
||||
138 | if (Summary::instance()->succeeded()) { |
||||
139 | $this->printSuccess(); |
||||
140 | } else { |
||||
141 | $this->printFailure(); |
||||
142 | } |
||||
143 | } |
||||
144 | |||||
145 | /** |
||||
146 | * Print console output when all tasks succeeded |
||||
147 | * |
||||
148 | * @return void |
||||
149 | */ |
||||
150 | protected function printSuccess(): void |
||||
151 | { |
||||
152 | $created = $updated = $toUpdate = []; |
||||
153 | |||||
154 | foreach (Summary::instance()->getSucceededTasks() as $task) { |
||||
155 | if (!$task instanceof AbstractFilesManipulatorTask) { |
||||
156 | continue; |
||||
157 | } |
||||
158 | |||||
159 | foreach ($task->getManipulatedFiles() as $file) { |
||||
160 | $array = $file->wasCreated() ? 'created' : 'updated'; |
||||
161 | $$array[] = $file->getRelativePath(); |
||||
162 | |||||
163 | if ($file->needsManualUpdate()) { |
||||
164 | $toUpdate[] = ucfirst($file->getManualUpdateReason()) . ' in ' . $file->getRelativePath(); |
||||
0 ignored issues
–
show
It seems like
$file->getManualUpdateReason() can also be of type null ; however, parameter $string of ucfirst() 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
![]() |
|||||
165 | } |
||||
166 | } |
||||
167 | } |
||||
168 | |||||
169 | $this->listItems('Created files', $created); |
||||
170 | $this->listItems('Updated files', $updated); |
||||
171 | $this->listItems('Files to update manually', $toUpdate); |
||||
172 | } |
||||
173 | |||||
174 | /** |
||||
175 | * List the given items with the provided title |
||||
176 | * |
||||
177 | * @param array $items |
||||
178 | * @param string $title |
||||
179 | * @return void |
||||
180 | */ |
||||
181 | protected function listItems(string $title, array $items): void |
||||
182 | { |
||||
183 | if ($items) { |
||||
0 ignored issues
–
show
The expression
$items of type array is implicitly converted to a boolean; are you sure this is intended? If so, consider using ! empty($expr) instead to make it clear that you intend to check for an array without elements.
This check marks implicit conversions of arrays to boolean values in a comparison. While in PHP an empty array is considered to be equal (but not identical) to false, this is not always apparent. Consider making the comparison explicit by using ![]() |
|||||
184 | $this->output->title($title); |
||||
185 | $this->output->listing($items); |
||||
186 | } |
||||
187 | } |
||||
188 | |||||
189 | /** |
||||
190 | * Print console output when not all tasks succeeded |
||||
191 | * |
||||
192 | * @return void |
||||
193 | */ |
||||
194 | protected function printFailure(): void |
||||
195 | { |
||||
196 | $rollbacks = $failedRollbacks = []; |
||||
197 | |||||
198 | foreach (Summary::instance()->getRolledbackTasks() as $scope) { |
||||
199 | if ($scope->rolledbackTask->rolledback()) { |
||||
0 ignored issues
–
show
|
|||||
200 | $rollbacks[] = $this->formatRollback($scope); |
||||
0 ignored issues
–
show
$scope of type Cerbero\ConsoleTasker\Tasks\AbstractTask is incompatible with the type Cerbero\ConsoleTasker\RollbackScope expected by parameter $scope of Cerbero\ConsoleTasker\Co...inter::formatRollback() .
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||
201 | } else { |
||||
202 | $failedRollbacks[] = $this->formatFailedRollback($scope); |
||||
0 ignored issues
–
show
$scope of type Cerbero\ConsoleTasker\Tasks\AbstractTask is incompatible with the type Cerbero\ConsoleTasker\RollbackScope expected by parameter $scope of Cerbero\ConsoleTasker\Co...:formatFailedRollback() .
(
Ignorable by Annotation
)
If this is a false-positive, you can also ignore this issue in your code via the
![]() |
|||||
203 | } |
||||
204 | } |
||||
205 | |||||
206 | $this->listItems('Rolled back tasks', $rollbacks); |
||||
207 | $this->listItems('Failed rollbacks', $failedRollbacks); |
||||
208 | } |
||||
209 | |||||
210 | /** |
||||
211 | * Retrieve the message to show when a task rolled back |
||||
212 | * |
||||
213 | * @param RollbackScope $scope |
||||
214 | * @return string |
||||
215 | */ |
||||
216 | protected function formatRollback(RollbackScope $scope): string |
||||
217 | { |
||||
218 | return vsprintf('The task to %s was rolled back due to failure to %s', [ |
||||
219 | lcfirst($scope->rolledbackTask->getPurpose()), |
||||
220 | lcfirst($scope->failedTask->getPurpose()), |
||||
221 | ]); |
||||
222 | } |
||||
223 | |||||
224 | /** |
||||
225 | * Retrieve the message to show when a task failed to rollback |
||||
226 | * |
||||
227 | * @param RollbackScope $scope |
||||
228 | * @return string |
||||
229 | */ |
||||
230 | protected function formatFailedRollback(RollbackScope $scope): string |
||||
231 | { |
||||
232 | $purpose = lcfirst($scope->rolledbackTask->getPurpose()); |
||||
233 | $exception = $scope->rolledbackTask->getRollbackException(); |
||||
234 | $reason = $exception ? ': ' . $exception->getMessage() : null; |
||||
235 | |||||
236 | return "The task to {$purpose} was not rolled back" . $reason; |
||||
237 | } |
||||
238 | } |
||||
239 |
This check looks for function or method calls that always return null and whose return value is assigned to a variable.
The method
getObject()
can return nothing but null, so it makes no sense to assign that value to a variable.The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.