2016-06-22

FlysystemをLaravelで使う

開発サイトの規模が大きくなってきたり、よりセキュアなサーバー環境を整えるためにサーバーを「ウェブサーバー」と「データサーバー」で物理的に分割する場合があると思います。

そして、PHPでファイルをリモートで読み込み/書き込みをするためには「Flysystem」という有名なパッケージを利用すればとても簡単にできるのですが、今回はこの「Flysystem」をLaravel(5.2)で使う方法をお届けしたいと思います。

※ちなみに今回はSFTPを使ってリモートサーバーとの連携をしますが、Flysystemは他にもaws」や「Azure」、その他には「DropBox」との連携までサポートしています。


【環境】

Laravel 5.2
SFTPで自分のVPSへSFTPを使って接続

【インストール】

まずは composer でパッケージのインストールです。
ここではLaravelと統合されているものをインストールします。
(ちなみにGitHubはこちら)
composer require graham-campbell/flysystem
次に私の場合はSFTPでの接続ですので、Flysystemのサブパッケージをインストールします。
league/flysystem-sftp:^1.0
はい。これでインストールは完了です。


【準備】

いつものように ServiceProvider と aliases を config/app.php に設置しましょう。

(ServiceProvider)
 GrahamCampbell\Flysystem\FlysystemServiceProvider::class  


(Aliases)
 'Flysystem' => GrahamCampbell\Flysystem\Facades\Flysystem::class  


そして、以下のコマンドで専用の設定ファイルを publish します。
php artisan vendor:publish
実行すると、configフォルダの中に「flysystem.php」というファイルが作成されていると思いますのでこの中で接続情報を保存します。

※もしコマンドを実行しても flysystem.php が作成されない場合は、以下のコマンドを実行してからもう一度トライしてみてください。
  • composer dumpautoload -o
  • php artisan config:cache

では、実際の中身です。

今回はSFTPでの接続なので「SFTP」のエリアを探して、必要な情報を入力すればOKです。
変更する場所としては、

  • host(IPアドレスなど)
  • port(変えている場合)
  • username
  • password
  • privateKey(プライベート・キーファイルのパス)
  • root(リモートサーバーの保存したいフォルダパス)

あたりになるかと思います。

はい、これで設定は完了です。


【使い方】

(基本的な使い方)

使い方はとても直感的でシンプルです。
次の例は、「test.txt」というファイルを作り、さらにそこに「bar」という文字列を書き込む手準になります。

 \Flysystem::connection('sftp')->put('test.txt', 'bar');  

たったこれだけです。
では逆にその保存した内容を読み込んでみましょう。

 echo \Flysystem::connection('sftp')->read('test.txt');  

これで「bar」が表示されます。


(フォルダを指定して保存)

もし、フォルダを指定して保存したい場合はこのようになります。

 \Flysystem::connection('sftp')->put('test_dir/test.txt', 'bar');  

この場合は、test_dir/test.txt にファイルが保存されます。


(画像を保存)

これもテキストファイルなどとやり方はほぼ同じで、

 $content = file_get_contents(public_path('images/my_photo.jpg'));  
 \Flysystem::connection('sftp')->put('me.jpg', $content); 

とやればOK。
とてもシンプルです。

ちなみに、Laravelを使って保存した画像をサーバーから呼び出して表示するには以下のようにすればいいでしょう。

(コントローラ)
 public function flysystem_image() {  
      $image_contents = \Flysystem::connection('sftp')->read('me.jpg');  
      return response($image_contents, 200)->header('Content-Type', 'image/jpeg');  
 }  

以上、Laravel と Flysystem を使ったサーバーの連携方法でした。
ではでは!



2016-06-09

受信したメールをLaravelで受け取る

受信メールをPHPプログラムへ送り、メールを解析して送信元のメールアドレスや本文を取得してDBに保存ということをLaravel(5.2)をからめてやるにはどうすればいいかをメールサーバーをたてるところからやってみたので備忘録としてお届けします。
(はっきり言って作業内容は多かったです、、^^;)




【作業環境】

CentOS 6.7


【作業の手順】
  1. Postfix をインストール/設定
  2. ドメインのDNS設定
  3. Pecl(Pear)本体をインストール
  4. Pecl の mailparse をインストール、extensionの読み込み
  5. Laravelパッケージ「php-mime-mail-parser」をインストール
  6. LaravelにCommandを追加

【実際の作業】

では、ここからは実際の作業になりますが、全部書くと確実に長くなってしまいますので途中は参考にしたサイトを紹介しながらすすめていきます。

1. Postfix をインストール/設定

