SchemaParser::getAttributes()   A
last analyzed

Complexity

Conditions 2
Paths 2

Size

Total Lines 7
Code Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 4
c 1
b 0
f 0
dl 0
loc 7
rs 10
cc 2
nc 2
nop 2
1
<?php
2
3
namespace Rawilk\LaravelModules\Support\Migrations;
4
5
use Illuminate\Contracts\Support\Arrayable;
6
use Illuminate\Support\Arr;
7
use Illuminate\Support\Str;
8
9
class SchemaParser implements Arrayable
10
{
11
    /** @var array */
12
    protected static $customAttributes = [
13
        'remember_token' => 'rememberToken()',
14
        'soft_delete'    => 'softDeletes()'
15
    ];
16
17
    /** @var array */
18
    protected static $relationshipKeys = ['belongsTo'];
19
20
    /** @var string|null */
21
    protected $schema;
22
23
    /**
24
     * @param string|null $schema
25
     */
26
    public function __construct(?string $schema = null)
27
    {
28
        $this->schema = $schema;
29
    }
30
31
    public function createField(string $column, array $attributes, string $type = 'add'): string
32
    {
33
        $results = "\t\t\t" . '$table';
34
35
        foreach ($attributes as $key => $field) {
36
            if (in_array($column, static::$relationshipKeys, true)) {
37
                $results .= $this->addRelationColumn($key, $field, $column);
38
            } else {
39
                $results .= $this->{"{$type}Column"}($key, $field, $column);
40
            }
41
        }
42
43
        return $results . ';' . PHP_EOL;
44
    }
45
46
    /**
47
     * Render the down function of the migration.
48
     *
49
     * @return string
50
     */
51
    public function down(): string
52
    {
53
        $results = '';
54
55
        foreach ($this->toArray() as $column => $attributes) {
56
            $attributes = [head($attributes)];
57
58
            $results .= $this->createField($column, $attributes, 'remove');
59
        }
60
61
        return $results;
62
    }
63
64
    public function getAttributes(string $column, string $schema): array
65
    {
66
        $fields = str_replace("{$column}:", '', $schema);
67
68
        return $this->hasCustomAttribute($column)
69
            ? $this->getCustomAttribute($column)
70
            : explode(':', $fields);
71
    }
72
73
    public function getColumn(string $schema): string
74
    {
75
        return Arr::get(explode(':', $schema), 0);
0 ignored issues
show
Bug Best Practice introduced by
The expression return Illuminate\Suppor...plode(':', $schema), 0) could return the type null|string[] which is incompatible with the type-hinted return string. Consider adding an additional type-check to rule them out.
Loading history...
76
    }
77
78
    public function getCustomAttribute(string $column): array
79
    {
80
        return (array) static::$customAttributes[$column];
81
    }
82
83
    public function getSchemas(): array
84
    {
85
        if ($this->schema === null) {
86
            return [];
87
        }
88
89
        return explode(',', str_replace(' ', '', $this->schema));
90
    }
91
92
    public function hasCustomAttribute(string $column): bool
93
    {
94
        return array_key_exists($column, static::$customAttributes);
95
    }
96
97
    public function parse(?string $schema): array
98
    {
99
        $this->schema = $schema;
100
101
        $parsed = [];
102
103
        foreach ($this->getSchemas() as $schemas) {
104
            $column = $this->getColumn($schemas);
105
106
            $attributes = $this->getAttributes($column, $schemas);
107
108
            $parsed[$column] = $attributes;
109
        }
110
111
        return $parsed;
112
    }
113
114
    public function render(): string
115
    {
116
        $results = '';
117
118
        foreach ($this->toArray() as $column => $attributes) {
119
            $results .= $this->createField($column, $attributes);
120
        }
121
122
        return $results;
123
    }
124
125
    public function toArray(): array
126
    {
127
        return $this->parse($this->schema);
128
    }
129
130
    /**
131
     * Render the up function of the migration.
132
     *
133
     * @return string
134
     */
135
    public function up(): string
136
    {
137
        return $this->render();
138
    }
139
140
    protected function addColumn(int $key, string $field, string $column): string
141
    {
142
        if ($this->hasCustomAttribute($column)) {
143
            return "->{$field}";
144
        }
145
146
        if ($key === 0) {
147
            return "->{$field}('{$column}')";
148
        }
149
150
        if (Str::contains($field, '(')) {
151
            return "->{$field}";
152
        }
153
154
        return "->{$field}()";
155
    }
156
157
    protected function addRelationColumn(int $key, string $field, string $column): string
158
    {
159
        if ($key === 0) {
160
            $relatedColumn = Str::snake(class_basename($field)) . '_id';
161
162
            return "->unsignedBigInteger('{$relatedColumn}');"
163
                . PHP_EOL . "\t\t\t\$table->foreign('{$relatedColumn}')";
164
        }
165
166
        if ($key === 1) {
167
            return "->references('{$field}')";
168
        }
169
170
        if ($key === 2) {
171
            return "->on('{$field}')";
172
        }
173
174
        if (Str::contains($field, '(')) {
175
            return "->{$field}";
176
        }
177
178
        return "->{$field}()";
179
    }
180
181
    protected function removeColumn(int $key, string $field, string $column): string
182
    {
183
        if ($this->hasCustomAttribute($column)) {
184
            return "->{$field}";
185
        }
186
187
        return "->dropColumn('{$column}')";
188
    }
189
}
190