views:

165

answers:

3

I need to perform a simply query.

Literally, all I need to perform is:

SELECT price, sqft, zipcode FROM homes WHERE home_id = X

When I use PHP PDO, which I've read is the recommended way to connect to a MySQL database, simply creating the connection takes a measured 610ms.

My code is below:

try {
    $conn_str = DB . ':host=' . DB_HOST . ';dbname=' . DB_NAME;
    $dbh = new PDO($conn_str, DB_USERNAME, DB_PASSWORD);
    $params = array();    
    $sql = 'SELECT price, sqft, zipcode FROM homes WHERE home_id = :home_id';
    $params[':home_id'] = X;
    $stmt = $dbh->prepare($sql);    
    $stmt->execute($params);
    $result_set = $stmt->fetchAll(PDO::FETCH_ASSOC);
    // json output  
    ob_start("ob_gzhandler");
    header('Content-type: text/javascript; charset=utf-8');
    print "{'homes' : ";
    print json_encode( $result_set );
    print '}';
    ob_end_flush();
    $dbh = null;
} catch (PDOException $e) {
    die('Unable to connect');
}

Question: What's the fastest way for me to connect to my MySQL database to perform the query above?

+1  A: 

Fastest possible :

mysqli_connect("servername", "user", "pass") or die("can't connect");
mysqli_select_db("dbname" or die("can't select db");

list($price, $sqft, $zipcode) = mysqli_fetch_array(mysqli_query("SELECT price, sqft, zipcode FROM homes WHERE home_id = ".mysqli_real_escape_string($home_id)));

[EDIT]: Now using mysqli instead of mysql.

shamittomar
So native mysql_ library is quicker than PDO?
mysql*i* would be faster.
Coronatus
@user434493, yes. Less abstraction, faster it becomes.
shamittomar
Doesn't your code above open my up to SQL Injection? It's that one of the main benefits of using PDO, that it protect you against security attacks on your SQL query string
Also, PDO offers PREPARED STATEMENTS and mysqli_connect doesn't. Doesn't that allow PDO to be faster?
JMC
Would using a STORED PROCEDURE with MYSQLi be the fastest?
Since your servers are on different boxes, you should troubleshoot the connection before changing your code. You may not see much of an upgrade by changing to mysqli if the path is the root problem.
JMC
mysqli *is* mysql-improved.
Russell Dias
+3  A: 

If the slowness is due to having to reach over the network for each connection, and mysql having to do a reverse DNS lookup to check through its GRANTs table, then that overhead could very well account for a large chunk of the latency. Switching to persistent connections would make it a one-time cost for the life of the connection.

However, this does lead to othe problems. Since transactions are rolled back and locks released when the connection holding them is closed, going persitent means they'll stay active. Without taking great care in your code to not leave the connection in an inconsistent state, you could very well create a deadlock or at least lock out all other connections until you go in manually and clean up.

Marc B
+1 good point about the reverse DNS lookup
Rob Olmos
Useful reading about persistent connections: http://www.mysqlperformanceblog.com/2006/11/12/are-php-persistent-connections-evil/And this article about PDO: http://www.phpeveryday.com/articles/PDO-Improve-Performance-with-Persistent-Connection-P558.html
JMC
@user434493 - If you decide to go with a persistent connection to solve a network issue, staying with PDO is likely the smart move.
JMC
A: 

as of version php 5.3.0 the fastest and most lightweight way of calling into the db from php is as follows:

This example uses the mysql/ext (not mysqli) and calls stored procedures

$conn = mysql_connect("localhost", "user", "pass");
mysql_select_db("db");

$sql = sprintf("call get_user(%d)", 1);

$result = mysql_query($sql);

mysql_free_result($result);
mysql_close($conn);

The stored procedure:

delimiter #
create procedure get_user
(
in p_user_id int unsigned
)
begin
    select 
     u.user_id, u.username, u.status_id, s.name as status_name, ...
    from 
        users u
    inner join user_status s on u.status_id = s.status_id
    ...
    where 
      u.user_id = p_user_id;
end #

delimiter ;
f00