Jump to content
Larry Ullman's Book Forums

sendy

Members
  • Posts

    13
  • Joined

  • Last visited

Everything posted by sendy

  1. Hi guys, i read about PDO in the book, then i read some PDO articles.. Most of the articles say that we should turn off PDO::ATTR_EMULATE_PREPARES if using MYSQL latest driver.. is this true? i searched some explanation why with recent mysql i should turn of PDO::ATTR_EMULATE_PREPARES, but unfortunately my newbie brain doesn't understand their explanation... all i know is PDO will send the query to the MYSQL when we use : $stmt = $pdo->prepare('query'); then PDO will send the data(placeholder's value) : $stmt->bindValue(':val', $value, PDO::PARAM_STR); $stmt->execute(); my mysql version : 5.x php version : 5.4 please guide me here , if possible with example codes
  2. SOLVED sorry guys my mistake actually its a pretty easy answer why MySessionHandler class doesnt produce error wihtout session_write_close() in the end of script, session_set_save_handler() by default will register session_write_close() to register_shutdown_function() so if u want to make your own shutdown function for session then use : session_set_save_handler($SessionClass, FALSE) if u do this then u must provide session_write_close() in your class destructor source : http://php.net/manual/en/function.session-set-save-handler.php thank you Larry for the support
  3. yes i have , its written in database using pdo and its even success accessing db session(using pdo) in the next browser request i added if($_SERVER['REQUEST_METHOD'] == 'POST') { $_SESSION['post_data'] = $_POST['post_data']; } <form action="session_link.php" method="post"> <input type="text" name="post_data" /> <input type="submit" name="submit" value="store data" /> </form> and confirmed that MySessionHandler() success storing the session data from $_POST method to the database
  4. im still newbie and i dont know much, but from what i know , protected static function instantiate($record) { $object = new self; foreach ($record as $attribute=>$value) { if ($object->has_attribute($attribute)){ $object->attribute = $value; } } return $object; } new self() will return the class that has define the method(even if u call Photograph::instantiate()) which is your DatabaseObject. then in that code, u try to do : $object->attribute = $value /* $object is instance of DatabaseObject because of the new self() , and because of that, it doesn't have the attribute u need.. */ its like this case : class ParentObject { protected static function getObject() { return new self(); } } class ChildObject extends ParentObject { public static function getObjectChild() { return self::getObject(); } } $obj = ChildObject::getObjectChild(); echo '<pre>' . print_r($obj) . '</pre>'; the print_r will show ParentObject, but if u change the ParentObject::getObject() to : class ParentObject { protected static function getObject() { return new static(); } } print_r will show ChildObject(); CMIIW
  5. erm i don't know if this would help or not, but try to use new static() //for static binding will return the class that call it instead of new self() // will return the class that have the method definition (if u dont override the method) note: sorry for the bad english.. correct me if im wrong
  6. SOLVED for solution see the last part of my first post _______________________________________________________________________ hi , i read chapter 3 and try to pass session_set_save_handler with an object, here's the code for my session handler class: <?php class MySessionHandler implements SessionHandlerInterface { protected $conn = NULL; public function open($savePath, $sessionName) { if(is_null($this->conn)) { $dsn = 'mysql:host=localhost;dbname=php_advanced'; $username = 'root'; $password = 'password'; try { $this->conn = new PDO($dsn, $username, $password); $this->conn->setAttribute(PDO::ATTR_ERRMODE,PDO::ERRMODE_EXCEPTION); } catch(PDOException $e) { $this->conn = NULL; die('error in open function ' . $e->getMessage()); } } return TRUE; } public function close() { echo '<p>close</p>'; $this->conn = NULL; return TRUE; } public function read($id) { echo '<p>read</p>'; $query = 'SELECT data FROM session_table WHERE session_id = :id'; try { $pdo = $this->conn->prepare($query); $pdo->bindValue(':id', $id); $pdo->execute(); // Kalo query berhasil nemuin id.. if($pdo->rowCount() == 1) { list($sessionData) = $pdo->fetch(); return $sessionData; } return FALSE; } catch(PDOException $e) { $this->conn = NULL; die('error in read function => ' . $e->getMessage()); } } public function write($id, $data) { echo '<p>write</p>'; $query = 'REPLACE INTO session_table(session_id, data) VALUES(:id, :data)'; try { $pdo = $this->conn->prepare($query); $pdo->bindValue(':id', $id); $pdo->bindValue(':data', $data); $pdo->execute(); // return the value whether its success or not return (bool)$pdo->rowCount(); } catch(PDOException $e) { $this->conn = NULL; die('error in write function => ' . $e->getMessage()); } } public function destroy($id) { echo '<p>destroy</p>'; $query = 'DELETE FROM session_table WHERE session_id = :id LIMIT 1'; try { $pdo = $this->conn->prepare($query); $pdo->bindValue(':id', $id); $pdo->execute(); $_SESSION = array(); return (bool)$pdo->rowCount(); } catch(PDOException $e) { $this->conn = NULL; die('error in destroy function => ' . $e->getMessage()); } } public function gc($maxLifeTime) { echo '<p>garbage collection</p>'; $query = 'DELETE FROM session_table WHERE DATE_ADD(last_accessed INTERVAL :time SECOND) < NOW()'; try { $pdo = $this->conn->prepare($query); $pdo->bindValue(':time', $maxLifeTime); $pdo->execute(); return TRUE; } catch(PDOException $e) { $this->conn = NULL; die('error in gc function => ' . $e->getMessage()); } } } $SessionHandler = new MySessionHandler(); session_set_save_handler($SessionHandler); session_name('my_session'); session_start(); i remove the session_write_close on purpose. This probably sounds stupid, but i want to get the session error to learn more.. here's session script(using Larry's code): <?php require('session_class.php'); ?><!doctype html> <html lang="en"> <head> <meta charset="utf-8"> <title>DB Session Test</title> <link rel="stylesheet" href="style.css"> </head> <body> <?php // Store some dummy data in the session, if no data is present: if (empty($_SESSION)) { $_SESSION['blah'] = 'umlaut'; $_SESSION['this'] = 3615684.45; $_SESSION['that'] = 'blue'; // Print a message indicating what's going on: echo '<p>Session data stored.</p>'; } else { // Print the already-stored data: echo '<p>Session Data Exists:<pre>' . print_r($_SESSION, 1) . '</pre></p>'; } // Log the user out, if applicable: if (isset($_GET['logout'])) { session_destroy(); echo '<p>Session destroyed.</p>'; } else { // Otherwise, print the "Log Out" link: echo '<a href="session_link.php?logout=true">Log Out</a>'; } // Reprint the session data: echo '<p>Session Data:<pre>' . print_r($_SESSION, 1) . '</pre></p>'; // Complete the page: echo '</body> </html>'; // Write and close the session: // session_write_close <<<<<--- I REMOVE THIS ON PURPOSE TO GET ERROR ?> but i dont get any error, then i try to use Larry's mysqli script to connect db and it produces error.. can anyone explain why if im using PDO it doesn't generate error? i'm even dont use register_shutdown_function('session_write_close'); in my session class destructor (on purpose) NOTE : I'm doing this on purpose because i want to learn more. the error im expecting is like when im using mysqli connection(connection closed by php at the end of script then session try to write and close but no connection available) : Warning: mysqli_real_escape_string() expects parameter 1 to be mysqli, null given in /var/www/ullman_advance/ch3/ullman_db.php on line 66 Warning: mysqli_real_escape_string() expects parameter 1 to be mysqli, null given in /var/www/ullman_advance/ch3/ullman_db.php on line 66 Warning: mysqli_query() expects parameter 1 to be mysqli, null given in /var/www/ullman_advance/ch3/ullman_db.php on line 67 Warning: mysqli_close() expects parameter 1 to be mysqli, null given in /var/www/ullman_advance/ch3/ullman_db.php on line 33 UPDATE i just tried to pass session_set_save_handler with function callback(using pdo as connection) and it produces error i expected, but still if using MySessionHandler class it doesn't produce any error. The codes in the MySessionHandler class is similar with my new session handler functions. here's the script <?php $conn = NULL; function open_session() { echo '<p>open session</p>'; global $conn; $_dsn = 'mysql:host=localhost;dbname=php_advanced'; $_username = 'root'; $_password = 'monyetsahur'; $conn = new PDO($_dsn, $_username, $_password); $conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); return TRUE; } function close_session() { echo '<p>close session</p>'; global $conn; $conn = NULL; return TRUE; } function read_session($sid) { echo '<p>read session</p>'; global $conn; $query = 'SELECT data FROM session_table WHERE session_id = :sid'; $pdo = $conn->prepare($query); $pdo->bindValue(':sid', $sid, PDO::PARAM_STR); $pdo->execute(); if($pdo->rowCount() == 1) { list($session_data) = $pdo->fetch(); echo '<pre>'; print_r($session_data); echo '</pre>'; return $session_data; } else { return ''; } } function write_session($sid, $data) { echo '<p>write session</p>'; global $conn; $query = 'REPLACE INTO session_table(session_id, data) VALUES(:sid, :data)'; $pdo = $conn->prepare($query); $pdo->bindValue(':sid', $sid, PDO::PARAM_STR); $pdo->bindValue(':data', $data, PDO::PARAM_STR); $pdo->execute(); return (bool)$pdo->rowCount(); } function destroy_session($sid) { echo '<p>destroy session </p>'; global $conn; $query = 'DELETE FROM session_table WHERE session_id = :sid'; $pdo = $conn->prepare($query); $pdo->bindValue(':sid', $sid, PDO::PARAM_STR); $pdo->execute(); // clean the session array; $_SESSION = array(); return TRUE } function clean_session($expire) { echo '<p>clean session</p>'; global $conn; $query = 'DELETE FROM session_table WHERE DATE_ADD(last_accessed, INTERVAL :expire SECOND) < NOW()'; $pdo = $conn->prepare($query); $pdo->bindValue(':expire', $expire, PDO::PARAM_INT); $pdo->execute(); return $pdo->rowCount(); } session_set_save_handler('open_session', 'close_session', 'read_session', 'write_session', 'destroy_session', 'clean_session'); session_name('my_session'); session_start(); SOLVED: SOLVED sorry guys my mistake actually its a pretty easy answer why MySessionHandler class doesnt produce error wihtout session_write_close() in the end of script, session_set_save_handler() by default will register session_write_close() to register_shutdown_function() so if u want to make your own shutdown function for session then use : session_set_save_handler($SessionClass, FALSE) if u do this then u must provide session_write_close() in your class destructor source : http://php.net/manual/en/function.session-set-save-handler.php thanks for the tips and your attention
  7. erm actually i did fix that by removing the addslashes() function (yes i forgot that pdo will use prepared statements) and its good without PDO::PARAM_LOB. i think varbinary(32) is right since i have tested it by registering and login using 3 different passwords.. but correct me if im wrong since im still newbie
  8. I just read about hash_hmac() function in this book, it says something about that hash_hmac() function return a string that would potentially breaks the query so i tried to use it for storing password in DB , by using PDO <?php $dsn = 'mysql:host=localhost;dbname=test'; $username = 'root'; $pass = 'password'; $conn = new PDO($dsn, $username, $pass); $conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); $conn->setAttribute(PDO::ATTR_PERSISTENT, TRUE); $password = '123MonyeTSahuR456'; $p addslashes(hash_hmac('sha256',$password,'13#slP3mK;"dA$@m',TRUE)); $query = "INSERT INTO table_one VALUES(NULL, :password)"; try { $pdo = $conn->prepare($query); $pdo->bindValue(':password', $p); if($pdo->execute()) { echo $pdo->rowCount(); } else { echo 'fail'; } } catch(PDOException $e) { echo $e->getMessage(); } **the DB details:** id INT NOT NULL AUTO INCREMENT password VARBINARY(32) NOT NULL after that i manually check my DB and found a row with BLOB(i never work/use with VARBINARY or BLOB data type before, so this is my first time) so there's 1 row exist and i try to select the row : $query = "SELECT * FROM table_one WHERE password = :password"; the value returned by pdo->rowCount() is 0 , it doesn't find the password im looking for. but when i use it without addslashes(), it works, why is this happen? **another details :** PHP version : 5.4 OS : Ubuntu 12.04 64 bit thanks EDIT: Sry my bad.. i just remember that PDO will escaped the query if using prepared statements.. btw i just tried using PDO::bindValue with PDO::PARAM_LOB and it works even with addslashes function, can anyone explain?
  9. $q = "UPDATE users SET last_login = NOW() WHERE id = $id"; $r = mysqli_query($dbc, $r) ermm i think this one: $r = mysqli_query($dbc, $r) should be replaced with : $r = mysqli_query($dbc, $q)
  10. hi guys ! i have question about output buffering(chapter 18 page 561) i have searched google about it and it came with alot of debates, some say its good practice, some say its bad practice to use it, but they dont provide any code for testing why its good and why its bad.. so the question is : is it a good practice to always use it ? as Larry's statement in the book that says "There can be a performance improvement with output buffering, but the main benefit is that it eradicates those pesky headers already sent error messages." if its bad practice, please give good reasons + codes(if neccessary) to prove why its bad
  11. ermm i dont get it about : "You can assign keys to a not yet existing array in PHP. It will then create it for you." i already tried to search google but didnt found anything , maybe it was because of wrong keywords.. do you have any link or reference about it?
  12. i think the problem lies here : $errors = array(); if(empty($email)) { $errors[] = "You forgot to enter the email"; } else { $email = mysqli_real_escape_string($conn, trim($email)); } if(empty($pass)) { $errors[] = "You forgot to enter the password"; } else { $pass = mysqli_real_escape_string($conn, trim($pass)); } because i use $errors = array(); what im thinking is like this, a bit mess up but solve the problem even tough its not the best way $errors = ''; if(empty($email)) { $errors = 'You forgot to enter the email'; } else { $email = mysqli_real_escape_string($conn, trim($email)); } if(empty($pass)) { if(!empty($errors)) //if there is a string in $errors { $tmp = $errors; $errors = array(); $errors[] = $tmp; $errors[] = 'You forgot to enter password'; } else { $errors = 'You forgot to enter password'; } } else { $pass = mysqli_real_escape_string($conn, trim($pass)); } then i use if(is_array($errors)) { foreach($errors as $error) echo $error; } else { echo $errors } i dont know any better way to do this, if anyone can give me some tips please do, i will really appreciate it
  13. Hello guys, this is my first question as well as my first post in this community Add code to the handling of the $errors variable on the login page that uses a foreach loop if $errors is an array, or just prints the value of $errors otherwise. what im thinking is using is_array() function, to test $errors : if( is_array($errors) ) then i tried to use var_dump() to test $errors (even if there is only 1 error) unfortunately its still an array. i cant figure it out, i really appreciate any help, but please dont post any code, just tell me what to do
×
×
  • Create New...