This isn’t hate on PHP.
We do web hosting. Most of our customers use PHP in some capacity or another. PHP has this great set of features that made it very accessible for a wide array of applications. People using it means there are lots of applications available for it. Lots of people. Lots of applications.
This is a good thing. Users have lots of choice about what programs they want to use, and there is a lot of competition to produce high quality, very polished user-interfaces. Users like those things.
Perl and Python programmers should take note: The number of polished and high-quality open source PHP applications is positively staggering. I can only name a few Perl and Python ones off the top of my head (and btw, Bugzilla is great; this isn’t Perl hate either), but if not from anything but the sheer accessibility of PHP, there is a lot of great stuff out there.
However users of PHP applications must wear diapers and be idiots because I cannot find a single PHP application on freshmeat that lets the user enter in the PDO dsn directly, or otherwise directly control the arguments to mysql_connect().
I wanted to take a look at piwik recently and I found it’s impossible to install. I suppose it’s their fault, and I opened a bug there about it, to which they immediately closed the bug with the friendly response:
PHP Bug #34988 is somewhat symptomatic of the problem, but not the problem itself. The proposed “solution” (note the bug is marked “Bogus”) is to put something into your DSN. Edward Sapir would be so proud. Recall that piwik, like most PHP applications, doesn’t let you enter the DSN. You’re stuck with with a brain-damaged “default” to look at whatever mysql_config –socket said on the machine that compiled PHP itself.
In this case, I would be able to work around the problem by typing in my “host name” as:
except for another bug in piwik (that thankfully has been “fixed”). Oh well.
It’s not really the piwik developers fault- PHP encourages a certain approach to things, and in at least this thing, PHP is completely and fundementally wrong. Annoyingly wrong.
The developers of PHP could fix this, of course. Add another override in php.ini perhaps. Maybe a mysql_magic_localhost= option, or similar.
Another way to go would be to encourage the desired behavior. PDO should accept a “short” DSN that is registered in the php.ini file. To support run-time database selection like phpMyAdmin, allow a “long” DSN to be specified, but only if a $_COOKIE is set that contains the SHA1-hash of the long DSN (plus some secret value).
If this were the case, PHP programs wouldn’t feel the need to individually, and collectively, reinvent the database-connection-wizard over and over again in subtly broken ways. I understand it’s trying to help me: asking for my mysql server name, username, and password. I’m not interested in supplying any of these because having the PHP script know these things is itself a security risk. If the PHP script can log in, then perhaps something else can… Having the PHP script have a username and password for your database server is a security risk.
Of course, it’s much too late for that. Backwards compatibility is far more important than the “right” API calls. Especially with PHP6 creaking around the corner about to remind us hosting providers why we still need to offer a PHP4 system.
For now, we’ll have to rely on advocacy, and an otherwise absurd argument: The assumption that the user is too stupid to enter a DSN in that their system administrator gives them, but the user is capable enough to ask and enact a complex set of firewall rules, is frankly stupid, and so is, by extension, your database connection wizard.
To the PHP developers using mysql_connect: Just use the defaults. Don’t ask the user for ANYTHING unless mysql_connect() with no argument fails. Even then, encourage the user to get their php.ini file correct. You don’t need any configuration, and most of the time, it’ll just work.
PHP developers using PDO: Let the user enter a DSN. It’s fine if you want to be helpful and “pre-populate it” with hostnames usernames and passwords, but the fact is you’re perpetuating a huge security risk, and there’s just no need for it. The DSN is designed to be edited by people, not you, not the programmer. If it were just for your program, it would be an array() of some sorts.
Developers of PHP: Nobody likes you because of crap like this. There’s nothing about the defaults here that make sense. The fact that they “accidentally” work for the case of servername=localhost is the only thing that lets Debian ship you. There are a dozen other ways you could do this, including naming DSNs in the php.ini file, smarter APIs, consulting the .my.cnf file that the mysql program uses, and even letting us override defaults like this at run-time. Please stop being so disappointing all the time, you’re difficult enough to support as it is.