-
Notifications
You must be signed in to change notification settings - Fork 3.4k
/
ResultSet.php
123 lines (97 loc) · 2.75 KB
/
ResultSet.php
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
<?php
/**
* PHP Version 5.4
*
* CakePHP(tm) : Rapid Development Framework (http://cakephp.org)
* Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
*
* Licensed under The MIT License
* For full copyright and license information, please see the LICENSE.txt
* Redistributions of files must retain the above copyright notice.
*
* @copyright Copyright (c) Cake Software Foundation, Inc. (http://cakefoundation.org)
* @link http://cakephp.org CakePHP(tm) Project
* @since CakePHP(tm) v 3.0.0
* @license MIT License (http://www.opensource.org/licenses/mit-license.php)
*/
namespace Cake\ORM;
use \Iterator;
use Cake\Database\Type;
class ResultSet implements Iterator {
protected $_query;
protected $_statement;
protected $_getNext = false;
protected $_count = 0;
protected $_counter = -1;
protected $_current;
protected $_types = [];
protected $_defaultTable;
protected $_map;
public function __construct($query, $statement) {
$this->_query = $query;
$this->_statement = $statement;
$this->_defaultTable = $this->_query->repository()->alias();
}
public function toArray() {
return iterator_to_array($this);
}
public function current() {
return $this->_groupResult($this->_current);
}
public function key() {
return $this->_count;
}
public function next() {
$this->_count++;
$this->_fetchResult();
}
public function rewind() {
}
public function valid() {
$this->_fetchResult();
return $this->_current !== false;
}
protected function _fetchResult() {
if ($this->_counter < $this->_count) {
$this->_current = $this->_statement->fetch('assoc');
$this->_counter = $this->_count;
}
}
protected function _groupResult() {
$results = [];
foreach ($this->_current as $key => $value) {
$table = $this->_defaultTable;
$field = $key;
if (empty($this->_map[$key])) {
$parts = explode('__', $key);
if (count($parts) > 1) {
if ($parts[0] !== $table) {
$assoc = $this->_query->repository()->association($parts[0]);
$parts[2] = $assoc->property();
}
$this->_map[$key] = $parts;
}
}
$parts = $this->_map[$key];
list($table, $field) = $parts;
$value = $this->_castValue($table, $field, $value);
if (!empty($parts[2])) {
$results[$parts[2]][$field] = $value;
} else {
$results[$field] = $value;
}
}
return $results;
}
protected function _castValue($table, $field, $value) {
$schema = $this->_query->aliasedTable($table)->schema();
if (!isset($schema[$field])) {
return $value;
}
$key = $table . '.' . $value;
if (!isset($this->types[$key])) {
$this->types[$key] = Type::build($schema[$field]['type']);
}
return $this->types[$key]->toPHP($value, $this->_query->connection()->driver());
}
}