Completed
Branch feature/pre-split (67216b)
by Anton
03:28
created

AddReference::execute()   B

Complexity

Conditions 6
Paths 4

Size

Total Lines 44
Code Lines 22

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 6
eloc 22
nc 4
nop 1
dl 0
loc 44
rs 8.439
c 0
b 0
f 0
1
<?php
2
/**
3
 * Spiral Framework.
4
 *
5
 * @license   MIT
6
 * @author    Anton Titov (Wolfy-J)
7
 */
8
namespace Spiral\Migrations\Operations\References;
9
10
use Spiral\Database\Schemas\Prototypes\AbstractReference;
11
use Spiral\Migrations\CapsuleInterface;
12
use Spiral\Migrations\Exceptions\Operations\ReferenceException;
13
use Spiral\Migrations\Operations\ReferenceOperation;
14
use Spiral\Migrations\Operations\Traits\OptionsTrait;
15
16
class AddReference extends ReferenceOperation
17
{
18
    use OptionsTrait;
19
20
    /**
21
     * Some options has set of aliases.
22
     *
23
     * @var array
24
     */
25
    private $aliases = [
0 ignored issues
show
Unused Code introduced by
The property $aliases is not used and could be removed.

This check marks private properties in classes that are never used. Those properties can be removed.

Loading history...
26
        'onDelete' => ['delete'],
27
        'onUpdate' => ['update']
28
    ];
29
30
    /**
31
     * @var string
32
     */
33
    protected $foreignTable = '';
34
35
    /**
36
     * @var string
37
     */
38
    protected $foreignKey = '';
39
40
    /**
41
     * AddReference constructor.
42
     *
43
     * @param string|null $database
44
     * @param string      $table
45
     * @param string      $column
46
     * @param string      $foreignTable
47
     * @param string      $foreignKey
48
     * @param array       $options
49
     */
50
    public function __construct(
51
        $database,
52
        string $table,
53
        string $column,
54
        string $foreignTable,
55
        string $foreignKey,
56
        array $options
57
    ) {
58
        parent::__construct($database, $table, $column);
59
        $this->foreignTable = $foreignTable;
60
        $this->foreignKey = $foreignKey;
61
        $this->options = $options;
62
    }
63
64
    /**
65
     * {@inheritdoc}
66
     */
67
    public function execute(CapsuleInterface $capsule)
68
    {
69
        $schema = $capsule->getSchema($this->getTable(), $this->getDatabase());
70
71
        if ($schema->hasForeign($this->column)) {
72
            throw new ReferenceException(
73
                "Unable to add foreign key '{$schema->getName()}'.({$this->column}), "
74
                . "foreign key already exists"
75
            );
76
        }
77
78
        $outerSchema = $capsule->getSchema($this->foreignTable, $this->database);
79
80
        if ($this->foreignTable != $this->table && !$outerSchema->exists()) {
81
            throw new ReferenceException(
82
                "Unable to add foreign key '{$schema->getName()}'.'{$this->column}', "
83
                . "foreign table '{$this->foreignTable}' does not exists"
84
            );
85
        }
86
87
        if ($this->foreignTable != $this->table && !$outerSchema->hasColumn($this->foreignKey)) {
88
            throw new ReferenceException(
89
                "Unable to add foreign key '{$schema->getName()}'.'{$this->column}',"
90
                . " foreign column '{$this->foreignTable}'.'{$this->foreignKey}' does not exists"
91
            );
92
        }
93
94
        $foreignKey = $schema->foreign($this->column)->references(
95
            $this->foreignTable,
96
            $this->foreignKey
97
        );
98
99
        /*
100
         * We are allowing both formats "NO_ACTION" and "NO ACTION".
101
         */
102
103
        $foreignKey->onDelete(
104
            str_replace('_', ' ', $this->getOption('delete', AbstractReference::NO_ACTION))
105
        );
106
107
        $foreignKey->onUpdate(
108
            str_replace('_', ' ', $this->getOption('update', AbstractReference::NO_ACTION))
109
        );
110
    }
111
}