There are parts of my app where a persistent connection is required, in particular the parts where every hour maybe 30,000 select requests are made by many different users, this is causing my mysql server to max out on the 100 connection limit, and i really don't want to increase it since 100 connections already seems like alot. So for the parts of the application where reading and selecting is the case I want to switch to persistent connections.
The other parts where data is being modified is usually done through a transaction, and the general rule is never to use persistent connections for transactions according to the php documentation. So I would like to keep this on non-persistent connections.
My question is, am i able to use persistent and non-persistent connections together in the same app, the same script etc?
I am using PHP 5.2+, MySQL 5+ (InnoDB tables) and the Zend Framework 10.6+
No, you cannot use persistent and non-persistent connections together in the same script.
And I doubt you really need persistent connection at all.
Related
I know that PHP automatically closes open MySQL connections at the end of the script, and the only viable way to open a persistent connection is to use the appropriate PHP function; many questions have been asked and answered.
What I would like to know is the benefit - or the inconvenient - of keeping a temporary connection instead of a persistent connection
EDIT :
A persistent connection for each PHP user session.
For instance, statements such as the following:
session_start();
$connection = new mysqli($host, $user, $pass, $db);
$_SESSION['connection'] = $connection;
might set up a reference to a mysqli object useful for performing multiple queries across navigation in the website within the same session by the same user.
If the connection is supposed to be used soon after its activation, would not be the right choice to leave it just open for further queries? Maybe this approach would generate an inconvenient situation (and possible security risks) when multiple users are HTTP-requesting pages from a web site which keeps MySQL connections alive?
I would like to know more. Thank you.
There's overhead to connecting to MySQL or any database, although it isn't typically large. This overhead can be greater when the MySQL service is running on a different server, or depending on the authentication method and init commands needed.
More, MySQL connections may have associated caches. So reusing a connection may be able to reuse these caches.
But saving a resource in the session doesn't work. Session data is serialized, and stored in e.g. a file between requests. That's why the persistent connect methods have to be used.
The reason is that the connection is ultimately a resource, or a socket connection on an internal class, and this can't be "saved" without special handling. Try it, and you'll see that you get an error (with PDO and mysqli.)
mysqli::query(): Couldn't fetch mysqli
I don't think there's any way to get session-specific connection reuse without writing an extension to implement it. Theoretically it's possible, though, and you could theoretically implement a method to pull a connection from the pool by session id.
There are a lot of potential drawbacks and risks to persistent db connections, though:
If your application creates TEMPORARY TABLEs, those tables will still exist on the next run, since it's the same MySQL session.
If you set any variables (SET SESSION or etc.), they will be retained.
Depending on how transactions are handled, it's theoretically possible a persistent connection may have an in-progress transaction.
If the application issues any LOCK commands or uses user-locks, the locks could be held between requests and unknowingly held in new requests.
On a multi-tenant (shared) webserver, the risk of another process somehow obtaining database access it shouldn't have is higher.
This may leave large numbers of connections open for long periods of time, increasing resource usage on the database server.
You still have to expect that the connection might be lost between requests.
On my website, when an user opens his profile or any other page, (almost all pages use data from mysql), my website makes around 50 connections to mysql in loading the page. This is the case on my development server, running elementary OS.
When I came to know about persistent connections in mysql, I was puzzled. If I am to run this website on a VPS (with low RAM in starting), and considering the overhead produced by a large number of mysql connections, will using persistent connections improve my website's performance?
Currently, I start and end a connection in every function. Is there a better way to connect to mysql?
And, taking into account that if 100 users are using my website simultaneously, what will be the performance if each page makes around 50-60 connections?
You asked so I will answer. You are doing this incorrectly. You should start the processing on each page request (each externally-accessible .php file) by using a common function to establish a single database connection, then you should reuse that connection.
You are getting away with this because you're probably using an automatic connection pool built in to your php database-access library, and because you have not yet scaled up your application.
You won't be able to scale this up very far using this multiconnection strategy because it will perform very badly indeed when you add users.
There are lots of examples of working open-source php-based web app systems you can look at. WordPress is an example. You'll find that most of them start by opening a database connection and storing its handle in a global variable.
You asked:
According to CBroe's comment, I changed my strategy. Actually, I am
using multiple database connections, but the functions are same (don't
ask why lol). So if I open connections on start, and then pass the
handler to the function, will that be an improvement?
Yes, that will be fine. You need to avoid churning connections to get best performance.
If you need connections to more than one different database, you can open them all. But it sounds like you need to hit just one database.
PHP doesn't have significant overhead when passing a handler to a function, so don't worry about that.
As explained wonderfully by Ollie Jones, I opened the connection on start, and my connections dropped from 50-60 per page to 1 per page. Although I don't see any change in performance on my local development server, this will surely we a great improvement when its on a live server. There is no need for me to use persistent connections yet.
I'm implementing an application that will have a lot of clients querying lots of small data packages from my webserver. Now I'm unsure whether to use persistent data connections to the database or not. The database is currently on the same system as the webserver and could connect via the socket, but this may change in the near future.
As I know a few releases of PHP ago mysqli_pconnect was removed because it behaved suboptimally. In the meantime it seems to be back again.
Based on my scenario I suppose I won't have an other chance to handle thousands of queries per minute but with loads of persistent connections and a MySQL configuration that reserves only little resources per connection, right?
Thanks for your input!
What happened when you tested it?
With the nest will in the world, there's no practical way you can convey all the informaton required for people to provide a definitive answer in a SO response. However usually there is very little overhead in establishing a mysql connection, particularly if it resides on the same system as the database client (in this case the webserver). There's even less overhead if you use a filesystem rather than a network socket.
So I'd suggest abstracting all your database calls so you can easily switch between connection types, but write your system to use on-demand connections, and ensure you code explicitly releases the connection as soon as practical - then see how it behaves.
C.
Are PHP persistant connections evil?
The problem is there can be only so
many connections active between Host
“Apache” and Host “MySQL”
Persistant connections usually give problems in that you hit the maximum number of connections. Also, in your case it does not give a great benefit since your database server is on the same host. Keep it to normal connections for now.
As they say, your mileage may vary, but I've never had good experiences using persistent connections from PHP, including MySQL and Oracle (both ODBC and OCI8). Every time I've tested it, the system fails to reuse connections. With high load, I end up hitting the top limit while I have hundreds of idle connections.
So my advice is that you actually try it and find out whether your set-up is reusing connections properly. If it isn't working as expected, it won't be a big lose anyway: opening a MySQL connection is not particularly costly compared to other DBMS.
Also, don't forget to reset all relevant settings when appropriate (whatever session value you change, it'll be waiting for you next time to stablish a connection and happen to reuse that one).
When querying the db is it plausible to feel extremely paranoid? I go as far as opening and closing mysql connection every time a new query has to be done. I am afraid that (especially with the ajax enabled pages) this would cause great performance downgrading.
Should I continue in this method or at least open and close connections once in everypage (instead of per-query)? (i'm writing in php btw)
thank you.
Yes, the overhead of connecting every time will be considerable. I suggest you just close it when you're done, it's very unlikely that simply having an open connection without running queries on it will open you to vulnerabilities.
I'd recommend a connection pool if it's possible with PHP. It's a way to simultaneously maximize performance and minimize connection time.
You should not close MySQL connections immediately. It's better to use a single connection for the entire PHP script. PHP will automatically close the connection if you don't explicitly.
Opening a new connection incurs some small time penalty, particularly if MySQL lives on another server on the network. New TCP connections require a three-way handshake, and each TCP connection consumes kernel resources for at least two minutes.
Although PHP doesn't support full-fledged connection pooling, the procedural MySQL API does support persistent connections. See mysql_pconnect() for more details. At my office we use pconnect to avoid crashing the TCP stacks on our high-traffic PHP site.
Consider PHP Data Objects, which can keep a persistent connection for you. You really only connect with credentials once and then cache the connection. Create the connection with something along these lines:
$dbh = new PDO('mysql:host=HOSTNAME;dbname=DBNAME',
'USER', 'PASSWORD',
array(PDO::ATTR_PERSISTENT => true));
For more information, see this page in the php manual.
Can't speak for PHP, but when I write this kind of thing in Apache/Perl I generally do two things to boost performance:
a) allow MySQL handles to stay open as long as the Apache daemon does.
b) keep cached statement handles around (using an LRU cache).
On production servers, some of those MySQL handles have been around for days, serving many thousands of quite complicated SQL queries. It isn't a problem.
I had never heard of persistent connections before, and I don't understand the advantages.
I run a PHP/MySQL based website, it receives tens of thousands of page views per day. In my header file on each of these pages I have just used mysql_connect() and I haven't bothered with terminating the connection in the footer file.
In my case are there any advantages of using mysql_pconnect()?
Using a persistent connection leaves the connection open after the script has finished executing. Opening and closing connections over and over causes overhead, while small, that will eventually mount up as the number of requests go up.
However, if you read the manual page for mysql_pconnect it states:
If PHP and MySQL are on the same server or local network, the connection time may be negligible, in which case there is no advantage to persistent connections.
If this is the case it may not be worth the trouble changing your code.
You can find more detailed information on persistent connections at the same site as above.
Check out this URL:
http://us3.php.net/manual/en/function.mysql-pconnect.php
Basically mysql_pconnect() tries to find a persistent connection already open with the credentials that you've specified. If it doesn't find one it makes a new one. It also doesn't close the connection after a statement is executed
So really in your case you may not notice a difference but in reality you should probably be using mysql_pconnect().