Rajout de doctrine/orm
[zf2.biz/galerie.git] / vendor / doctrine / dbal / lib / Doctrine / DBAL / Platforms / OraclePlatform.php
1 <?php
2 /*
3  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
4  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
5  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
6  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
7  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
8  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
9  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
10  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
11  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
12  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
13  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
14  *
15  * This software consists of voluntary contributions made by many individuals
16  * and is licensed under the MIT license. For more information, see
17  * <http://www.doctrine-project.org>.
18  */
19
20 namespace Doctrine\DBAL\Platforms;
21
22 use Doctrine\DBAL\Schema\ForeignKeyConstraint;
23 use Doctrine\DBAL\Schema\Index;
24 use Doctrine\DBAL\Schema\Sequence;
25 use Doctrine\DBAL\Schema\Table;
26 use Doctrine\DBAL\Schema\TableDiff;
27 use Doctrine\DBAL\DBALException;
28
29 /**
30  * OraclePlatform.
31  *
32  * @since 2.0
33  * @author Roman Borschel <roman@code-factory.org>
34  * @author Lukas Smith <smith@pooteeweet.org> (PEAR MDB2 library)
35  * @author Benjamin Eberlei <kontakt@beberlei.de>
36  */
37 class OraclePlatform extends AbstractPlatform
38 {
39     /**
40      * Assertion for Oracle identifiers
41      *
42      * @link http://docs.oracle.com/cd/B19306_01/server.102/b14200/sql_elements008.htm
43      *
44      * @param string
45      *
46      * @throws DBALException
47      */
48     static public function assertValidIdentifier($identifier)
49     {
50         if ( ! preg_match('(^(([a-zA-Z]{1}[a-zA-Z0-9_$#]{0,})|("[^"]+"))$)', $identifier)) {
51             throw new DBALException("Invalid Oracle identifier");
52         }
53     }
54
55     /**
56      * {@inheritDoc}
57      */
58     public function getSubstringExpression($value, $position, $length = null)
59     {
60         if ($length !== null) {
61             return "SUBSTR($value, $position, $length)";
62         }
63
64         return "SUBSTR($value, $position)";
65     }
66
67     /**
68      * {@inheritDoc}
69      */
70     public function getNowExpression($type = 'timestamp')
71     {
72         switch ($type) {
73             case 'date':
74             case 'time':
75             case 'timestamp':
76             default:
77                 return 'TO_CHAR(CURRENT_TIMESTAMP, \'YYYY-MM-DD HH24:MI:SS\')';
78         }
79     }
80
81     /**
82      * {@inheritDoc}
83      */
84     public function getLocateExpression($str, $substr, $startPos = false)
85     {
86         if ($startPos == false) {
87             return 'INSTR('.$str.', '.$substr.')';
88         }
89
90         return 'INSTR('.$str.', '.$substr.', '.$startPos.')';
91     }
92
93     /**
94      * {@inheritDoc}
95      */
96     public function getGuidExpression()
97     {
98         return 'SYS_GUID()';
99     }
100
101     /**
102      * {@inheritDoc}
103      *
104      * Note: Since Oracle timestamp differences are calculated down to the microsecond we have to truncate
105      * them to the difference in days. This is obviously a restriction of the original functionality, but we
106      * need to make this a portable function.
107      */
108     public function getDateDiffExpression($date1, $date2)
109     {
110         return "TRUNC(TO_NUMBER(SUBSTR((" . $date1 . "-" . $date2 . "), 1, INSTR(" . $date1 . "-" . $date2 .", ' '))))";
111     }
112
113     /**
114      * {@inheritDoc}
115      */
116     public function getDateAddDaysExpression($date, $days)
117     {
118         return '(' . $date . '+' . $days . ')';
119     }
120
121     /**
122      * {@inheritDoc}
123      */
124     public function getDateSubDaysExpression($date, $days)
125     {
126         return '(' . $date . '-' . $days . ')';
127     }
128
129     /**
130      * {@inheritDoc}
131      */
132     public function getDateAddMonthExpression($date, $months)
133     {
134         return "ADD_MONTHS(" . $date . ", " . $months . ")";
135     }
136
137     /**
138      * {@inheritDoc}
139      */
140     public function getDateSubMonthExpression($date, $months)
141     {
142         return "ADD_MONTHS(" . $date . ", -" . $months . ")";
143     }
144
145     /**
146      * {@inheritDoc}
147      */
148     public function getBitAndComparisonExpression($value1, $value2)
149     {
150         return 'BITAND('.$value1 . ', ' . $value2 . ')';
151     }
152
153     /**
154      * {@inheritDoc}
155      */
156     public function getBitOrComparisonExpression($value1, $value2)
157     {
158         return '(' . $value1 . '-' .
159                 $this->getBitAndComparisonExpression($value1, $value2)
160                 . '+' . $value2 . ')';
161     }
162
163     /**
164      * {@inheritDoc}
165      *
166      * Need to specifiy minvalue, since start with is hidden in the system and MINVALUE <= START WITH.
167      * Therefore we can use MINVALUE to be able to get a hint what START WITH was for later introspection
168      * in {@see listSequences()}
169      */
170     public function getCreateSequenceSQL(Sequence $sequence)
171     {
172         return 'CREATE SEQUENCE ' . $sequence->getQuotedName($this) .
173                ' START WITH ' . $sequence->getInitialValue() .
174                ' MINVALUE ' . $sequence->getInitialValue() .
175                ' INCREMENT BY ' . $sequence->getAllocationSize();
176     }
177
178     /**
179      * {@inheritDoc}
180      */
181     public function getAlterSequenceSQL(\Doctrine\DBAL\Schema\Sequence $sequence)
182     {
183         return 'ALTER SEQUENCE ' . $sequence->getQuotedName($this) .
184                ' INCREMENT BY ' . $sequence->getAllocationSize();
185     }
186
187     /**
188      * {@inheritDoc}
189      */
190     public function getSequenceNextValSQL($sequenceName)
191     {
192         return 'SELECT ' . $sequenceName . '.nextval FROM DUAL';
193     }
194
195     /**
196      * {@inheritDoc}
197      */
198     public function getSetTransactionIsolationSQL($level)
199     {
200         return 'SET TRANSACTION ISOLATION LEVEL ' . $this->_getTransactionIsolationLevelSQL($level);
201     }
202
203     /**
204      * {@inheritDoc}
205      */
206     protected function _getTransactionIsolationLevelSQL($level)
207     {
208         switch ($level) {
209             case \Doctrine\DBAL\Connection::TRANSACTION_READ_UNCOMMITTED:
210                 return 'READ UNCOMMITTED';
211             case \Doctrine\DBAL\Connection::TRANSACTION_READ_COMMITTED:
212                 return 'READ COMMITTED';
213             case \Doctrine\DBAL\Connection::TRANSACTION_REPEATABLE_READ:
214             case \Doctrine\DBAL\Connection::TRANSACTION_SERIALIZABLE:
215                 return 'SERIALIZABLE';
216             default:
217                 return parent::_getTransactionIsolationLevelSQL($level);
218         }
219     }
220
221     /**
222      * {@inheritDoc}
223      */
224     public function getBooleanTypeDeclarationSQL(array $field)
225     {
226         return 'NUMBER(1)';
227     }
228
229     /**
230      * {@inheritDoc}
231      */
232     public function getIntegerTypeDeclarationSQL(array $field)
233     {
234         return 'NUMBER(10)';
235     }
236
237     /**
238      * {@inheritDoc}
239      */
240     public function getBigIntTypeDeclarationSQL(array $field)
241     {
242         return 'NUMBER(20)';
243     }
244
245     /**
246      * {@inheritDoc}
247      */
248     public function getSmallIntTypeDeclarationSQL(array $field)
249     {
250         return 'NUMBER(5)';
251     }
252
253     /**
254      * {@inheritDoc}
255      */
256     public function getDateTimeTypeDeclarationSQL(array $fieldDeclaration)
257     {
258         return 'TIMESTAMP(0)';
259     }
260
261     /**
262      * {@inheritDoc}
263      */
264     public function getDateTimeTzTypeDeclarationSQL(array $fieldDeclaration)
265     {
266         return 'TIMESTAMP(0) WITH TIME ZONE';
267     }
268
269     /**
270      * {@inheritDoc}
271      */
272     public function getDateTypeDeclarationSQL(array $fieldDeclaration)
273     {
274         return 'DATE';
275     }
276
277     /**
278      * {@inheritDoc}
279      */
280     public function getTimeTypeDeclarationSQL(array $fieldDeclaration)
281     {
282         return 'DATE';
283     }
284
285     /**
286      * {@inheritDoc}
287      */
288     protected function _getCommonIntegerTypeDeclarationSQL(array $columnDef)
289     {
290         return '';
291     }
292
293     /**
294      * {@inheritDoc}
295      */
296     protected function getVarcharTypeDeclarationSQLSnippet($length, $fixed)
297     {
298         return $fixed ? ($length ? 'CHAR(' . $length . ')' : 'CHAR(2000)')
299                 : ($length ? 'VARCHAR2(' . $length . ')' : 'VARCHAR2(4000)');
300     }
301
302     /**
303      * {@inheritDoc}
304      */
305     public function getClobTypeDeclarationSQL(array $field)
306     {
307         return 'CLOB';
308     }
309
310     public function getListDatabasesSQL()
311     {
312         return 'SELECT username FROM all_users';
313     }
314
315     public function getListSequencesSQL($database)
316     {
317         return "SELECT sequence_name, min_value, increment_by FROM sys.all_sequences ".
318                "WHERE SEQUENCE_OWNER = '".strtoupper($database)."'";
319     }
320
321     /**
322      * {@inheritDoc}
323      */
324     protected function _getCreateTableSQL($table, array $columns, array $options = array())
325     {
326         $indexes = isset($options['indexes']) ? $options['indexes'] : array();
327         $options['indexes'] = array();
328         $sql = parent::_getCreateTableSQL($table, $columns, $options);
329
330         foreach ($columns as $name => $column) {
331             if (isset($column['sequence'])) {
332                 $sql[] = $this->getCreateSequenceSQL($column['sequence'], 1);
333             }
334
335             if (isset($column['autoincrement']) && $column['autoincrement'] ||
336                (isset($column['autoinc']) && $column['autoinc'])) {
337                 $sql = array_merge($sql, $this->getCreateAutoincrementSql($name, $table));
338             }
339         }
340
341         if (isset($indexes) && ! empty($indexes)) {
342             foreach ($indexes as $index) {
343                 $sql[] = $this->getCreateIndexSQL($index, $table);
344             }
345         }
346
347         return $sql;
348     }
349
350     /**
351      * {@inheritDoc}
352      *
353      * @license New BSD License
354      * @link http://ezcomponents.org/docs/api/trunk/DatabaseSchema/ezcDbSchemaOracleReader.html
355      */
356     public function getListTableIndexesSQL($table, $currentDatabase = null)
357     {
358         $table = strtoupper($table);
359
360         return "SELECT uind.index_name AS name, " .
361              "       uind.index_type AS type, " .
362              "       decode( uind.uniqueness, 'NONUNIQUE', 0, 'UNIQUE', 1 ) AS is_unique, " .
363              "       uind_col.column_name AS column_name, " .
364              "       uind_col.column_position AS column_pos, " .
365              "       (SELECT ucon.constraint_type FROM user_constraints ucon WHERE ucon.constraint_name = uind.index_name) AS is_primary ".
366              "FROM user_indexes uind, user_ind_columns uind_col " .
367              "WHERE uind.index_name = uind_col.index_name AND uind_col.table_name = '$table' ORDER BY uind_col.column_position ASC";
368     }
369
370     public function getListTablesSQL()
371     {
372         return 'SELECT * FROM sys.user_tables';
373     }
374
375     /**
376      * {@inheritDoc}
377      */
378     public function getListViewsSQL($database)
379     {
380         return 'SELECT view_name, text FROM sys.user_views';
381     }
382
383     public function getCreateViewSQL($name, $sql)
384     {
385         return 'CREATE VIEW ' . $name . ' AS ' . $sql;
386     }
387
388     public function getDropViewSQL($name)
389     {
390         return 'DROP VIEW '. $name;
391     }
392
393     public function getCreateAutoincrementSql($name, $table, $start = 1)
394     {
395         $table = strtoupper($table);
396         $sql   = array();
397
398         $indexName  = $table . '_AI_PK';
399
400         $idx = new Index($indexName, array($name), true, true);
401
402         $sql[] = 'DECLARE
403   constraints_Count NUMBER;
404 BEGIN
405   SELECT COUNT(CONSTRAINT_NAME) INTO constraints_Count FROM USER_CONSTRAINTS WHERE TABLE_NAME = \''.$table.'\' AND CONSTRAINT_TYPE = \'P\';
406   IF constraints_Count = 0 OR constraints_Count = \'\' THEN
407     EXECUTE IMMEDIATE \''.$this->getCreateConstraintSQL($idx, $table).'\';
408   END IF;
409 END;';
410
411         $sequenceName = $table . '_SEQ';
412         $sequence = new Sequence($sequenceName, $start);
413         $sql[] = $this->getCreateSequenceSQL($sequence);
414
415         $triggerName  = $table . '_AI_PK';
416         $sql[] = 'CREATE TRIGGER ' . $triggerName . '
417    BEFORE INSERT
418    ON ' . $table . '
419    FOR EACH ROW
420 DECLARE
421    last_Sequence NUMBER;
422    last_InsertID NUMBER;
423 BEGIN
424    SELECT ' . $sequenceName . '.NEXTVAL INTO :NEW.' . $name . ' FROM DUAL;
425    IF (:NEW.' . $name . ' IS NULL OR :NEW.'.$name.' = 0) THEN
426       SELECT ' . $sequenceName . '.NEXTVAL INTO :NEW.' . $name . ' FROM DUAL;
427    ELSE
428       SELECT NVL(Last_Number, 0) INTO last_Sequence
429         FROM User_Sequences
430        WHERE Sequence_Name = \'' . $sequenceName . '\';
431       SELECT :NEW.' . $name . ' INTO last_InsertID FROM DUAL;
432       WHILE (last_InsertID > last_Sequence) LOOP
433          SELECT ' . $sequenceName . '.NEXTVAL INTO last_Sequence FROM DUAL;
434       END LOOP;
435    END IF;
436 END;';
437
438         return $sql;
439     }
440
441     public function getDropAutoincrementSql($table)
442     {
443         $table = strtoupper($table);
444         $trigger = $table . '_AI_PK';
445
446         $sql[] = 'DROP TRIGGER ' . $trigger;
447         $sql[] = $this->getDropSequenceSQL($table.'_SEQ');
448
449         $indexName = $table . '_AI_PK';
450         $sql[] = $this->getDropConstraintSQL($indexName, $table);
451
452         return $sql;
453     }
454
455     public function getListTableForeignKeysSQL($table)
456     {
457         $table = strtoupper($table);
458
459         return "SELECT alc.constraint_name,
460           alc.DELETE_RULE,
461           alc.search_condition,
462           cols.column_name \"local_column\",
463           cols.position,
464           r_alc.table_name \"references_table\",
465           r_cols.column_name \"foreign_column\"
466      FROM user_cons_columns cols
467 LEFT JOIN user_constraints alc
468        ON alc.constraint_name = cols.constraint_name
469 LEFT JOIN user_constraints r_alc
470        ON alc.r_constraint_name = r_alc.constraint_name
471 LEFT JOIN user_cons_columns r_cols
472        ON r_alc.constraint_name = r_cols.constraint_name
473       AND cols.position = r_cols.position
474     WHERE alc.constraint_name = cols.constraint_name
475       AND alc.constraint_type = 'R'
476       AND alc.table_name = '".$table."'";
477     }
478
479     public function getListTableConstraintsSQL($table)
480     {
481         $table = strtoupper($table);
482         return 'SELECT * FROM user_constraints WHERE table_name = \'' . $table . '\'';
483     }
484
485     public function getListTableColumnsSQL($table, $database = null)
486     {
487         $table = strtoupper($table);
488
489         $tabColumnsTableName = "user_tab_columns";
490         $ownerCondition = '';
491
492         if (null !== $database){
493             $database = strtoupper($database);
494             $tabColumnsTableName = "all_tab_columns";
495             $ownerCondition = "AND c.owner = '".$database."'";
496         }
497
498         return "SELECT c.*, d.comments FROM $tabColumnsTableName c ".
499                "INNER JOIN user_col_comments d ON d.TABLE_NAME = c.TABLE_NAME AND d.COLUMN_NAME = c.COLUMN_NAME ".
500                "WHERE c.table_name = '" . $table . "' ".$ownerCondition." ORDER BY c.column_name";
501     }
502
503     /**
504      * {@inheritDoc}
505      */
506     public function getDropSequenceSQL($sequence)
507     {
508         if ($sequence instanceof Sequence) {
509             $sequence = $sequence->getQuotedName($this);
510         }
511
512         return 'DROP SEQUENCE ' . $sequence;
513     }
514
515     /**
516      * {@inheritDoc}
517      */
518     public function getDropForeignKeySQL($foreignKey, $table)
519     {
520         if ($foreignKey instanceof ForeignKeyConstraint) {
521             $foreignKey = $foreignKey->getQuotedName($this);
522         }
523
524         if ($table instanceof Table) {
525             $table = $table->getQuotedName($this);
526         }
527
528         return 'ALTER TABLE ' . $table . ' DROP CONSTRAINT ' . $foreignKey;
529     }
530
531     /**
532      * {@inheritDoc}
533      */
534     public function getDropDatabaseSQL($database)
535     {
536         return 'DROP USER ' . $database . ' CASCADE';
537     }
538
539     /**
540      * {@inheritDoc}
541      */
542     public function getAlterTableSQL(TableDiff $diff)
543     {
544         $sql = array();
545         $commentsSQL = array();
546         $columnSql = array();
547
548         $fields = array();
549
550         foreach ($diff->addedColumns as $column) {
551             if ($this->onSchemaAlterTableAddColumn($column, $diff, $columnSql)) {
552                 continue;
553             }
554
555             $fields[] = $this->getColumnDeclarationSQL($column->getQuotedName($this), $column->toArray());
556             if ($comment = $this->getColumnComment($column)) {
557                 $commentsSQL[] = $this->getCommentOnColumnSQL($diff->name, $column->getName(), $comment);
558             }
559         }
560
561         if (count($fields)) {
562             $sql[] = 'ALTER TABLE ' . $diff->name . ' ADD (' . implode(', ', $fields) . ')';
563         }
564
565         $fields = array();
566         foreach ($diff->changedColumns as $columnDiff) {
567             if ($this->onSchemaAlterTableChangeColumn($columnDiff, $diff, $columnSql)) {
568                 continue;
569             }
570
571             $column = $columnDiff->column;
572             $fields[] = $column->getQuotedName($this). ' ' . $this->getColumnDeclarationSQL('', $column->toArray());
573             if ($columnDiff->hasChanged('comment') && $comment = $this->getColumnComment($column)) {
574                 $commentsSQL[] = $this->getCommentOnColumnSQL($diff->name, $column->getName(), $comment);
575             }
576         }
577
578         if (count($fields)) {
579             $sql[] = 'ALTER TABLE ' . $diff->name . ' MODIFY (' . implode(', ', $fields) . ')';
580         }
581
582         foreach ($diff->renamedColumns as $oldColumnName => $column) {
583             if ($this->onSchemaAlterTableRenameColumn($oldColumnName, $column, $diff, $columnSql)) {
584                 continue;
585             }
586
587             $sql[] = 'ALTER TABLE ' . $diff->name . ' RENAME COLUMN ' . $oldColumnName .' TO ' . $column->getQuotedName($this);
588         }
589
590         $fields = array();
591         foreach ($diff->removedColumns as $column) {
592             if ($this->onSchemaAlterTableRemoveColumn($column, $diff, $columnSql)) {
593                 continue;
594             }
595
596             $fields[] = $column->getQuotedName($this);
597         }
598
599         if (count($fields)) {
600             $sql[] = 'ALTER TABLE ' . $diff->name . ' DROP (' . implode(', ', $fields).')';
601         }
602
603         $tableSql = array();
604
605         if ( ! $this->onSchemaAlterTable($diff, $tableSql)) {
606             if ($diff->newName !== false) {
607                 $sql[] = 'ALTER TABLE ' . $diff->name . ' RENAME TO ' . $diff->newName;
608             }
609
610             $sql = array_merge($sql, $this->_getAlterTableIndexForeignKeySQL($diff), $commentsSQL);
611         }
612
613         return array_merge($sql, $tableSql, $columnSql);
614     }
615
616     /**
617      * {@inheritDoc}
618      */
619     public function prefersSequences()
620     {
621         return true;
622     }
623
624     /**
625      * {@inheritDoc}
626      */
627     public function supportsCommentOnStatement()
628     {
629         return true;
630     }
631
632     /**
633      * {@inheritDoc}
634      */
635     public function getName()
636     {
637         return 'oracle';
638     }
639
640     /**
641      * {@inheritDoc}
642      */
643     protected function doModifyLimitQuery($query, $limit, $offset = null)
644     {
645         $limit = (int) $limit;
646         $offset = (int) $offset;
647
648         if (preg_match('/^\s*SELECT/i', $query)) {
649             if (!preg_match('/\sFROM\s/i', $query)) {
650                 $query .= " FROM dual";
651             }
652             if ($limit > 0) {
653                 $max = $offset + $limit;
654                 $column = '*';
655                 if ($offset > 0) {
656                     $min = $offset + 1;
657                     $query = 'SELECT * FROM (SELECT a.' . $column . ', rownum AS doctrine_rownum FROM (' .
658                             $query .
659                             ') a WHERE rownum <= ' . $max . ') WHERE doctrine_rownum >= ' . $min;
660                 } else {
661                     $query = 'SELECT a.' . $column . ' FROM (' . $query . ') a WHERE ROWNUM <= ' . $max;
662                 }
663             }
664         }
665
666         return $query;
667     }
668
669     /**
670      * {@inheritDoc}
671      *
672      * Oracle returns all column names in SQL result sets in uppercase.
673      */
674     public function getSQLResultCasing($column)
675     {
676         return strtoupper($column);
677     }
678
679     public function getCreateTemporaryTableSnippetSQL()
680     {
681         return "CREATE GLOBAL TEMPORARY TABLE";
682     }
683
684     /**
685      * {@inheritDoc}
686      */
687     public function getDateTimeTzFormatString()
688     {
689         return 'Y-m-d H:i:sP';
690     }
691
692     /**
693      * {@inheritDoc}
694      */
695     public function getDateFormatString()
696     {
697         return 'Y-m-d 00:00:00';
698     }
699
700     /**
701      * {@inheritDoc}
702      */
703     public function getTimeFormatString()
704     {
705         return '1900-01-01 H:i:s';
706     }
707
708     /**
709      * {@inheritDoc}
710      */
711     public function fixSchemaElementName($schemaElementName)
712     {
713         if (strlen($schemaElementName) > 30) {
714             // Trim it
715             return substr($schemaElementName, 0, 30);
716         }
717
718         return $schemaElementName;
719     }
720
721     /**
722      * {@inheritDoc}
723      */
724     public function getMaxIdentifierLength()
725     {
726         return 30;
727     }
728
729     /**
730      * {@inheritDoc}
731      */
732     public function supportsSequences()
733     {
734         return true;
735     }
736
737     /**
738      * {@inheritDoc}
739      */
740     public function supportsForeignKeyOnUpdate()
741     {
742         return false;
743     }
744
745     /**
746      * {@inheritDoc}
747      */
748     public function supportsReleaseSavepoints()
749     {
750         return false;
751     }
752
753     /**
754      * {@inheritDoc}
755      */
756     public function getTruncateTableSQL($tableName, $cascade = false)
757     {
758         return 'TRUNCATE TABLE '.$tableName;
759     }
760
761     /**
762      * {@inheritDoc}
763      */
764     public function getDummySelectSQL()
765     {
766         return 'SELECT 1 FROM DUAL';
767     }
768
769     /**
770      * {@inheritDoc}
771      */
772     protected function initializeDoctrineTypeMappings()
773     {
774         $this->doctrineTypeMapping = array(
775             'integer'           => 'integer',
776             'number'            => 'integer',
777             'pls_integer'       => 'boolean',
778             'binary_integer'    => 'boolean',
779             'varchar'           => 'string',
780             'varchar2'          => 'string',
781             'nvarchar2'         => 'string',
782             'char'              => 'string',
783             'nchar'             => 'string',
784             'date'              => 'datetime',
785             'timestamp'         => 'datetime',
786             'timestamptz'       => 'datetimetz',
787             'float'             => 'float',
788             'long'              => 'string',
789             'clob'              => 'text',
790             'nclob'             => 'text',
791             'raw'               => 'text',
792             'long raw'          => 'text',
793             'rowid'             => 'string',
794             'urowid'            => 'string',
795             'blob'              => 'blob',
796         );
797     }
798
799     /**
800      * {@inheritDoc}
801      */
802     public function releaseSavePoint($savepoint)
803     {
804         return '';
805     }
806
807     /**
808      * {@inheritDoc}
809      */
810     protected function getReservedKeywordsClass()
811     {
812         return 'Doctrine\DBAL\Platforms\Keywords\OracleKeywords';
813     }
814
815     /**
816      * {@inheritDoc}
817      */
818     public function getBlobTypeDeclarationSQL(array $field)
819     {
820         return 'BLOB';
821     }
822 }