LoginSignup
3
4

More than 5 years have passed since last update.

Imagickを使ってPDFからサムネイルを作成し、S3にアップロードする

Last updated at Posted at 2016-12-13

前置き

  • Imagick、S3ともに知識が浅いです。参考程度にお願いします。

前提

  • CentOS6.7(ローカルの開発環境なのでEC2じゃないです)
  • Imagick, フォント系モジュールはインストール済み
  • PDFの1枚目をJPEGに変換してサムネイルとしたい

始めの構想

  1. ImagickでPDFの1ページ目をJPEGに変換し、S3に直接保存
     こちらは、エラーが多発しなかなか実装できませんでした。
     エラー文を見る限り、ファイルの実体が無いとアップロードできないようにうかがえました。

  2. 表示するときだけ、JPEGにして表示する(実は試していない)

最終的な構想

ImagickでPDFの1ページ目をJPEGに変換し、自身のサーバー内に一次保存。
一次保存したファイルをS3へアップロードして、サーバー内のファイルを削除。

準備

  • Imagickのインストール
  • AWS SDK for PHPをCakePHP内のPluginディレクトリに入れておく(参照できればどこでもよし)
  • PDFで使用されるであろうFont群もダウンロードしておく( imagick pdf とかでググってると、ここら辺たくさん出てくる)

コード

HogeController.php
<?php
/**
 * HogeController
 * ほげほげするコントローラー
 **/
Class HogeController extends AppController {

  public $components = ['Amazon'];

~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

  /**
   *  資料のサムネイルを作成する
   *  @param string $fileName 元ファイルのパス
   *  @return void
   * */
  private function _createThumnail($fileName){
    $name = PREFIX_DOCUMENT.pathinfo($fileName, PATHINFO_FILENAME).".jpg"; //サムネイルのファイル名
    $thumbname = PATH_TMP_IMG_DIR.DS.$name; //サムネイルの一次保存先

    /* サムネイルの作成 */
    $thumbImg = new Imagick(); // 画像の読み込み
    $thumbImg->readImage(AWS_S3_HOSTNAME.AWS_S3_BUCKET."/xxxx/".$fileName); // 元ファイルのパス
    $thumbImg->setImageIndex(0); // 1ページ目を指定
    // $thumbImg->resizeImage(210, 180, Imagick::FILTER_POINT, 2); リサイズしたさあるけど、劣化激しい・・・
    $thumbImg->setImageFormat ("jpeg"); // jpegにする

    /* リサイズした画像を保存する */
    try {
      $thumbImg->writeImage($thumbname); // ファイルとして保存する
      $ret = $this->Amazon->putObject("xxxx/".$name, $thumbname); // S3へ保存

      if ( $ret !== "" ) {
        unlink($thumbname); // 一時ファイル削除
      }

      $thumbImg->destroy(); // imagickで作成したイメージ削除(これの必要性があまりわかってないけど、メモリ上で残るとかかな?)
    } catch (Exception $e) {
      echo $e->getMessage();
    }
  }

AmazonComponent.php
<?php
/**
 * AWS SDK for PHP
 * 
 **/
require ROOT. DS . APP_DIR . DS .'Plugin/AmazonSDK/vendor/autoload.php';
use Aws\S3\S3Client;
use Aws\Credentials\Credentials;

App::uses('Component', 'Controller');
class AmazonComponent extends Component {

  /**
   * S3へのファイルアップロード
   * @params $key string 保存先パス + ファイル名
   * @params $file string 実ファイルのパス
   * @return string 保存先
   **/
  function putObject($key, $file){
    try {
      $credentials = new Credentials(AWS_S3_KEY, AWS_S3_SECURITY);
      $aws = S3Client::factory([
        'version'    => AWS_S3_VERSION,
        'credentials' => $credentials,
        'region' => AWS_S3_REGION,
      ]);
      $result = $aws->putObject([
        'Bucket' => AWS_S3_BUCKET,
        'Key'    => $key,
        'SourceFile'   => $file,
        'StorageClass' => AWS_S3_STORAGE,
      ]);
      return $result['ObjectURL'];
    } catch (Exception $e) {
      echo $e->getMessage();
      return "";
    }
  }

  /**
   * S3のファイル削除
   * @params $file string 保存先パス + ファイル名
   * @return void
   **/
  function removeObject($file){
    try {
      $credentials = new Credentials(AWS_S3_KEY, AWS_S3_SECURITY);
      $aws = S3Client::factory([
        'version'    => AWS_S3_VERSION,
        'credentials' => $credentials,
        'region' => AWS_S3_REGION,
      ]);
      $result = $aws->deleteObject([
        'Bucket' => AWS_S3_BUCKET,
        'Key'    => $file
      ]);
    } catch (Exception $e) {
      echo $e->getMessage();
    }
  }
}


その他

ファイルサイズ制限に引っかかる

4MBくらいのサイズのPDFをアップできませんでした。
nginxやphpの設定を見てみると、アップロード制限が指定してあります。
(nginxは1MBとかですね)
その為、設定ファイルを編集し各サービスの再起動が必要です。

$ sudo vim /etc/php.ini

以下の通り書き換える。

/etc/php.ini
max_input_vars = 100000000
upload_max_filesize = 100M
post_max_size = 110M
$ sudo vim /etc/nginx/nginx.conf

以下の通り書き換える。(serverの中じゃ効かないカモです!)

/etc/nginx/nginx.conf
http {
  client_max_body_size 200000000;
  ...

nginxとphpの再起動

$ sudo service nginx -t
$ sudo service nginx -s reload
$ sudo service php-fpm restart

変更履歴

2017/01/06 追記: フォームの内容がある程度の容量を超えるとpostが出来ない

php.iniに「max_input_vars」と「post_max_size」の指定を追加しました。

/etc/php.ini
max_input_vars= 100000000
post_max_size = 110M
3
4
2

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
3
4