Passed
Push — master ( 288a96...964b09 )
by Daniel
10:30
created

src/ORM/Connect/MySQLStatement.php (1 issue)

1
<?php
2
3
namespace SilverStripe\ORM\Connect;
4
5
use mysqli_result;
6
use mysqli_stmt;
7
8
/**
9
 * Provides a record-view for mysqli statements
10
 *
11
 * By default streams unbuffered data, but seek(), rewind(), or numRecords() will force the statement to
12
 * buffer itself and sacrifice any potential performance benefit.
13
 */
14
class MySQLStatement extends Query
15
{
16
17
    /**
18
     * The related mysqli statement object if generated using a prepared query
19
     *
20
     * @var mysqli_stmt
21
     */
22
    protected $statement;
23
24
    /**
25
     * Metadata result for this statement
26
     *
27
     * @var mysqli_result
28
     */
29
    protected $metadata;
30
31
    /**
32
     * Is the statement bound to the current resultset?
33
     *
34
     * @var bool
35
     */
36
    protected $bound = false;
37
38
    /**
39
     * List of column names
40
     *
41
     * @var array
42
     */
43
    protected $columns = array();
44
45
    /**
46
     * List of bound variables in the current row
47
     *
48
     * @var array
49
     */
50
    protected $boundValues = array();
51
52
    /**
53
     * Binds this statement to the variables
54
     */
55
    protected function bind()
56
    {
57
        $variables = array();
58
59
        // Bind each field
60
        while ($field = $this->metadata->fetch_field()) {
61
            $this->columns[] = $field->name;
62
            // Note that while boundValues isn't initialised at this point,
63
            // later calls to $this->statement->fetch() Will populate
64
            // $this->boundValues later with the next result.
65
            $variables[] = &$this->boundValues[$field->name];
66
        }
67
68
        $this->bound = true;
69
        $this->metadata->free();
70
71
        // Buffer all results
72
        $this->statement->store_result();
73
74
        call_user_func_array(array($this->statement, 'bind_result'), $variables);
75
    }
76
77
    /**
78
     * Hook the result-set given into a Query class, suitable for use by SilverStripe.
79
     * @param mysqli_stmt $statement The related statement, if present
80
     * @param mysqli_result $metadata The metadata for this statement
81
     */
82
    public function __construct($statement, $metadata)
83
    {
84
        $this->statement = $statement;
85
        $this->metadata = $metadata;
86
87
        // Immediately bind and buffer
88
        $this->bind();
89
    }
90
91
    public function __destruct()
92
    {
93
        $this->statement->close();
94
        $this->currentRecord = false;
0 ignored issues
show
Documentation Bug introduced by
It seems like false of type false is incompatible with the declared type array of property $currentRecord.

Our type inference engine has found an assignment to a property that is incompatible with the declared type of that property.

Either this assignment is in error or the assigned type should be added to the documentation/type hint for that property..

Loading history...
95
    }
96
97
    public function seek($row)
98
    {
99
        $this->rowNum = $row - 1;
100
        $this->statement->data_seek($row);
101
        return $this->next();
102
    }
103
104
    public function numRecords()
105
    {
106
        return $this->statement->num_rows();
107
    }
108
109
    public function nextRecord()
110
    {
111
        // Skip data if out of data
112
        if (!$this->statement->fetch()) {
113
            return false;
114
        }
115
116
        // Dereferenced row
117
        $row = array();
118
        foreach ($this->boundValues as $key => $value) {
119
            $row[$key] = $value;
120
        }
121
        return $row;
122
    }
123
124
    public function rewind()
125
    {
126
        return $this->seek(0);
127
    }
128
}
129