public function updateTableAlias(ParserCallback $callback, &$callerSession) { list($tableAlias, $columnName) = ColumnNameHelper::splitColumnName($callback->marker); $updateAllowed = FALSE; if (isset($tableAlias)) { if (isset($this->oldTableAlias) && ($tableAlias === $this->oldTableAlias)) { $updateAllowed = TRUE; } } elseif (!isset($this->oldTableAlias)) { $updateAllowed = TRUE; } if ($updateAllowed) { $callback->marker = ColumnNameHelper::combineColumnName($this->newTableAlias, $columnName); } $this->adjustCallbackObject($callback, $callerSession); }
public function assembleColumnName($tableAlias) { $selectedTableAlias = $this->tableAlias; if (isset($selectedTableAlias)) { if (isset($tableAlias) && $selectedTableAlias != $tableAlias) { throw new UnsupportedOperationException(); } } else { $this->tableAlias = $tableAlias; $selectedTableAlias = $tableAlias; } return ColumnNameHelper::combineColumnName($selectedTableAlias, $this->name); }
public function assembleColumnName($tableAlias) { $selectedTableAlias = $this->tableAlias; if (isset($selectedTableAlias)) { if (isset($tableAlias) && ($selectedTableAlias != $tableAlias)) { throw new UnsupportedOperationException(); } } else { $this->tableAlias = $tableAlias; $selectedTableAlias = $tableAlias; } list(, $columnName) = ReferencePathHelper::splitReference($this->name); return ColumnNameHelper::combineColumnName($selectedTableAlias, $columnName); }
public function prepareSections(array $requestedColumnNames = NULL) { $retrieveAllColumns = !isset($requestedColumnNames); $tableCount = count($this->tables); if ($tableCount === 0) { throw new IllegalStateException(t('Tables have not been defined for this statement')); } if ($tableCount === 1) { $table = $this->tables[0]; if ($table instanceof SubquerySection) { if (!isset($table->columns) && !isset($this->conditions) && !isset($this->groupByColumns) && !isset($this->havingConditions)) { return array(TRUE, new AssembledSections(NULL, $table->body, NULL, NULL, NULL)); } } } // we need to find each column in order to avoid using sub select $isColumnAccessible = TRUE; $columnNameUsage = NULL; if (!$retrieveAllColumns) { // preparing tables which support each requested column foreach ($requestedColumnNames as $columnName) { $columnNameUsage[$columnName] = array(); } // preparing tables which support 'where' subject columns for which we did not select table alias if (isset($this->conditions)) { foreach ($this->conditions as $condition) { if (!isset($condition->subjectTableAlias)) { $columnNameUsage[(($condition instanceof AbstractConditionSection) ? $condition->subjectColumnName : NULL)] = array(); } } } } // if the statement contains just one table we do not need to worry about columns if (!$retrieveAllColumns) { if (($tableCount === 1) && (($table = $this->tables[0]) instanceof TableSection)) { if (isset($columnNameUsage)) { foreach ($columnNameUsage as &$usage) { $usage[] = $table; } unset($usage); } } else { // calculating how many tables support each column for ($i = 0; ($i < $tableCount) && $isColumnAccessible; $i++) { $table = $this->tables[$i]; if (isset($table->columns)) { foreach ($table->columns as $column) { if (isset($columnNameUsage[$column->alias])) { $columnNameUsage[$column->alias][] = $table; } } } else { if ($table instanceof TableSection) { // list of columns is not provided for the table // I hope that is because the table is just transitioning table to access data from other table // I do not want to use $isColumnAccessible = FALSE until we have a use case } else { // there is no access to columns for this type of table $isColumnAccessible = FALSE; } } } // checking how many tables support each column if (isset($columnNameUsage)) { foreach ($columnNameUsage as $sourceTables) { if (count($sourceTables) !== 1) { $isColumnAccessible = FALSE; break; } } } } } $useTableNameAsAlias = $tableCount > 1; $indentSectionElement = str_pad('', SelectStatementPrint::INDENT__SECTION_ELEMENT); $indexedSelect = $unindexedSelect = NULL; if ($isColumnAccessible && !$retrieveAllColumns) { // all columns are linked to corresponding tables foreach ($requestedColumnNames as $columnName) { $sourceTable = $columnNameUsage[$columnName][0]; $column = $sourceTable->findColumnByAlias($columnName); if (isset($column) && !$column->visible) { continue; } $columnTableAlias = $sourceTable->prepareColumnTableAlias($useTableNameAsAlias); // if there is no such columns we return just requested column name if (isset($column)) { $assembledColumn = $column->assemble($columnTableAlias); if (isset($column->requestColumnIndex)) { $indexedSelect[$column->requestColumnIndex][] = $assembledColumn; } else { $unindexedSelect[] = $assembledColumn; } } else { $unindexedSelect[] = ColumnNameHelper::combineColumnName($columnTableAlias, $columnName); } } } else { foreach ($this->tables as $table) { // we ignore a table which provides list of columns but the list is empty if (isset($table->columns) && (count($table->columns) === 0)) { continue; } $columnTableAlias = $table->prepareColumnTableAlias($useTableNameAsAlias); if (isset($table->columns)) { // returning only columns which are configured for the table foreach ($table->columns as $column) { if (!$column->visible) { continue; } $assembledColumn = $column->assemble($columnTableAlias); if (isset($column->requestColumnIndex)) { $indexedSelect[$column->requestColumnIndex][] = $assembledColumn; } else { $unindexedSelect[] = $assembledColumn; } } } else { // returning all columns from the table $unindexedSelect[] = ColumnNameHelper::combineColumnName($columnTableAlias, '*'); } } } // sorting select columns by request column index. If the index is not provided, corresponding column is placed at the end of the list $sortedSelect = array(); if (isset($indexedSelect)) { ksort($indexedSelect); foreach ($indexedSelect as $assembledColumns) { $sortedSelect = array_merge($sortedSelect, $assembledColumns); } } if (isset($unindexedSelect)) { $sortedSelect= array_merge($sortedSelect, $unindexedSelect); } $select = (count($sortedSelect) > 0) ? implode(",\n$indentSectionElement", $sortedSelect) : NULL; $from = NULL; for ($i = 0; $i < $tableCount; $i++) { $table = $this->tables[$i]; if ($i > 0) { $from .= "\n" . $indentSectionElement . 'LEFT OUTER JOIN '; } $from .= $table->assemble(); // assembling join conditions if ($i === 0) { if (isset($table->conditions)) { throw new IllegalStateException(t('Join conditions should not be defined for %tableName table', array('%tableName' => $table->name))); } } else { if (isset($table->conditions)) { $from .= ' ON '; for ($j = 0, $c = count($table->conditions); $j < $c; $j++) { $condition = $table->conditions[$j]; if ($j > 0) { $from .= ' AND '; } $from .= $condition->assemble($this, $table, $useTableNameAsAlias); } } else { throw new IllegalStateException(t('Join conditions were not defined for %tableName table', array('%tableName' => $table->name))); } } } $where = NULL; if (isset($this->conditions)) { foreach ($this->conditions as $condition) { if (isset($where)) { $where .= "\n AND "; } if (isset($condition->subjectTableAlias)) { $subjectTable = $this->getTable($condition->subjectTableAlias); } else { // We do not have table alias // Solution: find a column in a table and use the table alias and the column name to generate the condition if (isset($columnNameUsage)) { $sourceTables = $columnNameUsage[(($condition instanceof AbstractConditionSection) ? $condition->subjectColumnName : NULL)]; $subjectTable = (count($sourceTables) === 1) ? $sourceTables[0] : NULL; } else { $subjectTable = $this->findColumnTable($condition->subjectColumnName); } if (!isset($subjectTable)) { throw new IllegalStateException(t( 'Condition for %columnName column cannot be prepared', array('%columnName' => $condition->subjectColumnName))); } } $where .= $condition->assemble($this, $subjectTable, $useTableNameAsAlias); } } $groupBy = NULL; if (isset($this->groupByColumns)) { foreach ($this->groupByColumns as $groupByColumn) { if (isset($groupBy)) { $groupBy .= ', '; } $groupBy .= $groupByColumn->assemble(NULL); } } $having = NULL; if (isset($this->havingConditions)) { foreach ($this->havingConditions as $havingCondition) { if (isset($having)) { $having .= "\n AND "; } $having .= $havingCondition->assemble($this, FALSE); } } $isSubqueryRequired = !$isColumnAccessible; return array($isSubqueryRequired, new AssembledSections($select, $from, $where, $groupBy, $having)); }
public function assemble(Statement $statement, AbstractTableSection $table, $useTableNameAsAlias) { list($referencedDatasetName, $referencedColumnName) = ReferencePathHelper::splitReference($this->subjectColumnName); $columnByAlias = $table->findColumnByAlias($referencedColumnName); $column = isset($columnByAlias) ? $table->findColumn($referencedColumnName) : NULL; $selectedColumn = isset($columnByAlias) && isset($column) ? $column : $columnByAlias; $tableAlias = $table->prepareColumnTableAlias($useTableNameAsAlias); return (isset($selectedColumn) ? $selectedColumn->assembleColumnName($tableAlias) : ColumnNameHelper::combineColumnName($tableAlias, $referencedColumnName)) . $this->joinValue->assemble($statement, $useTableNameAsAlias); }