DDLQueryBuilder::addCommentOnColumn()   A
last analyzed

Complexity

Conditions 4
Paths 8

Size

Total Lines 33
Code Lines 21

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 21
CRAP Score 4.0105

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 21
c 1
b 0
f 0
dl 0
loc 33
ccs 21
cts 23
cp 0.913
rs 9.584
cc 4
nc 8
nop 3
crap 4.0105
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Yiisoft\Db\Mysql;
6
7
use Throwable;
8
use Yiisoft\Db\Exception\Exception;
9
use Yiisoft\Db\Exception\NotSupportedException;
10
use Yiisoft\Db\QueryBuilder\AbstractDDLQueryBuilder;
11
12
use function preg_match;
13
use function preg_quote;
14
use function preg_replace;
15
use function trim;
16
17
/**
18
 * Implements a (Data Definition Language) SQL statements for MySQL, MariaDB.
19
 */
20
final class DDLQueryBuilder extends AbstractDDLQueryBuilder
21
{
22
    /**
23
     * @throws NotSupportedException
24 2
     */
25
    public function addCheck(string $table, string $name, string $expression): string
26 2
    {
27
        throw new NotSupportedException(__METHOD__ . ' is not supported by MySQL.');
28
    }
29
30
    /**
31
     * @throws Throwable
32 5
     */
33
    public function addCommentOnColumn(string $table, string $column, string $comment): string
34
    {
35 5
        /* Strip existing comment which may include escaped quotes */
36 5
        $definition = trim(
37 5
            preg_replace(
38 5
                "/COMMENT '(?:''|[^'])*'/i",
39 5
                '',
40 5
                $this->getColumnDefinition($table, $column)
41 5
            )
42
        );
43 5
44 5
        $checkRegex = '/CHECK *(\(([^()]|(?-2))*\))/';
45
        $check = preg_match($checkRegex, $definition, $checkMatches);
46 5
47
        if ($check === 1) {
48
            $definition = preg_replace($checkRegex, '', $definition);
49
        }
50 5
51 5
        $alterSql = 'ALTER TABLE '
52 5
            . $this->quoter->quoteTableName($table)
53 5
            . ' CHANGE '
54 5
            . $this->quoter->quoteColumnName($column)
55 5
            . ' '
56 5
            . $this->quoter->quoteColumnName($column)
57 5
            . (empty($definition) ? '' : ' ' . $definition)
58 5
            . ' COMMENT '
59
            . (string) $this->quoter->quoteValue($comment);
60 5
61
        if ($check === 1) {
62
            $alterSql .= ' ' . $checkMatches[0];
63
        }
64 5
65
        return $alterSql;
66
    }
67 4
68
    public function addCommentOnTable(string $table, string $comment): string
69 4
    {
70 4
        return 'ALTER TABLE '
71 4
            . $this->quoter->quoteTableName($table)
72 4
            . ' COMMENT '
73
            . (string) $this->quoter->quoteValue($comment);
74
    }
75 2
76
    public function addDefaultValue(string $table, string $name, string $column, mixed $value): string
77 2
    {
78
        throw new NotSupportedException(__METHOD__ . ' is not supported by MySQL.');
79
    }
80 10
81
    public function createIndex(
82
        string $table,
83
        string $name,
84
        array|string $columns,
85
        string $indexType = null,
86
        string $indexMethod = null
87 10
    ): string {
88 10
        return 'CREATE ' . (!empty($indexType) ? $indexType . ' ' : '') . 'INDEX '
89 10
            . $this->quoter->quoteTableName($name)
90 10
            . (!empty($indexMethod) ? " USING $indexMethod" : '')
91 10
            . ' ON ' . $this->quoter->quoteTableName($table)
92
            . ' (' . $this->queryBuilder->buildColumns($columns) . ')';
93
    }
94 1
95
    public function checkIntegrity(string $schema = '', string $table = '', bool $check = true): string
96 1
    {
97
        return 'SET FOREIGN_KEY_CHECKS = ' . ($check ? 1 : 0);
98
    }
99
100
    /**
101
     * @throws NotSupportedException
102 1
     */
103
    public function dropCheck(string $table, string $name): string
104 1
    {
105
        throw new NotSupportedException(__METHOD__ . ' is not supported by MySQL.');
106
    }
107
108
    /**
109
     * @throws Exception
110
     * @throws Throwable
111 2
     */
112
    public function dropCommentFromColumn(string $table, string $column): string
113 2
    {
114
        return $this->addCommentOnColumn($table, $column, '');
115
    }
116
117
    /**
118
     * @throws \Exception
119 2
     */
120
    public function dropCommentFromTable(string $table): string
121 2
    {
122
        return $this->addCommentOnTable($table, '');
123
    }
124 1
125
    public function dropDefaultValue(string $table, string $name): string
126 1
    {
127
        throw new NotSupportedException(__METHOD__ . ' is not supported by MySQL.');
128
    }
129 2
130
    public function dropForeignKey(string $table, string $name): string
131 2
    {
132 2
        return 'ALTER TABLE '
133 2
            . $this->quoter->quoteTableName($table)
134 2
            . ' DROP FOREIGN KEY '
135
            . $this->quoter->quoteColumnName($name);
136
    }
137 3
138
    public function dropPrimaryKey(string $table, string $name): string
139 3
    {
140
        return 'ALTER TABLE ' . $this->quoter->quoteTableName($table) . ' DROP PRIMARY KEY';
141
    }
142 3
143
    public function dropUnique(string $table, string $name): string
144 3
    {
145
        return $this->dropIndex($table, $name);
146
    }
147
148
    /**
149
     * @throws Exception
150
     * @throws Throwable
151 2
     */
152
    public function renameColumn(string $table, string $oldName, string $newName): string
153 2
    {
154
        $quotedTable = $this->quoter->quoteTableName($table);
155 2
156
        $columnDefinition = $this->getColumnDefinition($table, $oldName);
157
158 2
        /* try to give back an SQL anyway */
159 2
        return "ALTER TABLE $quotedTable CHANGE "
160 2
            . $this->quoter->quoteColumnName($oldName) . ' '
161 2
            . $this->quoter->quoteColumnName($newName)
162
            . (!empty($columnDefinition) ? ' ' . $columnDefinition : '');
163
    }
164
165
    /**
166
     * Gets column definition.
167
     *
168
     * @param string $table The table name.
169
     * @param string $column The column name.
170
     *
171
     * @return string The column definition or empty string in case when schema does not contain the table
172
     * or the table doesn't contain the column.
173
     */
174 7
    private function getColumnDefinition(string $table, string $column): string
175
    {
176 7
        $sql = $this->schema->getTableSchema($table)?->getCreateSql();
177 7
178
        if (empty($sql)) {
179 7
            return '';
180
        }
181
182
        $quotedColumn = preg_quote($column, '/');
183 7
184 7
        if (preg_match("/^\s*([`\"])$quotedColumn\\1\s+(.*?),?$/m", $sql, $matches) !== 1) {
185 7
            return '';
186 7
        }
187
188
        return $matches[2];
189
    }
190
}
191