Completed
Push — master ( 89a52c...c0f6d4 )
by Marco
19s queued 13s
created

testReturnsBinaryTypeLongerThanMaxDeclarationSQL()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 4
rs 10
c 0
b 0
f 0
cc 1
eloc 2
nc 1
nop 0
1
<?php
2
3
namespace Doctrine\Tests\DBAL\Platforms;
4
5
use Doctrine\DBAL\DBALException;
6
use Doctrine\DBAL\Platforms\OraclePlatform;
7
use Doctrine\DBAL\Schema\Column;
8
use Doctrine\DBAL\Schema\Comparator;
9
use Doctrine\DBAL\Schema\ForeignKeyConstraint;
10
use Doctrine\DBAL\Schema\Table;
11
use Doctrine\DBAL\TransactionIsolationLevel;
12
use Doctrine\DBAL\Types\Type;
13
use function array_walk;
14
use function preg_replace;
15
use function strtoupper;
16
use function uniqid;
17
18
class OraclePlatformTest extends AbstractPlatformTestCase
19
{
20
    public static function dataValidIdentifiers()
21
    {
22
        return [
23
            ['a'],
24
            ['foo'],
25
            ['Foo'],
26
            ['Foo123'],
27
            ['Foo#bar_baz$'],
28
            ['"a"'],
29
            ['"1"'],
30
            ['"foo_bar"'],
31
            ['"@$%&!"'],
32
        ];
33
    }
34
35
    /**
36
     * @dataProvider dataValidIdentifiers
37
     */
38
    public function testValidIdentifiers($identifier)
39
    {
40
        $platform = $this->createPlatform();
41
        $platform->assertValidIdentifier($identifier);
42
43
        $this->addToAssertionCount(1);
44
    }
45
46
    public static function dataInvalidIdentifiers()
47
    {
48
        return [
49
            ['1'],
50
            ['abc&'],
51
            ['abc-def'],
52
            ['"'],
53
            ['"foo"bar"'],
54
        ];
55
    }
56
57
    /**
58
     * @dataProvider dataInvalidIdentifiers
59
     */
60
    public function testInvalidIdentifiers($identifier)
61
    {
62
        $this->expectException(DBALException::class);
63
64
        $platform = $this->createPlatform();
65
        $platform->assertValidIdentifier($identifier);
66
    }
67
68
    public function createPlatform()
69
    {
70
        return new OraclePlatform;
71
    }
72
73
    public function getGenerateTableSql()
74
    {
75
        return 'CREATE TABLE test (id NUMBER(10) NOT NULL, test VARCHAR2(255) DEFAULT NULL NULL, PRIMARY KEY(id))';
76
    }
77
78
    public function getGenerateTableWithMultiColumnUniqueIndexSql()
79
    {
80
        return array(
81
            'CREATE TABLE test (foo VARCHAR2(255) DEFAULT NULL NULL, bar VARCHAR2(255) DEFAULT NULL NULL)',
82
            'CREATE UNIQUE INDEX UNIQ_D87F7E0C8C73652176FF8CAA ON test (foo, bar)',
83
        );
84
    }
85
86
    public function getGenerateAlterTableSql()
87
    {
88
        return array(
89
            'ALTER TABLE mytable ADD (quota NUMBER(10) DEFAULT NULL NULL)',
90
            "ALTER TABLE mytable MODIFY (baz VARCHAR2(255) DEFAULT 'def' NOT NULL, bloo NUMBER(1) DEFAULT '0' NOT NULL)",
91
            "ALTER TABLE mytable DROP (foo)",
92
            "ALTER TABLE mytable RENAME TO userlist",
93
        );
94
    }
95
96
    /**
97
     * @expectedException \Doctrine\DBAL\DBALException
98
     */
99
    public function testRLike()
100
    {
101
        self::assertEquals('RLIKE', $this->_platform->getRegexpExpression(), 'Regular expression operator is not correct');
102
    }
103
104
    public function testGeneratesSqlSnippets()
105
    {
106
        self::assertEquals('"', $this->_platform->getIdentifierQuoteCharacter(), 'Identifier quote character is not correct');
107
        self::assertEquals('column1 || column2 || column3', $this->_platform->getConcatExpression('column1', 'column2', 'column3'), 'Concatenation expression is not correct');
108
    }
109
110
    public function testGeneratesTransactionsCommands()
111
    {
112
        self::assertEquals(
113
            'SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED',
114
            $this->_platform->getSetTransactionIsolationSQL(TransactionIsolationLevel::READ_UNCOMMITTED)
115
        );
116
        self::assertEquals(
117
            'SET TRANSACTION ISOLATION LEVEL READ COMMITTED',
118
            $this->_platform->getSetTransactionIsolationSQL(TransactionIsolationLevel::READ_COMMITTED)
119
        );
120
        self::assertEquals(
121
            'SET TRANSACTION ISOLATION LEVEL SERIALIZABLE',
122
            $this->_platform->getSetTransactionIsolationSQL(TransactionIsolationLevel::REPEATABLE_READ)
123
        );
124
        self::assertEquals(
125
            'SET TRANSACTION ISOLATION LEVEL SERIALIZABLE',
126
            $this->_platform->getSetTransactionIsolationSQL(TransactionIsolationLevel::SERIALIZABLE)
127
        );
128
    }
129
130
    /**
131
     * @expectedException \Doctrine\DBAL\DBALException
132
     */
133
    public function testCreateDatabaseThrowsException()
134
    {
135
        self::assertEquals('CREATE DATABASE foobar', $this->_platform->getCreateDatabaseSQL('foobar'));
136
    }
137
138
    public function testDropDatabaseThrowsException()
139
    {
140
        self::assertEquals('DROP USER foobar CASCADE', $this->_platform->getDropDatabaseSQL('foobar'));
141
    }
142
143
    public function testDropTable()
144
    {
145
        self::assertEquals('DROP TABLE foobar', $this->_platform->getDropTableSQL('foobar'));
146
    }
147
148
    public function testGeneratesTypeDeclarationForIntegers()
149
    {
150
        self::assertEquals(
151
            'NUMBER(10)',
152
            $this->_platform->getIntegerTypeDeclarationSQL(array())
153
        );
154
        self::assertEquals(
155
            'NUMBER(10)',
156
            $this->_platform->getIntegerTypeDeclarationSQL(array('autoincrement' => true)
157
            ));
158
        self::assertEquals(
159
            'NUMBER(10)',
160
            $this->_platform->getIntegerTypeDeclarationSQL(
161
                array('autoincrement' => true, 'primary' => true)
162
            ));
163
    }
164
165
    public function testGeneratesTypeDeclarationsForStrings()
166
    {
167
        self::assertEquals(
168
            'CHAR(10)',
169
            $this->_platform->getVarcharTypeDeclarationSQL(
170
                array('length' => 10, 'fixed' => true)
171
            ));
172
        self::assertEquals(
173
            'VARCHAR2(50)',
174
            $this->_platform->getVarcharTypeDeclarationSQL(array('length' => 50)),
175
            'Variable string declaration is not correct'
176
        );
177
        self::assertEquals(
178
            'VARCHAR2(255)',
179
            $this->_platform->getVarcharTypeDeclarationSQL(array()),
180
            'Long string declaration is not correct'
181
        );
182
    }
183
184
    public function testPrefersIdentityColumns()
185
    {
186
        self::assertFalse($this->_platform->prefersIdentityColumns());
187
    }
188
189
    public function testSupportsIdentityColumns()
190
    {
191
        self::assertFalse($this->_platform->supportsIdentityColumns());
192
    }
193
194
    public function testSupportsSavePoints()
195
    {
196
        self::assertTrue($this->_platform->supportsSavepoints());
197
    }
198
199
    /**
200
     * {@inheritdoc}
201
     */
202
    protected function supportsCommentOnStatement()
203
    {
204
        return true;
205
    }
206
207
    public function getGenerateIndexSql()
208
    {
209
        return 'CREATE INDEX my_idx ON mytable (user_name, last_login)';
210
    }
211
212
    public function getGenerateUniqueIndexSql()
213
    {
214
        return 'CREATE UNIQUE INDEX index_name ON test (test, test2)';
215
    }
216
217
    public function getGenerateForeignKeySql()
218
    {
219
        return 'ALTER TABLE test ADD FOREIGN KEY (fk_name_id) REFERENCES other_table (id)';
220
    }
221
222
    /**
223
     * @group DBAL-1097
224
     *
225
     * @dataProvider getGeneratesAdvancedForeignKeyOptionsSQLData
226
     */
227
    public function testGeneratesAdvancedForeignKeyOptionsSQL(array $options, $expectedSql)
228
    {
229
        $foreignKey = new ForeignKeyConstraint(array('foo'), 'foreign_table', array('bar'), null, $options);
230
231
        self::assertSame($expectedSql, $this->_platform->getAdvancedForeignKeyOptionsSQL($foreignKey));
232
    }
233
234
    /**
235
     * @return array
236
     */
237
    public function getGeneratesAdvancedForeignKeyOptionsSQLData()
238
    {
239
        return array(
240
            array(array(), ''),
241
            array(array('onUpdate' => 'CASCADE'), ''),
242
            array(array('onDelete' => 'CASCADE'), ' ON DELETE CASCADE'),
243
            array(array('onDelete' => 'NO ACTION'), ''),
244
            array(array('onDelete' => 'RESTRICT'), ''),
245
            array(array('onUpdate' => 'SET NULL', 'onDelete' => 'SET NULL'), ' ON DELETE SET NULL'),
246
        );
247
    }
248
249
    /**
250
     * {@inheritdoc}
251
     */
252
    public function getReturnsForeignKeyReferentialActionSQL()
253
    {
254
        return array(
255
            array('CASCADE', 'CASCADE'),
256
            array('SET NULL', 'SET NULL'),
257
            array('NO ACTION', ''),
258
            array('RESTRICT', ''),
259
            array('CaScAdE', 'CASCADE'),
260
        );
261
    }
262
263
    public function testModifyLimitQuery()
264
    {
265
        $sql = $this->_platform->modifyLimitQuery('SELECT * FROM user', 10, 0);
266
        self::assertEquals('SELECT a.* FROM (SELECT * FROM user) a WHERE ROWNUM <= 10', $sql);
267
    }
268
269
    public function testModifyLimitQueryWithEmptyOffset()
270
    {
271
        $sql = $this->_platform->modifyLimitQuery('SELECT * FROM user', 10);
272
        self::assertEquals('SELECT a.* FROM (SELECT * FROM user) a WHERE ROWNUM <= 10', $sql);
273
    }
274
275
    public function testModifyLimitQueryWithNonEmptyOffset()
276
    {
277
        $sql = $this->_platform->modifyLimitQuery('SELECT * FROM user', 10, 10);
278
        self::assertEquals('SELECT * FROM (SELECT a.*, ROWNUM AS doctrine_rownum FROM (SELECT * FROM user) a WHERE ROWNUM <= 20) WHERE doctrine_rownum >= 11', $sql);
279
    }
280
281
    public function testModifyLimitQueryWithEmptyLimit()
282
    {
283
        $sql = $this->_platform->modifyLimitQuery('SELECT * FROM user', null, 10);
284
        self::assertEquals('SELECT * FROM (SELECT a.*, ROWNUM AS doctrine_rownum FROM (SELECT * FROM user) a) WHERE doctrine_rownum >= 11', $sql);
285
    }
286
287
    public function testModifyLimitQueryWithAscOrderBy()
288
    {
289
        $sql = $this->_platform->modifyLimitQuery('SELECT * FROM user ORDER BY username ASC', 10);
290
        self::assertEquals('SELECT a.* FROM (SELECT * FROM user ORDER BY username ASC) a WHERE ROWNUM <= 10', $sql);
291
    }
292
293
    public function testModifyLimitQueryWithDescOrderBy()
294
    {
295
        $sql = $this->_platform->modifyLimitQuery('SELECT * FROM user ORDER BY username DESC', 10);
296
        self::assertEquals('SELECT a.* FROM (SELECT * FROM user ORDER BY username DESC) a WHERE ROWNUM <= 10', $sql);
297
    }
298
299
    public function testGenerateTableWithAutoincrement()
300
    {
301
        $columnName = strtoupper('id' . uniqid());
302
        $tableName = strtoupper('table' . uniqid());
303
        $table = new \Doctrine\DBAL\Schema\Table($tableName);
304
        $column = $table->addColumn($columnName, 'integer');
305
        $column->setAutoincrement(true);
306
        $targets = array(
307
            "CREATE TABLE {$tableName} ({$columnName} NUMBER(10) NOT NULL)",
308
            "DECLARE constraints_Count NUMBER; BEGIN SELECT COUNT(CONSTRAINT_NAME) INTO constraints_Count FROM USER_CONSTRAINTS WHERE TABLE_NAME = '{$tableName}' AND CONSTRAINT_TYPE = 'P'; IF constraints_Count = 0 OR constraints_Count = '' THEN EXECUTE IMMEDIATE 'ALTER TABLE {$tableName} ADD CONSTRAINT {$tableName}_AI_PK PRIMARY KEY ({$columnName})'; END IF; END;",
309
            "CREATE SEQUENCE {$tableName}_SEQ START WITH 1 MINVALUE 1 INCREMENT BY 1",
310
            "CREATE TRIGGER {$tableName}_AI_PK BEFORE INSERT ON {$tableName} FOR EACH ROW DECLARE last_Sequence NUMBER; last_InsertID NUMBER; BEGIN SELECT {$tableName}_SEQ.NEXTVAL INTO :NEW.{$columnName} FROM DUAL; IF (:NEW.{$columnName} IS NULL OR :NEW.{$columnName} = 0) THEN SELECT {$tableName}_SEQ.NEXTVAL INTO :NEW.{$columnName} FROM DUAL; ELSE SELECT NVL(Last_Number, 0) INTO last_Sequence FROM User_Sequences WHERE Sequence_Name = '{$tableName}_SEQ'; SELECT :NEW.{$columnName} INTO last_InsertID FROM DUAL; WHILE (last_InsertID > last_Sequence) LOOP SELECT {$tableName}_SEQ.NEXTVAL INTO last_Sequence FROM DUAL; END LOOP; END IF; END;"
311
        );
312
        $statements = $this->_platform->getCreateTableSQL($table);
313
        //strip all the whitespace from the statements
314
        array_walk($statements, function(&$value){
315
            $value = preg_replace('/\s+/', ' ',$value);
316
        });
317
        foreach($targets as $key => $sql){
318
            self::assertArrayHasKey($key,$statements);
319
            self::assertEquals($sql, $statements[$key]);
320
        }
321
    }
322
323
    public function getCreateTableColumnCommentsSQL()
324
    {
325
        return array(
326
            "CREATE TABLE test (id NUMBER(10) NOT NULL, PRIMARY KEY(id))",
327
            "COMMENT ON COLUMN test.id IS 'This is a comment'",
328
        );
329
    }
330
331
    public function getCreateTableColumnTypeCommentsSQL()
332
    {
333
        return array(
334
            "CREATE TABLE test (id NUMBER(10) NOT NULL, data CLOB NOT NULL, PRIMARY KEY(id))",
335
            "COMMENT ON COLUMN test.data IS '(DC2Type:array)'"
336
        );
337
    }
338
339
    public function getAlterTableColumnCommentsSQL()
340
    {
341
        return array(
342
            "ALTER TABLE mytable ADD (quota NUMBER(10) NOT NULL)",
343
            "COMMENT ON COLUMN mytable.quota IS 'A comment'",
344
            "COMMENT ON COLUMN mytable.foo IS ''",
345
            "COMMENT ON COLUMN mytable.baz IS 'B comment'",
346
        );
347
    }
348
349
    public function getBitAndComparisonExpressionSql($value1, $value2)
350
    {
351
        return 'BITAND('.$value1 . ', ' . $value2 . ')';
352
    }
353
354
    public function getBitOrComparisonExpressionSql($value1, $value2)
355
    {
356
        return '(' . $value1 . '-' .
357
        $this->getBitAndComparisonExpressionSql($value1, $value2)
358
        . '+' . $value2 . ')';
359
    }
360
361
    protected function getQuotedColumnInPrimaryKeySQL()
362
    {
363
        return array('CREATE TABLE "quoted" ("create" VARCHAR2(255) NOT NULL, PRIMARY KEY("create"))');
364
    }
365
366
    protected function getQuotedColumnInIndexSQL()
367
    {
368
        return array(
369
            'CREATE TABLE "quoted" ("create" VARCHAR2(255) NOT NULL)',
370
            'CREATE INDEX IDX_22660D028FD6E0FB ON "quoted" ("create")',
371
        );
372
    }
373
374
    protected function getQuotedNameInIndexSQL()
375
    {
376
        return array(
377
            'CREATE TABLE test (column1 VARCHAR2(255) NOT NULL)',
378
            'CREATE INDEX "key" ON test (column1)',
379
        );
380
    }
381
382
    protected function getQuotedColumnInForeignKeySQL()
383
    {
384
        return array(
385
            'CREATE TABLE "quoted" ("create" VARCHAR2(255) NOT NULL, foo VARCHAR2(255) NOT NULL, "bar" VARCHAR2(255) NOT NULL)',
386
            'ALTER TABLE "quoted" ADD CONSTRAINT FK_WITH_RESERVED_KEYWORD FOREIGN KEY ("create", foo, "bar") REFERENCES foreign ("create", bar, "foo-bar")',
387
            'ALTER TABLE "quoted" ADD CONSTRAINT FK_WITH_NON_RESERVED_KEYWORD FOREIGN KEY ("create", foo, "bar") REFERENCES foo ("create", bar, "foo-bar")',
388
            'ALTER TABLE "quoted" ADD CONSTRAINT FK_WITH_INTENDED_QUOTATION FOREIGN KEY ("create", foo, "bar") REFERENCES "foo-bar" ("create", bar, "foo-bar")',
389
        );
390
    }
391
392
    /**
393
     * @group DBAL-472
394
     * @group DBAL-1001
395
     */
396
    public function testAlterTableNotNULL()
397
    {
398
        $tableDiff = new \Doctrine\DBAL\Schema\TableDiff('mytable');
399
        $tableDiff->changedColumns['foo'] = new \Doctrine\DBAL\Schema\ColumnDiff(
400
            'foo', new \Doctrine\DBAL\Schema\Column(
401
                'foo', \Doctrine\DBAL\Types\Type::getType('string'), array('default' => 'bla', 'notnull' => true)
402
            ),
403
            array('type')
404
        );
405
        $tableDiff->changedColumns['bar'] = new \Doctrine\DBAL\Schema\ColumnDiff(
406
            'bar', new \Doctrine\DBAL\Schema\Column(
407
                'baz', \Doctrine\DBAL\Types\Type::getType('string'), array('default' => 'bla', 'notnull' => true)
408
            ),
409
            array('type', 'notnull')
410
        );
411
        $tableDiff->changedColumns['metar'] = new \Doctrine\DBAL\Schema\ColumnDiff(
412
            'metar', new \Doctrine\DBAL\Schema\Column(
413
                'metar', \Doctrine\DBAL\Types\Type::getType('string'), array('length' => 2000, 'notnull' => false)
414
            ),
415
            array('notnull')
416
        );
417
418
        $expectedSql = array(
419
            "ALTER TABLE mytable MODIFY (foo VARCHAR2(255) DEFAULT 'bla', baz VARCHAR2(255) DEFAULT 'bla' NOT NULL, metar VARCHAR2(2000) DEFAULT NULL NULL)",
420
        );
421
        self::assertEquals($expectedSql, $this->_platform->getAlterTableSQL($tableDiff));
422
    }
423
424
    /**
425
     * @group DBAL-2555
426
     */
427
    public function testInitializesDoctrineTypeMappings()
428
    {
429
        self::assertTrue($this->_platform->hasDoctrineTypeMappingFor('long raw'));
430
        self::assertSame('blob', $this->_platform->getDoctrineTypeMapping('long raw'));
431
432
        self::assertTrue($this->_platform->hasDoctrineTypeMappingFor('raw'));
433
        self::assertSame('binary', $this->_platform->getDoctrineTypeMapping('raw'));
434
435
        self::assertTrue($this->_platform->hasDoctrineTypeMappingFor('date'));
436
        self::assertSame('date', $this->_platform->getDoctrineTypeMapping('date'));
437
    }
438
439
    protected function getBinaryMaxLength()
440
    {
441
        return 2000;
442
    }
443
444
    public function testReturnsBinaryTypeDeclarationSQL()
445
    {
446
        self::assertSame('RAW(255)', $this->_platform->getBinaryTypeDeclarationSQL(array()));
447
        self::assertSame('RAW(2000)', $this->_platform->getBinaryTypeDeclarationSQL(array('length' => 0)));
448
        self::assertSame('RAW(2000)', $this->_platform->getBinaryTypeDeclarationSQL(array('length' => 2000)));
449
450
        self::assertSame('RAW(255)', $this->_platform->getBinaryTypeDeclarationSQL(array('fixed' => true)));
451
        self::assertSame('RAW(2000)', $this->_platform->getBinaryTypeDeclarationSQL(array('fixed' => true, 'length' => 0)));
452
        self::assertSame('RAW(2000)', $this->_platform->getBinaryTypeDeclarationSQL(array('fixed' => true, 'length' => 2000)));
453
    }
454
455
    /**
456
     * @group legacy
457
     * @expectedDeprecation Binary field length 2001 is greater than supported by the platform (2000)
458
     */
459
    public function testReturnsBinaryTypeLongerThanMaxDeclarationSQL()
460
    {
461
        self::assertSame('BLOB', $this->_platform->getBinaryTypeDeclarationSQL(['length' => 2001]));
462
        self::assertSame('BLOB', $this->_platform->getBinaryTypeDeclarationSQL(['fixed' => true, 'length' => 2001]));
463
    }
464
465
    public function testDoesNotPropagateUnnecessaryTableAlterationOnBinaryType()
466
    {
467
        $table1 = new Table('mytable');
468
        $table1->addColumn('column_varbinary', 'binary');
469
        $table1->addColumn('column_binary', 'binary', array('fixed' => true));
470
471
        $table2 = new Table('mytable');
472
        $table2->addColumn('column_varbinary', 'binary', array('fixed' => true));
473
        $table2->addColumn('column_binary', 'binary');
474
475
        $comparator = new Comparator();
476
477
        // VARBINARY -> BINARY
478
        // BINARY    -> VARBINARY
479
        self::assertEmpty($this->_platform->getAlterTableSQL($comparator->diffTable($table1, $table2)));
0 ignored issues
show
Bug introduced by
It seems like $comparator->diffTable($table1, $table2) can also be of type false; however, parameter $diff of Doctrine\DBAL\Platforms\...orm::getAlterTableSQL() does only seem to accept Doctrine\DBAL\Schema\TableDiff, maybe add an additional type check? ( Ignorable by Annotation )

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

479
        self::assertEmpty($this->_platform->getAlterTableSQL(/** @scrutinizer ignore-type */ $comparator->diffTable($table1, $table2)));
Loading history...
480
    }
481
482
    /**
483
     * @group DBAL-563
484
     */
485
    public function testUsesSequenceEmulatedIdentityColumns()
486
    {
487
        self::assertTrue($this->_platform->usesSequenceEmulatedIdentityColumns());
488
    }
489
490
    /**
491
     * @group DBAL-563
492
     * @group DBAL-831
493
     */
494
    public function testReturnsIdentitySequenceName()
495
    {
496
        self::assertSame('MYTABLE_SEQ', $this->_platform->getIdentitySequenceName('mytable', 'mycolumn'));
497
        self::assertSame('"mytable_SEQ"', $this->_platform->getIdentitySequenceName('"mytable"', 'mycolumn'));
498
        self::assertSame('MYTABLE_SEQ', $this->_platform->getIdentitySequenceName('mytable', '"mycolumn"'));
499
        self::assertSame('"mytable_SEQ"', $this->_platform->getIdentitySequenceName('"mytable"', '"mycolumn"'));
500
    }
501
502
    /**
503
     * @dataProvider dataCreateSequenceWithCache
504
     * @group DBAL-139
505
     */
506
    public function testCreateSequenceWithCache($cacheSize, $expectedSql)
507
    {
508
        $sequence = new \Doctrine\DBAL\Schema\Sequence('foo', 1, 1, $cacheSize);
509
        self::assertContains($expectedSql, $this->_platform->getCreateSequenceSQL($sequence));
510
    }
511
512
    public function dataCreateSequenceWithCache()
513
    {
514
        return array(
515
            array(1, 'NOCACHE'),
516
            array(0, 'NOCACHE'),
517
            array(3, 'CACHE 3')
518
        );
519
    }
520
521
    /**
522
     * @group DBAL-234
523
     */
524
    protected function getAlterTableRenameIndexSQL()
525
    {
526
        return array(
527
            'ALTER INDEX idx_foo RENAME TO idx_bar',
528
        );
529
    }
530
531
    /**
532
     * @group DBAL-234
533
     */
534
    protected function getQuotedAlterTableRenameIndexSQL()
535
    {
536
        return array(
537
            'ALTER INDEX "create" RENAME TO "select"',
538
            'ALTER INDEX "foo" RENAME TO "bar"',
539
        );
540
    }
541
542
    /**
543
     * {@inheritdoc}
544
     */
545
    protected function getQuotedAlterTableRenameColumnSQL()
546
    {
547
        return array(
548
            'ALTER TABLE mytable RENAME COLUMN unquoted1 TO unquoted',
549
            'ALTER TABLE mytable RENAME COLUMN unquoted2 TO "where"',
550
            'ALTER TABLE mytable RENAME COLUMN unquoted3 TO "foo"',
551
            'ALTER TABLE mytable RENAME COLUMN "create" TO reserved_keyword',
552
            'ALTER TABLE mytable RENAME COLUMN "table" TO "from"',
553
            'ALTER TABLE mytable RENAME COLUMN "select" TO "bar"',
554
            'ALTER TABLE mytable RENAME COLUMN quoted1 TO quoted',
555
            'ALTER TABLE mytable RENAME COLUMN quoted2 TO "and"',
556
            'ALTER TABLE mytable RENAME COLUMN quoted3 TO "baz"',
557
        );
558
    }
559
560
    /**
561
     * {@inheritdoc}
562
     */
563
    protected function getQuotedAlterTableChangeColumnLengthSQL()
564
    {
565
        $this->markTestIncomplete('Not implemented yet');
566
    }
567
568
    /**
569
     * @group DBAL-807
570
     */
571
    protected function getAlterTableRenameIndexInSchemaSQL()
572
    {
573
        return array(
574
            'ALTER INDEX myschema.idx_foo RENAME TO idx_bar',
575
        );
576
    }
577
578
    /**
579
     * @group DBAL-807
580
     */
581
    protected function getQuotedAlterTableRenameIndexInSchemaSQL()
582
    {
583
        return array(
584
            'ALTER INDEX "schema"."create" RENAME TO "select"',
585
            'ALTER INDEX "schema"."foo" RENAME TO "bar"',
586
        );
587
    }
588
589
    protected function getQuotesDropForeignKeySQL()
590
    {
591
        return 'ALTER TABLE "table" DROP CONSTRAINT "select"';
592
    }
593
594
    /**
595
     * @group DBAL-423
596
     */
597
    public function testReturnsGuidTypeDeclarationSQL()
598
    {
599
        self::assertSame('CHAR(36)', $this->_platform->getGuidTypeDeclarationSQL(array()));
600
    }
601
602
    /**
603
     * {@inheritdoc}
604
     */
605
    public function getAlterTableRenameColumnSQL()
606
    {
607
        return array(
608
            'ALTER TABLE foo RENAME COLUMN bar TO baz',
609
        );
610
    }
611
612
    /**
613
     * @dataProvider getReturnsDropAutoincrementSQL
614
     * @group DBAL-831
615
     */
616
    public function testReturnsDropAutoincrementSQL($table, $expectedSql)
617
    {
618
        self::assertSame($expectedSql, $this->_platform->getDropAutoincrementSql($table));
0 ignored issues
show
Bug introduced by
The method getDropAutoincrementSql() does not exist on Doctrine\DBAL\Platforms\AbstractPlatform. It seems like you code against a sub-type of Doctrine\DBAL\Platforms\AbstractPlatform such as Doctrine\DBAL\Platforms\OraclePlatform. ( Ignorable by Annotation )

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

618
        self::assertSame($expectedSql, $this->_platform->/** @scrutinizer ignore-call */ getDropAutoincrementSql($table));
Loading history...
619
    }
620
621
    public function getReturnsDropAutoincrementSQL()
622
    {
623
        return array(
624
            array(
625
                'myTable',
626
                array(
627
                    'DROP TRIGGER MYTABLE_AI_PK',
628
                    'DROP SEQUENCE MYTABLE_SEQ',
629
                    'ALTER TABLE MYTABLE DROP CONSTRAINT MYTABLE_AI_PK',
630
                )
631
            ),
632
            array(
633
                '"myTable"',
634
                array(
635
                    'DROP TRIGGER "myTable_AI_PK"',
636
                    'DROP SEQUENCE "myTable_SEQ"',
637
                    'ALTER TABLE "myTable" DROP CONSTRAINT "myTable_AI_PK"',
638
                )
639
            ),
640
            array(
641
                'table',
642
                array(
643
                    'DROP TRIGGER TABLE_AI_PK',
644
                    'DROP SEQUENCE TABLE_SEQ',
645
                    'ALTER TABLE "TABLE" DROP CONSTRAINT TABLE_AI_PK',
646
                )
647
            ),
648
        );
649
    }
650
651
    /**
652
     * {@inheritdoc}
653
     */
654
    protected function getQuotesTableIdentifiersInAlterTableSQL()
655
    {
656
        return array(
657
            'ALTER TABLE "foo" DROP CONSTRAINT fk1',
658
            'ALTER TABLE "foo" DROP CONSTRAINT fk2',
659
            'ALTER TABLE "foo" ADD (bloo NUMBER(10) NOT NULL)',
660
            'ALTER TABLE "foo" MODIFY (bar NUMBER(10) DEFAULT NULL NULL)',
661
            'ALTER TABLE "foo" RENAME COLUMN id TO war',
662
            'ALTER TABLE "foo" DROP (baz)',
663
            'ALTER TABLE "foo" RENAME TO "table"',
664
            'ALTER TABLE "table" ADD CONSTRAINT fk_add FOREIGN KEY (fk3) REFERENCES fk_table (id)',
665
            'ALTER TABLE "table" ADD CONSTRAINT fk2 FOREIGN KEY (fk2) REFERENCES fk_table2 (id)',
666
        );
667
    }
668
669
    /**
670
     * {@inheritdoc}
671
     */
672
    protected function getCommentOnColumnSQL()
673
    {
674
        return array(
675
            'COMMENT ON COLUMN foo.bar IS \'comment\'',
676
            'COMMENT ON COLUMN "Foo"."BAR" IS \'comment\'',
677
            'COMMENT ON COLUMN "select"."from" IS \'comment\'',
678
        );
679
    }
680
681
    /**
682
     * @group DBAL-1004
683
     */
684
    public function testAltersTableColumnCommentWithExplicitlyQuotedIdentifiers()
685
    {
686
        $table1 = new Table('"foo"', array(new Column('"bar"', Type::getType('integer'))));
687
        $table2 = new Table('"foo"', array(new Column('"bar"', Type::getType('integer'), array('comment' => 'baz'))));
688
689
        $comparator = new Comparator();
690
691
        $tableDiff = $comparator->diffTable($table1, $table2);
692
693
        self::assertInstanceOf('Doctrine\DBAL\Schema\TableDiff', $tableDiff);
694
        self::assertSame(
695
            array(
696
                'COMMENT ON COLUMN "foo"."bar" IS \'baz\'',
697
            ),
698
            $this->_platform->getAlterTableSQL($tableDiff)
0 ignored issues
show
Bug introduced by
It seems like $tableDiff can also be of type false; however, parameter $diff of Doctrine\DBAL\Platforms\...orm::getAlterTableSQL() does only seem to accept Doctrine\DBAL\Schema\TableDiff, maybe add an additional type check? ( Ignorable by Annotation )

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

698
            $this->_platform->getAlterTableSQL(/** @scrutinizer ignore-type */ $tableDiff)
Loading history...
699
        );
700
    }
701
702
    public function testQuotedTableNames()
703
    {
704
        $table = new Table('"test"');
705
        $table->addColumn('"id"', 'integer', array('autoincrement' => true));
706
707
        // assert tabel
708
        self::assertTrue($table->isQuoted());
709
        self::assertEquals('test', $table->getName());
710
        self::assertEquals('"test"', $table->getQuotedName($this->_platform));
711
712
        $sql = $this->_platform->getCreateTableSQL($table);
713
        self::assertEquals('CREATE TABLE "test" ("id" NUMBER(10) NOT NULL)', $sql[0]);
714
        self::assertEquals('CREATE SEQUENCE "test_SEQ" START WITH 1 MINVALUE 1 INCREMENT BY 1', $sql[2]);
715
        $createTriggerStatement = <<<EOD
716
CREATE TRIGGER "test_AI_PK"
717
   BEFORE INSERT
718
   ON "test"
719
   FOR EACH ROW
720
DECLARE
721
   last_Sequence NUMBER;
722
   last_InsertID NUMBER;
723
BEGIN
724
   SELECT "test_SEQ".NEXTVAL INTO :NEW."id" FROM DUAL;
725
   IF (:NEW."id" IS NULL OR :NEW."id" = 0) THEN
726
      SELECT "test_SEQ".NEXTVAL INTO :NEW."id" FROM DUAL;
727
   ELSE
728
      SELECT NVL(Last_Number, 0) INTO last_Sequence
729
        FROM User_Sequences
730
       WHERE Sequence_Name = 'test_SEQ';
731
      SELECT :NEW."id" INTO last_InsertID FROM DUAL;
732
      WHILE (last_InsertID > last_Sequence) LOOP
733
         SELECT "test_SEQ".NEXTVAL INTO last_Sequence FROM DUAL;
734
      END LOOP;
735
   END IF;
736
END;
737
EOD;
738
739
        self::assertEquals($createTriggerStatement, $sql[3]);
740
    }
741
742
    /**
743
     * @dataProvider getReturnsGetListTableColumnsSQL
744
     * @group DBAL-831
745
     */
746
    public function testReturnsGetListTableColumnsSQL($database, $expectedSql)
747
    {
748
        // note: this assertion is a bit strict, as it compares a full SQL string.
749
        // Should this break in future, then please try to reduce the matching to substring matching while reworking
750
        // the tests
751
        self::assertEquals($expectedSql, $this->_platform->getListTableColumnsSQL('"test"', $database));
752
    }
753
754
    public function getReturnsGetListTableColumnsSQL()
755
    {
756
        return array(
757
            array(
758
                null,
759
                "SELECT   c.*,
760
                         (
761
                             SELECT d.comments
762
                             FROM   user_col_comments d
763
                             WHERE  d.TABLE_NAME = c.TABLE_NAME 
764
                             AND    d.COLUMN_NAME = c.COLUMN_NAME
765
                         ) AS comments
766
                FROM     user_tab_columns c
767
                WHERE    c.table_name = 'test' 
768
                ORDER BY c.column_id"
769
            ),
770
            array(
771
                '/',
772
                "SELECT   c.*,
773
                         (
774
                             SELECT d.comments
775
                             FROM   user_col_comments d
776
                             WHERE  d.TABLE_NAME = c.TABLE_NAME 
777
                             AND    d.COLUMN_NAME = c.COLUMN_NAME
778
                         ) AS comments
779
                FROM     user_tab_columns c
780
                WHERE    c.table_name = 'test' 
781
                ORDER BY c.column_id"
782
            ),
783
            array(
784
                'scott',
785
                "SELECT   c.*,
786
                         (
787
                             SELECT d.comments
788
                             FROM   all_col_comments d
789
                             WHERE  d.TABLE_NAME = c.TABLE_NAME AND d.OWNER = c.OWNER
790
                             AND    d.COLUMN_NAME = c.COLUMN_NAME
791
                         ) AS comments
792
                FROM     all_tab_columns c
793
                WHERE    c.table_name = 'test' AND c.owner = 'SCOTT'
794
                ORDER BY c.column_id"
795
            ),
796
        );
797
    }
798
799
    /**
800
     * {@inheritdoc}
801
     */
802
    protected function getQuotesReservedKeywordInUniqueConstraintDeclarationSQL()
803
    {
804
        return 'CONSTRAINT "select" UNIQUE (foo)';
805
    }
806
807
    /**
808
     * {@inheritdoc}
809
     */
810
    protected function getQuotesReservedKeywordInIndexDeclarationSQL()
811
    {
812
        return 'INDEX "select" (foo)';
813
    }
814
815
    /**
816
     * {@inheritdoc}
817
     */
818
    protected function getQuotesReservedKeywordInTruncateTableSQL()
819
    {
820
        return 'TRUNCATE TABLE "select"';
821
    }
822
823
    /**
824
     * {@inheritdoc}
825
     */
826
    protected function getAlterStringToFixedStringSQL()
827
    {
828
        return array(
829
            'ALTER TABLE mytable MODIFY (name CHAR(2) DEFAULT NULL)',
830
        );
831
    }
832
833
    /**
834
     * {@inheritdoc}
835
     */
836
    protected function getGeneratesAlterTableRenameIndexUsedByForeignKeySQL()
837
    {
838
        return array(
839
            'ALTER INDEX idx_foo RENAME TO idx_foo_renamed',
840
        );
841
    }
842
843
    /**
844
     * @group DBAL-2436
845
     */
846
    public function testQuotesDatabaseNameInListSequencesSQL()
847
    {
848
        self::assertContains("'Foo''Bar\\\\'", $this->_platform->getListSequencesSQL("Foo'Bar\\"), '', true);
849
    }
850
851
    /**
852
     * @group DBAL-2436
853
     */
854
    public function testQuotesTableNameInListTableIndexesSQL()
855
    {
856
        self::assertContains("'Foo''Bar\\\\'", $this->_platform->getListTableIndexesSQL("Foo'Bar\\"), '', true);
857
    }
858
859
    /**
860
     * @group DBAL-2436
861
     */
862
    public function testQuotesTableNameInListTableForeignKeysSQL()
863
    {
864
        self::assertContains("'Foo''Bar\\\\'", $this->_platform->getListTableForeignKeysSQL("Foo'Bar\\"), '', true);
865
    }
866
867
    /**
868
     * @group DBAL-2436
869
     */
870
    public function testQuotesTableNameInListTableConstraintsSQL()
871
    {
872
        self::assertContains("'Foo''Bar\\\\'", $this->_platform->getListTableConstraintsSQL("Foo'Bar\\"), '', true);
873
    }
874
875
    /**
876
     * @group DBAL-2436
877
     */
878
    public function testQuotesTableNameInListTableColumnsSQL()
879
    {
880
        self::assertContains("'Foo''Bar\\\\'", $this->_platform->getListTableColumnsSQL("Foo'Bar\\"), '', true);
881
    }
882
883
    /**
884
     * @group DBAL-2436
885
     */
886
    public function testQuotesDatabaseNameInListTableColumnsSQL()
887
    {
888
        self::assertContains("'Foo''Bar\\\\'", $this->_platform->getListTableColumnsSQL('foo_table', "Foo'Bar\\"), '', true);
889
    }
890
}
891