From 3efe3efd58029b243ca6fd45a4ce0cf2826d1d5a Mon Sep 17 00:00:00 2001 From: Michael Wallner Date: Thu, 25 Sep 2014 13:48:56 +0200 Subject: [PATCH] pq\Result docs --- pq/Result.md | 77 +++++++++++++ pq/Result/: Fetching Results.md | 195 ++++++++++++++++++++++++++++++++ pq/Result/bind.md | 45 ++++++++ pq/Result/count.md | 16 +++ pq/Result/desc.md | 18 +++ pq/Result/fetchAll.md | 38 +++++++ pq/Result/fetchAllCols.md | 51 +++++++++ pq/Result/fetchBound.md | 19 ++++ pq/Result/fetchCol.md | 39 +++++++ pq/Result/fetchRow.md | 41 +++++++ pq/Result/map.md | 55 +++++++++ 11 files changed, 594 insertions(+) create mode 100644 pq/Result.md create mode 100644 pq/Result/: Fetching Results.md create mode 100644 pq/Result/bind.md create mode 100644 pq/Result/count.md create mode 100644 pq/Result/desc.md create mode 100644 pq/Result/fetchAll.md create mode 100644 pq/Result/fetchAllCols.md create mode 100644 pq/Result/fetchBound.md create mode 100644 pq/Result/fetchCol.md create mode 100644 pq/Result/fetchRow.md create mode 100644 pq/Result/map.md diff --git a/pq/Result.md b/pq/Result.md new file mode 100644 index 0000000..a6f3f8a --- /dev/null +++ b/pq/Result.md @@ -0,0 +1,77 @@ +# class pq\Result implements \Traversable, \Countable + +A query result. + +See [Fetching Results](pq/Result: Fetching Results) for a general overview. + +## Constants: + +### Status values: + +* EMPTY_QUERY + The query sent to the server was empty. +* COMMAND_OK + The query did not generate a result set and completed successfully. +* TUPLES_OK + The query successfully generated a result set. +* SINGLE_TUPLE + The result contains a single row of the result set when using pq\Connection::$unbuffered. +* COPY_OUT + COPY data can be recevied from the server. +* COPY_IN + COPY data can be sent to the server. +* BAD_RESPONSE + The server sent a bad response. +* NONFATAL_ERROR + A nonfatal error (notice or warning) occurred. +* FATAL_ERROR + A fatal error occurred. + + +### Fetch types: + +* FETCH_ARRAY + Fetch rows numerically indexed, where the index start with 0. +* FETCH_ASSOC + Fetch rows associatively indexed by column name. +* FETCH_OBJECT + Fetch rows as stdClass instance, where the column names are the property names. + +### Conversion bits: + +* CONV_BOOL + Automatically convert 'f' and 't' to FALSE and TRUE and vice versa. +* CONV_INT + Automatically convert integral strings to either int if it fits into maximum integer size and vice versa. +* CONV_FLOAT + Automatically convert floating point numbers. +* CONV_SCALAR + Do all scalar conversions listed above. +* CONV_ARRAY + Automatically convert arrays. +* CONV_DATETIME + Automatically convert date strings to pq\DateTime and vice versa. +* CONV_JSON + Automatically convert JSON. +* CONV_ALL + Do all of the above. + + +## Properties: + +* public (readonly) int $status + A [status constant](pq/Result#Status.values:). +* public (readonly) string $statusMessage + The accompanying status messsage. +* public (readonly) string $errorMessage + Any error message if $status indicates an error. +* public (readonly) int $numRows + The number of rows in the result set. +* public (readonly) int $numCols + The number of fields in a single tuple of the result set. +* public (readonly) int $affectedRows + The number of rows affected by a statement. +* public int $fetchType = pq\Result::FETCH_ARRAY + The [type of return value](pq/Result#Fetch.types:) the fetch methods should return when no fetch type argument was given. Defaults to pq\Connection::$defaultFetchType. +* public int $autoConvert = pq\Result::CONV_ALL + What [type of conversions](pq\Result#Conversion.bits:) to perform automatically. diff --git a/pq/Result/: Fetching Results.md b/pq/Result/: Fetching Results.md new file mode 100644 index 0000000..57acbe2 --- /dev/null +++ b/pq/Result/: Fetching Results.md @@ -0,0 +1,195 @@ +# pq\Result: Overview + +An synchronous pq\Connection::exec*() call, or calls to pq\Connection::getResult() after using [asynchronous queries](pq/Connection/: Asynchronous Usage) returns an instance of pq\Result on success. See [Query execution](pq/Connection/: Executing Queries), optionally with [Types](pq/: Using Types) and [Prepared Statements](pq/Statement/: Overview) for details about how to execute queries. + +## Fetch types: + +pq\Result supports the follwing fetch types: + +* pq\Result::FETCH_ARRAY + Fetch the row as ***numerically indexed array***. +* pq\Result::FETCH_ASSOC + Fetch the row as ***associative array*** indexed by column name. +* pq\Result::FETCH_OBJECT + Fetch the row as stdClass ***object***. + +The fetch type is inherited from pq\Connection::$defaultFetchType can be set through the ***public*** property named pq\Result::$fetchType, to be used when no fetch type is specified in the call to a fetch method. + +## Number of rows: + +The number of rows can be obtained from the ***public readonly*** property pq\Result::$numRows, or passing the result instance, which implements the Countable interface, to the count() function. + +## Number of columns: + +The number of columns each row has, can be obtained from the ***public readonly*** property pq\Result::$numCols. + +## Fetching everything as an array of rows: + +pq\Result::fetchAll() fetches the complete result set as an array of arrays or objects, depending on the default fetch type, as explained above, or the ***fetch type*** passed as first argument to the method. + + exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'"); + + foreach ($result->fetchAll(pq\Result::FETCH_OBJECT) as $row) { + echo "ID: {$row->id}\n"; + echo "Name: {$row->name}\n"; + echo "Mail: {$row->email}\n\n"; + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> + +pq\Result implements the virtual Traversable interface, so the above task can also be accomplished by this code: + + defaultFetchType = pq\Result::FETCH_OBJECT; + + $result = $connection->exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'"); + + foreach ($result as $row) { + echo "ID: {$row->id}\n"; + echo "Name: {$row->name}\n"; + echo "Mail: {$row->email}\n\n"; + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> + +## Iteratively fetching row by row: + +pq\Result::fetchRow() will return FALSE when the end of the result set has been reached. + + exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'"); + + while (list($id, $name, $email) = $result->fetchRow()) { + echo "ID: {$id}\n"; + echo "Name: {$name}\n"; + echo "Mail: {$email}\n\n"; + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> + +As with most ```fetch*()``` methods, the fetch type can be passed as argument here, too. + +## Fetching a single column by row: + +Because a column value can be NULL or FALSE, pq\Result::fetchCol() stores the ***value*** into the first argument ***passed by reference***. The demanded ***column index/name*** can be passed as second argument, where ***column indices start with 0***, which is also the default. + + exec("SELECT email FROM accounts WHERE email LIKE '_@%'"); + + while ($result->fetchCol($email)) { + echo "Mail: {$email}\n"; + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> + +When the end of the result set has been reached, pq\Result::fetchCol() will return FALSE. + +> ***NOTE:*** +> pq\Result::fetchCol() does not accept a fetch type argument. + +## Fetching bound variables: + +It is possible to bind variables to result columns by reference by calling pq\Result::bind() for each demanded column and then retreive the results by calling pq\Result::fetchBound() iteratively. + + exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'"); + + $result->bind("id", $id); + $result->bind("name", $name); + $result->bind("email", $email); + + while ($result->fetchBound()) { + echo "ID: {$id}\n"; + echo "Name: {$name}\n"; + echo "Mail: {$email}\n\n"; + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> + + +pq\Result::bind() expects the ***column index/name*** as first argument and the ***variable to bind by reference to this result column*** as second argument. + +> ***NOTE:*** +> pq\Result::fetchBound() does not accept a fetch type argument. + +## Fetching simple maps: + +pq\Result::map() fetches the complete result set as a simple map, a ***multi dimensional array***, each dimension indexed by a column. + +Consider the following example: + + exec("SELECT a,b,c from generate_series(1,3) a, + generate_series(4,6) b, + generate_series(7,9) c"); + + foreach($result->map(array(0,1,2)) as $a => $aa) { + foreach ($aa as $b => $bb) { + foreach ($bb as $c => $res) { + printf("%s,%s,%s = %s ", $a, $b, $c, implode(",", $res)); + } + printf("\n"); + } + printf("\n"); + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> + + +It should produce: + + 1,4,7 = 1,4,7 1,4,8 = 1,4,8 1,4,9 = 1,4,9 + 1,5,7 = 1,5,7 1,5,8 = 1,5,8 1,5,9 = 1,5,9 + 1,6,7 = 1,6,7 1,6,8 = 1,6,8 1,6,9 = 1,6,9 + + 2,4,7 = 2,4,7 2,4,8 = 2,4,8 2,4,9 = 2,4,9 // This should help generate maps + 2,5,7 = 2,5,7 2,5,8 = 2,5,8 2,5,9 = 2,5,9 // of f.e. statistical data with + 2,6,7 = 2,6,7 2,6,8 = 2,6,8 2,6,9 = 2,6,9 // some GROUP BYs etc. + + 3,4,7 = 3,4,7 3,4,8 = 3,4,8 3,4,9 = 3,4,9 + 3,5,7 = 3,5,7 3,5,8 = 3,5,8 3,5,9 = 3,5,9 + 3,6,7 = 3,6,7 3,6,8 = 3,6,8 3,6,9 = 3,6,9 + +pq\Result::map() optionally expects an ***array containing the column indices/names used to index the map*** as first argument, and uses the first column (at index 0) by default. The second argument can optionally be an ***array of column indices/names*** which should build up the leaf entry of the map. A ***fetch type*** can also be specified as optional third argument. diff --git a/pq/Result/bind.md b/pq/Result/bind.md new file mode 100644 index 0000000..1b5d449 --- /dev/null +++ b/pq/Result/bind.md @@ -0,0 +1,45 @@ +# bool pq\Result::bind(mixed $col, mixed &$var) + +Bind a variable to a result column. +See pq\Result::fetchBound(). + +## Params: + +* mixed $col + The column name or index to bind to. +* mixed $var + The variable reference. + +## Returns: + +* bool, success. + +## Throws: + +* pq\Exception\InvalidArgumentException +* pq\Exception\BadMethodCallException + +## Example: + + exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'"); + + $result->bind("id", $id); + $result->bind("name", $name); + $result->bind("email", $email); + + while ($result->fetchBound()) { + echo "ID: {$id}\n"; + echo "Name: {$name}\n"; + echo "Mail: {$email}\n\n"; + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> + diff --git a/pq/Result/count.md b/pq/Result/count.md new file mode 100644 index 0000000..a6f25a9 --- /dev/null +++ b/pq/Result/count.md @@ -0,0 +1,16 @@ +# int pq\Result::count() + +Count number of rows in this result set. + +## Params: + +None. + +## Returns: + +* int, the number of rows. + +## Throws: + +* pq\Exception\BadMethodCallException + diff --git a/pq/Result/desc.md b/pq/Result/desc.md new file mode 100644 index 0000000..d73363f --- /dev/null +++ b/pq/Result/desc.md @@ -0,0 +1,18 @@ +# array pq\Result::desc() + +Describe a prepared statement. + +> ***NOTE:*** + This will only return meaningful information for a result of pq\Statement::desc(). + +## Params: + +None. + +## Returns: + +* array, list of parameter type OIDs for the prepared statement. + +## Throws: + +* pq\Exception\BadMethodCallException diff --git a/pq/Result/fetchAll.md b/pq/Result/fetchAll.md new file mode 100644 index 0000000..4c8ead3 --- /dev/null +++ b/pq/Result/fetchAll.md @@ -0,0 +1,38 @@ +# array pq\Result::fetchAll([int $fetch_type = pq\Result::$fetchType]) + +Fetch all rows at once. + +## Params: + +* Optional int $fetch_type = pq\Result::$fetchType + The type the return value should have, see pq\Result::FETCH_* constants. + +## Returns: + +* array, all fetched rows. + +## Throws: + +* pq\Exception\InvalidArgumentException +* pq\Exception\BadMethodCallException + +## Example: + + exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'"); + + foreach ($result->fetchAll(pq\Result::FETCH_OBJECT) as $row) { + echo "ID: {$row->id}\n"; + echo "Name: {$row->name}\n"; + echo "Mail: {$row->email}\n\n"; + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> + diff --git a/pq/Result/fetchAllCols.md b/pq/Result/fetchAllCols.md new file mode 100644 index 0000000..baf1fad --- /dev/null +++ b/pq/Result/fetchAllCols.md @@ -0,0 +1,51 @@ +# array pq\Result::fetchAllCols([int $col = 0]) + +Fetch all rows of a single column. + +## Params: + +* Optional int $col = 0 + The column name or index to fetch. + +## Returns: + +* array, list of column values. + +## Throws: + +* pq\Exception\InvalidArgumentException +* pq\Exception\BadMethodCallException +* pq\Exception\RuntimeException + +## Example: + + fetchAllCols(0); /* this call would fetch: + array(4) { + int(1), + int(2), + int(3), + int(4) + } + */ + + $result->fetchAllCols("name"); /* this call would fetch: + array(4) { + string(3) "ann", + string(4) "barb", + string(4) "john", + string(4) "mike" + } + */ diff --git a/pq/Result/fetchBound.md b/pq/Result/fetchBound.md new file mode 100644 index 0000000..56f63c1 --- /dev/null +++ b/pq/Result/fetchBound.md @@ -0,0 +1,19 @@ +# array pq\Result::fetchBound() + +Iteratively fetch a row into bound variables. +See pq\Result::bind(). + +## Params: + +None. + +## Returns: + +* array, the fetched row as numerically indexed array. +* NULL, when iteration ends. + +## Throws: + +* pq\Exception\InvalidArgumentException +* pq\Exception\BadMethodCallException +* pq\Exception\RuntimeException diff --git a/pq/Result/fetchCol.md b/pq/Result/fetchCol.md new file mode 100644 index 0000000..735d01d --- /dev/null +++ b/pq/Result/fetchCol.md @@ -0,0 +1,39 @@ +# bool pq\Result::fetchCol(mixed &$ref[, mixed $col = 0]) + +Iteratively fetch a single column. + +## Params: + +* mixed $ref + The variable where the column value will be stored in. +* Optional mixed $col = 0 + The column name or index. + +## Returns: + +* bool, success. +* NULL, when iteration ends. + +## Throws: + +* pq\Exception\InvalidArgumentException +* pq\Exception\BadMethodCallException +* pq\Exception\RuntimeException + +## Example: + + exec("SELECT email FROM accounts WHERE email LIKE '_@%'"); + + while ($result->fetchCol($email)) { + echo "Mail: {$email}\n"; + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> diff --git a/pq/Result/fetchRow.md b/pq/Result/fetchRow.md new file mode 100644 index 0000000..381ca7a --- /dev/null +++ b/pq/Result/fetchRow.md @@ -0,0 +1,41 @@ +# mixed pq\Result::fetchRow([int $fetch_type = pq\Result::$fetchType]) + +Iteratively fetch a row. + +## Params: + +* Optional int $fetch_type = pq\Result::$fetchType + The type the return value should have, see pq\Result::FETCH_* constants. + +## Returns: + +* array, numerically indexed for pq\Result::FETCH_ARRAY +* array, associatively indexed for pq\Result::FETCH_ASSOC +* object, stdClass instance for pq\Result::FETCH_OBJECT +* NULL, when iteration ends. + +## Throws: + +* pq\Exception\InvalidArgumentException +* pq\Exception\BadMethodCallException +* pq\Exception\RuntimeException + +## Example: + +exec("SELECT id, name, email FROM accounts WHERE email LIKE '_@%'"); + + while (list($id, $name, $email) = $result->fetchRow()) { + echo "ID: {$id}\n"; + echo "Name: {$name}\n"; + echo "Mail: {$email}\n\n"; + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> diff --git a/pq/Result/map.md b/pq/Result/map.md new file mode 100644 index 0000000..a2b5946 --- /dev/null +++ b/pq/Result/map.md @@ -0,0 +1,55 @@ +# array pq\Result::map([mixed $keys = 0[, mixed $vals = NULL]]) + +Fetch the complete result set as a simple map, a *multi dimensional array*, each dimension indexed by a column. + +## Params: + +* Optional mixed $keys = 0 + The the column indices/names used to index the map. +* Optional mixed $vals = NULL + The column indices/names which should build up the leaf entry of the map. + +## Returns: + +* array, the mapped columns. + +## Example: + + exec("SELECT a,b,c from generate_series(1,3) a, + generate_series(4,6) b, + generate_series(7,9) c"); + + foreach($result->map(array(0,1,2)) as $a => $aa) { + foreach ($aa as $b => $bb) { + foreach ($bb as $c => $res) { + printf("%s,%s,%s = %s ", $a, $b, $c, implode(",", $res)); + } + printf("\n"); + } + printf("\n"); + } + } catch (\pq\Exception $e) { + echo $e->getMessage(), "\n"; + } + + ?> + + +It should produce: + + 1,4,7 = 1,4,7 1,4,8 = 1,4,8 1,4,9 = 1,4,9 + 1,5,7 = 1,5,7 1,5,8 = 1,5,8 1,5,9 = 1,5,9 + 1,6,7 = 1,6,7 1,6,8 = 1,6,8 1,6,9 = 1,6,9 + + 2,4,7 = 2,4,7 2,4,8 = 2,4,8 2,4,9 = 2,4,9 // This should help generate maps + 2,5,7 = 2,5,7 2,5,8 = 2,5,8 2,5,9 = 2,5,9 // of f.e. statistical data with + 2,6,7 = 2,6,7 2,6,8 = 2,6,8 2,6,9 = 2,6,9 // some GROUP BYs etc. + + 3,4,7 = 3,4,7 3,4,8 = 3,4,8 3,4,9 = 3,4,9 + 3,5,7 = 3,5,7 3,5,8 = 3,5,8 3,5,9 = 3,5,9 + 3,6,7 = 3,6,7 3,6,8 = 3,6,8 3,6,9 = 3,6,9 -- 2.30.2