ModuleCreator::copyStubFileIntoModule()   A
last analyzed

Complexity

Conditions 3
Paths 3

Size

Total Lines 22
Code Lines 15

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 22
rs 9.2
c 0
b 0
f 0
cc 3
eloc 15
nc 3
nop 5
1
<?php
2
3
namespace Mnabialek\LaravelModular\Console\Traits;
4
5
use Exception;
6
use Mnabialek\LaravelModular\Models\Module;
7
use Mnabialek\LaravelModular\Traits\Normalizer;
8
9
trait ModuleCreator
10
{
11
    use Normalizer;
12
13
    /**
14
     * Verify stub group
15
     *
16
     * @param string $stubGroup
17
     *
18
     * @throws \Exception
19
     */
20
    protected function verifyStubGroup($stubGroup)
21
    {
22
        // first verify whether this group is in config file
23
24
        if (!collect($this->laravel['modular.config']->stubGroups())->contains($stubGroup)) {
0 ignored issues
show
Bug introduced by
The property laravel does not exist. Did you maybe forget to declare it?

In PHP it is possible to write to properties without declaring them. For example, the following is perfectly valid PHP code:

class MyClass { }

$x = new MyClass();
$x->foo = true;

Generally, it is a good practice to explictly declare properties to avoid accidental typos and provide IDE auto-completion:

class MyClass {
    public $foo;
}

$x = new MyClass();
$x->foo = true;
Loading history...
25
            throw new Exception("Stub group {$stubGroup} does not exist. You need to add it to stubs_groups");
26
        }
27
28
        // then verify whether this stub group directory exists
29
        $directory = $this->getStubGroupDirectory($stubGroup);
30
        if (!$this->exists($directory)) {
31
            throw new Exception("Stub group directory {$directory} does not exist");
32
        }
33
    }
34
35
    /**
36
     * Get directory for given stub group
37
     *
38
     * @param string $group
39
     *
40
     * @return string
41
     */
42
    protected function getStubGroupDirectory($group)
43
    {
44
        return $this->normalizePath($this->laravel['modular.config']->stubsPath() .
45
            DIRECTORY_SEPARATOR .
46
            $this->laravel['modular.config']->stubGroupDirectory($group));
47
    }
48
49
    /**
50
     * Verify whether module config was published
51
     *
52
     * @throws \Exception
53
     */
54
    protected function verifyConfigExistence()
55
    {
56
        if (!$this->exists($this->laravel['modular.config']->configPath())) {
57
            throw new Exception('Config file does not exists. Please run php artisan vendor:publish (see docs for details)');
58
        }
59
    }
60
61
    /**
62
     * Verify whether given file or directory exists
63
     *
64
     * @param string $path
65
     * @param Module $module
66
     *
67
     * @return bool
68
     */
69
    protected function exists($path, Module $module = null)
70
    {
71
        if ($module !== null) {
72
            $path = $module->directory() . DIRECTORY_SEPARATOR . $path;
73
        }
74
75
        return $this->laravel['files']->exists($path);
76
    }
77
78
    /**
79
     * Get stub group - either from input of default one
80
     *
81
     * @return mixed
82
     */
83
    protected function getStubGroup()
84
    {
85
        return $this->option('group') ?: $this->laravel['modular.config']->stubsDefaultGroup();
0 ignored issues
show
Bug introduced by
It seems like option() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
86
    }
87
88
    protected function getFilesStubGroup()
89
    {
90
        return $this->option('group') ?: $this->laravel['modular.config']->filesStubsDefaultGroup();
0 ignored issues
show
Bug introduced by
It seems like option() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
91
    }
92
93
    /**
94
     * Creates module directories
95
     *
96
     * @param Module $module
97
     * @param string $stubGroup
98
     */
99
    protected function createModuleDirectories(Module $module, $stubGroup)
100
    {
101
        $directories = collect($this->laravel['modular.config']
102
            ->stubGroupDirectories($stubGroup))->unique();
103
104
        if ($directories->isEmpty()) {
105
            $this->warn("[Module {$module->name()}] No explicit directories created");
0 ignored issues
show
Bug introduced by
It seems like warn() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
106
        } else {
107
            $directories->each(function ($directory) use ($module) {
108
                $this->createDirectory($module, $directory);
109
            });
110
        }
111
    }
112
113
    /**
114
     * Creates directory
115
     *
116
     * @param Module $module
117
     * @param string $directory
118
     *
119
     * @return bool
120
     * @throws Exception
121
     */
122
    protected function createDirectory(Module $module, $directory)
123
    {
124
        if (!$this->exists($directory, $module)) {
125
            $result =
126
                $this->laravel['files']->makeDirectory($module->directory() .
127
                    DIRECTORY_SEPARATOR . $directory, 0755, true);
128
            if ($result) {
129
                $this->line("[Module {$module->name()}] Created directory {$directory}");
0 ignored issues
show
Bug introduced by
It seems like line() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
130
            } else {
131
                throw new Exception("[Module {$module->name()}] Cannot create directory {$directory}");
132
            }
133
134
            return true;
135
        }
136
137
        return false;
138
    }
139
140
    /**
141
     * Create files inside given module
142
     *
143
     * @param Module $module
144
     * @param string $stubGroup
145
     * @param string $subModule
146
     *
147
     * @return bool
148
     */
149
    protected function createModuleFiles(
150
        Module $module,
151
        $stubGroup,
152
        $subModule = null
153
    ) {
154
        $files = collect($this->laravel['modular.config']
155
            ->stubGroupFiles($stubGroup));
156
157
        if ($files->isEmpty()) {
158
            $this->warn("[Module {$module->name()}] No files created");
0 ignored issues
show
Bug introduced by
It seems like warn() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
159
160
            return false;
161
        }
162
163
        $replacements = $subModule ? ['class' => $subModule] : [];
164
165
        $files->each(function ($stubFile, $moduleFile) use ($module, $stubGroup, $replacements) {
166
            $this->copyStubFileIntoModule($module, $stubFile, $stubGroup,
167
                $moduleFile, $replacements);
168
        });
169
170
        return true;
171
    }
172
173
    /**
174
     * Copy single stub file into module
175
     *
176
     * @param Module $module
177
     * @param $stubFile
178
     * @param $stubGroup
179
     * @param $moduleFile
180
     * @param array $replacements
181
     *
182
     * @throws Exception
183
     */
184
    protected function copyStubFileIntoModule(
185
        Module $module,
186
        $stubFile,
187
        $stubGroup,
188
        $moduleFile,
189
        array $replacements = []
190
    ) {
191
        $stubPath = $this->getStubGroupDirectory($stubGroup) .
192
            DIRECTORY_SEPARATOR . $stubFile;
193
194
        if (!$this->exists($stubPath)) {
195
            throw new Exception("Stub file {$stubPath} does NOT exist");
196
        }
197
        $moduleFile = $this->replace($moduleFile, $module, $replacements);
0 ignored issues
show
Bug introduced by
It seems like replace() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
198
199
        if ($this->exists($moduleFile, $module)) {
200
            throw new Exception("[Module {$module->name()}] File {$moduleFile} already exists");
201
        }
202
203
        $this->createMissingDirectory($module, $moduleFile);
204
        $this->createFile($module, $stubPath, $moduleFile, $replacements);
205
    }
206
207
    /**
208
     * Creates directory for given file (if it doesn't exist)
209
     *
210
     * @param Module $module
211
     * @param string $file
212
     */
213
    protected function createMissingDirectory(Module $module, $file)
214
    {
215
        if (!$this->exists(($dir = dirname($file)), $module)) {
216
            $this->createDirectory($module, $dir);
217
        }
218
    }
219
220
    /**
221
     * Creates single file
222
     *
223
     * @param Module $module
224
     * @param string $sourceFile
225
     * @param string $destinationFile
226
     * @param array $replacements
227
     *
228
     * @throws Exception
229
     */
230
    protected function createFile(
231
        Module $module,
232
        $sourceFile,
233
        $destinationFile,
234
        array $replacements = []
235
    ) {
236
        $result = $this->laravel['files']->put($module->directory() .
237
            DIRECTORY_SEPARATOR . $destinationFile,
238
            $this->replace($this->laravel['files']->get($sourceFile), $module,
0 ignored issues
show
Bug introduced by
It seems like replace() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
239
                $replacements)
240
        );
241
242
        if ($result === false) {
243
            throw new Exception("[Module {$module->name()}] Cannot create file {$destinationFile}");
244
        }
245
246
        $this->line("[Module {$module->name()}] Created file {$destinationFile}");
0 ignored issues
show
Bug introduced by
It seems like line() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
247
    }
248
}
249