(2018/12/21)env
関数から直接値を取得するのは避けた方がいいのでconfig経由で取得するようにしましょう
Laravel(Lumen)でLeague\Flysystemを使ってFTP接続してみます。
準備
まず**composer
**でインストール。
composer require league/flysystem
使う際は以下のようにFTP情報をAdapterに渡してFilesystemをインスタンス化してやればいいみたいです。
use League\Flysystem\Filesystem;
use League\Flysystem\Adapter\Ftp as Adapter;
$filesystem = new Filesystem(new Adapter([
'host' => 'ftp.example.com',
'username' => 'username',
'password' => 'password',
/** optional config settings */
'port' => 21,
'root' => '/path/to/root',
'passive' => true,
'ssl' => true,
'timeout' => 30,
]));
実際に実装した際のコード
「サーバーにあるファイルを取得しローカルにダウンロードする処理」の実装時のコードです。
本番とテストで使用するサーバーが異なるので直書きせず、**.env
**に接続先の情報を記述
.env
FILE_SYSTEM_HOST=
FILE_SYSTEM_USERNAME=
FILE_SYSTEM_PASSWORD=
FILE_SYSTEM_PORT=
FILE_SYSTEM_ROOT=
FILE_SYSTEM_PASSIVE=
FILE_SYSTEM_SSL=
FILE_SYSTEM_TIMEOUT=
STORAGE_DIRECTORY=
以下バッチ処理のClassです。
実行させる処理は**execute()**を想定しています。
FileOperation.php
<?php
namespace App;
use Log; // Log出さないなら不要
use League\Flysystem\Filesystem;
use League\Flysystem\Adapter\Local;
use League\Flysystem\Adapter\Ftp as Adapter;
class FileOperation
{
/**
* FTP接続情報
* @see __construct()
*/
private $ftpConnection = [];
/**
* 保存先ディレクトリパス
* @see __construct()
*/
private $storageDirectory;
/**
* ダウンロード対象ファイル名
* @see __construct()
*/
private $downloadFiles = [];
/**
* 最大試行回数
* @see __construct()
*/
private $maxTries;
/**
* Create a new controller instance.
*
* @return void
*/
public function __construct()
{
// この辺りの処理は場合によって異なるかもしれません・・・
$this->ftpConnection = [
'host' => env('FILE_SYSTEM_HOST'),
'username' => env('FILE_SYSTEM_USERNAME'),
'password' => env('FILE_SYSTEM_PASSWORD'),
'port' => env('FILE_SYSTEM_PORT'),
'root' => env('FILE_SYSTEM_ROOT'),
'ssl' => env('FILE_SYSTEM_SSL'),
'timeout' => env('FILE_SYSTEM_TIMEOUT'),
];
$this->storageDirectory = env('STORAGE_DIRECTORY');
// ダウンロードするファイル名をここに記述する
$this->downloadFiles = [
'AAA.txt',
'BBB.txt',
'CCC.txt',
];
$this->maxTries = 3;
}
/**
* ファイル操作処理を実行する
*
* @return bool
*/
public function execute()
{
if ($this->download($this->ftpConnection) === false) {
return false;
}
return true;
}
/**
* ファイルのダウンロードを行う
*
* @param array $ftpConnection FTP接続情報
* @return bool
*/
public function download(array $ftpConnection)
{
Log::info('App\FileOperation:download() start');
// エラー時、設定したトライ回数分処理を行う
for ($i = 1; $i <= $this->maxTries; $i++) {
try {
// 接続先
$remoteFilesystem = new Filesystem(new Adapter($ftpConnection));
// ローカル
$localFilesystem = new Filesystem(new Local($this->storageDirectory));
// 設定したファイル数分取得処理を行う
foreach ($this->downloadFiles as $downloadFile) {
// ファイル内容の読み込み
$content = $remoteFilesystem->read($downloadFile);
// 前回ファイルをアーカイブ
if ($localFilesystem->has($downloadFile) === true) {
$localFilesystem->rename($downloadFile, 'archive/' . $downloadFile);
}
// ローカルファイルに書き込み(ファイルがない場合は新規で作られる)
$result = $localFilesystem->write($downloadFile, $content);
Log::info('App\FileOperation:download() ' . $downloadFile . ' download processed. Result : ' . ($result === true ? 'SUCCESS' : 'FAILURE'));
}
Log::info('App\FileOperation:download() end');
return $result;
} catch (\Exception $e) {
Log::error("App\FileOperation:download() ExceptionError(Try count " . $i . "): \n" . $e);
sleep(10);
}
}
Log::error("App\FileOperation:download() Error (Max trial end.)");
return false;
}
}
一応さくらサーバーに接続してローカルにファイルをDLすることには成功しました。
(バッチ処理の作りとしてはどうなんでしょうかね・・・?いかんせん初めてなもので・・・)