src/PdoDatabase.php
private function selectInternal(callable $callback, $query, array $bindValues = null) {
		$this->normalizeConnection();

		try {
			// create a prepared statement from the supplied SQL string
			$stmt = $this->pdo->prepare($query);
		}
		catch (PDOException $e) {
			ErrorHandler::rethrow($e);
		}

		// if a performance profiler has been defined
		if (isset($this->profiler)) {
			$this->profiler->beginMeasurement();
		}

		/** @var PDOStatement $stmt */

		// bind the supplied values to the query and execute it
		try {
			$stmt->execute($bindValues);
		}
		catch (PDOException $e) {
			ErrorHandler::rethrow($e);
		}

		// if a performance profiler has been defined
		if (isset($this->profiler)) {
			$this->profiler->endMeasurement($query, $bindValues, 1);
		}

		// fetch the desired results from the result set via the supplied callback
		$results = $callback($stmt);

		$this->denormalizeConnection();

		// if the result is empty
		if (empty($results) && $stmt->rowCount() === 0) {
			// consistently return `null`
			return null;
		}
		// if some results have been found
		else {
			// return these as extracted by the callback
			return $results;
		}
	}
private function selectInternal(callable $callback, $query, array $bindValues = null) {
		$this->normalizeConnection();

		try {
			// create a prepared statement from the supplied SQL string
			$stmt = $this->pdo->prepare($query);
		}
		catch (PDOException $e) {
			ErrorHandler::rethrow($e);
		}

		// if a performance profiler has been defined
		if (isset($this->profiler)) {
			$this->profiler->beginMeasurement();
		}

		/** @var PDOStatement $stmt */

		// bind the supplied values to the query and execute it
		try {
			$stmt->execute($bindValues);
		}
		catch (PDOException $e) {
			ErrorHandler::rethrow($e);
		}

		// if a performance profiler has been defined
		if (isset($this->profiler)) {
			$this->profiler->endMeasurement($query, $bindValues, 1);
		}

		// fetch the desired results from the result set via the supplied callback
		$results = $callback($stmt);

		$this->denormalizeConnection();

		// if the result is empty
		if (empty($results) && $stmt->rowCount() === 0) {
			// consistently return `null`
			return null;
		}
		// if some results have been found
		else {
			// return these as extracted by the callback
			return $results;
		}
	}
Selects from the database using the specified query and returns what the supplied callback extracts from the result set

You should not include any dynamic input in the query

Instead, pass `?` characters (without any quotes) as placeholders and pass the actual values in the third argument

@param callable $callback the callback that receives the executed statement and can then extract and return the desired results
@param string $query the query to select with
@param array|null $bindValues (optional) the values to bind as replacements for the `?` characters in the query
@return mixed whatever the callback has extracted and returned from the result set