PHPのSplFileObjectでURLを指定してCSVを読み込む

シェアする

  • このエントリーをはてなブックマークに追加
  • Evernoteに保存Evernoteに保存

URLをSplFileObjectで使うにはNoRewindIteratorクラスも一緒に使う


$url = 'http://sample.com/data.csv'; //オンライン上のCSVファイル
$file = new NoRewindIterator( new SplFileObject( $url ));
$file->setFlags( SplFileObject::READ_CSV );
foreach ( $file as $line ) {
$results[] = $line;
}
var_dump( $results );

所感

PHPでCSVファイルを読み込んで配列に入れるなど、最近は「SplFileObject::READ_CSV」を使った方が早いという情報が増えてきています。


$path_file = "./sample.csv"; //ローカル上のCSVファイル
$file = new SplFileObject( $path_file );
$file->setFlags( SplFileObject::READ_CSV );
foreach ( $file as $line ) {
    $results[] = $line;
}
var_dump( $results );

確かに早い気がするのですが、オブジェクトを生成する際の引数にURLを使うと下記のようなエラーが発生します。

Warning: SplFileObject::rewind(): stream does not support seeking in /xxxx/xxxx/get_json.php on line xx

Fatal error: Uncaught exception ‘RuntimeException’ with message ‘Cannot rewind file https://xxxx/xxxx.csv’ in /xxxx/xxxx/get_json.php:xx
Stack trace: #0 /xxxx/xxxx/get_json.php(xx):
SplFileObject->rewind() #1 {main} thrown in /xxxx/xxxx/get_json.php on line xx

しかし、公式のマニュアルには下記のようにオブジェクト作成時の引数にファイル名の代わりにURLは使えると書かれています。

ヒント
fopen wrappers が有効の場合、この関数のファイル名として URL を使用することができます。ファイル名の指定方法に関する詳細は fopen() を参照ください。 サポートするプロトコル/ラッパー には、さまざまなラッパーの機能やその使用法、 提供される定義済み変数などの情報がまとめられています。

「使える」とあるのに使えない理由は、SplFileObjectクラスは面倒な繰り返し処理をクラス化したイテレータの1つであるためです。

SplFileObjectクラスはSPL(Standard PHP Library)というPHPの標準ライブラリのうちファイル操作用のイテレータです。つまり、基本的にファイルを開き、1行ずつ処理することが前提です。そのため、rewind()というメソッドでファイルのポインタを先頭に戻しながら処理していくのですが、スキーム付きのファイル名(”http://〜”や”php://〜”や”ftp://〜)の場合はストリームとなるため(区切りがわからず)行ごとの処理ができません。つまり、このrewind()処理の時にポインタを先頭に戻せないためエラーが発生します。

そこで、rewind処理をさせないためにrewindできないNoRewindIteratorクラスにSplFileObjectクラスのインスタンスを渡して処理させます。

イテレータに関してhnwさんの記事が大変参考になったので、一読をおすすめします。

参考文献

関連記事

PHPでPOSTした結果を取得する関数:フォームの動作を模擬する... PHPのfile_get_contents関数のPOST版ユーザ関数"file_post_contents()"を作りました。 このPHPのユーザ関数で、フォームからmethodをPOSTでリクエストしたのと同じ結果が簡単に得られます。 RESTを使ったサービスを利用する際の簡易的な実装にど...
PHPからGoogleAppsのGoogle SpreadsheetsをDBとして利用する... 何度か言及しているのですが、Google SpreadsheetsをWEBサイトのデータ更新に利用すると便利です。 つまり、データをGoogleスプレッドシートに記載・管理して、PHPでそれを読み込んで表示する方法です。 Google Spreadsheetsは、オンライン版Excelのよう...
ロリポップでfile_get_contentsが使えなくなった場合の確認箇所... 現象ですが、ロリポップで、下記スクリプトを実行すると"Warning: file_get_contents() file-access is disabled"エラーが出てしまいます。 ■スクリプト
PHPのfile_get_contentsで404エラーを検知する... PHPのfile_get_contents関数を使ってURL先のコンテンツを取得する際に、取得先にファイルがない(404エラーであった)場合の処理のサンプル・コードです。URLが存在するか調べるだけであれば、HTTPヘッダーを調べる方が軽いです。

スポンサーリンク
レクタングル(大)広告

シェアする

  • このエントリーをはてなブックマークに追加
  • Evernoteに保存Evernoteに保存
スポンサーリンク
レクタングル(大)広告