WindowsのXAMPPのPHPではstrptimeは使用不可。代替はdate_parse_from_formatを使う
2024/08/10
Windowsの PHPには strptimeは未実装。代替は date_parse_from_format
Linuxで動作していたシステムのメンテナンスを行うため、Windowsに XAMPP環境を構築し、そこで動作をさせてみました。
そうしたところ、「strptime()」でエラーが出ました。
エラーメッセージは、以下の通りでした。
Fatal error: Uncaught Error: Call to undefined function strptime() in C:\xampp\htdocs\test.php:999 Stack trace: #0 {main} thrown in C:\xampp\htdocs\test.php on line 999
「『strptime』はないよぅ」という内容です。
ちなみに、「strptime()」は、与えられた文字列が、指定した日時のフォーマットに沿っているか、その日時が存在する日時か、をチェックする関数です。
日時を引数として受け取る祭に、プログラム内で使用する前に正しい日時のフォーマットであることを確認するような場面で使用します。
PHPのマニュアルに Windowsの PHPに strptimeは未実装と書いてある
https://www.php.net/manual/ja/function.strptime.php
PHPの標準的なコマンドだと思っていましたが、いろいろ調べてみた結果、マニュアルにしっかりと書かれていました。
1 |
注意: この関数は Windows 環境にはまだ実装されていません。 |
改めて、手元にある XAMPP環境で確認したところ、下記のいずれにも入っていませんでしたので、バージョンの問題でもないようです。
PHP5.6.24
PHP7.3.2
PHP8.1.4
https://www.php.net/manual/ja/function.strptime.php
また、上記のマニュアルの最初の方に下記のように書いてあります。
1 |
警告:この関数は PHP 8.1.0 で 非推奨になります。この関数に頼らないことを強く推奨します。 |
つまりは、「まだ実装されていません」の「まだ」は、「まだ」と言いつつ、非推奨になることを期待して放置したのではないか、と疑問に感じるところです。
「strptime()」と「date_parse_from_format()」の違いと実装方法
それはさておき、Windows環境の XAMPPでは「strptime()」は使えませんので、代替の関数として用意されている「date_parse_from_format()」を使うとよさそうです。
https://www.php.net/manual/ja/function.date-parse-from-format.php
ただ、「strptime()」と「date_parse_from_format()」とでは少し挙動が異なりますので、単純に「strptime」を「date_parse_from_format」に置き換えるだけ、というわけにはいかないようです。
では、詳しく確認していきましょう。
「strptime()」と「date_parse_from_format()」の違い:実装の方法
「strptime()」と「date_parse_from_format()」を使用して、年月日が正しいかどうかをチェックする処理を行います。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 |
<?php $datetime = '2024-08-03'; echo "<br>■strptime<br><pre>"; var_export(strptime($datetime, '%Y-%m-%d')); echo "</pre>"; if(strptime($datetime, '%Y-%m-%d')){ echo "true:strptime"; } else { echo "false:strptime"; } echo " <br>"; echo "<br>■date_parse_from_format<br><pre>"; var_export(date_parse_from_format('Y-m-d', $datetime)); echo "</pre>"; if(date_parse_from_format('Y-m-d', $datetime)){ echo "true:date_parse_from_format"; } else { echo "false:date_parse_from_format"; } |
「strptime()」と「date_parse_from_format()」の違い・引数の順番が違う
実装方法の 1つめの違いは、「strptime()」と「date_parse_from_format()」とで引数の、チェックする対象の変数と、日時のフォーマットの順番が逆になっています。
チェック対象の変数が、「strptime()」は第一引数なのに対し、「date_parse_from_format()」は第二引数になっています。
「strptime()」と「date_parse_from_format()」の違い・日時のフォーマットの指定形式が違う
実装方法の 2つ目の違いは、日時をチェックするためのフォーマットの指定形式が異なります。
「2024-08-03
」をチェックするにあたって、「strptime()」では「%Y-%m-%d
」と指定しますが、「date_parse_from_format()」では「Y-m-d
」となります。
各項目のフォーマットに関しては、下記の PHPのマニュアルを参照してください。
PHPマニュアル DateTimeImmutable::createFromFormat
https://www.php.net/manual/ja/datetimeimmutable.createfromformat.php
「strptime()」と「date_parse_from_format()」の違い:実行結果
「strptime()」と「date_parse_from_format()」とでは、実装方法も異なりますが、実行結果(レスポンス)も異なります。
前項のサンプルプログラムを実行した結果が下記になります。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
■strptime array ( 'tm_sec' => 0, 'tm_min' => 0, 'tm_hour' => 0, 'tm_mday' => 3, 'tm_mon' => 7, 'tm_year' => 124, 'tm_wday' => 6, 'tm_yday' => 215, 'unparsed' => '', ) true:strptime ■date_parse_from_format array ( 'year' => 2024, 'month' => 8, 'day' => 3, 'hour' => false, 'minute' => false, 'second' => false, 'fraction' => false, 'warning_count' => 0, 'warnings' => array ( ), 'error_count' => 0, 'errors' => array ( ), 'is_localtime' => false, ) true:date_parse_from_format |
年、月、日などの値が入っている配列のキー名称も異なりますが、値がない場合の結果の表記も異なります。
「strptime()」と「date_parse_from_format()」の違い・正しくない日時のレスポンスが全く違う
正しくない「2024-08-33
」を日時として与えた場合
前項では、正しい年月日が入力された場合の処理ですが、ここでは、正しくない「2024-08-33
」を日時として与えた場合の確認をしてみます。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
$datetime = '2024-08-33'; echo "<br>■strptime<br><pre>"; var_export(strptime($datetime, '%Y-%m-%d')); echo "</pre>"; if(strptime($datetime, '%Y-%m-%d')){ echo "true:strptime"; } else { echo "false:strptime"; } echo " <br>"; echo "■date_parse_from_format<br><pre>"; var_export(date_parse_from_format('Y-m-d', $datetime)); echo "</pre>"; if(date_parse_from_format('Y-m-d', $datetime)){ echo "true:date_parse_from_format"; } else { echo "false:date_parse_from_format"; } |
以下が、上記の結果となります。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 |
■strptime false false:strptime ■date_parse_from_format array ( 'year' => 2024, 'month' => 8, 'day' => 33, 'hour' => false, 'minute' => false, 'second' => false, 'fraction' => false, 'warning_count' => 1, 'warnings' => array ( 10 => 'The parsed date was invalid', ), 'error_count' => 0, 'errors' => array ( ), 'is_localtime' => false, ) true:date_parse_from_format |
上記を確認すると明らかな違いがあります。
「strptime()」では「false」を返して終了です。
ですが、「date_parse_from_format()」は情報を返してくれます。
また、「'warning_count' => 1
」「'warnings' => array(10 => 'The parsed date was invalid',)
」のように、不具合がある内容を返してくれます。
正しくない「2024-a-03
」を日時として与えた場合
次に、「2024-a-03
」を入力した場合の結果を確認します。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
array ( 'year' => 2024, 'month' => 3, 'day' => false, 'hour' => false, 'minute' => false, 'second' => false, 'fraction' => false, 'warning_count' => 0, 'warnings' => array ( ), 'error_count' => 2, 'errors' => array ( 5 => 'Unexpected data found.', 9 => 'Not enough data available to satisfy format', ), 'is_localtime' => false, ) |
「月」に「a」を入れていますので「'error_count' => 2
」となり、エラー内容が返ってきています。
ちなみに「2024-08-33
」の時のワーニングメッセージは「The parsed date was invalid」で「date」ですが、「2024-a-03
」のエラーメッセージは「Unexpected data found.」で「data」ですね。
「2024-08-33
」は日時として認識できますが、「2024-a-03
」は日時としては認識できません、ということかも知れないですね。
「strptime()」と「date_parse_from_format()」を使った日時チェックの記述方法
これまでの確認した内容から、「strptime()」と「date_parse_from_format()」を使用して、日付のフォーマットが正しいか否かをチェックする処理はそれぞれ下記のようになります。
1 2 3 4 5 6 |
// strptime を使用する場合 if(strptime($datetime, '%Y-%m-%d')){ // 正しい時の処理 } else { // 正しくない時の処理 } |
1 2 3 4 5 6 7 |
// date_parse_from_format を使用する場合 $dateParseFromFormat = date_parse_from_format('Y-m-d', $datetime); if(!$dateParseFromFormat["warning_count"] && !$dateParseFromFormat["error_count"]){ // 正しい時の処理 } else { // 正しくない時の処理 } |
「date_parse_from_format()」を使用する場合は、ワーニングとエラーの数が「0」である場合に「正しい」と判断する処理になりますね。
日時のフォーマットが正しくない場合「strptime()」では「false」になりますが、「date_parse_from_format()」ではフォーマットが正しい、正しくないに関わらずレスポンスはありますので、「date_parse_from_format()」では、レスポンスの有無で判定はできないということになります。
「strptime()」は環境によって挙動が異なる
「strptime()」についてさらなる追い討ちが!
https://www.php.net/manual/ja/function.strptime.php
「strptime()」については、マニュアルに下記のようにも書かれています。
1 |
注意:内部では、この関数はシステムの C ライブラリ関数 strptime() をコールしています。 このライブラリ関数は、OS によって挙動が異なることがあります。 |
https://qiita.com/YujiSoftware/items/1b65591efda79933fc79
上記の記事では挙動の違いを実際に試した結果を紹介してあります。
つまりは、「strptime()」は Linuxと Macで挙動が異なり、Windowsには実装されていない...ということになるわけです。
そんな関数は安心して使えないので、PHP8.1での非推奨勧告と関係なく、「date_parse_from_format()」を使う方がいいんでしょうね。
GoogleAdwords
GoogleAdwords
この記事が参考になったと思いましたらソーシャルメディアで共有していただけると嬉しいです!
関連記事
-
PHPで特定の日間の日付を for、strtotimeで表示する
ある特定の間の日付の情報を for文、strtotimeを使って作成し、その解説をしています。
-
ECCUBE mtb_constants initパラメータ設定の項目を追加する方法
ECCUBEのパラメータ設定で設定できる項目を追加する方法を説明します。
-
PHPで月末から1ヶ月後「+1 month」を算出すると想定する日付にならない場合がある
PHPでは月末の1ヶ月後が想定した日付にならない場合がある。原因はバグではなくPHPの1ヶ月後の定義によるもの。なので必要とする日付を定義しそれに合わせてDateTime、modifyを使用して算出方法を解説している。
-
PHP画面が真っ白 header(“Location: $url”);
PHPの開発で header(“Location: $url”);を使うと画面が真っ白になる不具合が出る場合もあります。
-
フォルダを指定してファイルのパーミッションを変更するプログラム
フォームからフォルダ、パーミッションを指定しパーミッションを変更するサンプルプログラムの解説です。
-
Smartyの Syntax Errorの原因はスペースかも
Smartyのなかなか原因がつかめない Syntax Errorの原因はスペースかもしれません。
-
PHPのデバッグで使う print_r、var_dump、var_exportの動作の違い
PHPのデバッグ等で変数や配列の中身を確認するために使用する関数print_r、var_dump、var_exportの動作の違い、仕様の違いについて確認した。var_exportがオススメ。
-
数値がMySQLのint(11)に保存できない!PHPの変数が本当にint型か確認!
PHPでintegerとdoubleが混在するような計算をする場合は要注意!計算結果が整数値であっても途中で使用する変数にdoubleの値が入っているときは計算結果がintegerではない場合があります。
-
ECCUBEでアップロードできない。upload_max_filesizeを設定する場所
テンプレートをアップロードする際に発生するエラー「テンプレートファイルがアップロードされていません」の対処方法。これはファイル容量の制限に引っかかっています。
-
PHPパーミッション変更のchmod関数・モードを変数で指定する方法
パーミッション変更関数であるchmod関数の第二引数、ファイルモードの指定に変数を使う場合は8進数に変換するoctdec関数を使って変換します。