001/*
002 * Copyright (c) 2009 The openGion Project.
003 *
004 * Licensed under the Apache License, Version 2.0 (the "License");
005 * you may not use this file except in compliance with the License.
006 * You may obtain a copy of the License at
007 *
008 *     http://www.apache.org/licenses/LICENSE-2.0
009 *
010 * Unless required by applicable law or agreed to in writing, software
011 * distributed under the License is distributed on an "AS IS" BASIS,
012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
013 * either express or implied. See the License for the specific language
014 * governing permissions and limitations under the License.
015 */
016package org.opengion.hayabusa.io;
017
018import java.io.File;
019import java.util.function.Supplier;                                                                     // 8.0.0.2 (2021/10/15)
020
021import org.opengion.fukurou.model.FileOperation;
022import org.opengion.fukurou.model.FileOperationFactory;
023import org.opengion.fukurou.util.StringUtil;
024import org.opengion.fukurou.util.FileUtil;                                                      // 8.0.0.2 (2021/10/15)
025import org.opengion.hayabusa.common.HybsSystem;
026// import org.opengion.fukurou.system.HybsConst;                                        // 5.10.9.0 (2019/03/01)
027
028/**
029 * クラウドを含むファイル操作クラスの生成
030 *
031 * システムリソース参照のみで、クラウドクラスを生成します。(8.0.0.1 (2021/10/08)で固定)
032 * 引数付きの場合は、直接、org.opengion.fukurou.model.FileOperationFactory をご利用ください。
033 *
034 * 直接fukurouをCallしてもよいのですが、hayabusaからの呼び出しではシステムリソースを参照する必要があるため
035 * ラッパー的にこのクラスを経由してCallする事でシステムリソースが使われるようにしておきます。
036 * (タグ以外からも呼び出されるため、commonTagSupportではなく専用クラスをioパッケージに作成しています)
037 *
038 * ※ plugin → storage に変更。
039 *
040 * ローカルのファイルを扱いたい場合は、storageかbucketにLOCALを指定してください。
041 *
042 * @og.rev 5.10.8.0 (2019/02/01) 新規作成
043 * @og.rev 8.0.0.1 (2021/10/08) 修正対応
044 * @og.group
045 *
046 * @version 5.0
047 * @author Takahashi Masakazu
048 * @since JDK7.0
049 */
050public final class HybsFileOperationFactory {
051        private static String STORAGE = HybsSystem.sys("CLOUD_TARGET");
052        private static String BUCKET  = HybsSystem.sys("CLOUD_BUCKET");
053        private static String LOCAL   = "LOCAL" ;
054
055        /**
056         * コンストラクタはprivate化しておきます。
057         */
058        private HybsFileOperationFactory(){
059                // コンストラクタ
060        }
061
062        /**
063         * fukurouのFileOperationFactoryを呼び出してFileOperationを取得します。
064         * storage,bucketを指定しない場合はシステムリソースを利用します。
065         *
066         * @og.rev 8.0.1.0 (2021/10/29) useLocal 属性を追加
067         *
068         * @param useLocal 強制的にローカルファイルを使用する場合、true にセットします。
069         * @param path ファイルパス
070         * @return FileOperationインスタンス
071         */
072        public static FileOperation create( final boolean useLocal,final String path ) {
073                final String bucket = useLocal ? LOCAL : BUCKET ;
074
075                return FileOperationFactory.newStorageOperation( STORAGE,bucket,path );
076        }
077
078        /**
079         * ディレクトリとファイル名を指定用です。
080         *
081         * @og.rev 8.0.1.0 (2021/10/29) useLocal 属性を追加
082         *
083         * @param useLocal 強制的にローカルファイルを使用する場合、true にセットします。
084         * @param dir ディレクトリパス
085         * @param fileName ファイル名
086         * @return FileOperationインスタンス
087         */
088        public static FileOperation create( final boolean useLocal,final String dir, final String fileName ) {
089                final String bucket = useLocal ? LOCAL : BUCKET ;
090                return FileOperationFactory.newStorageOperation( STORAGE,bucket,dir,fileName );         // 連結方法を統一します。
091        }
092
093        /**
094         * FileOperation(ディレクトリ)とファイル名を指定用です。
095         *
096         * @og.rev 8.0.1.0 (2021/10/29) useLocal 属性を追加
097         *
098         * @param useLocal 強制的にローカルファイルを使用する場合、true にセットします。
099         * @param dir ファイル(ディレクトリパス取得)
100         * @param fileName ファイル名
101         * @return FileOperationインスタンス
102         */
103        public static FileOperation create( final boolean useLocal,final File dir, final String fileName ) {
104                return create( useLocal,new File( dir,fileName ).getPath() );
105        }
106
107        /**
108         * fukurouのFileOperationFactoryを呼び出してFileOperationを取得します。
109         * storage,bucketを指定しない場合はシステムリソースを利用します。
110         *
111         * @param storage ストレージ(AWS など)
112         * @param bucket バケット名
113         * @param path ファイルパス
114         * @return FileOperationインスタンス
115         */
116        public static FileOperation create(final String storage, final String bucket, final String path) {
117                return FileOperationFactory.newStorageOperation(
118                                StringUtil.nval(storage, STORAGE), StringUtil.nval(bucket, BUCKET), path );
119        }
120
121        /**
122         * FileOperation(ディレクトリ)とファイル名を指定用です。
123         *
124         * @param storage ストレージ(AWS など)
125         * @param bucket バケット名
126         * @param dir ファイル(ディレクトリパス取得)
127         * @param filename ファイル名
128         * @return FileOperationインスタンス
129         */
130        public static FileOperation create(final String storage, final String bucket, final File dir, final String filename) {
131                return create(storage, bucket, new File( dir,filename ).getPath() );
132        }
133
134        /**
135         * ディレクトリとファイル名を指定用です。
136         *
137         * @param storage ストレージ(AWS など)
138         * @param bucket バケット名
139         * @param dir ディレクトリパス
140         * @param filename ファイル名
141         * @return FileOperationインスタンス
142         */
143        public static FileOperation create(final String storage, final String bucket, final String dir, final String filename) {
144                return create(storage, bucket, new File( dir,filename ).getPath() );
145        }
146
147        /**
148         * システム定数で、クラウド設定されているかどうか
149         *
150         * システム定数の、CLOUD_TARGET か、CLOUD_BUCKET のどちらかが、
151         * null(ゼロ文字列、タブ、空白のみ)の場合、false です。
152         * それ以外は、true を返しますが、正常にクラウドにアクセス出来る保証はありません。
153         * あくまで、リソース設定がされているかどうかのみで、判定しています。
154         *
155         * @og.rev 8.0.0.1 (2021/10/08) クラウド修正
156         *
157         * @return クラウド設定されていれば true
158         */
159        public static boolean useCloud() {
160                return ! StringUtil.isNull( STORAGE,BUCKET );   // どれか一つでも null なら、false
161        }
162
163        /**
164         * ローカルファイルをクラウドに移動<del>後、ローカルファイルを削除</del>します。
165         *
166         * クラウド設定されている場合、指定のサプライヤを実行してローカルファイルを取得し、
167         * クラウドにコピー後、ローカルファイルを削除します。
168         * クラウド設定されていなければ、何もしません。
169         *
170         * @og.rev 8.0.0.2 (2021/10/15) ローカルファイルとクラウドファイル間の移動
171         * @og.rev 8.0.1.0 (2021/10/29) useLocal 属性を追加、ファイル削除は行わない。
172         *
173         * @param useLocal 強制的にローカルファイルを使用する場合、true にセットします。
174         * @param supp ローカルファイルを生成するサプライヤ
175         */
176        public static void local2cloud( final boolean useLocal,final Supplier<File> supp ) {
177                if( !useLocal && useCloud() ) {
178                        final File localFile = supp.get();
179                        final FileOperation cloudFile = create( false,localFile.getPath() );
180                        FileUtil.copy( localFile, cloudFile );
181        //              localFile.delete();
182                }
183        }
184
185        /**
186         * クラウドファイルをローカルに移動<del>後、クラウドファイルを</del>削除します。
187         *
188         * クラウド設定されている場合、指定のサプライヤを実行してローカルファイルを取得し、
189         * まず、ローカルファイルを削除後、ローカルファイルの親フォルダを作成して、
190         * クラウドファイルをローカルに移動後、クラウドファイルを削除します。
191         * クラウド設定されていなければ、何もしません。
192         *
193         * @og.rev 8.0.0.2 (2021/10/15) ローカルファイルとクラウドファイル間の移動
194         * @og.rev 8.0.1.0 (2021/10/29) useLocal 属性を追加、ファイル削除は行わない。
195         *
196         * @param useLocal 強制的にローカルファイルを使用する場合、true にセットします。
197         * @param supp ローカルファイルを生成するサプライヤ
198         */
199        public static void cloud2local( final boolean useLocal,final Supplier<File> supp ) {
200                if( !useLocal && useCloud() ) {
201                        final File localFile = supp.get();
202                        final FileOperation cloudFile = create( false,localFile.getPath() );
203
204                        localFile.delete();
205                        final File localParent = localFile.getParentFile();
206                        if( localParent != null ) { localParent.mkdirs(); }
207
208                        FileUtil.copy( cloudFile, localFile );
209        //              cloudFile.delete();
210                }
211        }
212
213        /**
214         * #create(String,String,String)を呼び出してFileOperationを取得します。
215         * storage,bucketを指定しない場合はシステムリソースを利用します。
216         *
217         * 引数をディレクトリとして処理します。
218         * ローカルフォルダの場合、ディレクトリの作成、ディレクトリかどうかのチェック、書き込みチェックを行います。
219         *
220         * @og.rev 8.0.0.2 (2021/10/15) ローカルファイルとクラウドファイル間の移動
221         *
222         * @param storage ストレージ(AWS など)
223         * @param bucket バケット名
224         * @param dir ディレクトリパス
225         * @return FileOperationインスタンス
226         * @throws IllegalArgumentException 引数のディレクトリが作成できない、ディレクトリでない、書き込めない場合
227         * @see #create(String,String,String)
228         */
229        public static FileOperation createDir(final String storage, final String bucket, final String dir) {
230                final FileOperation cloudDir = create( storage,bucket,dir );
231
232                if( !useCloud() ) {
233                        // セーブディレクトリ 作成
234                        if( ! cloudDir.exists() && ! cloudDir.mkdirs() ) {
235                                throw new IllegalArgumentException( "Not make directory: " + dir );
236                        }
237
238                        // Check saveDirectory is truly a directory
239                        if(!cloudDir.isDirectory()) {
240                                throw new IllegalArgumentException("Not a directory: " + dir);
241                        }
242
243                        // Check saveDirectory is writable
244                        if(!cloudDir.canWrite()) {
245                                throw new IllegalArgumentException("Not writable: " + dir);
246                        }
247                }
248
249                return cloudDir ;
250        }
251}