私の場合はCentOSなので
sudo yum install postfix
でインストールしましたが、環境によって変更してください。
また、設定の方法は以下のページがとてもわかりやすいと思いますのでぜひ参考にしてみてください。


また、この記事の中にも紹介されていますが、設定が完了したら以下のサイトでセキュアチェックができます。


そして「/etc/aliases」をエディタで開き、以下のような振り分け設定を追加しましょう。

mail: "| /usr/bin/php /path/to/your/public/folder/example.com/artisan mail:parse"

意味としては

  • mail・・・はユーザー名。つまり、mail@example.comでメール受信した場合の設定ですよという意味です。
  • /usr/bin/php(以下略)・・・PHPを使ってLaravelのartisanを実行
  • mail:parse・・・実行するコマンド(「6.LaravelにCommandを追加」で作る独自コマンドです)

完了したら、 sudo postalias /etc/aliases でエイリアスをアップデートします。
そして、最後に sudo service postfix reload でpostfixをリロードで完了です。


2.ドメインのDNS設定

これも人によって記述が違うと思いますが私の設定は以下のようにしています。
mx mail.example.com. 10
a * 01.234.567.890
txt @ v=spf1 a:example.com ~all
2行目はIPアドレスです。
※ちなみにこれはサーバー設定ではなく、取得したドメインの管理サイトで設定をします。


3.Pecl(Pear)本体をインストール
sudo yum install php-pear
ここは戸惑いました。
Peclをインストールするにはpearをインストールするんですね。
(その昔、mecabをインストールしたことあるのに...)

なお、リポジトリを設定しないとパッケージが見つからないかもしれません。


4. Pecl の mailparse をインストール、extensionの読み込み
pecl install mailparse
でメール解析に必要な mailparse をインストールします。
ただ、もしかすると
The php-devel package is required for use of this command.
というエラーがでてインストールできないかもしれません。
そのときはエラーの表示にある php-devel をインストールしてからやってみてください。

では、インストールした mailparse を PHPが利用できるように設定をしましょう。
ファイルを作成する場所は php.ini の「Additional .ini files parsed」でリストに出てくるフォルダです。



たとえば、もし「/etc/php5/apache2/conf.d/05-opcache.ini」が表示されているとするなら「/etc/php5/apache2/conf.d」がそのフォルダになります。

ではここに mailparse.ini というファイルを作成し、以下の内容を保存します。
php extension=mailparse.so
はい。
これでmailparseの設定は完了です。
ウェブサーバーを再起動してもう一度 phpinfo を確認すると以下のようにmailparse が表示されているはずです。



5.Laravelパッケージ「php-mime-mail-parser」をインストール

これはとても簡単です。
composer で一気にインストールできます。
composer require php-mime-mail-parser/php-mime-mail-parser
ちなみに、パッケージがあるなら mailparse は要らないんじゃ?と思った方。
私もそうでした。
でも、実際は mailparse を前提にしたパッケージなのでやはり Pecl他は必要なんです。^^;

※GitHubのページはこちらです。


6.LaravelにCommandを追加

やっとここまで来ました。
コマンドの作成/設定方法は本家Laravelページで確認してください。

コマンドの中身は以下のようになります。
$parser = new Parser();
$parser->setStream(fopen('php://stdin', 'r'));
あとは、以下のような便利なメソッドが備わっているのでこれを使ってメールを思うように加工してください。
$to = $parser->getHeader('to'); // 送信先
$addressesTo = $parser->getAddresses('to'); // 送信先(配列)
$from = $parser->getHeader('from'); // 送信元
$addressesFrom = $parser->getAddresses('from'); // 送信元(配列)
$subject = $parser->getHeader('subject');  // 件名

$text = $parser->getMessageBody('text');   // 本文(テキスト)
$html = $parser->getMessageBody('html');   // 本文(HTML
$htmlEmbedded = $parser->getMessageBody('htmlEmbedded');   // データを含む本文(HTML
添付ファイル

添付ファイルの扱い方は以下になります。

(保存)
$parser->saveAttachments('/path/to/save/attachments/');

(ループ)
$attachments = $parser->getAttachments();
if (count($attachments) > 0) {
   foreach ($attachments as $attachment) {
      $filename = $attachment->getFilename();
      $path = '/path/to/save/attachments/'. $attachment->getFilename();
      $type = $attachment->getContentType();
   }
}

ということで、環境の違いもあるので全てを一気にやろうと思うとなかなか難しいかもしれませんがこんな感じで受信メールをLaravelで受け取ることができます。

お疲れ様でした。

【その他参考にしたページ】

https://sboersma.nl/blog/setting-up-postfix-and-pipe-incoming-emails-to-laravel