I am working on writing a PHP backend program, but my program doesn't work because PHP doesn't support the get_result() and fetch_assoc() function.
How can I rewrite the code so that they can work in the same way as this function?
public function storeUser($userLoginID, $password) {
$uuid = uniqid('', true);
$hash = $this->hashSSHA($password);
$encrypted_password = $hash["encrypted"];
$salt = $hash["salt"];
$stmt = $this->conn->prepare("INSERT INTO hkcheung.users(unique_id,userLoginID,encrypted_password,salt,created_at) VALUES (?,?,?,?,NOW())");
$stmt->bind_param("ssss", $uuid, $userLoginID, $encrypted_password, $salt);
$result = $stmt->execute();
$stmt->close();
if ($result) {
$stmt = $this->conn->prepare("SELECT * FROM hkcheung.users WHERE userLoginID=?");
$stmt->bind_param("s", $userLoginID);
$stmt->execute();
$result = $stmt->get_result();
$users = $result->fetch_assoc();
$stmt->close();
return $users;
} else {
return false;
}
}
add below function to your php file
function get_result( $Statement ) {
$RESULT = array();
$Statement->store_result();
for ( $i = 0; $i < $Statement->num_rows; $i++ ) {
$Metadata = $Statement->result_metadata();
$PARAMS = array();
while ( $Field = $Metadata->fetch_field() ) {
$PARAMS[] = &$RESULT[ $i ][ $Field->name ];
}
call_user_func_array( array( $Statement, 'bind_result' ), $PARAMS );
$Statement->fetch();
}
return $RESULT;
}
and at the get_result line, change it to
$result = $this->get_result($stmt);
Related
I have the following query.
$mysqldb = mysqlidb_class();
$query = "select * from post where idx < ?"
Then I bind the parameter and execute.
$bindvariable = array();
array_push($bindvariable, $post_photoidx);
array_push($bindvariable, $post_idx);
$res = $mysqldb->rawQuery($query, $bindvariable);
Then I get the following error.
Warning: mysqli_stmt::bind_param(): Number of variables doesn't match number of parameters in prepared statement
But when I change the query like below, the error disappears.
$query = "select * from post where idx = ?"
What am I doing wrong here?
Here is the class I use for the mysql query
<?php
class MysqliDb
{
......
public function rawQuery ($query, $bindParams = null, $sanitize = true)
{
$this->_query = $query;
if ($sanitize)
$this->_query = filter_var ($query, FILTER_SANITIZE_STRING,
FILTER_FLAG_NO_ENCODE_QUOTES);
$stmt = $this->_prepareQuery();
if (is_array($bindParams) === true) {
$params = array(''); // Create the empty 0 index
foreach ($bindParams as $prop => $val) {
$params[0] .= $this->_determineType($val);
array_push($params, $bindParams[$prop]);
}
call_user_func_array(array($stmt, 'bind_param'), $this->refValues($params));
}
$stmt->execute();
$this->_stmtError = $stmt->error;
$this->reset();
return $this->_dynamicBindResults($stmt);
}
......
protected function _buildQuery($numRows = null, $tableData = null)
{
$this->_buildJoin();
$this->_buildTableData ($tableData);
$this->_buildWhere();
$this->_buildGroupBy();
$this->_buildOrderBy();
$this->_buildLimit ($numRows);
$this->_lastQuery = $this->replacePlaceHolders ($this->_query, $this->_bindParams);
if ($this->isSubQuery)
return;
// Prepare query
$stmt = $this->_prepareQuery();
// Bind parameters to statement if any
if (count ($this->_bindParams) > 1)
call_user_func_array(array($stmt, 'bind_param'), $this->refValues($this->_bindParams));
return $stmt;
}
protected function _prepareQuery()
{
if (!$stmt = $this->_mysqli->prepare($this->_query)) {
trigger_error("Problem preparing query ($this->_query) " . $this->_mysqli->error, E_USER_ERROR);
}
return $stmt;
}
protected function refValues($arr)
{
//Reference is required for PHP 5.3+
if (strnatcmp(phpversion(), '5.3') >= 0) {
$refs = array();
foreach ($arr as $key => $value) {
$refs[$key] = & $arr[$key];
}
return $refs;
}
return $arr;
}
......
} // END class
You mightn't use array(2).
Instead, use
$sql = "select * from post where idx < :i";
$stmt->bindparam("i", 2);
$stmt->execute();
or use
$array = array($something,$else,$whatever);
$sql = "select * from post where idx < ?";
$stmt->bindparam("i", $array[2]);
$stmt->execute();
It looks like you are not preparing your query before biding parameters to it.
$sql = "SELECT * FROM post WHERE idx < ?";
if($stmt = $stmt->prepare($sql)) {
$stmt->bind_param('i', 2);
$stmt->execute();
}
Santize filters ruined my SQL query.
I have changed the source to the following to resolve the problem.
$mysqldb->rawQuery($query, $bindvariable, false);
i am using This code for showing user data record but this code is not work on my side
I want to echo out specific user data. I created a function where I insert multiple arguments (each argument represents a column in the database) and then echo whichever column I want with a simple line of code.
Index.php
include('function.php');
$conn = new MySQLi(localhost, root, password, database);
$user_id = $_SESSION['login_user']; // like 1
$user = user_data($conn, $user_id, 'login', 'pass', 'nikename', 'email');
if(empty($user)){
echo 'error'; // always showing this error
}else{
echo $user['nickename'];
}
Always Showing echo 'error';
function user_data($conn, $user_id){
$data = array();
$user_id = (int)$user_id;
$func_num_args = func_num_args();
$func_get_args = func_get_args();
if ($func_num_args > 1) {
unset($func_get_args[0]);
unset($func_get_args[1]);
$valid = array('login', 'pass', 'nikename', 'email');
$fields = array();
foreach($func_get_args as $arg) {
if(in_array($arg, $valid)) $fields[] = $arg;
}
$fields = '`' . implode ('`, `', $fields) . '`';
if($stmt = $conn->prepare("SELECT $fields FROM `users` WHERE `user_id` = ?")) {
$stmt->bind_param('si', $fields, $user_id);
$stmt->execute();
//here I am trying to convert the result into an array
$meta = $stmt->result_metadata();
while ($field = $meta->fetch_field()) {
$parameters[] = &$row[$field->name];
}
call_user_func_array(array($stmt, 'bind_result'), $parameters);
while ($stmt->fetch()) {
foreach($row as $key => $val) {
$x[$key] = $val;
}
$results[] = $x;
}
return $results;
$stmt->close();
}
}
}
Seeing and analyzing your code several times, I think the below will solve your issue.
Add this before your while/fetch loop
$row = array();
stmt_bind_assoc($stmt, $row);
so your code will look like this
$row = array();
stmt_bind_assoc($stmt, $row);
while ($stmt->fetch()) {
foreach($row as $key => $val) {
$x[$key] = $val;
}
$results[] = $x;
}
Also make sure you read the full documentation of bind_param on php.net here
Thanks and Best Regards
I guess, instead of
if($stmt = $conn->prepare("SELECT $fields FROM `users` WHERE `user_id` = ?")) {
$stmt->bind_param('si', $fields, $user_id);
you should go with
if($stmt = $conn->prepare("SELECT $fields FROM `users` WHERE `user_id` = ?")) {
$stmt->bind_param('i', $fields, $user_id);
Bind parameters. Types: s = string, i = integer, d = double, b = blob
As far as you have one argument with type INT you need to pass 'i' as a first parameters.
Try debugging over line by line in that function where you will get exact flaw by var_dump().
my question is how to translate get_result() to bind_result()
here is my index.php
//
$app->get('/tasks', 'authenticate', function() {
global $user_id;
$response = array();
$db = new DbHandler();
// fetching all user tasks
$result = $db->getAllUserTasks($user_id);
$response["error"] = false;
$response["tasks"] = array();
// looping through result and preparing tasks array
while ($task = $result->fetch_assoc()) {
$tmp = array();
$tmp["id"] = $task["id"];
$tmp["task"] = $task["task"];
$tmp["status"] = $task["status"];
$tmp["createdAt"] = $task["created_at"];
array_push($response["tasks"], $tmp);
}
echoRespnse(200, $response);
});
//
here is the dbhandler.php
public function getAllUserTasks($user_id) {
$stmt = $this->conn->prepare("SELECT t.* FROM tasks t, user_tasks ut WHERE t.id = ut.task_id AND ut.user_id = ?");
$stmt->bind_param("i", $user_id);
$stmt->execute();
$tasks = $stmt->get_result();
$stmt->close();
return $tasks;
}
i am having all sorts of trouble trying to convert it to use bind_result() instead of get_result(), can some please give me some advice
thank you advance
Jason
here is my approach trying to convert it without luck please point out the problem thanks
index.php
///
$app->get('/companies', 'authenticate', function() {
global $user_id;
$response = array();
$db = new DbHandler();
// fetching all user tasks
$result = $db->getAllUserCompanies($user_id);
$response["error"] = false;
$response["companies"] = array();
$companies = array();
while ($companies = $result->fetch()) {
$tmp = array();
$tmp["CompanyID"] = $companies["CompanyID"];
$tmp["UserID"] = $companies["UserID"];
$tmp["CompanyName"] = $companies["CompanyName"];
$tmp["CompanyAddress"] = $companies["CompanyAddress"];
$tmp["CompanyCity"] = $companies["CompanyCity"];
$tmp["CompanyIndustry"] = $companies["CompanyIndustry"];
$tmp["CompanyContact"] = $companies["CompanyContact"];
$tmp["CompanyNotes"] = $companies["CompanyNotes"];
$tmp["CreatedDate"] = $companies["CreatedDate"];
$tmp["UpdatedTime"] = $companies["UpdatedTime"];
$tmp["UpdatedBy"] = $companies["UpdatedBy"];
array_push($response["companies"], $tmp);
echoRespnse(200, $response);
}
});
dbhealper.php
//
public function getAllUserCompanies($user_id) {
$stmt = $this->conn->prepare("SELECT CompanyID, UserID, CompanyName, CompanyAddress, CompanyCity, CompanyIndustry, CompanyContact, CompanyNotes, CreatedDate, UpdatedTime, UpdatedBy FROM company WHERE UserID = ?");
$stmt->bind_param("i", $user_id);
//if ($stmt->execute()) {
($stmt->execute());
$companies = array();
$companies = $stmt->bind_result($CompanyID, $UserID, $CompanyName, $CompanyAddress, $CompanyCity, $CompanyIndustry, $CompanyContact, $CompanyNotes, $CreatedDate, $UpdatedTime, $UpdatedBy);
$stmt->close();
return $companies;
}
dbhealper.php //
You can try this
public function getAllUserCompanies($user_id) {
$stmt = $this->conn->prepare("SELECT CompanyID, UserID, CompanyName, CompanyAddress, CompanyCity, CompanyIndustry, CompanyContact, CompanyNotes, CreatedDate, UpdatedTime, UpdatedBy FROM company WHERE UserID = ?");
$stmt->bind_param("i", $user_id);
$stmt->execute();
/* Store the result (to get properties) */
$stmt->store_result();
/* Get the number of rows */
$num_of_rows = $stmt->num_rows;
/* Bind the result to variables */
$companies = $stmt->bind_result($CompanyID, $UserID, $CompanyName, $CompanyAddress, $CompanyCity, $CompanyIndustry, $CompanyContact, $CompanyNotes, $CreatedDate, $UpdatedTime, $UpdatedBy);
return $companies;
/* free results */
$stmt->free_result();
}
if you look there is no much changes which has been done to it but to store the results I have added a line after $stmt->execute(); $stmt->store_result();
If your getting an error with $stmt->get_result, it may be because of this:
it works only with mysqlnd driver (http://us2.php.net/manual/en/m.... Solve it by using this:
DbHandler.php
/**
* Fetching all user tasks
* #param String $user_id id of the user
*/
public function getAllUserTasks($user_id) {
$stmt = $this->conn->prepare("SELECT t.* FROM tasks t, user_tasks ut WHERE t.id = ut.task_id AND ut.user_id = ?");
$stmt->bind_param("i", $user_id);
$stmt->execute();
$stmt->bind_result($id, $task, $status, $created_at);
$tasks = array();
while($stmt->fetch()) {
$tmp = array();
$tmp["id"] = $id;
$tmp["task"] = $task;
$tmp["status"] = $status;
$tmp["createdAt"] = $created_at;
array_push($tasks, $tmp);
}
$stmt->close();
return $tasks;
}
and in index.php:
/**
* Fetching all user tasks
* #param String $user_id id of the user
*/
public function getAllUserTasks($user_id) {
$stmt = $this->conn->prepare("SELECT t.* FROM tasks t, user_tasks ut WHERE t.id = ut.task_id AND ut.user_id = ?");
$stmt->bind_param("i", $user_id);
$stmt->execute();
$stmt->bind_result($id, $task, $status, $created_at);
$tasks = array();
while($stmt->fetch()) {
$tmp = array();
$tmp["id"] = $id;
$tmp["task"] = $task;
$tmp["status"] = $status;
$tmp["createdAt"] = $created_at;
array_push($tasks, $tmp);
}
$stmt->close();
return $tasks;
}
I am guessing the code sample is from http://www.androidhive.info/2014/01/how-to-create-rest-api-for-android-app-using-php-slim-and-mysql-day-23/
I advise against using get_result() in any php code, simply because it requires mysqlnd to be installed, and is not supported in libmysql, which is the most common libary used for interfacing with mysql from php. instead, fetch() should be used to create an array of rows from the result set, or bind_result() for situations where you are only returning 1 row.
public function getAllUserTasks($user_id) {
$tasks = [];
$stmt = $this->conn->prepare("SELECT t.* FROM tasks t, user_tasks ut WHERE t.id = ut.task_id AND ut.user_id = ?");
$stmt->bind_param("i", $user_id);
$stmt->execute();
if($stmt->num_rows > 0)
{
while($row = $stmt->fetch())
{
$tasks[] = $row;
}
$stmt->close();
}
return $tasks;
}
EDIT
to use it index.php
$app->get('/companies', 'authenticate', function() {
global $user_id;
$db = new DbHandler();
// fetching all user tasks
$response = $db->getAllUserCompanies($user_id);
if(!empty($response))
{
echoRespnse(200, $response);
}else{
//handle your error
}
});
I've this function:
private function db_bind_array($stmt, &$row) {
$md = $stmt->result_metadata();
$param = array();
while($field = $md->fetch_field()) { $param[] = &$row[$field->name];}
return call_user_func_array(array($stmt, 'bind_result'), $param);
}
private function db_query($sql, $bind_param, $param) {
if($stmt = $this->conn->prepare($sql)) {
if(!$bindRet = call_user_func_array(array($stmt,'bind_param'),
array_merge(array($bind_param), $param))) $this->Terminate();
if(!$stmt->execute()) $this->Terminate();
$res = array();
if($this->db_bind_array($stmt, $res)) return array($stmt, $res);
}
}
protected function Select($recs, $table, $where, $bind_param, $param, $order_by = '', $sort = '', $limit = 1) {
if($order_by != '') $order_by = 'ORDER BY '.$order_by;
$sql = "SELECT $recs FROM $table WHERE $where $order_by $sort LIMIT $limit";
return $this->ExeSelect($sql, $bind_param, $param);
}
private function ExeSelect($sql, $bind_param, $param) {
if($res = $this->db_query($sql, $bind_param, array(&$param))) {
$stmt = $res[0]; $row = $res[1];
while($stmt->fetch()) {$this->row = $row; return $row;}
$stmt->close();
}
}
And I use it:
$row = $this->Select('id, name, title, 'Articles', where id >, 'i', 10, 'DESC', '', 10)
The problem is that it returns only one record instead of 10.
What's the problem?
Thanks
The problem is this line: while($stmt->fetch()) {$this->row = $row; return $row;}. You immediately return that result. Build an array before you return it.
private function ExeSelect($sql, $bind_param, $param) {
$ret = array();
if($res = $this->db_query($sql, $bind_param, array(&$param))) {
$stmt = $res[0]; $row = $res[1];
while($stmt->fetch()) {$ret[] = $row; }
$stmt->close();
}
return $ret;
}
I have a function i use for selecting from the database
function selectquery ($sql, $types, $params)
{
$connection = getConnect ();
$result = $connection->prepare("$sql");
$result->bind_param($types, $params);
$status = $result->execute();
$result->store_result();
$return=array('obj'=>$result, 'status' => $status, 'data'=>array());
$meta = $result->result_metadata();
while ( $field = $meta->fetch_field() )
{
$parameters[] = &$row[$field->name];
}
call_user_func_array(array($result, 'bind_result'), $parameters);
while ( $result->fetch())
{
$x = array();
foreach( $row as $key => $val )
{
$x[$key] = $val;
}
$return['data'][] = $x;
}
$result->close();
return $return;
}
When i run my query:
$resultobj=selectquery ("select id from employers where subdomain = ? ", "s", $reg_subdomain);
if ($resultobj['obj']->num_rows()>0 || in_array($reg_subdomain, $locked_subdomains)) { $error .="Subdomain already exist, please choose another <br>"; }
I get this error message:
Warning: mysqli_stmt::num_rows() [mysqli-stmt.num-rows]: Couldn't fetch mysqli_stmt in /home/drac/public_html/dracxyz.com/functions.php on line 174
Please what am i not doing right?
Thanks
Use it like
$resultobj->num_rows()
http://php.net/manual/en/mysqli-result.num-rows.php