TCPDFでエラー「Unable to get the size of the image」

カテゴリー: 手順書,

TCPDFを利用したPHPプログラムでのPDF出力で不具合。サーバで直近にSSL証明書のアップデートを行っていたので原因はそれだろうと思うのですが、とりあえずいろいろと調べてみました。

症状

[Image] Unable to get the size of the image:」とエラーが表示され、PHPで外部への接続ができない。PDF上に画像ファイルを配置して出力する部分でコケているようです。いろいろ掘っていくと「SSL routines:ssl3_get_server_certificate:certificate verify failed」なんて感じのエラーがログに残ってました。

解決方法1 openssl.cafile

php.ini で「openssl.cafile」を設定するそうです。

(現在は解決しました)PHPの外部への接続でSSLのエラーが出てしまう@KUSANAGI PHP7.2 – Qiita
https://qiita.com/yousan/items/dc2cc789dcb0f07a61dc

解決方法2 getimagesize() を代替

方法1で解決するのが望ましいのですが、そうもいかない場合の暫定的な対処方法です。

TCPDFでは画像を配置する際に、画像の縦横サイズを取得して計算してくれるのですが、この getimagesize() 利用時にSSLエラーが出ます。そこで一応動きそうなコードに差し替えました。

※これは応急処置です
※動作確認したかったのですが、どういう条件で該当部分が動作するのかよくわからず未検証です

tcpdf.php

元コード 6850行目

			if (($imsize = @getimagesize($file)) === FALSE) {
				if (in_array($file, $this->imagekeys)) {
					// get existing image data
					$info = $this->getImageBuffer($file);
					$imsize = array($info['w'], $info['h']);
				} elseif (strpos($file, '__tcpdf_'.$this->file_id.'_img') === FALSE) {
					$imgdata = TCPDF_STATIC::fileGetContents($file);
				}
			}

改変後

			// (+) 2019-0903
			$my_options['ssl']['verify_peer'] = false;
			$my_img_temp = file_get_contents($file, false, stream_context_create($my_options));
			$my_img = getimagesizefromstring($my_img_temp);
			if (($imsize = $my_img) === FALSE) {
				if (in_array($file, $this->imagekeys)) {
					$imsize = array($my_img[0], $my_img[1]);
				} elseif (strpos($file, '__tcpdf_'.$this->file_id.'_img') === FALSE) {
					$imgdata = TCPDF_STATIC::fileGetContents($file);
				}
			}
			// (+) END
			// if (($imsize = @getimagesize($file)) === FALSE) {
			// 	if (in_array($file, $this->imagekeys)) {
			// 		// get existing image data
			// 		$info = $this->getImageBuffer($file);
			// 		$imsize = array($info['w'], $info['h']);
			// 	} elseif (strpos($file, '__tcpdf_'.$this->file_id.'_img') === FALSE) {
			// 		$imgdata = TCPDF_STATIC::fileGetContents($file);
			// 	}
			// }
		}

元コード 6871行目

			$imsize = @getimagesize($file);

改変後

			// (+) 2019-0903
			$my_options['ssl']['verify_peer'] = false;
			$my_img_temp = file_get_contents($file, false, stream_context_create($my_options));
			$imsize = getimagesizefromstring($my_img_temp);

			// $imsize = getimagesize($file);
			// (+) END

include/tcpdf_images.php

元コード 171行目

		$a = getimagesize($file);

改変後

			// (+) 2019-0903
			$my_options['ssl']['verify_peer'] = false;
			$my_img_temp = file_get_contents($file, false, stream_context_create($my_options));
			$a = getimagesizefromstring($my_img_temp);
		// $a = getimagesize($file);
			// (+) END

元コード 209行目

		$data = file_get_contents($file);

改変後

			// (-) 2019-0903
		// $data = file_get_contents($file);
			// (-) END
			// (+) 2019-0903
		$data = $my_img_temp;
			// (+) END

けっこう危うい

これで一応動きはしたんですけれど、予期しない動きになる可能性は高いです、責任取れませんのでよろしくおねがいいたします。方法2よりは1のほうを行うのが正しい解決方法だと思いますので、できればそちらでお試しください。

参照URL

PHP5.6でSSL通信エラー (2016/07/05) | yoo-s.com
http://yoo-s.com/topic/detail/641

php 7.1 – getimagesize() not working in PHP 7.1 – Stack Overflow
https://stackoverflow.com/questions/45260188/getimagesize-not-working-in-php-7-1

phpでhttp越しに画像サイズを取得するいくつかの方法 · kamatari
https://kamatari.github.io/2014/10/01/how-to-get-external-image-using-php/

PHP で画像ファイルを一時保存せずに縦横幅を知る | バシャログ。
http://bashalog.c-brains.jp/14/06/03-200000.php


関連記事

関連記事はまだありません

手順書」のBookmark
「手順書」記事一覧