Abstract Class Yiisoft\Db\QueryBuilder\AbstractDMLQueryBuilder
| Inheritance | Yiisoft\Db\QueryBuilder\AbstractDMLQueryBuilder |
|---|---|
| Implements | Yiisoft\Db\QueryBuilder\DMLQueryBuilderInterface |
It's used to manipulate data in tables.
This manipulation involves inserting data into database tables, retrieving existing data, deleting data from existing tables and modifying existing data.
Protected Properties
Public Methods
Protected Methods
Property Details
Method Details
| public mixed __construct ( Yiisoft\Db\QueryBuilder\QueryBuilderInterface $queryBuilder, Yiisoft\Db\Schema\QuoterInterface $quoter, Yiisoft\Db\Schema\SchemaInterface $schema ) | ||
| $queryBuilder | Yiisoft\Db\QueryBuilder\QueryBuilderInterface | |
| $quoter | Yiisoft\Db\Schema\QuoterInterface | |
| $schema | Yiisoft\Db\Schema\SchemaInterface | |
public function __construct(
protected QueryBuilderInterface $queryBuilder,
protected QuoterInterface $quoter,
protected SchemaInterface $schema,
) {}
| protected string buildSimpleSelect ( array $columns ) | ||
| $columns | array | |
protected function buildSimpleSelect(array $columns): string
{
$quoter = $this->quoter;
foreach ($columns as $name => &$column) {
$column .= ' AS ' . $quoter->quoteSimpleColumnName($name);
}
return 'SELECT ' . implode(', ', $columns);
}
| public string delete ( string $table, array|string $condition, array &$params ) | ||
| $table | string | |
| $condition | array|string | |
| $params | array | |
public function delete(string $table, array|string $condition, array &$params): string
{
$sql = 'DELETE FROM ' . $this->quoter->quoteTableName($table);
$where = $this->queryBuilder->buildWhere($condition, $params);
return $where === '' ? $sql : $sql . ' ' . $where;
}
Extract column names from columns and rows.
| protected string[] extractColumnNames ( array[]|Iterator $rows, string[] $columns ) | ||
| $rows | array[]|Iterator |
The rows to be batch inserted into the table. |
| $columns | string[] |
The column names. |
| return | string[] |
The column names. |
|---|---|---|
protected function extractColumnNames(array|Iterator $rows, array $columns): array
{
$columns = $this->getNormalizedColumnNames($columns);
if (!empty($columns)) {
return $columns;
}
if ($rows instanceof Iterator) {
$row = $rows->current();
} else {
$row = reset($rows);
}
$row = match (gettype($row)) {
'array' => $row,
'object' => $row instanceof Traversable
? iterator_to_array($row)
: get_object_vars($row),
default => [],
};
if (array_key_exists(0, $row)) {
return [];
}
/** @var string[] $columnNames */
$columnNames = array_keys($row);
return array_combine($columnNames, $columnNames);
}
Get normalized column names
| protected string[] getNormalizedColumnNames ( string[] $columns ) | ||
| $columns | string[] |
The column names. |
| return | string[] |
Normalized column names. |
|---|---|---|
protected function getNormalizedColumnNames(array $columns): array
{
foreach ($columns as &$name) {
$name = $this->quoter->ensureColumnName($name);
$name = $this->quoter->unquoteSimpleColumnName($name);
}
return $columns;
}
Prepare select-subQuery and field names for INSERT INTO ... SELECT SQL statement.
| protected string[] getQueryColumnNames ( Yiisoft\Db\Query\QueryInterface $query, array &$params = [] ) | ||
| $query | Yiisoft\Db\Query\QueryInterface |
Object, which represents a select query. |
| $params | array |
The parameters to bind to the generated SQL statement. These parameters will be included in the result, with the more parameters generated during the query building process. |
| return | string[] |
Array of column names, values, and params. |
|---|---|---|
| throws | Yiisoft\Db\Exception\Exception | |
| throws | InvalidArgumentException | |
| throws | Yiisoft\Db\Exception\InvalidConfigException | |
| throws | Yiisoft\Db\Exception\NotSupportedException | |
protected function getQueryColumnNames(QueryInterface $query, array &$params = []): array
{
/** @var string[] $select */
$select = $query->getSelect();
if (empty($select) || in_array('*', $select, true)) {
throw new InvalidArgumentException('Expected select query object with enumerated (named) parameters');
}
$names = [];
foreach ($select as $title => $field) {
if (is_string($title)) {
$names[] = $title;
} else {
if ($field instanceof ExpressionInterface) {
$field = $this->queryBuilder->buildExpression($field, $params);
}
if (preg_match('/^(.*?)(?i:\s+as\s+|\s+)([\w\-_.]+)$/', $field, $matches)) {
$names[] = $matches[2];
} else {
$names[] = $field;
}
}
}
return $this->getNormalizedColumnNames($names);
}
| public string insert ( string $table, array|Yiisoft\Db\Query\QueryInterface $columns, array &$params = [] ) | ||
| $table | string | |
| $columns | array|Yiisoft\Db\Query\QueryInterface | |
| $params | array | |
public function insert(string $table, array|QueryInterface $columns, array &$params = []): string
{
[$names, $placeholders, $values, $params] = $this->prepareInsertValues($table, $columns, $params);
$quotedNames = array_map($this->quoter->quoteColumnName(...), $names);
return 'INSERT INTO ' . $this->quoter->quoteTableName($table)
. (!empty($quotedNames) ? ' (' . implode(', ', $quotedNames) . ')' : '')
. (!empty($placeholders) ? ' VALUES (' . implode(', ', $placeholders) . ')' : ' ' . $values);
}
| public string insertBatch ( string $table, iterable $rows, array $columns = [], array &$params = [] ) | ||
| $table | string | |
| $rows | iterable | |
| $columns | array | |
| $params | array | |
public function insertBatch(string $table, iterable $rows, array $columns = [], array &$params = []): string
{
if (!is_array($rows)) {
$rows = $this->prepareTraversable($rows);
}
if (empty($rows)) {
return '';
}
$columns = $this->extractColumnNames($rows, $columns);
$values = $this->prepareBatchInsertValues($table, $rows, $columns, $params);
$query = 'INSERT INTO ' . $this->quoter->quoteTableName($table);
if (count($columns) > 0) {
$quotedColumnNames = array_map($this->quoter->quoteColumnName(...), $columns);
$query .= ' (' . implode(', ', $quotedColumnNames) . ')';
}
return $query . ' VALUES (' . implode('), (', $values) . ')';
}
| public string insertReturningPks ( string $table, array|Yiisoft\Db\Query\QueryInterface $columns, array &$params = [] ) | ||
| $table | string | |
| $columns | array|Yiisoft\Db\Query\QueryInterface | |
| $params | array | |
| throws | Yiisoft\Db\Exception\NotSupportedException | |
|---|---|---|
public function insertReturningPks(string $table, array|QueryInterface $columns, array &$params = []): string
{
throw new NotSupportedException(__METHOD__ . '() is not supported by this DBMS.');
}
| public boolean isTypecastingEnabled ( ) |
public function isTypecastingEnabled(): bool
{
return $this->typecasting;
}
Normalizes the column names.
| protected array normalizeColumnNames ( array $columns ) | ||
| $columns | array |
The column data (name => value). |
| return | array |
The normalized column names (name => value). |
|---|---|---|
protected function normalizeColumnNames(array $columns): array
{
/** @var string[] $columnNames */
$columnNames = array_keys($columns);
$normalizedNames = $this->getNormalizedColumnNames($columnNames);
return array_combine($normalizedNames, $columns);
}
Prepare values for batch insert.
| protected string[] prepareBatchInsertValues ( string $table, iterable $rows, string[] $columnNames, array &$params ) | ||
| $table | string |
The table name. |
| $rows | iterable |
The rows to be batch inserted into the table. |
| $columnNames | string[] |
The column names. |
| $params | array |
The binding parameters that will be generated by this method. |
| return | string[] |
The values. |
|---|---|---|
protected function prepareBatchInsertValues(string $table, iterable $rows, array $columnNames, array &$params): array
{
$values = [];
$names = array_values($columnNames);
$keys = array_fill_keys($names, false);
$columns = $this->typecasting ? $this->schema->getTableSchema($table)?->getColumns() ?? [] : [];
$queryBuilder = $this->queryBuilder;
foreach ($rows as $row) {
$i = 0;
$placeholders = $keys;
/** @var int|string $key */
foreach ($row as $key => $value) {
$columnName = $columnNames[$key] ?? (isset($keys[$key]) ? $key : $names[$i] ?? $i);
if (isset($columns[$columnName])) {
$value = $columns[$columnName]->dbTypecast($value);
}
$placeholders[$columnName] = $queryBuilder->buildValue($value, $params);
++$i;
}
$values[] = implode(', ', $placeholders);
}
return $values;
}
Prepare column names and placeholders for INSERT SQL statement.
| protected array prepareInsertValues ( string $table, array|Yiisoft\Db\Query\QueryInterface $columns, array $params = [] ) | ||
| $table | string |
The table to insert new rows into. |
| $columns | array|Yiisoft\Db\Query\QueryInterface |
The column data (name => value) to insert into the table or instance of
{@see \Yiisoft\Db\QueryBuilder\Query} to perform |
| $params | array |
The binding parameters that will be generated by this method. They should be bound to the DB command later. |
| return | array |
Array of column names, placeholders, values, and params. |
|---|---|---|
| throws | Yiisoft\Db\Exception\Exception | |
| throws | Yiisoft\Db\Exception\InvalidConfigException | |
| throws | InvalidArgumentException | |
| throws | Yiisoft\Db\Exception\NotSupportedException | |
protected function prepareInsertValues(string $table, array|QueryInterface $columns, array $params = []): array
{
if (empty($columns)) {
return [[], [], 'DEFAULT VALUES', []];
}
if ($columns instanceof QueryInterface) {
$names = $this->getQueryColumnNames($columns, $params);
[$values, $params] = $this->queryBuilder->build($columns, $params);
return [$names, [], $values, $params];
}
$placeholders = [];
$columns = $this->normalizeColumnNames($columns);
$tableColumns = $this->typecasting ? $this->schema->getTableSchema($table)?->getColumns() ?? [] : [];
foreach ($columns as $name => $value) {
if (isset($tableColumns[$name])) {
$value = $tableColumns[$name]->dbTypecast($value);
}
$placeholders[] = $this->queryBuilder->buildValue($value, $params);
}
return [array_keys($columns), $placeholders, '', $params];
}
Prepare traversable for batch insert.
| protected array|Iterator prepareTraversable ( Traversable $rows ) | ||
| $rows | Traversable |
The rows to be batch inserted into the table. |
| return | array|Iterator |
The prepared rows. |
|---|---|---|
final protected function prepareTraversable(Traversable $rows): Iterator|array
{
while ($rows instanceof IteratorAggregate) {
$rows = $rows->getIterator();
}
/** @var Iterator $rows */
if (!$rows->valid()) {
return [];
}
return $rows;
}
Prepare column names and placeholders for UPDATE SQL statement.
| protected string[] prepareUpdateSets ( string $table, array $columns, array &$params, boolean $forUpsert = false, boolean $useTableName = false ) | ||
| $table | string | |
| $columns | array | |
| $params | array | |
| $forUpsert | boolean | |
| $useTableName | boolean | |
protected function prepareUpdateSets(
string $table,
array $columns,
array &$params,
bool $forUpsert = false,
bool $useTableName = false,
): array {
$sets = [];
$columns = $this->normalizeColumnNames($columns);
$tableColumns = $this->schema->getTableSchema($table)?->getColumns() ?? [];
$typecastColumns = $this->typecasting ? $tableColumns : [];
$queryBuilder = $this->queryBuilder;
$quoter = $this->quoter;
if ($useTableName) {
$quotedTableName = $quoter->quoteTableName($table);
$columnPrefix = "$quotedTableName.";
} else {
$columnPrefix = '';
}
foreach ($columns as $name => $value) {
if (isset($typecastColumns[$name])) {
$value = $typecastColumns[$name]->dbTypecast($value);
}
$quotedName = $quoter->quoteSimpleColumnName($name);
if ($forUpsert && $value instanceof MultiOperandFunction && empty($value->getOperands())) {
$quotedTableName ??= $quoter->quoteTableName($table);
$value->add(new Expression("$quotedTableName.$quotedName"))
->add(new Expression("EXCLUDED.$quotedName"));
if (isset($tableColumns[$name]) && $value instanceof ArrayMerge) {
$value->type($tableColumns[$name]);
}
$builtValue = $queryBuilder->buildExpression($value, $params);
} else {
$builtValue = $queryBuilder->buildValue($value, $params);
}
$sets[] = "$columnPrefix$quotedName=$builtValue";
}
return $sets;
}
Prepare column names and constraints for "upsert" operation.
| protected array prepareUpsertColumns ( string $table, array|Yiisoft\Db\Query\QueryInterface $insertColumns, array|boolean $updateColumns, Yiisoft\Db\Constraint\Index[] &$constraints = [] ) | ||
| $table | string | |
| $insertColumns | array|Yiisoft\Db\Query\QueryInterface | |
| $updateColumns | array|boolean | |
| $constraints | Yiisoft\Db\Constraint\Index[] | |
| return | array |
Array of unique, insert and update column names. |
|---|---|---|
protected function prepareUpsertColumns(
string $table,
array|QueryInterface $insertColumns,
array|bool $updateColumns,
array &$constraints = [],
): array {
if ($insertColumns instanceof QueryInterface) {
$insertNames = $this->getQueryColumnNames($insertColumns);
} else {
$insertNames = $this->getNormalizedColumnNames(array_keys($insertColumns));
}
$uniqueNames = $this->getTableUniqueColumnNames($table, $insertNames, $constraints);
if ($updateColumns === true) {
return [$uniqueNames, $insertNames, array_diff($insertNames, $uniqueNames)];
}
return [$uniqueNames, $insertNames, null];
}
Prepare column names and placeholders for upsert SQL statement.
| protected string[] prepareUpsertSets ( string $table, array|boolean $updateColumns, array|null $updateNames, array &$params ) | ||
| $table | string | |
| $updateColumns | array|boolean | |
| $updateNames | array|null | |
| $params | array | |
protected function prepareUpsertSets(
string $table,
array|bool $updateColumns,
?array $updateNames,
array &$params,
): array {
if ($updateColumns === true) {
$quoter = $this->quoter;
$sets = [];
/** @var string[] $updateNames */
foreach ($updateNames as $name) {
$quotedName = $quoter->quoteSimpleColumnName($name);
$sets[] = "$quotedName=EXCLUDED.$quotedName";
}
return $sets;
}
return $this->prepareUpdateSets($table, $updateColumns, $params, true);
}
| public string resetSequence ( string $table, integer|string|null $value = null ) | ||
| $table | string | |
| $value | integer|string|null | |
| throws | Yiisoft\Db\Exception\NotSupportedException | |
|---|---|---|
public function resetSequence(string $table, int|string|null $value = null): string
{
throw new NotSupportedException(__METHOD__ . '() is not supported by this DBMS.');
}
| public string update ( string $table, array $columns, array|Yiisoft\Db\Expression\ExpressionInterface|string $condition, array|Yiisoft\Db\Expression\ExpressionInterface|string|null $from = null, array &$params = [] ) | ||
| $table | string | |
| $columns | array | |
| $condition | array|Yiisoft\Db\Expression\ExpressionInterface|string | |
| $from | array|Yiisoft\Db\Expression\ExpressionInterface|string|null | |
| $params | array | |
public function update(
string $table,
array $columns,
array|ExpressionInterface|string $condition,
array|ExpressionInterface|string|null $from = null,
array &$params = [],
): string {
$updates = $this->prepareUpdateSets($table, $columns, $params);
$sql = 'UPDATE ' . $this->quoter->quoteTableName($table) . ' SET ' . implode(', ', $updates);
$where = $this->queryBuilder->buildWhere($condition, $params);
if ($from !== null) {
$from = DbArrayHelper::normalizeExpressions($from);
$fromClause = $this->queryBuilder->buildFrom($from, $params);
$sql .= $fromClause === '' ? '' : ' ' . $fromClause;
}
return $where === '' ? $sql : $sql . ' ' . $where;
}
| public string upsert ( string $table, array|Yiisoft\Db\Query\QueryInterface $insertColumns, array|boolean $updateColumns = true, array &$params = [] ) | ||
| $table | string | |
| $insertColumns | array|Yiisoft\Db\Query\QueryInterface | |
| $updateColumns | array|boolean | |
| $params | array | |
| throws | Yiisoft\Db\Exception\NotSupportedException | |
|---|---|---|
public function upsert(
string $table,
array|QueryInterface $insertColumns,
array|bool $updateColumns = true,
array &$params = [],
): string {
throw new NotSupportedException(__METHOD__ . ' is not supported by this DBMS.');
}
| public string upsertReturning ( string $table, array|Yiisoft\Db\Query\QueryInterface $insertColumns, array|boolean $updateColumns = true, array|null $returnColumns = null, array &$params = [] ) | ||
| $table | string | |
| $insertColumns | array|Yiisoft\Db\Query\QueryInterface | |
| $updateColumns | array|boolean | |
| $returnColumns | array|null | |
| $params | array | |
| throws | Yiisoft\Db\Exception\NotSupportedException | |
|---|---|---|
public function upsertReturning(
string $table,
array|QueryInterface $insertColumns,
array|bool $updateColumns = true,
?array $returnColumns = null,
array &$params = [],
): string {
throw new NotSupportedException(__METHOD__ . '() is not supported by this DBMS.');
}
| public Yiisoft\Db\QueryBuilder\AbstractDMLQueryBuilder withTypecasting ( boolean $typecasting = true ) | ||
| $typecasting | boolean | |
public function withTypecasting(bool $typecasting = true): static
{
$new = clone $this;
$new->typecasting = $typecasting;
return $new;
}
Signup or Login in order to comment.