Passed
Push — master ( ad6b2a...b41ca0 )
by Caen
07:45 queued 14s
created

BuildTaskService::canTransferMediaAssets()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 0
dl 0
loc 3
rs 10
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Hyde\Framework\Services;
6
7
use Hyde\Facades\Config;
8
use Hyde\Facades\Features;
9
use Hyde\Facades\Filesystem;
10
use Hyde\Framework\Features\BuildTasks\BuildTask;
11
use Hyde\Framework\Features\BuildTasks\PreBuildTask;
12
use Hyde\Framework\Features\BuildTasks\PostBuildTask;
13
use Hyde\Framework\Actions\PreBuildTasks\CleanSiteDirectory;
14
use Hyde\Framework\Actions\PostBuildTasks\GenerateRssFeed;
15
use Hyde\Framework\Actions\PostBuildTasks\GenerateSitemap;
16
use Hyde\Framework\Actions\PreBuildTasks\TransferMediaAssets;
17
use Hyde\Framework\Actions\PostBuildTasks\GenerateBuildManifest;
18
use Illuminate\Console\OutputStyle;
19
use Illuminate\Support\Str;
20
21
use function array_map;
22
use function array_values;
23
use function class_basename;
24
use function is_string;
25
use function str_replace;
26
27
/**
28
 * This service manages the build tasks that are called before and after the site is compiled using the build command.
29
 *
30
 * The class is registered as a singleton in the Laravel service container and is run by the build command.
31
 * Build Tasks can be registered programmatically, through the config, and through autodiscovery.
32
 * The service determines when to run a task depending on which class it extends.
33
 */
