Skip to content

Commit

Permalink
query builder: add index hints support [closes #77]
Browse files Browse the repository at this point in the history
  • Loading branch information
hrach committed Apr 10, 2020
1 parent 91ff937 commit 470731f
Show file tree
Hide file tree
Showing 3 changed files with 42 additions and 0 deletions.
16 changes: 16 additions & 0 deletions doc/query-builder.texy
Expand Up @@ -118,3 +118,19 @@ $builder->joinLeft('[books] AS [b]', '[a.id] = [b.authorId] AND [b.title] = %s',
// FROM [authors] AS [a]
// LEFT JOIN [books] AS [b] ON ([a.id] = [b.authorId] AND [b.title] = %s)
\--


------------

INDEX HINTS (MySQL)
===================

Use `indexHints()` method to tell the query planner how to efficiently execute your query.

/--php
$builder->from('[authors]', 'a');
$builder->indexHints('FORCE INDEX(%column)', 'my_index_name');

// will produce
// ... FROM [authors] AS [a] FORCE INDEX (`my_index_name`) ...
\--
23 changes: 23 additions & 0 deletions src/QueryBuilder/QueryBuilder.php
Expand Up @@ -34,6 +34,7 @@ class QueryBuilder
private $args = [
'select' => null,
'from' => null,
'indexHints' => null,
'join' => null,
'where' => null,
'group' => null,
Expand All @@ -50,6 +51,9 @@ class QueryBuilder
*/
private $from;

/** @var string|null */
private $indexHints;

/**
* @var array|null
* @phpstan-var array<array{type: string, from: string, alias: string, table: string, on: string}>|null
Expand Down Expand Up @@ -110,6 +114,7 @@ public function getQueryParameters(): array
return array_merge(
(array) $this->args['select'],
(array) $this->args['from'],
(array) $this->args['indexHints'],
(array) $this->args['join'],
(array) $this->args['where'],
(array) $this->args['group'],
Expand Down Expand Up @@ -141,6 +146,10 @@ private function getFromClauses(): string
{
$query = $this->from[0] . ($this->from[1] ? " AS [{$this->from[1]}]" : '');

if ($this->indexHints !== null) {
$query .= ' ' . $this->indexHints;
}

foreach ((array) $this->join as $join) {
$query .= " $join[type] JOIN $join[table] ON ($join[on])";
}
Expand Down Expand Up @@ -175,6 +184,20 @@ public function from(string $fromExpression, ?string $alias = null, ...$args): s
}


/**
* MySQL only feature.
* @phpstan-param array<int, mixed> $args
* @return static
*/
public function indexHints(?string $indexHintsExpression, ...$args): self
{
$this->dirty();
$this->indexHints = $indexHintsExpression;
$this->pushArgs('indexHints', $args);
return $this;
}


public function getFromAlias(): ?string
{
if ($this->from === null) {
Expand Down
3 changes: 3 additions & 0 deletions tests/cases/unit/QueryBuilderTest.basics.phpt
Expand Up @@ -34,13 +34,15 @@ class QueryBuilderBasicsTest extends QueryBuilderTestCase
[
'SELECT %i, %i ' .
'FROM func(%i) AS [table] ' .
'USE INDEX (%column) ' .
'WHERE ((id = %s) OR (id2 = %i)) AND (id3 = %i) ' .
'GROUP BY %column, %column ' .
'HAVING (id = %s) AND (id2 = %i) ' .
'ORDER BY FIELD(id, %i, %i), FIELD(id2, %i, %i)',

4, 9, // select
3, // from
'my_index_name', // index hints
'foo_w', 7, 8, // where
'foo_g', 'foo_g_2', // group by
'foo_h', 6, // having
Expand All @@ -59,6 +61,7 @@ class QueryBuilderBasicsTest extends QueryBuilderTestCase
->orWhere('id2 = %i', 7)
->andWhere('id3 = %i', 8)
->addSelect('%i', 9)
->indexHints('USE INDEX (%column)', 'my_index_name')
);
}

Expand Down

0 comments on commit 470731f

Please sign in to comment.