Passed
Pull Request — main (#122)
by Andreas
02:05
created

CratePlatform::getRegexpExpression()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 1
Bugs 0 Features 0
Metric Value
eloc 1
c 1
b 0
f 0
dl 0
loc 3
ccs 2
cts 2
cp 1
rs 10
cc 1
nc 1
nop 0
crap 1
1
<?php
2
3
/**
4
 * Licensed to CRATE Technology GmbH("Crate") under one or more contributor
5
 * license agreements.  See the NOTICE file distributed with this work for
6
 * additional information regarding copyright ownership.  Crate licenses
7
 * this file to you under the Apache License, Version 2.0 (the "License");
8
 * you may not use this file except in compliance with the License.  You may
9
 * obtain a copy of the License at
10
 *
11
 * http://www.apache.org/licenses/LICENSE-2.0
12
 *
13
 * Unless required by applicable law or agreed to in writing, software
14
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
15
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
16
 * License for the specific language governing permissions and limitations
17
 * under the License.
18
 *
19
 * However, if you have executed another commercial license agreement
20
 * with Crate these terms will supersede the license and you may use the
21
 * software solely pursuant to the terms of the relevant commercial agreement.
22
 */
23
24
namespace Crate\DBAL\Platforms;
25
26
use Crate\DBAL\Types\MapType;
27
use Crate\DBAL\Types\TimestampType;
28
use Doctrine\DBAL\Event\SchemaCreateTableColumnEventArgs;
29
use Doctrine\DBAL\Event\SchemaCreateTableEventArgs;
30
use Doctrine\DBAL\Events;
31
use Doctrine\DBAL\Exception as DBALException;
32
use Doctrine\DBAL\Platforms\AbstractPlatform;
33
use Doctrine\DBAL\Schema\ForeignKeyConstraint;
34
use Doctrine\DBAL\Schema\Identifier;
35
use Doctrine\DBAL\Schema\Index;
36
use Doctrine\DBAL\Schema\Table;
37
use Doctrine\DBAL\Schema\TableDiff;
38
use Doctrine\DBAL\Types\Type;
39
use InvalidArgumentException;
40
41
class CratePlatform extends AbstractPlatform
42
{
43
    public const TIMESTAMP_FORMAT =  'Y-m-d\TH:i:s';
44
    public const TIMESTAMP_FORMAT_TZ =  'Y-m-d\TH:i:sO';
45
    public const TABLE_WHERE_CLAUSE_FORMAT = '%s.table_name = %s AND %s.schema_name = %s';
46
47
    /**
48
     * {@inheritDoc}
49
     */
50 260
    public function __construct()
51
    {
52 260
        $this->initializeDoctrineTypeMappings();
53 260
        if (!Type::hasType(MapType::NAME)) {
54
            Type::addType(MapType::NAME, 'Crate\DBAL\Types\MapType');
55
        }
56 260
        if (!Type::hasType(TimestampType::NAME)) {
57
            Type::addType(TimestampType::NAME, 'Crate\DBAL\Types\TimestampType');
58
        }
59 260
        Type::overrideType('array', 'Crate\DBAL\Types\ArrayType');
60
    }
61
62
    /**
63
     * {@inheritDoc}
64
     */
65 2
    public function getSubstringExpression($value, $from = 0, $length = null): string
66
    {
67 2
        if ($length === null) {
68 2
            return 'SUBSTR(' . $value . ', ' . $from . ')';
69
        }
70
71 2
        return 'SUBSTR(' . $value . ', ' . $from . ', ' . $length . ')';
72
    }
73
74
    /**
75
     * {@inheritDoc}
76
     */
77 2
    public function getNowExpression()
78
    {
79 2
        throw DBALException::notSupported(__METHOD__);
80
    }
81
82
    /**
83
     * {@inheritDoc}
84
     */
85 2
    public function getRegexpExpression(): string
86
    {
87 2
        return 'LIKE';
88
    }
89
90
    /**
91
     * {@inheritDoc}
92
     */
93 2
    public function getDateDiffExpression($date1, $date2): string
94
    {
95 2
        throw DBALException::notSupported(__METHOD__);
96
    }
97
98
    /**
99
     * {@inheritDoc}
100
     */
101 8
    public function supportsSequences(): bool
102
    {
103 8
        return false;
104
    }
105
106
    /**
107
     * If we want to support Schemas, we need to implement
108
     * getListNamespacesSQL and getCreateSchemaSQL methods
109
     *
110
     * {@inheritDoc}
111
     */
112 10
    public function supportsSchemas(): bool
113
    {
114 10
        return false;
115
    }
116
117
    /**
118
     * {@inheritDoc}
119
     */
120 2
    public function supportsIdentityColumns(): bool
121
    {
122 2
        return true;
123
    }
124
125
    /**
126
     * {@inheritDoc}
127
     */
128 2
    public function supportsIndexes()
129
    {
130 2
        return false;
131
    }
132
133
    /**
134
     * {@inheritDoc}
135
     */
136 112
    public function supportsCommentOnStatement(): bool
137
    {
138 112
        return false;
139
    }
140
141
    /**
142
     * {@inheritDoc}
143
     */
144 10
    public function supportsForeignKeyConstraints()
145
    {
146 10
        return false;
147
    }
148
149
    /**
150
     * {@inheritDoc}
151
     */
152 2
    public function supportsForeignKeyOnUpdate()
153
    {
154 2
        return false;
155
    }
156
157
    /**
158
     * {@inheritDoc}
159
     */
160 2
    public function supportsViews()
161
    {
162 2
        return false;
163
    }
164
165
    /**
166
     * {@inheritDoc}
167
     */
168 2
    public function prefersSequences()
169
    {
170 2
        return false;
171
    }
172
173
    /**
174
     * {@inheritDoc}
175
     */
176 2
    public function getListDatabasesSQL(): string
177
    {
178 2
        throw DBALException::notSupported(__METHOD__);
179
    }
180
181
    /**
182
     * {@inheritDoc}
183
     */
184
    public function getListTablesSQL()
185
    {
186
        return "SELECT table_name, schema_name FROM information_schema.tables " .
187
               "WHERE schema_name = 'doc' OR schema_name = 'blob'";
188
    }
189
190
    /**
191
     * {@inheritDoc}
192
     */
193 8
    public function getListTableColumnsSQL($table, $database = null)
194
    {
195 8
        return "SELECT * from information_schema.columns c " .
196 8
               "WHERE " . $this->getTableWhereClause($table);
197
    }
198
199
    /**
200
     * {@inheritDoc}
201
     */
202
    public function getListTableConstraintsSQL($table, $database = null)
0 ignored issues
show
Unused Code introduced by
The parameter $database is not used and could be removed. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-unused  annotation

202
    public function getListTableConstraintsSQL($table, /** @scrutinizer ignore-unused */ $database = null)

This check looks for parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
203
    {
204
        return "SELECT c.constraint_name, c.constraint_type " .
205
               "FROM information_schema.table_constraints c " .
206
               "WHERE " . $this->getTableWhereClause($table) . " AND constraint_type = 'PRIMARY KEY'";
207
    }
208
209
    /**
210
     * {@inheritDoc}
211
     */
212 8
    public function getListTableIndexesSQL($table, $currentDatabase = null)
213
    {
214 8
        return "SELECT c.constraint_name, c.constraint_type, k.column_name " .
215 8
               "FROM information_schema.table_constraints c " .
216 8
               "JOIN information_schema.key_column_usage k on c.constraint_name = k.constraint_name " .
217 8
               "WHERE " . $this->getTableWhereClause($table);
218
    }
219
220 10
    private function getTableWhereClause($table, $tableAlias = 'c')
221
    {
222 10
        if (strpos($table, '.') !== false) {
223
            [$schema, $table] = explode('.', $table);
224
            $schema = $this->quoteStringLiteral($schema);
225
        } else {
226 10
            $schema = $this->quoteStringLiteral('doc');
227
        }
228
229 10
        $table = new Identifier($table);
230 10
        $table = $this->quoteStringLiteral($table->getName());
231
232 10
        return sprintf(
233 10
            $this->getTableWhereClauseFormat(),
234 10
            $tableAlias,
235 10
            $table,
236 10
            $tableAlias,
237 10
            $schema
238 10
        );
239
    }
240
241
    /**
242
     * Return sprintf format string for usage at getTableWhereClause
243
     *
244
     * @return string
245
     */
246
    protected function getTableWhereClauseFormat()
247
    {
248
        return self::TABLE_WHERE_CLAUSE_FORMAT;
249
    }
250
251
    /**
252
     * {@inheritDoc}
253
     */
254 6
    public function getAlterTableSQL(TableDiff $diff): array
255
    {
256 6
        $sql = array();
257 6
        $commentsSQL = array();
258 6
        $columnSql = array();
259
260 6
        foreach ($diff->addedColumns as $column) {
261 4
            if ($this->onSchemaAlterTableAddColumn($column, $diff, $columnSql)) {
262
                continue;
263
            }
264
265 4
            $query = 'ADD ' . $this->getColumnDeclarationSQL($column->getQuotedName($this), $column->toArray());
266 4
            $sql[] = 'ALTER TABLE ' . $diff->name . ' ' . $query;
0 ignored issues
show
Deprecated Code introduced by
The property Doctrine\DBAL\Schema\TableDiff::$name has been deprecated: Use {@see getOldTable()} instead. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

266
            $sql[] = 'ALTER TABLE ' . /** @scrutinizer ignore-deprecated */ $diff->name . ' ' . $query;

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
267 4
            if ($comment = $this->getColumnComment($column)) {
0 ignored issues
show
Deprecated Code introduced by
The function Doctrine\DBAL\Platforms\...orm::getColumnComment() has been deprecated: This method will be removed without replacement. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

267
            if ($comment = /** @scrutinizer ignore-deprecated */ $this->getColumnComment($column)) {

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
268
                $commentsSQL[] = $this->getCommentOnColumnSQL($diff->name, $column->getName(), $comment);
0 ignored issues
show
Deprecated Code introduced by
The property Doctrine\DBAL\Schema\TableDiff::$name has been deprecated: Use {@see getOldTable()} instead. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

268
                $commentsSQL[] = $this->getCommentOnColumnSQL(/** @scrutinizer ignore-deprecated */ $diff->name, $column->getName(), $comment);

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
269
            }
270
        }
271
272 6
        if (count($diff->removedColumns) > 0) {
273
            throw DBALException::notSupported("Alter Table: drop columns");
274
        }
275 6
        if (count($diff->changedColumns) > 0) {
276
            throw DBALException::notSupported("Alter Table: change column options");
277
        }
278 6
        if (count($diff->renamedColumns) > 0) {
279
            throw DBALException::notSupported("Alter Table: rename columns");
280
        }
281
282 6
        $tableSql = array();
283
284 6
        if (!$this->onSchemaAlterTable($diff, $tableSql)) {
285 6
            if ($diff->newName !== false) {
0 ignored issues
show
Deprecated Code introduced by
The property Doctrine\DBAL\Schema\TableDiff::$newName has been deprecated: Rename tables via {@link AbstractSchemaManager::renameTable()} instead. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

285
            if (/** @scrutinizer ignore-deprecated */ $diff->newName !== false) {

This property has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.

Loading history...
286
                throw DBALException::notSupported("Alter Table: rename table");
287
            }
288
289 6
            $sql = array_merge($sql, $this->getPreAlterTableIndexForeignKeySQL($diff), $commentsSQL);
290
        }
291
292 6
        return array_merge($sql, $tableSql, $columnSql);
293
    }
294
295
    /**
296
     * {@inheritDoc}
297
     */
298 122
    public function getColumnDeclarationSQL($name, array $column): string
299
    {
300 122
        if (isset($column['columnDefinition'])) {
301 62
            $columnDef = $this->getCustomTypeDeclarationSQL($column);
0 ignored issues
show
Deprecated Code introduced by
The function Doctrine\DBAL\Platforms\...tomTypeDeclarationSQL() has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

301
            $columnDef = /** @scrutinizer ignore-deprecated */ $this->getCustomTypeDeclarationSQL($column);
Loading history...
302
        } else {
303 120
            $typeDecl = $column['type']->getSqlDeclaration($column, $this);
304 120
            $columnDef = $typeDecl;
305
        }
306
307 122
        return $name . ' ' . $columnDef;
308
    }
309
310
    /**
311
     * Generate table index column declaration
312
     * @param string $name
313
     * @param Index $index
314
     * @codeCoverageIgnore
315
     */
316
    public function getIndexDeclarationSQL($name, Index $index): string
317
    {
318
        $columns = $index->getQuotedColumns($this);
319
        $name = new Identifier($name);
320
321
        if (count($columns) == 0) {
322
            throw new \InvalidArgumentException("Incomplete definition. 'columns' required.");
323
        }
324
325
        return 'INDEX ' . $name->getQuotedName($this) .
326
               ' USING FULLTEXT ('. $this->getIndexFieldDeclarationListSQL($index) . ')';
0 ignored issues
show
Deprecated Code introduced by
The function Doctrine\DBAL\Platforms\...eldDeclarationListSQL() has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

326
               ' USING FULLTEXT ('. /** @scrutinizer ignore-deprecated */ $this->getIndexFieldDeclarationListSQL($index) . ')';
Loading history...
327
    }
328
329
    /**
330
     * {@inheritDoc}
331
     *
332
     * Crate wants boolean values converted to the strings 'true'/'false'.
333
     */
334 4
    public function convertBooleans($item): mixed
335
    {
336 4
        if (is_array($item)) {
337 2
            foreach ($item as $key => $value) {
338 2
                if (is_bool($value)) {
339 2
                    $item[$key] = ($value) ? 'true' : 'false';
340 2
                } elseif (is_numeric($value)) {
341 2
                    $item[$key] = ($value > 0) ? 'true' : 'false';
342
                }
343
            }
344
        } else {
345 4
            if (is_bool($item)) {
346 4
                $item = ($item) ? 'true' : 'false';
347 2
            } elseif (is_numeric($item)) {
348 2
                $item = ($item > 0) ? 'true' : 'false';
349
            }
350
        }
351
352 4
        return $item;
353
    }
354
355
    /**
356
     * {@inheritDoc}
357
     */
358 22
    public function getBooleanTypeDeclarationSQL(array $field): string
359
    {
360 22
        return 'BOOLEAN';
361
    }
362
363
    /**
364
     * {@inheritDoc}
365
     */
366 108
    public function getIntegerTypeDeclarationSQL(array $field): string
367
    {
368 108
        return 'INTEGER';
369
    }
370
371
    /**
372
     * {@inheritDoc}
373
     */
374
    public function getBigIntTypeDeclarationSQL(array $field): string
375
    {
376
        return 'LONG';
377
    }
378
379
    /**
380
     * {@inheritDoc}
381
     */
382
    public function getSmallIntTypeDeclarationSQL(array $field): string
383
    {
384
        return 'SHORT';
385
    }
386
387
    /**
388
     * {@inheritDoc}
389
     */
390
    public function getFloatDeclarationSQL(array $field): string
391
    {
392
        return 'DOUBLE';
393
    }
394
395
    /**
396
     * {@inheritDoc}
397
     */
398
    public function getDecimalTypeDeclarationSQL(array $columnDef): string
399
    {
400
        return 'DOUBLE';
401
    }
402
403
    /**
404
     * {@inheritDoc}
405
     */
406 48
    public function getDateTimeTypeDeclarationSQL(array $fieldDeclaration): string
407
    {
408 48
        return 'TIMESTAMP';
409
    }
410
411
    /**
412
     * {@inheritDoc}
413
     */
414 2
    public function getDateTimeTzTypeDeclarationSQL(array $fieldDeclaration): string
415
    {
416 2
        return 'TIMESTAMP';
417
    }
418
419
    /**
420
     * {@inheritDoc}
421
     */
422 2
    public function getDateTypeDeclarationSQL(array $fieldDeclaration): string
423
    {
424 2
        return 'TIMESTAMP';
425
    }
426
427
    /**
428
     * {@inheritDoc}
429
     */
430 2
    public function getTimeTypeDeclarationSQL(array $fieldDeclaration): string
431
    {
432 2
        return 'TIMESTAMP';
433
    }
434
435
    /**
436
     * {@inheritDoc}
437
     */
438
    // phpcs:ignore PSR2.Methods.MethodDeclaration.Underscore
439
    protected function _getCommonIntegerTypeDeclarationSQL(array $columnDef): string
440
    {
441
        return '';
442
    }
443
444
    /**
445
     * {@inheritDoc}
446
     * @param false|int $length
447
     * @param $fixed
448
     */
449
    protected function getVarcharTypeDeclarationSQLSnippet($length, $fixed): string
450
    {
451
        return 'STRING';
452
    }
453
454
    /**
455
     * {@inheritDoc}
456
     */
457
    public function getClobTypeDeclarationSQL(array $field): string
458
    {
459
        return 'STRING';
460
    }
461
462
    /**
463
     * {@inheritDoc}
464
     */
465
    public function getName()
466
    {
467
        return 'crate';
468
    }
469
470
    /**
471
     * {@inheritDoc}
472
     *
473
     * PostgreSQL returns all column names in SQL result sets in lowercase.
474
     */
475 2
    public function getSQLResultCasing($column)
476
    {
477 2
        return strtolower($column);
478
    }
479
480
    /**
481
     * {@inheritDoc}
482
     */
483 4
    public function getDateTimeTzFormatString(): string
484
    {
485 4
        return self::TIMESTAMP_FORMAT_TZ;
486
    }
487
488
    /**
489
     * {@inheritDoc}
490
     */
491 10
    public function getDateTimeFormatString(): string
492
    {
493 10
        return self::TIMESTAMP_FORMAT;
494
    }
495
496
    /**
497
     * {@inheritDoc}
498
     */
499 2
    public function getDateFormatString(): string
500
    {
501 2
        return self::TIMESTAMP_FORMAT;
502
    }
503
504
    /**
505
     * {@inheritDoc}
506
     */
507 2
    public function getTimeFormatString(): string
508
    {
509 2
        return self::TIMESTAMP_FORMAT;
510
    }
511
512
    /**
513
     * {@inheritDoc}
514
     */
515 2
    public function getTruncateTableSQL($tableName, $cascade = false): string
516
    {
517 2
        throw DBALException::notSupported(__METHOD__);
518
    }
519
520
    /**
521
     * {@inheritDoc}
522
     */
523 2
    public function getReadLockSQL()
524
    {
525 2
        throw DBALException::notSupported(__METHOD__);
526
    }
527
528
    /**
529
     * {@inheritDoc}
530
     */
531 20
    protected function initializeDoctrineTypeMappings(): void
532
    {
533 20
        $this->doctrineTypeMapping = array(
534 20
            'short'         => 'smallint',
535 20
            'integer'       => 'integer',
536 20
            'long'          => 'bigint',
537 20
            'int'           => 'integer',
538 20
            'bool'          => 'boolean',
539 20
            'boolean'       => 'boolean',
540 20
            'string'        => 'string',
541 20
            'float'         => 'float',
542 20
            'double'        => 'float',
543 20
            'timestamp'     => 'timestamp',
544 20
            'object'        => 'map',
545 20
            'array'         => 'array',
546 20
        );
547
    }
548
549
    /**
550
     * {@inheritDoc}
551
     */
552 14
    public function getDoctrineTypeMapping($dbType): string
553
    {
554
        // typed arrays will always end up in the same generic php array type
555 14
        if (substr_compare($dbType, 'array', -5) === 0) {
556 2
            $dbType = 'array';
557
        }
558 14
        return parent::getDoctrineTypeMapping($dbType);
559
    }
560
561
562
    /**
563
     * {@inheritDoc}
564
     */
565 106
    public function getVarcharMaxLength()
566
    {
567 106
        return PHP_INT_MAX;
568
    }
569
570
    /**
571
     * {@inheritDoc}
572
     */
573 54
    protected function getReservedKeywordsClass()
574
    {
575 54
        return 'Crate\DBAL\Platforms\Keywords\CrateKeywords';
576
    }
577
578
    /**
579
     * {@inheritDoc}
580
     */
581 2
    public function getBlobTypeDeclarationSQL(array $field): string
582
    {
583 2
        throw DBALException::notSupported(__METHOD__);
584
    }
585
586
    /**
587
     * {@inheritDoc}
588
     * Gets the SQL statement(s) to create a table with the specified name, columns and constraints
589
     * on this platform.
590
     *
591
     * @param Table $table The name of the table.
592
     * @param integer $createFlags
593
     *
594
     * @return array The sequence of SQL statements.
595
     */
596 120
    public function getCreateTableSQL(Table $table, $createFlags = self::CREATE_INDEXES): array
597
    {
598 120
        if (!is_int($createFlags)) {
0 ignored issues
show
introduced by
The condition is_int($createFlags) is always true.
Loading history...
599
            $msg = "Second argument of CratePlatform::getCreateTableSQL() has to be integer.";
600
            throw new InvalidArgumentException($msg);
601
        }
602
603 120
        if (count($table->getColumns()) === 0) {
604 4
            throw DBALException::noColumnsSpecifiedForTable($table->getName());
605
        }
606
607 116
        $tableName = $table->getQuotedName($this);
608 116
        $options = $table->getOptions();
609 116
        $options['uniqueConstraints'] = array();
610 116
        $options['indexes'] = array();
611 116
        $options['primary'] = array();
612
613 116
        if (($createFlags & self::CREATE_INDEXES) > 0) {
614 116
            foreach ($table->getIndexes() as $index) {
615
                /* @var $index Index */
616 82
                if ($index->isPrimary()) {
617 72
                    $platform = $this;
618 72
                    $options['primary'] = array_map(function ($columnName) use ($table, $platform) {
619 72
                        return $table->getColumn($columnName)->getQuotedName($platform);
620 72
                    }, $index->getColumns());
621 72
                    $options['primary_index'] = $index;
622 10
                } elseif ($index->isUnique()) {
623 4
                    throw DBALException::notSupported(
624 4
                        "Unique constraints are not supported. Use `primary key` instead"
625 4
                    );
626
                } else {
627 6
                    $options['indexes'][$index->getName()] = $index;
628
                }
629
            }
630
        }
631
632 112
        $columnSql = array();
633 112
        $columns = array();
634
635 112
        foreach ($table->getColumns() as $column) {
636 112
            if (null !== $this->_eventManager &&
0 ignored issues
show
Deprecated Code introduced by
The property Doctrine\DBAL\Platforms\...latform::$_eventManager has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

636
            if (null !== /** @scrutinizer ignore-deprecated */ $this->_eventManager &&
Loading history...
637 112
                $this->_eventManager->hasListeners(Events::onSchemaCreateTableColumn)
0 ignored issues
show
Deprecated Code introduced by
The property Doctrine\DBAL\Platforms\...latform::$_eventManager has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

637
                /** @scrutinizer ignore-deprecated */ $this->_eventManager->hasListeners(Events::onSchemaCreateTableColumn)
Loading history...
introduced by
The constant Doctrine\DBAL\Events::onSchemaCreateTableColumn has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

637
                $this->_eventManager->hasListeners(/** @scrutinizer ignore-deprecated */ Events::onSchemaCreateTableColumn)
Loading history...
638
            ) {
639 2
                $eventArgs = new SchemaCreateTableColumnEventArgs($column, $table, $this);
0 ignored issues
show
Deprecated Code introduced by
The class Doctrine\DBAL\Event\Sche...ateTableColumnEventArgs has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

639
                $eventArgs = /** @scrutinizer ignore-deprecated */ new SchemaCreateTableColumnEventArgs($column, $table, $this);
Loading history...
640 2
                $this->_eventManager->dispatchEvent(Events::onSchemaCreateTableColumn, $eventArgs);
0 ignored issues
show
introduced by
The constant Doctrine\DBAL\Events::onSchemaCreateTableColumn has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

640
                $this->_eventManager->dispatchEvent(/** @scrutinizer ignore-deprecated */ Events::onSchemaCreateTableColumn, $eventArgs);
Loading history...
Deprecated Code introduced by
The property Doctrine\DBAL\Platforms\...latform::$_eventManager has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

640
                /** @scrutinizer ignore-deprecated */ $this->_eventManager->dispatchEvent(Events::onSchemaCreateTableColumn, $eventArgs);
Loading history...
641
642 2
                $columnSql = array_merge($columnSql, $eventArgs->getSql());
643
644 2
                if ($eventArgs->isDefaultPrevented()) {
645
                    continue;
646
                }
647
            }
648 112
            $columns[$column->getQuotedName($this)] = self::prepareColumnData($this, $column, $options['primary']);
649
        }
650
651 110
        if (null !== $this->_eventManager && $this->_eventManager->hasListeners(Events::onSchemaCreateTable)) {
0 ignored issues
show
Deprecated Code introduced by
The property Doctrine\DBAL\Platforms\...latform::$_eventManager has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

651
        if (null !== $this->_eventManager && /** @scrutinizer ignore-deprecated */ $this->_eventManager->hasListeners(Events::onSchemaCreateTable)) {
Loading history...
introduced by
The constant Doctrine\DBAL\Events::onSchemaCreateTable has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

651
        if (null !== $this->_eventManager && $this->_eventManager->hasListeners(/** @scrutinizer ignore-deprecated */ Events::onSchemaCreateTable)) {
Loading history...
652 2
            $eventArgs = new SchemaCreateTableEventArgs($table, $columns, $options, $this);
0 ignored issues
show
Deprecated Code introduced by
The class Doctrine\DBAL\Event\SchemaCreateTableEventArgs has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

652
            $eventArgs = /** @scrutinizer ignore-deprecated */ new SchemaCreateTableEventArgs($table, $columns, $options, $this);
Loading history...
653 2
            $this->_eventManager->dispatchEvent(Events::onSchemaCreateTable, $eventArgs);
0 ignored issues
show
introduced by
The constant Doctrine\DBAL\Events::onSchemaCreateTable has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

653
            $this->_eventManager->dispatchEvent(/** @scrutinizer ignore-deprecated */ Events::onSchemaCreateTable, $eventArgs);
Loading history...
Deprecated Code introduced by
The property Doctrine\DBAL\Platforms\...latform::$_eventManager has been deprecated. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

653
            /** @scrutinizer ignore-deprecated */ $this->_eventManager->dispatchEvent(Events::onSchemaCreateTable, $eventArgs);
Loading history...
654
655 2
            if ($eventArgs->isDefaultPrevented()) {
656
                return array_merge($eventArgs->getSql(), $columnSql);
657
            }
658
        }
659
660 110
        $sql = $this->_getCreateTableSQL($tableName, $columns, $options);
661 108
        if ($this->supportsCommentOnStatement()) {
662
            foreach ($table->getColumns() as $column) {
663
                if ($this->getColumnComment($column)) {
0 ignored issues
show
Deprecated Code introduced by
The function Doctrine\DBAL\Platforms\...orm::getColumnComment() has been deprecated: This method will be removed without replacement. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

663
                if (/** @scrutinizer ignore-deprecated */ $this->getColumnComment($column)) {

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
664
                    $sql[] = $this->getCommentOnColumnSQL(
665
                        $tableName,
666
                        $column->getName(),
667
                        $this->getColumnComment($column)
0 ignored issues
show
Deprecated Code introduced by
The function Doctrine\DBAL\Platforms\...orm::getColumnComment() has been deprecated: This method will be removed without replacement. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

667
                        /** @scrutinizer ignore-deprecated */ $this->getColumnComment($column)

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
668
                    );
669
                }
670
            }
671
        }
672
673 108
        return array_merge($sql, $columnSql);
674
    }
675
676
    /**
677
     * {@inheritDoc}
678
     */
679
    // phpcs:ignore PSR2.Methods.MethodDeclaration.Underscore
680 110
    protected function _getCreateTableSQL($name, array $columns, array $options = array()): array
681
    {
682 110
        $columnListSql = $this->getColumnDeclarationListSQL($columns);
683
684 110
        if (isset($options['primary']) && ! empty($options['primary'])) {
685 72
            $keyColumns = array_unique(array_values($options['primary']));
686 72
            $columnListSql .= ', PRIMARY KEY(' . implode(', ', $keyColumns) . ')';
687
        }
688
689 110
        if (isset($options['indexes']) && ! empty($options['indexes'])) {
690 6
            foreach ($options['indexes'] as $index => $definition) {
691 6
                $columnListSql .= ', ' . $this->getIndexDeclarationSQL($index, $definition);
692
            }
693
        }
694
695 110
        if (isset($options['foreignKeys'])) {
696
            throw DBALException::notSupported("Create Table: foreign keys");
697
        }
698
699 110
        $query = 'CREATE TABLE ' . $name . ' (' . $columnListSql . ')';
700 110
        $query .= $this->buildShardingOptions($options);
701 110
        $query .= $this->buildPartitionOptions($options);
702 108
        $query .= $this->buildTableOptions($options);
703 108
        return array($query);
704
    }
705
706
    /**
707
     * Build SQL for table options
708
     *
709
     * @param mixed[] $options
710
     *
711
     * @return string
712
     */
713 108
    private function buildTableOptions(array $options)
714
    {
715 108
        if (! isset($options['table_options'])) {
716 104
            return '';
717
        }
718
719 4
        $tableOptions = [];
720 4
        foreach ($options['table_options'] as $key => $val) {
721 4
            $tableOptions[] = sprintf('"%s" = %s', $key, $this->quoteStringLiteral($val));
722
        }
723 4
        if (count($tableOptions) == 0) {
724
            return '';
725
        }
726
727 4
        return sprintf(' WITH (%s)', implode(', ', $tableOptions));
728
    }
729
730
    /**
731
     * Build SQL for sharding options.
732
     *
733
     * @param mixed[] $options
734
     *
735
     * @return string
736
     */
737 110
    private function buildShardingOptions(array $options)
738
    {
739 110
        $shardingOptions = [];
740
741 110
        if (isset($options['sharding_routing_column'])) {
742 4
            $columnName = new Identifier($options['sharding_routing_column']);
743 4
            $shardingOptions[] = sprintf('BY (%s)', $columnName->getQuotedName($this));
744
        }
745 110
        if (isset($options['sharding_num_shards'])) {
746 4
            $shardingOptions[] = sprintf("INTO %d SHARDS", $options['sharding_num_shards']);
747
        }
748
749 110
        if (count($shardingOptions) == 0) {
750 106
            return '';
751
        }
752
753 4
        return sprintf(" CLUSTERED %s", implode(' ', $shardingOptions));
754
    }
755
756
    /**
757
     * Build SQL for partition options.
758
     *
759
     * @param mixed[] $options
760
     *
761
     * @return string
762
     */
763 110
    private function buildPartitionOptions(array $options)
764
    {
765 110
        if (! isset($options['partition_columns'])) {
766 104
            return '';
767
        }
768 6
        $columns = $options['partition_columns'];
769 6
        if (! is_array($columns)) {
770 2
            throw new InvalidArgumentException(sprintf("Expecting array type at 'partition_columns'"));
771
        }
772 4
        $quotedNames = [];
773 4
        foreach ($columns as $name) {
774 4
            $name = new Identifier($name);
775 4
            $quotedNames[] = $name->getQuotedName($this);
776
        }
777
778 4
        return sprintf(" PARTITIONED BY (%s)", implode(', ', $quotedNames));
779
    }
780
781
    /**
782
     * @param \Doctrine\DBAL\Schema\Column $column The name of the table.
783
     * @param array List of primary key column names
0 ignored issues
show
Bug introduced by
The type Crate\DBAL\Platforms\List was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
784
     *
785
     * @return array The column data as associative array.
786
     * @throws DBALException
787
     */
788 116
    public static function prepareColumnData(AbstractPlatform $platform, $column, $primaries = array())
789
    {
790 116
        if ($column->hasCustomSchemaOption("unique") ? $column->getCustomSchemaOption("unique") : false) {
0 ignored issues
show
Deprecated Code introduced by
The function Doctrine\DBAL\Schema\Col...hasCustomSchemaOption() has been deprecated: Use {@link hasPlatformOption()} instead ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

790
        if (/** @scrutinizer ignore-deprecated */ $column->hasCustomSchemaOption("unique") ? $column->getCustomSchemaOption("unique") : false) {

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
Deprecated Code introduced by
The function Doctrine\DBAL\Schema\Col...getCustomSchemaOption() has been deprecated: Use {@link getPlatformOption()} instead ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

790
        if ($column->hasCustomSchemaOption("unique") ? /** @scrutinizer ignore-deprecated */ $column->getCustomSchemaOption("unique") : false) {

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
791 2
            throw DBALException::notSupported("Unique constraints are not supported. Use `primary key` instead");
792
        }
793
794 114
        $columnData = array();
795 114
        $columnData['name'] = $column->getQuotedName($platform);
796 114
        $columnData['type'] = $column->getType();
797 114
        $columnData['length'] = $column->getLength();
798 114
        $columnData['notnull'] = $column->getNotNull();
799 114
        $columnData['fixed'] = $column->getFixed();
800 114
        $columnData['unique'] = false;
801 114
        $columnData['version'] = $column->hasPlatformOption("version") ? $column->getPlatformOption("version") : false;
802
803 114
        if (strtolower($columnData['type']->getName()) ==
804 114
            strtolower($platform->getVarcharTypeDeclarationSQLSnippet(0, false))
805 114
                && $columnData['length'] === null) {
806
            $columnData['length'] = 255;
807
        }
808
809 114
        $columnData['unsigned'] = $column->getUnsigned();
810 114
        $columnData['precision'] = $column->getPrecision();
811 114
        $columnData['scale'] = $column->getScale();
812 114
        $columnData['default'] = $column->getDefault();
813 114
        $columnData['columnDefinition'] = $column->getColumnDefinition();
814 114
        $columnData['autoincrement'] = $column->getAutoincrement();
815 114
        $columnData['comment'] = $platform->getColumnComment($column);
816 114
        $columnData['platformOptions'] = $column->getPlatformOptions();
817
818 114
        if (in_array($column->getName(), $primaries)) {
819 70
            $columnData['primary'] = true;
820
        }
821 114
        return $columnData;
822
    }
823
824
    /**
825
     * {@inheritDoc}
826
     */
827 2
    public function getCreateDatabaseSQL($database): string
828
    {
829 2
        throw DBALException::notSupported(__METHOD__);
830
    }
831
832
    /**
833
     * {@inheritDoc}
834
     */
835 2
    public function getDropDatabaseSQL($database): string
836
    {
837 2
        throw DBALException::notSupported(__METHOD__);
838
    }
839
840
    /**
841
     * {@inheritDoc}
842
     */
843
    public function getCreateForeignKeySQL(ForeignKeyConstraint $foreignKey, $table): string
844
    {
845
        throw DBALException::notSupported(__METHOD__);
846
    }
847
848
    /**
849
     * {@inheritDoc}
850
     */
851 2
    public function getGuidTypeDeclarationSQL(array $field): string
852
    {
853 2
        throw DBALException::notSupported(__METHOD__);
854
    }
855
856
    /**
857
     * Returns the SQL query to return the CrateDB specific table options associated
858
     * with a given table.
859
     *
860
     * @return string
861
     */
862 6
    public function getTableOptionsSQL(string $table): string
863
    {
864 6
        return "SELECT clustered_by, number_of_shards, partitioned_by, number_of_replicas, column_policy, settings " .
865 6
               "FROM information_schema.tables c " .
866 6
               "WHERE " . $this->getTableWhereClause($table);
867
    }
868
869
    /**
870
     * {@inheritDoc}
871
     */
872 10
    public function getCurrentDatabaseExpression(): string
873
    {
874
        // Added by Doctrine 3.
875 10
        return 'CURRENT_DATABASE()';
876
    }
877
}
878