34
class BuildTaskService
35
{
36
    /** @var array<string, \Hyde\Framework\Features\BuildTasks\BuildTask> */
37
    protected array $buildTasks = [];
38
39
    protected ?OutputStyle $output = null;
40
41
    public function __construct()
42
    {
43
        $this->registerFrameworkTasks();
44
45
        $this->registerTasks($this->findTasksInConfig());
46
47
        $this->registerTasks($this->findTasksInAppDirectory());
48
    }
49
50
    public function setOutput(?OutputStyle $output): void
51
    {
52
        $this->output = $output;
53
    }
54
55
    /** @return array<class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask>|class-string<\Hyde\Framework\Features\BuildTasks\PostBuildTask>> */
0 ignored issues
show
Documentation Bug introduced by
The doc comment array<class-string<\Hyde...ldTasks\PostBuildTask>> at position 2 could not be parsed: Unknown type name 'class-string' at position 2 in array<class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask>|class-string<\Hyde\Framework\Features\BuildTasks\PostBuildTask>>.
Loading history...
56
    public function getRegisteredTasks(): array
57
    {
58
        return array_map(fn (BuildTask $task): string => $task::class, array_values($this->buildTasks));
59
    }
60
61
    public function runPreBuildTasks(): void
62
    {
63
        foreach ($this->buildTasks as $task) {
64
            if ($task instanceof PreBuildTask) {
65
                $task->run($this->output);
66
            }
67
        }
68
    }
69
70
    public function runPostBuildTasks(): void
71
    {
72
        foreach ($this->buildTasks as $task) {
73
            if ($task instanceof PostBuildTask) {
74
                $task->run($this->output);
75
            }
76
        }
77
    }
78
79
    /** @param  \Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask|class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask>  $task */
0 ignored issues
show
Documentation Bug introduced by
The doc comment \Hyde\Framework\Features...ildTasks\PostBuildTask> at position 4 could not be parsed: Unknown type name 'class-string' at position 4 in \Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask|class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask>.
Loading history...
80
    public function registerTask(PreBuildTask|PostBuildTask|string $task): void
81
    {
82
        $this->registerTaskInService(is_string($task) ? new $task() : $task);
83
    }
84
85
    protected function registerTaskInService(PreBuildTask|PostBuildTask $task): void
86
    {
87
        $this->buildTasks[$this->makeTaskIdentifier($task)] = $task;
88
    }
89
90
    /** @param class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask> $task */
0 ignored issues
show
Documentation Bug introduced by
The doc comment class-string<\Hyde\Frame...ildTasks\PostBuildTask> at position 0 could not be parsed: Unknown type name 'class-string' at position 0 in class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask>.
Loading history...
91
    protected function registerIf(string $task, bool $condition): void
92
    {
93
        if ($condition) {
94
            $this->registerTask($task);
95
        }
96
    }
97
98
    /** @param array<\Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask|class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask>> $tasks */
0 ignored issues
show
Documentation Bug introduced by
The doc comment array<\Hyde\Framework\Fe...ldTasks\PostBuildTask>> at position 6 could not be parsed: Unknown type name 'class-string' at position 6 in array<\Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask|class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask|\Hyde\Framework\Features\BuildTasks\PostBuildTask>>.
Loading history...
99
    protected function registerTasks(array $tasks): void
100
    {
101
        foreach ($tasks as $task) {
102
            $this->registerTask($task);
103
        }
104
    }
105
106
    /** @return array<class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask>|class-string<\Hyde\Framework\Features\BuildTasks\PostBuildTask>> */
0 ignored issues
show
Documentation Bug introduced by
The doc comment array<class-string<\Hyde...ldTasks\PostBuildTask>> at position 2 could not be parsed: Unknown type name 'class-string' at position 2 in array<class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask>|class-string<\Hyde\Framework\Features\BuildTasks\PostBuildTask>>.
Loading history...
107
    protected function findTasksInConfig(): array
108
    {
109
        return Config::getArray('hyde.build_tasks', []);
110
    }
111
112
    /** @return array<class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask>|class-string<\Hyde\Framework\Features\BuildTasks\PostBuildTask>> */
0 ignored issues
show
Documentation Bug introduced by
The doc comment array<class-string<\Hyde...ldTasks\PostBuildTask>> at position 2 could not be parsed: Unknown type name 'class-string' at position 2 in array<class-string<\Hyde\Framework\Features\BuildTasks\PreBuildTask>|class-string<\Hyde\Framework\Features\BuildTasks\PostBuildTask>>.
Loading history...
113
    protected function findTasksInAppDirectory(): array
114
    {
115
        return Filesystem::smartGlob('app/Actions/*BuildTask.php')->map(function (string $file): string {
116
            return static::pathToClassName($file);
117
        })->toArray();
118
    }
119
120
    protected static function pathToClassName(string $file): string
121
    {
122
        return str_replace(['app', '.php', '/'], ['App', '', '\\'], $file);
123
    }
124
125
    protected function makeTaskIdentifier(BuildTask $class): string
126
    {
127
        // If a user-land task is registered with the same class name (excluding namespaces) as a framework task,
128
        // this will allow the user-land task to override the framework task, making them easy to swap out.
129
130
        return Str::kebab(class_basename($class));
131
    }
132
133
    private function registerFrameworkTasks(): void
134
    {
135
        $this->registerIf(CleanSiteDirectory::class, $this->canCleanSiteDirectory());
136
        $this->registerIf(TransferMediaAssets::class, $this->canTransferMediaAssets());
137
        $this->registerIf(GenerateBuildManifest::class, $this->canGenerateManifest());
138
        $this->registerIf(GenerateSitemap::class, $this->canGenerateSitemap());
139
        $this->registerIf(GenerateRssFeed::class, $this->canGenerateFeed());
140
    }
141
142
    private function canCleanSiteDirectory(): bool
143
    {
144
        return Config::getBool('hyde.empty_output_directory', true);
145
    }
146
147
    private function canTransferMediaAssets(): bool
148
    {
149
        return Config::getBool('hyde.transfer_media_assets', true);
150
    }
151
152
    private function canGenerateManifest(): bool
153
    {
154
        return Config::getBool('hyde.generate_build_manifest', true);
155
    }
156
157
    private function canGenerateSitemap(): bool
158
    {
159
        return Features::hasSitemap();
160
    }
161
162
    private function canGenerateFeed(): bool
163
    {
164
        return Features::hasRss();
165
    }
166
}
167