delight-im / PHP-Auth

Authentication for PHP. Simple, lightweight and secure.
MIT License
1.09k stars 234 forks source link

Compatibility note for stacks without mysqlnd #18

Closed rgvy closed 7 years ago

rgvy commented 7 years ago

Hello

I don't know much about DevOps or how common mysqlnd is in LAMP stacks, but Bluehost currently doesn't provide it out-of-the-box. The other PDO MySQL connector doesn't typecast (instead treating everything as a string) which causes a bug on if ($userData['verified'] === 1) { and if ($userData['verified'] !== 1) { in Auth.php lines 587 and 682.

Obviously the preferred solution is for users to configure the server with mysqlnd, but I just thought I'd mention this...

ocram commented 7 years ago

Thanks!

You're right in that we should either support the old MySQL driver as well, or, mention that we require the newer driver as a hard dependency. Right now, we're doing neither.

In order to find out what we should do, does the discussion in https://github.com/delight-im/PHP-Auth/issues/7 change your personal opinion on this topic in any way?

What stack does one get on Bluehost, exactly? Are they providing an old PHP version? Is there any way to upgrade the MySQL driver?

Requiring the newer MySQL driver sounds reasonable at first, and making the code work with the old driver seems to be pointless when reading about the good driver support in PHP's documentation. But if that looks quite different in practice and lots of platforms don't have the new driver or it's hard for users to find out how to set it up, maybe we have to adapt to reality.

What do you think?

rgvy commented 7 years ago

I see I am not the first one with this issue...

Perhaps setting PDO::ATTR_STRINGIFY_FETCHES to false would solve the problem? If so, that might be the easiest way to offer support for the old driver... I have not tested this, but assume thats what the other user from issue #7 was trying.

Bluehost supports PHP 5.2 and 5.4 and is offering 7.0 in beta. Their support team did not indicate how to install mysqlnd, but did mention they are implementing it. However, they are slow with this stuff... I have found instructions somewhere on installing PHP 7 with mysqlnd on Bluehost from before those were offered. But those instructions were non-trivial for developers without much experience in DevOps such as myself.

Personally, I use the latest MAMP for dev and plan on using Digital Ocean for production. I just happen to have access to a Bluehost box for testing.

My workaround was simply to modify Auth.php to change strict comparison ===, !== to weak comparison ==, !=. This a very quick and temporary measure to allow my colleagues to perform some quick testing.

ocram commented 7 years ago

Perhaps setting PDO::ATTR_STRINGIFY_FETCHES to false would solve the problem?

No, unfortunately, the old MySQL driver just returns everything as a string and does not provide you any way to change this. We would therefore have to change large parts of the code, e.g. because we couldn't use === when comparing cells from the database against numbers or booleans, because with the old driver, everything is a string. I would rather not do this if everybody could just upgrade to the new driver easily.

I see I am not the first one with this issue...

Definitely not! That's why I said that the easy choice of the new driver is perhaps just theory and we have to adjust to reality. Maybe!

Bluehost supports PHP 5.2 and 5.4 and is offering 7.0 in beta. Their support team did not indicate how to install mysqlnd, but did mention they are implementing it. However, they are slow with this stuff...

That explains it all, I think. I'm not even sure how that works, since 5.2 and 5.4 have long been obsolete and do not get any security updates! You shouldn't really use those versions anymore. Now "beta" support is not perfect, either. But 5.6 is still fine, for the moment. You can absolutely get everything working on 5.6 in a secure way. And then there's more than 1.5 years left for upgrading to 7.x.

There are even quite a lot of "Platform as a Service" (PaaS) providers, which are perfect if you don't want to set up your own server. Just to name a few:

Some have special requirements and limitations, though, e.g. a read-only filesystem on Heroku, as far as I remember, i.e. you can't create local files (permanently) from your PHP application.

Personally, I use the latest MAMP for dev and plan on using Digital Ocean for production.

Good choices! However, Digital Ocean requires a bit more knowledge than a typical PaaS provider. On the other hand, there's less of a lock-in. If you're fine with some basic setup and configuration, it's great!

I just happen to have access to a Bluehost box for testing.

Well, as long as it's just for testing ... If you can upgrade to 5.6 there, it will probably be fine, though.

Anyway, this library should work fine in your MAMP environment then, shouldn't it?

My workaround was simply to modify Auth.php to change strict comparison ===, !== to weak comparison ==, !=. This a very quick and temporary measure to allow my colleagues to perform some quick testing.

Not entirely sure whether this is really sufficient in all cases, but as a temporary solution for testing, why not :) Yet some kind of parity between development and testing (and production later, of course) is quite useful, and makes testing more effective.

Do you modify Auth.php in the vendor directory then? If so, that will break whenever you update via Composer, right? The other solution is probably installing everything manually, but that's probably much more work.

rgvy commented 7 years ago

There are even quite a lot of "Platform as a Service" (PaaS) providers, which are perfect if you don't want to set up your own server.

That's a great list, Thanks! I'll check them out.

Anyway, this library should work fine in your MAMP environment then, shouldn't it?

Perfectly :)

However, Digital Ocean requires a bit more knowledge than a typical PaaS provider

Thanks for the warning!

Do you modify Auth.php in the vendor directory then? If so, that will break whenever you update via Composer, right?

I don't use composer (too difficult with MAMP). I simply edited the Auth.php on Bluehost. That took 1 minute whereas other solutions might take 30-60. If I deploy to that server less than 30 times, it's time saved. (and maybe they'll fix it sooner than later).

ocram commented 7 years ago

Composer is really the one thing I'd recommend to look into for making PHP development much more efficient, either now or some time in the future. It's really easy to use, actually, and should work on OS X or macOS as well, if that's your platform.

As for the mysqlnd requirement, I think we don't need to add this to the README for now, since this issue here has shown again that some other configuration was the reason for the problems. It was the PHP version, which was below the mentioned requirement of 5.6, that caused the problems. For everyone using 5.6+, everything should work fine. And since mysqlnd is the default then, it is an implicit requirement that doesn't need to be mentioned explicitly. We don't list all the other possible deviations from the default configuration that can cause problems, either :)

Anyway, thanks for bringing this up again so that we could discuss this in its own thread. As you said, and as history has shown, you won't be the last one having trouble with mysqlnd ;)

ocram commented 7 years ago

In order to make this library work with SQLite (as an alternative database engine, apart from MySQL), the two specific lines mentioned here had to be fixed with an explicit typecast, anyway: https://github.com/delight-im/PHP-Auth/commit/ee485f99ab242002233c8669bd0f5507a4eff82b

Thus, at least the enforcement of the hard dependency on the mysqlnd driver in code could be removed again, for now: https://github.com/delight-im/PHP-Auth/commit/47afa1c411db2b50a80931b76ba65782884fc934

That means there's no need anymore to make any manual changes to this library if you want to use it with the old MySQL Client Library (libmysqlclient) instead of the new MySQL Native Driver (mysqlnd). But this may just be temporary. The dependency on mysqlnd is still documented and there may be new issues in the future that prevent this library from working with the old driver.