Passed
Push — master ( 719292...2fce0a )
by Sebastien
05:40
created

CrudPackage::handle()   B

Complexity

Conditions 8
Paths 11

Size

Total Lines 51
Code Lines 31

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 8
eloc 31
nc 11
nop 0
dl 0
loc 51
rs 8.1795
c 1
b 0
f 0

How to fix   Long Method   

Long Method

Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.

For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.

Commonly applied refactorings include:

1
<?php
2
3
namespace Sebastienheyd\BoilerplatePackager\Commands;
4
5
use Illuminate\Support\Facades\Schema;
6
use Illuminate\Support\Str;
7
8
class CrudPackage extends Command
9
{
10
    /**
11
     * The name and signature of the console command.
12
     *
13
     * @var string
14
     */
15
    protected $signature = 'boilerplate:packager:crud {package : package name where to scaffold}';
16
17
    /**
18
     * The console command description.
19
     *
20
     * @var string
21
     */
22
    protected $description = '';
23
24
    /**
25
     * @throws \Illuminate\Contracts\Filesystem\FileNotFoundException
26
     * @return int
27
     */
28
    public function handle()
29
    {
30
        $package = Str::lower($this->argument('package'));
0 ignored issues
show
Bug introduced by
It seems like $this->argument('package') can also be of type string[]; however, parameter $value of Illuminate\Support\Str::lower() 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

30
        $package = Str::lower(/** @scrutinizer ignore-type */ $this->argument('package'));
Loading history...
31
        if (! $this->packagist->checkFormat($package)) {
32
            $this->error('Package name format must be vendor/package');
33
34
            return 1;
35
        }
36
37
        if (! $this->storage->exists($package)) {
38
            $this->error('Package does not exists');
39
40
            return 1;
41
        }
42
43
        $tables = $this->getPackageTables($package);
44
45
        if (empty($tables)) {
46
            $this->error('No table creation in the package');
47
48
            return 1;
49
        }
50
51
        foreach ($tables as $table) {
52
            foreach (Schema::getConnection()->getDoctrineSchemaManager()->listTableForeignKeys($table) as $fk) {
53
                if (in_array($fk->getForeignTableName(), $tables)) {
54
                    continue;
55
                }
56
57
                $model = Str::studly(Str::singular($fk->getForeignTableName()));
58
                $namespaces[$fk->getForeignTableName()] = $this->checkModel($model);
59
            }
60
        }
61
62
        $warn = '  Warning ! This command will overwrite all files in the package '.$package.'  ';
63
        $this->warn(str_repeat('*', strlen($warn)));
64
        $this->warn($warn);
65
        $this->warn(str_repeat('*', strlen($warn)));
66
67
        if (! $this->confirm('Confirm?')) {
68
            return 0;
69
        }
70
71
        $args = ['tables' => $tables, 'package' => $package];
72
        $this->callCommand('model', array_merge_recursive($args, ['namespaces' => $namespaces]));
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $namespaces does not seem to be defined for all execution paths leading up to this point.
Loading history...
73
        $this->callCommand('routes', $args);
74
        $this->callCommand('lang', $args);
75
        $this->callCommand('permissions', $args);
76
        $this->callCommand('controller', array_merge_recursive($args, ['namespaces' => $namespaces]));
77
        $this->callCommand('menu', $args);
78
        $this->callCommand('views', $args);
79
    }
80
81
    private function callCommand($action, $args)
82
    {
83
        $this->getApplication()->addCommands([$this->resolveCommand(__NAMESPACE__.'\\Crud\\'.ucfirst($action))]);
84
        $this->call('boilerplate:packager:crud:'.$action, $args);
85
    }
86
87
    private function getPackageTables($package)
88
    {
89
        $migrations = $this->storage->files($package.'/src/database/migrations');
90
91
        $tables = [];
92
93
        foreach ($migrations as $migrationFile) {
94
            $migration = $this->storage->get($migrationFile);
95
96
            if (! preg_match_all('#Schema::create\(\s*[\'"]([a-z]+)[\'"]#', $migration, $m)) {
97
                continue;
98
            }
99
100
            $tables = array_merge($tables, $m[1]);
101
        }
102
103
        return array_unique($tables);
104
    }
105
106
    private function checkModel($model)
107
    {
108
        $msg = sprintf('Input the namespace for the model <comment>%s</comment>', $model);
109
        $ns = $this->ask($msg, 'App\Models');
110
111
        if (! class_exists($ns.'\\'.$model)) {
112
            $this->line(' <error> Class <fg=yellow;bg=red>'.$ns.'\\'.$model.'</> does not exists </error>');
113
114
            return $this->checkModel($model);
115
        }
116
117
        return $ns;
118
    }
119
}
120