Passed
Pull Request — 2.x (#224)
by
unknown
19:26
created

Table::getDependencies()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 0
dl 0
loc 3
ccs 0
cts 0
cp 0
crap 2
rs 10
c 0
b 0
f 0
1
<?php
2
3
/**
4
 * This file is part of Cycle ORM package.
5
 *
6
 * For the full copyright and license information, please view the LICENSE
7
 * file that was distributed with this source code.
8
 */
9
10
declare(strict_types=1);
11
12
namespace Cycle\Database;
13
14
use Cycle\Database\Exception\BuilderException;
15
use Cycle\Database\Query\DeleteQuery;
16
use Cycle\Database\Query\InsertQuery;
17
use Cycle\Database\Query\SelectQuery;
18
use Cycle\Database\Query\UpdateQuery;
19
use Cycle\Database\Query\UpsertQuery;
20
use Cycle\Database\Schema\AbstractTable;
21
22
/**
23
 * Represent table level abstraction with simplified access to SelectQuery associated with such
24
 * table.
25
 *
26
 * @method int avg($identifier) Perform aggregation (AVG) based on column or expression value.
27
 * @method int min($identifier) Perform aggregation (MIN) based on column or expression value.
28
 * @method int max($identifier) Perform aggregation (MAX) based on column or expression value.
29
 * @method int sum($identifier) Perform aggregation (SUM) based on column or expression value.
30
 */
31
final class Table implements TableInterface, \IteratorAggregate, \Countable
32
{
33
    /**
34
     * @param DatabaseInterface $database Parent DBAL database.
35
     *
36 2052
     * @psalm-param non-empty-string $name Table name without prefix.
37
     */
38
    public function __construct(
39
        protected DatabaseInterface $database,
40 2052
        private string $name,
41
    ) {}
42
43
    /**
44
     * Get associated database.
45
     */
46
    public function getDatabase(): DatabaseInterface
47
    {
48
        return $this->database;
49 50
    }
50
51 50
    /**
52
     * Real table name, will include database prefix.
53
     *
54
     * @psalm-return non-empty-string
55
     */
56
    public function getFullName(): string
57 8
    {
58
        return $this->database->getPrefix() . $this->name;
59 8
    }
60
61
    /**
62
     * @psalm-return non-empty-string
63
     */
64
    public function getName(): string
65
    {
66
        return $this->name;
67 8
    }
68
69 8
    /**
70
     * Get modifiable table schema.
71
     */
72
    public function getSchema(): AbstractTable
73
    {
74
        return $this->database
75 2
            ->getDriver(DatabaseInterface::WRITE)
76
            ->getSchemaHandler()
77 2
            ->getSchema(
78
                $this->name,
79
                $this->database->getPrefix(),
80
            );
81
    }
82
83 1974
    /**
84
     * Erase all table data.
85 1974
     */
86 1974
    public function eraseData(): void
87 1974
    {
88 1974
        $this->database
89 1974
            ->getDriver(DatabaseInterface::WRITE)
90 1974
            ->getSchemaHandler()
91
            ->eraseTable($this->getSchema());
92
    }
93
94
    /**
95
     * Insert one fieldset into table and return last inserted id.
96
     *
97 16
     * Example:
98
     * $table->insertOne(["name" => "Wolfy-J", "balance" => 10]);
99 16
     *
100 16
     * @throws BuilderException
101 16
     */
102 16
    public function insertOne(array $rowset = []): int|string|null
103 8
    {
104
        return $this->database
105
            ->insert($this->name)
106
            ->values($rowset)
107
            ->run();
108
    }
109
110
    /**
111
     * Perform batch insert into table, every rowset should have identical amount of values matched
112
     * with column names provided in first argument. Method will return lastInsertID on success.
113 240
     *
114
     * Example:
115 240
     * $table->insertMultiple(["name", "balance"], array(["Bob", 10], ["Jack", 20]))
116 240
     *
117 240
     * @param array $columns Array of columns.
118 240
     * @param array $rowsets Array of rowsets.
119
     */
120
    public function insertMultiple(array $columns = [], array $rowsets = []): void
121
    {
122
        //No return value
123
        $this->database
124
            ->insert($this->name)
125
            ->columns($columns)
126
            ->values($rowsets)
127
            ->run();
128
    }
129
130
    /**
131 110
     * Upsert one fieldset into table and return last inserted id.
132
     *
133
     * Example:
134 110
     * $table->upsertOne(["name" => "Wolfy-J", "balance" => 10]);
135 110
     *
136 110
     * @throws BuilderException
137 110
     */
138 110
    public function upsertOne(array $rowset = []): int|string|null
139 102
    {
140
        return $this->database
141
            ->upsert($this->name)
142
            ->values($rowset)
143
            ->run();
144 16
    }
145
146 16
    /**
147 16
     * Perform batch upsert into table, every rowset should have identical amount of values matched
148
     * with column names provided in first argument. Method will return lastInsertID on success.
149
     *
150
     * Example:
151
     * $table->insertMultiple(["name", "balance"], array(["Bob", 10], ["Jack", 20]))
152
     *
153 376
     * @param array $columns Array of columns.
154
     * @param array $rowsets Array of rowsets.
155 376
     */
156 376
    public function upsertMultiple(array $columns = [], array $rowsets = []): void
157 376
    {
158
        $this->database
159
            ->upsert($this->name)
160
            ->columns($columns)
161
            ->values($rowsets)
162
            ->run();
163
    }
164
165
    /**
166
     * Get insert builder specific to current table.
167 32
     */
168
    public function insert(): InsertQuery
169 32
    {
170 32
        return $this->database
171
            ->insert($this->name);
172
    }
173
174
    /**
175
     * Get upsert builder specific to current table.
176
     */
177
    public function upsert(): UpsertQuery
178
    {
179
        return $this->database
180 48
            ->upsert($this->name);
181
    }
182 48
183 48
    /**
184
     * Get SelectQuery builder with pre-populated from tables.
185
     */
186
    public function select(mixed $columns = '*'): SelectQuery
187
    {
188
        return $this->database
189 222
            ->select(\func_num_args() ? \func_get_args() : '*')
190
            ->from($this->name);
191 222
    }
192
193
    /**
194
     * Get DeleteQuery builder with pre-populated table name. This is NOT table delete method, use
195
     * schema()->drop() for this purposes. If you want to remove all records from table use
196
     * Table->truncate() method. Call ->run() to perform query.
197
     *
198
     * @param array $where Initial set of where rules specified as array.
199 8
     */
200
    public function delete(array $where = []): DeleteQuery
201 8
    {
202
        return $this->database
203
            ->delete($this->name, $where);
204
    }
205
206
    /**
207 24
     * Get UpdateQuery builder with pre-populated table name and set of columns to update. Columns
208
     * can be scalar values, Parameter objects or even SQLFragments. Call ->run() to perform query.
209 24
     *
210
     * @param array $values Initial set of columns associated with values.
211
     * @param array $where  Initial set of where rules specified as array.
212 8
     */
213
    public function update(array $values = [], array $where = []): UpdateQuery
214 8
    {
215
        return $this->database
216
            ->update($this->name, $values, $where);
217
    }
218
219
    /**
220
     * Count number of records in table.
221 8
     */
222
    public function count(): int
223 8
    {
224
        return $this->select()->count();
225
    }
226
227
    /**
228
     * Retrieve an external iterator, SelectBuilder will return PDOResult as iterator.
229
     *
230
     * @link http://php.net/manual/en/iteratoraggregate.getiterator.php
231 16
     */
232
    public function getIterator(): SelectQuery
233 16
    {
234
        return $this->select();
235
    }
236
237
    /**
238
     * A simple alias for table query without condition (returns array of rows).
239
     */
240
    public function fetchAll(): array
241 8
    {
242
        return $this->select()->fetchAll();
243 8
    }
244
245
    public function exists(): bool
246
    {
247
        return $this->getSchema()->exists();
248
    }
249
250
    /**
251 8
     * Array of columns dedicated to primary index. Attention, this methods will ALWAYS return
252
     * array, even if there is only one primary key.
253 8
     */
254
    public function getPrimaryKeys(): array
255
    {
256
        return $this->getSchema()->getPrimaryKeys();
257
    }
258
259
    /**
260
     * Check if table have specified column.
261 8
     *
262
     * @psalm-param non-empty-string $name Column name.
263 8
     */
264
    public function hasColumn(string $name): bool
265
    {
266
        return $this->getSchema()->hasColumn($name);
267
    }
268
269
    /**
270
     * Get all declared columns.
271 8
     *
272
     * @return ColumnInterface[]
273 8
     */
274
    public function getColumns(): array
275
    {
276
        return $this->getSchema()->getColumns();
277
    }
278
279
    /**
280
     * Check if table has index related to set of provided columns. Columns order does matter!
281 8
     *
282
     */
283 8
    public function hasIndex(array $columns = []): bool
284
    {
285
        return $this->getSchema()->hasIndex($columns);
286
    }
287
288
    /**
289
     * Get all table indexes.
290 8
     *
291
     * @return IndexInterface[]
292 8
     */
293
    public function getIndexes(): array
294
    {
295
        return $this->getSchema()->getIndexes();
296
    }
297
298
    /**
299
     * Check if table has foreign key related to table column.
300
     *
301
     * @param array $columns Column names.
302
     */
303
    public function hasForeignKey(array $columns): bool
304
    {
305
        return $this->getSchema()->hasForeignKey($columns);
306
    }
307
308
    /**
309
     * Get all table foreign keys.
310
     *
311
     * @return ForeignKeyInterface[]
312
     */
313
    public function getForeignKeys(): array
314
    {
315
        return $this->getSchema()->getForeignKeys();
316
    }
317
318
    /**
319
     * Get list of table names current schema depends on, must include every table linked using
320
     * foreign key or other constraint. Table names MUST include prefixes.
321
     */
322
    public function getDependencies(): array
323
    {
324
        return $this->getSchema()->getDependencies();
325
    }
326
327
    /**
328
     * Bypass call to SelectQuery builder.
329
     *
330
     * @psalm-param non-empty-string $method
331
     *
332
     * @return mixed|SelectQuery
333
     */
334
    public function __call(string $method, array $arguments): mixed
335
    {
336
        return \call_user_func_array([$this->select(), $method], $arguments);
337
    }
338
}
339