package org.opengion.fukurou.model;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.nio.file.StandardCopyOption;

/**
 * ファイル操作のインタフェース
 *
 * ローカルサーバ、クラウドストレージ(AWS,AZURE,BLUEMIX,ORACLE)のファイル操作用です。
 * FileOperationFactoryを通して、インスタンスを生成可能です。
 * Fileクラスを継承しているため、通常のFileとしても扱えます。
 *
 * @og.group ファイル操作
 *
 * @og.rev 5.10.8.0 (2019/02/01) 新規作成
 * @og.rev 5.10.9.0 (2019/03/01) 変更対応
 * @author oota
 * @since	JDK7.0
 */
public class FileOperation extends File{
	//* このプログラムのVERSION文字列を設定します。{@VALUE} */
	private static final String VERSION = "7.2.9.4 (2020/11/20)" ;
	private static final long serialVersionUID = 729420201120L ;

	private String myplugin;
	private String mybucket;

	/**
	 * コンストラクタ
	 *
	 * 初期化処理。
	 *
	 * @param path ファイルパス
	 */
	public FileOperation(final String path) {
		super(path);
	}

	/**
	 * コンストラクタ
	 *
	 * FileOperationクラスでは、buketは使用しません。
	 *
	 * @param bucket バケット名
	 * @param path ファイルパス
	 */
	public FileOperation(final String bucket, final String path) {
		this(path);
		this.mybucket = bucket;
	}

	/**
	 * 書き込み処理
	 *
	 * InputStreamのデータを書き込みます。
	 *
	 * @param is 書き込みデータのInputStream
	 * @throws IOException ファイル関連エラー情報
	 */
	public void write(final InputStream is) throws IOException {
		// InpustStreamを対象パスに出力
		Files.copy(is, Paths.get(this.getPath()), StandardCopyOption.REPLACE_EXISTING);
	}

	/**
	 * 読み込み処理
	 *
	 * データを読み込み、InputStreamとして、返します。
	 *
	 * @return 読み込みデータのInputStream
	 * @throws FileNotFoundException ファイル非存在エラー情報
	 */
	public InputStream read() throws FileNotFoundException {
		return new FileInputStream(this.getPath());
	}

	/**
	 * コピー処理
	 *
	 * ファイルを指定先にコピーします。
	 *
	 * @param afPath コピー先
	 * @return 成否フラグ
	 */
	public boolean copy(final String afPath) {
		boolean flgRtn = false;

		try {
			// 指定パスのファイルを、指定先にコピー from;jdk7
			Files.copy(Paths.get(this.getPath()), Paths.get(afPath), StandardCopyOption.REPLACE_EXISTING);
			flgRtn = true;
		} catch (IOException ie) {
			;	// スルーしてfalseを返す
		}

		return flgRtn;
	}

	/**
	 * ファイル移動
	 *
	 * ファイルを指定先に移動します。
	 *
	 * @param afPath 移動先
	 * @return 成否フラグ
	 */
	public boolean move(final String afPath) {
		boolean flgRtn = false;

		try {
			// 指定パスのファイルを、指定先に移動 from:jdk7
			Files.move(Paths.get(this.getPath()), Paths.get(afPath), StandardCopyOption.REPLACE_EXISTING);
			flgRtn = true;
		} catch (IOException ie) {
			;	// スルーしてfalseを返す
		}
		return flgRtn;
	}

	/**
	 * 保存先のローカル判定。
	 *
	 * 判定結果を返します。
	 * trueの場合は、ローカル保存。
	 * falseの場合は、クラウドストレージに保存です。
	 *
	 * @return ローカルフラグ
	 */
	public boolean isLocal() {
		return true;
	}

	/**
	 * カノニカルファイル取得。
	 *
	 * カノニカルファイル情報を取得します。
	 *
	 * @throws IOException ファイル関連エラー情報
	 * @return カノニカルファイル情報
	 */
	@Override
	public FileOperation getCanonicalFile() throws IOException {
		final String canonPath = getCanonicalPath();
		return new FileOperation(canonPath);
	}

	/**
	 * バケット名取得。
	 *
	 * バケット名を取得します。
	 *
	 * @return バケット名
	 */
	public String getBucket() {
		return this.mybucket;
	}

	/**
	 * プラグイン名取得。
	 *
	 * プラグイン名を取得します。
	 *
	 * @return プラグイン名
	 */
	public String getPlugin() {
		return this.myplugin;
	}

	/**
	 * プラグイン名のセット。
	 *
	 * プラグイン名をセットします。
	 *
	 * @param plugin プラグイン名
	 */
	protected void setPlugin( final String plugin ) {
		myplugin = plugin;
	}

	/**
	 * このオブジェクトと他のオブジェクトが等しいかどうかを示します。
	 * インタフェース Comparable の 実装に関連して、再定義しています。
	 *
	 * @og.rev 7.2.9.4 (2020/11/20) spotbugs:スーパークラスの equals メソッドをオーバーライドしていないクラス
	 *
	 * @param   object 比較対象の参照オブジェクト
	 *
	 * @return	引数に指定されたオブジェクトとこのオブジェクトが等しい場合は true、そうでない場合は false
	 */
	@Override
	public boolean equals( final Object object ) {
		return object instanceof File && super.equals( object );	// myplugin とmybucket は無視して、Fileとして比較します。
	}

	/**
	 * オブジェクトのハッシュコード値を返します。
	 * このメソッドは、java.io.File のハッシュ値を返すことで、equals メソッドとの整合性を取っています。
	 *
	 * @og.rev 7.2.9.4 (2020/11/20) spotbugs:equals メソッドは定義していますが hashCode メソッドは定義していないクラス
	 *
	 * @return  このオブジェクトのハッシュコード値
	 */
	@Override
	public int hashCode() {
		return super.hashCode() ;
	}

//	/** テスト用メソッドです。*/
//	public static void main(String[] args) {
//		System.out.println("start");
//
//		try {
//			test01();
//		}catch(IOException ie) {
//			System.out.println(ie);
//		}
//
//		System.out.println("end");
//	}
//
//	public static void test01() throws IOException{
//		File file = new FileOperation("test.txt");
//		File file2 = file.getCanonicalFile();
//
//		System.out.println(file2.getClass());
//
//		FileOperation fo = (FileOperation)file2;
//		System.out.println(fo.getPath());
//	}
//
//	public static void writeTest() {
//		File file = new FileOperation("test.txt");
//		FileOperation fileOperation = (FileOperation) file;
////		FileOperation_AWS aws = (FileOperation_AWS)file;
//		//		file.delete();
//
//		try( ByteArrayInputStream bais = new ByteArrayInputStream("テスト".getBytes())) {
//			fileOperation.write(bais);
//		} catch (IOException ie) {
//			System.out.println(ie);
//		}
//	}
}