Skip to content

Commit f98cf2d

Browse files
committed
Improve getColumnAliases helper
1 parent bb0ea19 commit f98cf2d

File tree

5 files changed

+59
-16
lines changed

5 files changed

+59
-16
lines changed

composer.json

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,9 @@
1717
"autoload": {
1818
"psr-4": {
1919
"Ngekoding\\CodeIgniterDataTables\\": "src"
20-
}
20+
},
21+
"files": [
22+
"src/functions.php"
23+
]
2124
}
2225
}

src/Config.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@ class Config
2323
'getFieldNames' => 'list_fields',
2424
'getResult' => 'result',
2525
'getResultArray' => 'result_array',
26+
'getCompiledSelect' => 'get_compiled_select',
2627
'groupStart' => 'group_start',
2728
'groupEnd' => 'group_end'
2829
]

src/DataTables.php

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -41,11 +41,7 @@ public function __construct($queryBuilder, $ciVersion = NULL)
4141
$this->request = Request::createFromGlobals();
4242
$this->queryBuilder = $queryBuilder;
4343

44-
$replection = new \ReflectionProperty($queryBuilder, $this->config->get('QBSelect'));
45-
$replection->setAccessible(TRUE);
46-
47-
$qbSelect = $replection->getValue($queryBuilder);
48-
$this->columnAliases = Helper::getColumnAliases($qbSelect);
44+
$this->columnAliases = Helper::getColumnAliases($queryBuilder, $this->config);
4945

5046
// When getting the field names, the query builder will be changed
5147
// So we need to make a clone to keep the original

src/Helper.php

Lines changed: 44 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -6,28 +6,62 @@
66

77
class Helper
88
{
9-
public static function getColumnAliases($qbSelect)
9+
public static function getColumnAliases($queryBuilder, $config)
1010
{
11-
if (empty($qbSelect)) return [];
11+
$queryBuilderClone = clone $queryBuilder;
12+
$compiledSelect = $queryBuilderClone->{$config->get('getCompiledSelect')}();
1213

13-
$sql = 'SELECT '.implode(', ', $qbSelect);
1414
$parser = new PHPSQLParser();
15-
$parsed = $parser->parse($sql);
15+
$parsed = $parser->parse($compiledSelect);
16+
17+
$tableAliases = [];
18+
foreach ($parsed['FROM'] as $from) {
19+
if ($from['expr_type'] === 'table') {
20+
$name = $from['no_quotes']['parts'][0];
21+
$alias = isset($from['alias']['name']) ? $from['alias']['no_quotes']['parts'][0] : $name;
22+
$tableAliases[$alias] = $name;
23+
}
24+
}
1625

1726
$columnAliases = [];
1827
foreach ($parsed['SELECT'] as $select) {
19-
if ($select['alias']) {
20-
$alias = $select['alias']['name'];
21-
if ($select['expr_type'] == 'colref') {
22-
$key = $select['base_expr'];
23-
} elseif (strpos($select['expr_type'], 'function') !== FALSE) {
28+
$expr_type = $select['expr_type'];
29+
$base_expr = $select['base_expr'];
30+
31+
if (isset($select['alias']['name'])) {
32+
$alias = $select['alias']['no_quotes']['parts'][0];
33+
34+
if ($expr_type === 'colref') {
35+
$key = implode('.', $select['no_quotes']['parts']);
36+
} elseif ($expr_type === 'expression') {
37+
$key = trim(str_replace($alias, '', $base_expr));
38+
} elseif (str_contains($expr_type, 'function')) {
2439
$parts = [];
2540
foreach ($select['sub_tree'] as $part) {
2641
$parts[] = $part['base_expr'];
2742
}
28-
$key = $select['base_expr'].'('.implode(', ', $parts).')';
43+
$key = $base_expr . '(' . implode(', ', $parts) . ')';
2944
}
3045
$columnAliases[$alias] = $key;
46+
} elseif ($expr_type === 'colref') {
47+
if (str_contains($base_expr, '*')) {
48+
if (str_contains($base_expr, '.')) {
49+
$tableAlias = $select['no_quotes']['parts'][0];
50+
} else {
51+
$tableAlias = array_key_first($tableAliases);
52+
}
53+
54+
$tableName = $tableAliases[$tableAlias];
55+
$fields = $queryBuilder->{$config->get('getFieldNames')}($tableName);
56+
foreach ($fields as $field) {
57+
$key = "{$tableAlias}.{$field}";
58+
$columnAliases[$field] = $key;
59+
}
60+
} elseif (str_contains($base_expr, '.')) {
61+
$field = $select['no_quotes']['parts'][1];
62+
$key = implode('.', $select['no_quotes']['parts']);
63+
$columnAliases[$field] = $key;
64+
}
3165
}
3266
}
3367

src/functions.php

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
<?php
2+
3+
if ( ! function_exists('str_contains'))
4+
{
5+
function str_contains($haystack, $needle)
6+
{
7+
return $needle !== '' && mb_strpos($haystack, $needle) !== false;
8+
}
9+
}

0 commit comments

Comments
 (0)