LoginSignup
7
1

More than 3 years have passed since last update.

あの PDO::PARAM_INT の挙動が変わった!

Last updated at Posted at 2020-03-02

(2020/3/27 追記)徳丸さんが記事書かれたので、リンクしときます!

PHP 7.2以降におけるPDO::PARAM_INTの仕様変更
さすが、検証の方法が、私のよりちゃんとしてますね^^;
float に関しての言及がないので、一応、以下は役に立つはず!

以下、元記事

あの何もしないことで有名な PDO::PARAM_INT の仕様がいつのまにか変わっていました。
が、解説記事が見当たらなかったので、検証とともに記事にしときます。
多分、アップグレードガイドにも載ってない秘密の情報ですw1

何もしない PDO::PARAM_INT とは?

PDO 使用している人には結構有名な話ですが、こいつ、ほとんど働きませんでしたw
参考記事:PDOでの数値列の扱いにはワナがいっぱい(2)

PDO::PARAM_INTはboolをintに変換(他は何もしない)

つまり、int へキャストされることを期待して
$stmt->bindValue(':test', 1.1, PDO::PARAM_INT);
なんてぶっこんでも、普通に1.1が投入されます:sweat:
サボりすぎだろw

何が変わったのか?

プリペアドステートメントのエミュレーションが ON な時、ちゃんと働くようになりました!
正しく、int へキャストされます:grinning:

本件は以下の変更で対応されたようです。
Emulated statements let value dictate parameter type

ただし、エミュレーションが OFF だと、まだサボりやがりますw

検証

以下のサンプルをいくつかのバージョンで動かしてみました。


<?php
try {
    $pdo = new PDO(
        'mysql:dbname=hoge;host=localhost;charset=utf8',
        '',
        '',
        [
            PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
            PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC,
            // PDO::ATTR_EMULATE_PREPARES => false,
            PDO::ATTR_EMULATE_PREPARES => true,
        ]
    );
    $stmt = $pdo->prepare('INSERT INTO test (php_v,test) VALUES (:php,:test)');
    $stmt->bindValue(':php', phpversion(), PDO::PARAM_STR);
    $stmt->bindValue(':test', 1.1, PDO::PARAM_INT);
    $stmt->execute();
} catch (PDOException $e) {
    exit($e->getMessage());
}
php のバージョン エミュレーション
7.1.33 OFF 1.1
7.1.33 ON 1.1
7.2.26 OFF 1.1
7.2.26 ON 1
7.3.13 OFF 1.1
7.3.13 ON 1
7.4.1 OFF 1.1
7.4.1 ON 1

影響

いくつかのトラブルを見ると、float にデータを突っ込む時にPDO::PARAM_STRを使うのを気持ち悪がって、PDO::PARAM_INTを採用したケースで被害が出ているようです。
まぁ、2択で INT を選ぶ気持ちはわかる!

これ、結構でかい問題になると思うので、バージョンアップ対応時には注意してください。


  1. Binding value as PDO::PARAM_INT has different behaviour in PHP 7.2 で、なぜかアップグレードガイドに載せることがスルーされてます:sweat_smile: 

7
1
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
1