Completed
Pull Request — master (#5)
by Rougin
02:15
created

MySQLDriver::getTableNames()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
c 0
b 0
f 0
dl 0
loc 4
ccs 2
cts 2
cp 1
rs 10
cc 1
eloc 2
nc 1
nop 0
crap 1
1
<?php
2
3
namespace Rougin\Describe\Driver;
4
5
use Rougin\Describe\Column;
6
7
/**
8
 * MySQL Driver
9
 *
10
 * A database driver extension for MySQL.
11
 *
12
 * @package  Describe
13
 * @category Driver
14
 * @author   Rougin Royce Gutib <[email protected]>
15
 */
16
class MySQLDriver extends AbstractDriver implements DriverInterface
17
{
18
    /**
19
     * @var string
20
     */
21
    protected $database;
22
23
    /**
24
     * @var \PDO
25
     */
26
    protected $pdo;
27
28
    /**
29
     * @param PDO    $pdo
30
     * @param string $database
31
     */
32 60
    public function __construct(\PDO $pdo, $database)
33
    {
34 60
        $this->database = $database;
35 60
        $this->pdo = $pdo;
36 60
    }
37
38
    /**
39
     * Returns a listing of columns from the specified table.
40
     *
41
     * @param  string $tableName
42
     * @return array
43
     * @throws \Rougin\Describe\Exceptions\TableNameNotFoundException
44
     */
45 51
    public function getColumns($tableName)
46
    {
47 51
        return $this->getColumnsFromQuery($tableName, 'DESCRIBE ' . $tableName);
48
    }
49
50
    /**
51
     * Returns a listing of columns from the specified table.
52
     * NOTE: To be removed in v2.0.0.
53
     *
54
     * @param  string $tableName
55
     * @return array
56
     * @throws \Rougin\Describe\Exceptions\TableNameNotFoundException
57
     */
58 51
    public function getTable($tableName)
59
    {
60 51
        return $this->getColumns($tableName);
61
    }
62
63
    /**
64
     * Returns a listing of tables from the specified database.
65
     *
66
     * @return array
67
     */
68 9
    public function getTableNames()
69
    {
70 9
        return $this->showTables();
71
    }
72
73
    /**
74
     * Shows the list of tables.
75
     * NOTE: To be removed in v2.0.0.
76
     *
77
     * @return array
78
     */
79 9
    public function showTables()
80
    {
81 9
        $tables = [];
82
83 9
        $information = $this->pdo->prepare('SHOW TABLES');
84 9
        $information->execute();
85
86 9
        while ($row = $information->fetch()) {
87 9
            array_push($tables, $row[0]);
88 9
        }
89
90 9
        return $tables;
91
    }
92
93
    /**
94
     * Prepares the defined columns.
95
     *
96
     * @param  string $tableName
97
     * @param  mixed  $row
98
     * @return \Rougin\Describe\Column
99
     */
100 48
    protected function setColumn($tableName, $row)
101
    {
102 48
        preg_match('/(.*?)\((.*?)\)/', $row->Type, $match);
103
104 48
        $column = new Column;
105
106
107 48
        $column->setDataType($row->Type);
108 48
        $column->setDefaultValue($row->Default);
109 48
        $column->setField($row->Field);
110
111 48
        if (isset($match[1])) {
112 48
            $column->setDataType($match[1]);
113 48
            $column->setLength($match[2]);
114 48
        }
115
116 48
        $column = $this->setProperties($row, $column);
117 48
        $column = $this->setKey($row, $column);
118 48
        $column = $this->setForeignColumn($tableName, $row, $column);
119
120 48
        return $column;
121
    }
122
123
    /**
124
     * Sets the key of the specified column.
125
     *
126
     * @param  mixed                   $row
127
     * @param  \Rougin\Describe\Column $column
128
     * @return \Rougin\Describe\Column
129
     */
130 48
    protected function setKey($row, Column $column)
131
    {
132 48
        switch ($row->Key) {
133 48
            case 'PRI':
134 48
                $column->setPrimary(true);
135
136 48
                break;
137
            
138 48
            case 'MUL':
139 48
                $column->setForeign(true);
140
141 48
                break;
142
143 48
            case 'UNI':
144 48
                $column->setUnique(true);
145
146 48
                break;
147 48
        }
148
149 48
        return $column;
150
    }
151
152
    /**
153
     * Sets the properties of the specified column if it does exists.
154
     *
155
     * @param  string                  $tableName
156
     * @param  mixed                   $row
157
     * @param  \Rougin\Describe\Column $column
158
     * @return \Rougin\Describe\Column
159
     */
160 48
    protected function setForeignColumn($tableName, $row, Column $column)
161
    {
162
        $query = 'SELECT COLUMN_NAME as "column", REFERENCED_COLUMN_NAME as "referenced_column",' .
163 48
            'CONCAT(REFERENCED_TABLE_SCHEMA, ".", REFERENCED_TABLE_NAME) as "referenced_table"' .
164 48
            'FROM INFORMATION_SCHEMA.KEY_COLUMN_USAGE ' .
165 48
            'WHERE CONSTRAINT_SCHEMA = "' . $this->database . '" ' .
166 48
            'AND TABLE_NAME = "' . $tableName . '";';
167
168 48
        $statement = $this->pdo->prepare($query);
169
170 48
        $statement->execute();
171 48
        $statement->setFetchMode(\PDO::FETCH_OBJ);
172
173 48
        $callback = function ($item) use ($row) {
174 45
            return $item->column == $row->Field;
175 48
        };
176
177 48
        $columns = array_filter($statement->fetchAll(), $callback);
178
179 48
        foreach ($columns as $row) {
180 45
            $referencedTable = $this->stripTableSchema($row->referenced_table);
181
182 45
            $column->setReferencedField($row->referenced_column);
183 45
            $column->setReferencedTable($referencedTable);
184 48
        }
185
186 48
        return $column;
187
    }
188
189
    /**
190
     * Sets the properties of the specified column.
191
     *
192
     * @param  mixed                   $row
193
     * @param  \Rougin\Describe\Column $column
194
     * @return \Rougin\Describe\Column
195
     */
196 48
    protected function setProperties($row, Column $column)
197
    {
198 48
        $null = 'Null';
199
200 48
        if ($row->Extra == 'auto_increment') {
201 48
            $column->setAutoIncrement(true);
202 48
        }
203
204 48
        if ($row->$null == 'YES') {
205 48
            $column->setNull(true);
206 48
        }
207
208 48
        return $column;
209
    }
210
211
    /**
212
     * Strips the table schema from the table name.
213
     *
214
     * @param  string $table
215
     * @return string
216
     */
217 45
    protected function stripTableSchema($table)
218
    {
219 45
        return (strpos($table, '.') !== false) ? substr($table, strpos($table, '.') + 1) : $table;
220
    }
221
}
222