36 parent::__construct();
49 switch ((
string)$this->databaseConnection->handlerCfg[$this->databaseConnection->lastHandlerKey][
'type']) {
51 if ($this->databaseConnection->runningADOdbDriver(
'mssql')) {
54 $value = parent::getValueInQuotes($parseString, $quote);
58 $value = parent::getValueInQuotes($parseString, $quote);
71 $previousIsQuote = FALSE;
74 for ($c = 0; $c < strlen($parseString); $c++) {
76 if ($parseString[$c] === $quote) {
80 if ($previousIsQuote) {
85 $previousIsQuote = !$previousIsQuote;
90 } elseif ($inQuote && $previousIsQuote) {
92 $previousIsQuote = FALSE;
94 $previousIsQuote = FALSE;
97 $parts = explode($quote, substr($parseString, 1));
99 foreach ($parts as $v) {
102 preg_match(
'/\\\\$/', $v, $reg);
103 if ($reg && strlen($reg[0]) % 2) {
106 $parseString = ltrim(substr($parseString, strlen($buffer) + 2));
123 public function compileFieldList($selectFields, $compileComments = TRUE, $functionMapping = TRUE) {
125 switch ((
string)$this->databaseConnection->handlerCfg[$this->databaseConnection->lastHandlerKey][
'type']) {
127 $output = parent::compileFieldList($selectFields, $compileComments);
131 if (is_array($selectFields)) {
132 $outputParts = array();
133 foreach ($selectFields as $k => $v) {
135 switch ($v[
'type']) {
137 $outputParts[$k] = $v[
'function'] .
'(' . $v[
'func_content'] .
')';
140 if ($v[
'flow-control'][
'type'] ===
'CASE') {
145 $outputParts[$k] = ($v[
'distinct'] ? $v[
'distinct'] :
'') . ($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field'];
150 $outputParts[$k] .=
' ' . $v[
'as_keyword'] .
' ' . $v[
'as'];
154 $outputParts[$k] .=
' ' . $v[
'sortDir'];
158 if (FALSE && $selectFields[0][
'comments']) {
159 $output = $selectFields[0][
'comments'] .
' ';
161 $output .= implode(
', ', $outputParts);
178 switch ((
string)$this->databaseConnection->handlerCfg[$this->databaseConnection->lastHandlerKey][
'type']) {
180 $output = parent::compileCaseStatement($components);
184 if (isset($components[
'case_field'])) {
185 $statement .=
' ' . $components[
'case_field'];
186 } elseif (isset($components[
'case_value'])) {
187 $statement .=
' ' . $components[
'case_value'][1] . $components[
'case_value'][0] . $components[
'case_value'][1];
189 foreach ($components[
'when'] as $when) {
190 $statement .=
' WHEN ';
192 $statement .=
' THEN ';
193 $statement .= $when[
'then_value'][1] . $when[
'then_value'][0] . $when[
'then_value'][1];
195 if (isset($components[
'else'])) {
196 $statement .=
' ELSE ';
197 $statement .= $components[
'else'][1] . $components[
'else'][0] . $components[
'else'][1];
199 $statement .=
' END';
200 $output = $statement;
217 if ((
string)$this->databaseConnection->handlerCfg[$this->databaseConnection->lastHandlerKey][
'type'] ===
'native') {
218 return parent::compileAddslashes($str);
239 switch ((
string)$this->databaseConnection->handlerCfg[$this->databaseConnection->lastHandlerKey][
'type']) {
241 $query = parent::compileINSERT($components);
245 if (isset($components[
'VALUES_ONLY']) && is_array($components[
'VALUES_ONLY'])) {
246 $valuesComponents = $components[
'EXTENDED'] ===
'1' ? $components[
'VALUES_ONLY'] : array($components[
'VALUES_ONLY']);
247 $tableFields = array_keys($this->databaseConnection->cache_fieldType[$components[
'TABLE']]);
249 $valuesComponents = $components[
'EXTENDED'] ===
'1' ? $components[
'FIELDS'] : array($components[
'FIELDS']);
250 $tableFields = array_keys($valuesComponents[0]);
252 foreach ($valuesComponents as $valuesComponent) {
255 foreach ($valuesComponent as $fV) {
256 $fields[$tableFields[$fc++]] = $fV[0];
260 $query = count($values) === 1 ? $values[0] : $values;
276 switch ((
string)$this->databaseConnection->handlerCfg[$this->databaseConnection->handler_getFromTableList($components[
'TABLE'])][
'type']) {
278 $query[] = parent::compileCREATETABLE($components);
282 $fieldsKeys = array();
283 $indexKeys = array();
284 foreach ($components[
'FIELDS'] as $fN => $fCfg) {
285 $handlerKey = $this->databaseConnection->handler_getFromTableList($components[
'TABLE']);
286 $fieldsKeys[$fN] = $this->databaseConnection->quoteName($fN, $handlerKey, TRUE) .
' ' . $this->
compileFieldCfg($fCfg[
'definition']);
288 if (isset($components[
'KEYS']) && is_array($components[
'KEYS'])) {
289 foreach ($components[
'KEYS'] as $kN => $kCfg) {
290 if ($kN ===
'PRIMARYKEY') {
291 foreach ($kCfg as $field) {
292 $fieldsKeys[$field] .=
' PRIMARY';
294 } elseif ($kN ===
'UNIQUE') {
295 foreach ($kCfg as $n => $field) {
296 $indexKeys = array_merge($indexKeys, $this->databaseConnection->handlerInstance[$this->databaseConnection->handler_getFromTableList($components[
'TABLE'])]->DataDictionary->CreateIndexSQL($n, $components[
'TABLE'], $field, array(
'UNIQUE')));
299 $indexKeys = array_merge($indexKeys, $this->databaseConnection->handlerInstance[$this->databaseConnection->handler_getFromTableList($components[
'TABLE'])]->DataDictionary->CreateIndexSQL($components[
'TABLE'] .
'_' . $kN, $components[
'TABLE'], $kCfg));
304 $tableOptions = array(
'postgres' =>
'WITHOUT OIDS');
306 $tableName = $this->databaseConnection->quoteName($components[
'TABLE'], NULL, TRUE);
307 $query = array_merge($this->databaseConnection->handlerInstance[$this->databaseConnection->lastHandlerKey]->DataDictionary->CreateTableSQL($tableName, implode(
',' . chr(10), $fieldsKeys), $tableOptions), $indexKeys);
323 switch ((
string)$this->databaseConnection->handlerCfg[$this->databaseConnection->lastHandlerKey][
'type']) {
325 $query = parent::compileALTERTABLE($components);
328 $tableName = $this->databaseConnection->quoteName($components[
'TABLE'], NULL, TRUE);
329 $fieldName = $this->databaseConnection->quoteName($components[
'FIELD'], NULL, TRUE);
330 switch (strtoupper(str_replace(array(
' ',
"\n",
"\r",
"\t"),
'', $components[
'action']))) {
332 $query = $this->databaseConnection->handlerInstance[$this->databaseConnection->lastHandlerKey]->DataDictionary->AddColumnSQL($tableName, $fieldName .
' ' . $this->
compileFieldCfg($components[
'definition']));
335 $query = $this->databaseConnection->handlerInstance[$this->databaseConnection->lastHandlerKey]->DataDictionary->AlterColumnSQL($tableName, $fieldName .
' ' . $this->
compileFieldCfg($components[
'definition']));
343 case 'ADDPRIMARYKEY':
346 $query .=
' (' . implode(
',', $components[
'fields']) .
')';
348 case 'DEFAULTCHARACTERSET':
367 switch ((
string)$this->databaseConnection->handlerCfg[$this->databaseConnection->lastHandlerKey][
'type']) {
369 $cfg = parent::compileFieldCfg($fieldCfg);
373 $type = $this->databaseConnection->MySQLMetaType($fieldCfg[
'fieldType']);
376 if (strlen($fieldCfg[
'value']) && in_array($type, array(
'C',
'C2'))) {
377 $cfg .=
' ' . $fieldCfg[
'value'];
378 } elseif (!isset($fieldCfg[
'value']) && in_array($type, array(
'C',
'C2'))) {
383 if (is_array($fieldCfg[
'featureIndex'])) {
386 if (isset($fieldCfg[
'featureIndex'][
'NOTNULL']) && !isset($fieldCfg[
'featureIndex'][
'DEFAULT']) && !isset($fieldCfg[
'featureIndex'][
'AUTO_INCREMENT'])) {
393 $fieldCfg[
'featureIndex'][
'DEFAULT'] = array(
'keyword' =>
'DEFAULT',
'value' => array(
'0',
''));
396 $fieldCfg[
'featureIndex'][
'DEFAULT'] = array(
'keyword' =>
'DEFAULT',
'value' => array(
'',
'\''));
399 foreach ($fieldCfg[
'featureIndex'] as $feature => $featureDef) {
401 case $feature ===
'UNSIGNED' && !$this->databaseConnection->runningADOdbDriver(
'mysql'):
402 case $feature ===
'NOTNULL' && $this->databaseConnection->runningADOdbDriver(
'oci8'):
404 case $feature ===
'AUTO_INCREMENT':
405 $cfg .=
' AUTOINCREMENT';
407 case $feature ===
'NOTNULL':
411 $cfg .=
' ' . $featureDef[
'keyword'];
414 if (is_array($featureDef[
'value'])) {
415 if ($featureDef[
'value'][0] ===
'') {
418 $cfg .=
' ' . $featureDef[
'value'][1] . $this->
compileAddslashes($featureDef[
'value'][0]) . $featureDef[
'value'][1];
419 if (!is_numeric($featureDef[
'value'][0])) {
443 if (!is_array($featureIndex[
'DEFAULT'][
'value'])) {
446 return !is_numeric($featureIndex[
'DEFAULT'][
'value'][0]) && empty($featureIndex[
'DEFAULT'][
'value'][0]);
467 switch ((
string)$this->databaseConnection->handlerCfg[$this->databaseConnection->lastHandlerKey][
'type']) {
469 $output = parent::compileWhereClause($clauseArray);
475 if (is_array($clauseArray)) {
476 foreach ($clauseArray as $v) {
478 $output .= $v[
'operator'] ?
' ' . $v[
'operator'] :
'';
480 if (is_array($v[
'sub'])) {
482 } elseif (isset($v[
'func']) && $v[
'func'][
'type'] ===
'EXISTS') {
483 $output .=
' ' . trim($v[
'modifier']) .
' EXISTS (' . $this->
compileSELECT($v[
'func'][
'subquery']) .
')';
485 if (isset($v[
'func']) && $v[
'func'][
'type'] ===
'LOCATE') {
486 $output .=
' ' . trim($v[
'modifier']);
488 case $this->databaseConnection->runningADOdbDriver(
'mssql') && $functionMapping:
489 $output .=
' CHARINDEX(';
490 $output .= $v[
'func'][
'substr'][1] . $v[
'func'][
'substr'][0] . $v[
'func'][
'substr'][1];
491 $output .=
', ' . ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
492 $output .= isset($v[
'func'][
'pos']) ?
', ' . $v[
'func'][
'pos'][0] :
'';
495 case $this->databaseConnection->runningADOdbDriver(
'oci8') && $functionMapping:
496 $output .=
' INSTR(';
497 $output .= ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
498 $output .=
', ' . $v[
'func'][
'substr'][1] . $v[
'func'][
'substr'][0] . $v[
'func'][
'substr'][1];
499 $output .= isset($v[
'func'][
'pos']) ?
', ' . $v[
'func'][
'pos'][0] :
'';
503 $output .=
' LOCATE(';
504 $output .= $v[
'func'][
'substr'][1] . $v[
'func'][
'substr'][0] . $v[
'func'][
'substr'][1];
505 $output .=
', ' . ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
506 $output .= isset($v[
'func'][
'pos']) ?
', ' . $v[
'func'][
'pos'][0] :
'';
509 } elseif (isset($v[
'func']) && $v[
'func'][
'type'] ===
'IFNULL') {
510 $output .=
' ' . trim($v[
'modifier']) .
' ';
512 case $this->databaseConnection->runningADOdbDriver(
'mssql') && $functionMapping:
515 case $this->databaseConnection->runningADOdbDriver(
'oci8') && $functionMapping:
522 $output .= ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
523 $output .=
', ' . $v[
'func'][
'default'][1] . $this->
compileAddslashes($v[
'func'][
'default'][0]) . $v[
'func'][
'default'][1];
525 } elseif (isset($v[
'func']) && $v[
'func'][
'type'] ===
'FIND_IN_SET') {
526 $output .=
' ' . trim($v[
'modifier']) .
' ';
527 if ($functionMapping) {
529 case $this->databaseConnection->runningADOdbDriver(
'mssql'):
530 $field = ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
531 if (!isset($v[
'func'][
'str_like'])) {
532 $v[
'func'][
'str_like'] = $v[
'func'][
'str'][0];
534 $output .=
'\',\
'+' . $field .
'+\',\' LIKE \'%,' . $v[
'func'][
'str_like'] .
',%\'';
536 case $this->databaseConnection->runningADOdbDriver(
'oci8'):
537 $field = ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
538 if (!isset($v[
'func'][
'str_like'])) {
539 $v[
'func'][
'str_like'] = $v[
'func'][
'str'][0];
541 $output .=
'\',\
'||' . $field .
'||\',\' LIKE \'%,' . $v[
'func'][
'str_like'] .
',%\'';
543 case $this->databaseConnection->runningADOdbDriver(
'postgres'):
544 $output .=
' FIND_IN_SET(';
545 $output .= $v[
'func'][
'str'][1] . $v[
'func'][
'str'][0] . $v[
'func'][
'str'][1];
546 $output .=
', ' . ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
550 $field = ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
551 if (!isset($v[
'func'][
'str_like'])) {
552 $v[
'func'][
'str_like'] = $v[
'func'][
'str'][0];
554 $output .=
'(' . $field .
' LIKE \'%,' . $v[
'func'][
'str_like'] .
',%\'' .
' OR ' . $field .
' LIKE \'' . $v[
'func'][
'str_like'] .
',%\'' .
' OR ' . $field .
' LIKE \'%,' . $v[
'func'][
'str_like'] .
'\'' .
' OR ' . $field .
'= ' . $v[
'func'][
'str'][1] . $v[
'func'][
'str'][0] . $v[
'func'][
'str'][1] .
')';
558 case $this->databaseConnection->runningADOdbDriver(
'mssql'):
560 case $this->databaseConnection->runningADOdbDriver(
'oci8'):
562 case $this->databaseConnection->runningADOdbDriver(
'postgres'):
563 $output .=
' FIND_IN_SET(';
564 $output .= $v[
'func'][
'str'][1] . $v[
'func'][
'str'][0] . $v[
'func'][
'str'][1];
565 $output .=
', ' . ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
569 $field = ($v[
'func'][
'table'] ? $v[
'func'][
'table'] .
'.' :
'') . $v[
'func'][
'field'];
570 if (!isset($v[
'func'][
'str_like'])) {
571 $v[
'func'][
'str_like'] = $v[
'func'][
'str'][0];
573 $output .=
'(' . $field .
' LIKE \'%,' . $v[
'func'][
'str_like'] .
',%\'' .
' OR ' . $field .
' LIKE \'' . $v[
'func'][
'str_like'] .
',%\'' .
' OR ' . $field .
' LIKE \'%,' . $v[
'func'][
'str_like'] .
'\'' .
' OR ' . $field .
'= ' . $v[
'func'][
'str'][1] . $v[
'func'][
'str'][0] . $v[
'func'][
'str'][1] .
')';
578 $output .=
' ' . trim($v[
'modifier']) .
' ';
580 if ($v[
'calc'] ===
'&' && $functionMapping) {
582 case $this->databaseConnection->runningADOdbDriver(
'oci8'):
584 $output .=
'BITAND(' . trim((($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field'])) .
',' . $v[
'calc_value'][1] . $this->
compileAddslashes($v[
'calc_value'][0]) . $v[
'calc_value'][1] .
')';
588 $output .= trim((($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field'])) . $v[
'calc'] . $v[
'calc_value'][1] . $this->
compileAddslashes($v[
'calc_value'][0]) . $v[
'calc_value'][1];
590 } elseif ($v[
'calc']) {
591 $output .= trim((($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field'])) . $v[
'calc'];
592 if (isset($v[
'calc_table'])) {
593 $output .= trim(($v[
'calc_table'] ? $v[
'calc_table'] .
'.' :
'') . $v[
'calc_field']);
595 $output .= $v[
'calc_value'][1] . $this->
compileAddslashes($v[
'calc_value'][0]) . $v[
'calc_value'][1];
597 } elseif (!($this->databaseConnection->runningADOdbDriver(
'oci8') && preg_match(
'/(NOT )?LIKE( BINARY)?/', $v[
'comparator']) && $functionMapping)) {
598 $output .= trim(($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field']);
602 if ($v[
'comparator']) {
603 $isLikeOperator = preg_match(
'/(NOT )?LIKE( BINARY)?/', $v[
'comparator']);
605 case $this->databaseConnection->runningADOdbDriver(
'oci8') && $isLikeOperator && $functionMapping:
607 if (isset($v[
'value'][
'operator'])) {
609 foreach ($v[
'value'][
'args'] as $fieldDef) {
610 $values[] = ($fieldDef[
'table'] ? $fieldDef[
'table'] .
'.' :
'') . $fieldDef[
'field'];
612 $compareValue =
' ' . $v[
'value'][
'operator'] .
'(' . implode(
',', $values) .
')';
614 $compareValue = $v[
'value'][1] . $this->
compileAddslashes(trim($v[
'value'][0],
'%')) . $v[
'value'][1];
623 $tableName = substr($v[
'table'], 1, strlen($v[
'table']) - 2);
624 $fieldName = substr($v[
'field'], 1, strlen($v[
'field']) - 2);
625 $fieldType = $this->databaseConnection->sql_field_metatype($tableName, $fieldName);
626 $isLob = $fieldType ===
'B' || $fieldType ===
'XL';
628 if (strtoupper(substr($v[
'comparator'], -6)) ===
'BINARY') {
630 $output .=
'(dbms_lob.instr(' . trim((($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field'])) .
', ' . $compareValue .
',1,1) > 0)';
632 $output .=
'(instr(' . trim((($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field'])) .
', ' . $compareValue .
',1,1) > 0)';
636 $output .=
'(dbms_lob.instr(LOWER(' . trim((($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field'])) .
'), ' .
GeneralUtility::strtolower($compareValue) .
',1,1) > 0)';
638 $output .=
'(instr(LOWER(' . trim((($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field'])) .
'), ' .
GeneralUtility::strtolower($compareValue) .
',1,1) > 0)';
643 if ($isLikeOperator && $functionMapping) {
644 if ($this->databaseConnection->runningADOdbDriver(
'postgres') || $this->databaseConnection->runningADOdbDriver(
'postgres64') || $this->databaseConnection->runningADOdbDriver(
'postgres7') || $this->databaseConnection->runningADOdbDriver(
'postgres8')) {
647 switch ($v[
'comparator']) {
649 $v[
'comparator'] =
'ILIKE';
652 $v[
'comparator'] =
'NOT ILIKE';
655 $v[
'comparator'] = str_replace(
' BINARY',
'', $v[
'comparator']);
659 $v[
'comparator'] = str_replace(
' BINARY',
'', $v[
'comparator']);
662 $output .=
' ' . $v[
'comparator'];
664 $comparator = strtoupper(str_replace(array(
' ', TAB, CR, LF),
'', $v[
'comparator']));
666 if (isset($v[
'subquery'])) {
667 $output .=
' (' . $this->
compileSELECT($v[
'subquery']) .
')';
669 $valueBuffer = array();
670 foreach ($v[
'value'] as $realValue) {
671 $valueBuffer[] = $realValue[1] . $this->
compileAddslashes($realValue[0]) . $realValue[1];
674 $dbmsSpecifics = $this->databaseConnection->getSpecifics();
675 if ($dbmsSpecifics === NULL) {
676 $output .=
' (' . trim(implode(
',', $valueBuffer)) .
')';
678 $chunkedList = $dbmsSpecifics->splitMaxExpressions($valueBuffer);
679 $chunkCount = count($chunkedList);
681 if ($chunkCount === 1) {
682 $output .=
' (' . trim(implode(
',', $valueBuffer)) .
')';
684 $listExpressions = array();
685 $field = trim(($v[
'table'] ? $v[
'table'] .
'.' :
'') . $v[
'field']);
687 switch ($comparator) {
698 for ($i = 0; $i < $chunkCount; ++$i) {
699 $listPart = trim(implode(
',', $chunkedList[$i]));
700 $listExpressions[] =
' (' . $listPart .
')';
703 $implodeString =
' ' . $operator .
' ' . $field .
' ' . $v[
'comparator'];
706 $lastFieldPos = strrpos($output, $field);
707 $output = substr_replace($output,
'(', $lastFieldPos, 0);
708 $output .= implode($implodeString, $listExpressions) .
')';
713 $lbound = $v[
'values'][0];
714 $ubound = $v[
'values'][1];
718 } elseif (isset($v[
'value'][
'operator'])) {
720 foreach ($v[
'value'][
'args'] as $fieldDef) {
721 $values[] = ($fieldDef[
'table'] ? $fieldDef[
'table'] .
'.' :
'') . $fieldDef[
'field'];
723 $output .=
' ' . $v[
'value'][
'operator'] .
'(' . implode(
',', $values) .
')';
725 $output .=
' ' . $v[
'value'][1] . $this->
compileAddslashes($v[
'value'][0]) . $v[
'value'][1];
745 $parseResult = $this->
parseSQL($SQLquery);
747 if (is_array($parseResult)) {
753 if (!is_array($testResult)) {
756 debug(array(
'ERROR MESSAGE' =>
'Input query did not match the parsed and recompiled query exactly (not observing whitespace)',
'TEST result' => $testResult),
'SQL parsing failed:');
760 debug(array(
'query' => $SQLquery,
'ERROR MESSAGE' => $parseResult),
'SQL parsing failed:');
checkEmptyDefaultValue($featureIndex)
static isFirstPartOfStr($str, $partStr)
compileALTERTABLE($components)
__construct(DatabaseConnection $databaseConnection=NULL)
getValueInQuotes(&$parseString, $quote)
getValueInQuotesMssql(&$parseString, $quote)
compileFieldList($selectFields, $compileComments=TRUE, $functionMapping=TRUE)
compileCREATETABLE($components)
compileSELECT($components)
debug($variable='', $name=' *variable *', $line=' *line *', $file=' *file *', $recursiveDepth=3, $debugLevel=E_DEBUG)
if(!defined('TYPO3_MODE')) $GLOBALS['TYPO3_CONF_VARS']['SC_OPTIONS']['t3lib/class.t3lib_userauth.php']['logoff_pre_processing'][]
compileFieldCfg($fieldCfg)
static inList($list, $item)
debug_parseSQLpartCompare($str, $newStr, $caseInsensitive=FALSE)
compileWhereClause($clauseArray, $functionMapping=TRUE)
compileCaseStatement(array $components, $functionMapping=TRUE)
compileINSERT($components)