001package org.opengion.fukurou.model;
002
003import java.io.File;
004import java.io.FileInputStream;
005import java.io.FileNotFoundException;
006import java.io.IOException;
007import java.io.InputStream;
008import java.nio.file.Files;
009import java.nio.file.Paths;
010import java.nio.file.StandardCopyOption;
011import java.util.ArrayList;
012import java.util.List;
013
014import org.opengion.fukurou.util.HybsFileFilter;
015
016/**
017 * ローカルサーバのファイル操作クラス
018 * 
019 * FileOperationFactoryでデフォルトとして設定されており、
020 * ローカルサーバでのファイル操作を行います。
021 * ※java.io.Fileと同等のファイル操作になります。
022 * 
023 * @og.group ファイル操作
024 * 
025 * @og.rev 5.10.8.0 (2019/02/01) 新規作成
026 * @author oota
027 * @sinse JDK7.0
028 */
029public class DefaultFileOperation extends AbstractFileOperation {
030        // ファイル操作用
031        private final File file;
032
033        /**
034         * コンストラクタ
035         * 
036         * 引数のパスから、java.io.Fileインスタンスを生成します。
037         * @param inPath ファイルパス
038         * 
039         */
040        public DefaultFileOperation(String inPath) {
041                file = new File(inPath);
042        }
043        
044        /**
045         * コンストラクタ
046         * 
047         * 引数のパスから、java.io.Fileインスタンスを生成します。
048         * FileOperationFactoryからの呼び出し用で、
049         * このクラスではbuketは使用しません。
050         * @param buket バケット
051         * @param inPath ファイルパス 
052         */
053        public DefaultFileOperation(String buket, String inPath) {
054                this(inPath);
055        }
056
057        /**
058         * InputStreamのデータを書き込みます。
059         * 
060         * @param is 書き込みデータのInputStream
061         * @throws IOException
062         */
063        @Override
064        public void write(final InputStream is) throws IOException {
065                // InpustStreamを対象パスに出力
066                Files.copy(is, Paths.get(file.getPath()), StandardCopyOption.REPLACE_EXISTING);
067        }
068
069        /**
070         * データを読み込み、InputStreamとして、返します。
071         * 
072         * @return 読み込みデータのInputStream
073         * @throws FileNotFoundException
074         */
075        @Override
076        public InputStream read() throws FileNotFoundException {
077                return new FileInputStream(file.getPath());
078        }
079
080        /**
081         * ファイルを削除します。
082         * 
083         * @return 成否フラグ
084         */
085        @Override
086        public boolean delete() {
087                return file.delete();
088        }
089
090        /**
091         * ファイルを指定先に、コピーします。
092         * 
093         * @param afPath コピー先
094         * @return 成否フラグ
095         */
096        @Override
097        public boolean copy(String afPath) {
098                boolean flgRtn = false;
099
100                try {
101                        // 指定パスのファイルを、指定先にコピー from;jdk7
102                        Files.copy(Paths.get(file.getPath()), Paths.get(afPath), StandardCopyOption.REPLACE_EXISTING);
103                        flgRtn = true;
104                } catch (IOException ie) {
105                        // スルーしてfalseを返す
106                }
107
108                return flgRtn;
109        }
110
111        /**
112         * ファイルを指定先に、移動します。
113         * 
114         * @param afPath 移動先
115         * @return 成否フラグ
116         */
117        @Override
118        public boolean move(String afPath) {
119                boolean flgRtn = false;
120
121                try {
122                        // 指定パスのファイルを、指定先に移動 from:jdk7
123                        Files.move(Paths.get(file.getPath()), Paths.get(afPath), StandardCopyOption.REPLACE_EXISTING);
124                        flgRtn = true;
125                } catch (IOException ie) {
126                        // スルーしてfalseを返す
127                }
128                return flgRtn;
129        }
130
131        /**
132         * 設定パスを取得します。
133         * 
134         * @return 設定パス
135         */
136        @Override
137        public String getPath() {
138                return file.getPath();
139        }
140
141        /**
142         * 絶対パスを取得します。
143         * 
144         * @return 絶対パス
145         */
146        @Override
147        public String getAbsolutePath() {
148                return file.getAbsolutePath();
149        }
150
151        /**
152         * 名称を取得します。
153         * 
154         * @return 名称
155         */
156        @Override
157        public String getName() {
158                return file.getName();
159        }
160
161        /**
162         * 親のパスを取得します。
163         * 
164         * @return 親のパス
165         */
166        @Override
167        public String getParent() {
168                return file.getParent();
169        }
170
171        /**
172         * ファイルサイズを返します
173         * 
174         * @return ファイルサイズ
175         */
176        @Override
177        public long length() {
178                return file.length();
179        }
180
181        /**
182         * 最終更新時刻を取得します。
183         * 
184         * @return 最終更新時刻
185         */
186        @Override
187        public long lastModified() {
188                return file.lastModified();
189        }
190
191        /**
192         * ファイルの場合は、trueを返します。
193         * 
194         * @return ファイルフラグ
195         */
196        @Override
197        public boolean isFile() {
198                return file.isFile();
199        }
200
201        /**
202         * ディレクトリの場合は、trueを返します。
203         * 
204         * @return ディレクトリフラグ
205         */
206        @Override
207        public boolean isDirectory() {
208                return file.isDirectory();
209        }
210
211        /**
212         * 存在する場合は、trueを返します。
213         * 
214         * @return 存在フラグ
215         */
216        @Override
217        public boolean exists() {
218                return file.exists();
219        }
220
221        /**
222         * パスのファイルとディレクトリ一覧を取得します。
223         * 
224         * @return ファイルとティレクトリ一覧
225         */
226        @Override
227        public FileOperation[] listFiles() {
228                return listFiles(new HybsFileFilter());
229        }
230
231        /**
232         * パスのファイルとディレクトリ一覧を取得して、
233         * 引数でフィルターを行います。
234         * 
235         * @param filter フィルター
236         * @return      ファイルとディレクトリ一覧
237         */
238        @Override
239        public FileOperation[] listFiles(FileOperationFileFilter filter) {
240                // 存在チェック
241                if (!exists()) {
242                        return new FileOperationInfo[0];
243                }
244
245                // カノニカルファイル取得
246                File trg = null;
247                try {
248                        trg = file.getCanonicalFile();
249                } catch (IOException ie) {
250                        return new FileOperationInfo[0];
251                }
252
253                // 直下のファイルとディレクトリ情報の取得
254                File[] files = trg.listFiles();
255
256                // 取得情報をリストに格納
257                List<FileOperationInfo> fileList = new ArrayList<FileOperationInfo>();
258                for (File file : files) {
259                        FileOperationInfo info = new FileOperationInfo();
260
261                        info.setPath(file.getPath());
262                        info.setName(file.getName());
263                        info.setParent(file.getParent());
264                        info.setLastModifiedValue(file.lastModified());
265                        info.setCanWrite(file.canWrite());
266                        info.setCanRead(file.canRead());
267                        info.setHidden(file.isHidden());
268
269                        if (file.isFile()) {
270                                // ファイル情報
271                                info.setFile(true);
272                                info.setSize(file.length());
273                        } else if (file.isDirectory()) {
274                                // ディレクトリ情報
275                                info.setDirectory(true);
276                        }
277
278                        fileList.add(info);
279                }
280
281                // フィルタ処理
282                FileOperation[] rtnArray = filter(fileList, filter);
283
284                return rtnArray;
285        }
286
287        /**
288         * ディレクトリを作成します。
289         * 
290         * ※1つのディレクトリのみ作成します。
291         * (クラウドストレージにはディレクトリの概念が無いため、
292         * 作成は行わず、trueを返します)
293         * 
294         * @return 成否フラグ
295         */
296        @Override
297        public boolean mkdir() {
298                return file.mkdir();
299        }
300
301        /**
302         * ディレクトリを作成します。
303         * 
304         * ※複数のディレクトリを作成します。
305         * (クラウドストレージにはディレクトリの概念が無いため、
306         * 作成は行わず、trueを返します)
307         * 
308         * @return 成否フラグ
309         */
310        @Override
311        public boolean mkdirs() {
312                return file.mkdirs();
313        }
314
315        /**
316         * 指定のファイル情報のファイル名に変更します。
317         * 
318         * @param dest 変更後のファイル情報
319         * @return 成否フラグ
320         */
321        @Override
322        public boolean renameTo(FileOperation dest) {
323                return file.renameTo(new File(dest.getPath()));
324        }
325
326        /**
327         * 親のディレクトリを返します。
328         * 
329         * @return 親のディレクトリ
330         */
331        @Override
332        public FileOperation getParentFile() {
333                return new DefaultFileOperation(getParent());
334        }
335
336        /**
337         * 書き込み可能フラグ
338         * 
339         * ※クラウドストレージの場合は、
340         * 必ずtrueを返します。
341         * 
342         * @return 書き込み可能フラグ
343         */
344        @Override
345        public boolean canWrite() {
346                return file.canWrite();
347        }
348
349        /**
350         * 読み取り可能フラグ
351         * 
352         * ※クラウドストレージの場合は、
353         * 必ずtrueを返します。
354         * 
355         * @return 読み取り可能フラグ
356         */
357        @Override
358        public boolean canRead() {
359                return file.canRead();
360        }
361
362        /**
363         * 隠しファイルフラグ
364         * 
365         * ※クラウドストレージの場合は、
366         * 必ずfalseを返します。
367         * 
368         * @return 隠しファイルフラグ
369         */
370        @Override
371        public boolean isHidden() {
372                return file.isHidden();
373        }
374
375        /**
376         * 新規ファイル作成
377         * 
378         * 既にファイルが存在しない場合のみ、
379         * 空のファイルを作成します。
380         *
381         * @return 成否フラグ
382         * @throws IOException
383         */
384        @Override
385        public boolean createNewFile() throws IOException {
386                return file.createNewFile();
387        }
388
389        /**
390         * 最終更新時刻の更新
391         * 
392         * 最終更新時刻の更新を行います。
393         * ※クラウドストレージの場合は、
394         * 最終更新時刻の更新を行えません。
395         * 
396         * @param time 更新する最終更新時刻
397         * @return 成否フラグ
398         */
399        @Override
400        public boolean setLastModified(long time) {
401                return file.setLastModified(time);
402        }
403
404        /**
405         * カノニカルファイル情報を取得します。
406         * 
407         * ※ローカルサーバのみ通常ファイルと、
408         * カノニカルファイルで異なります。
409         * 
410         * @return カノニカルファイル情報
411         * @throws IOException
412         */
413        @Override
414        public FileOperation getCanonicalFile() throws IOException {
415                File path = file.getCanonicalFile();
416                return new DefaultFileOperation(path.getPath());
417        }
418
419        /**
420         * toStringでは、パスを返します。
421         * 
422         * @return パス
423         */
424        @Override
425        public String toString() {
426                return getPath();
427        }
428
429        /**
430         * テスト用メソッドです
431         * 
432         * @param args
433         */
434        public static void main(String[] args) {
435                // listTest();
436                // methodTest();
437        }
438        /* テスト用
439        // リストテスト用
440        public static void listTest() {
441                String path = "";
442                FileOperation file = new DefaultFileOperation(path);
443                
444                try {
445                        // フィルタを行う場合
446                        // 以下の場合は、bで始まるファイルと、全てのディレクトリ(指定パスの直下)が取得されます。
447                        // HybsFileOperationFileFilter filter = new HybsFileOperationFileFilter();
448                        HybsFileFilter filter = new HybsFileFilter(true);
449                        filter.startsWith("b");
450                        
451                        FileOperation[] list = file.getCanonicalFile().listFiles(filter);
452                        
453                        System.out.println(list.length);
454                        for(FileOperation f: list) {
455                                System.out.println(f.getPath());
456                        }
457                }catch(Exception e) {
458                        System.out.println(e.getMessage());
459                }
460        }
461        
462        // メソッドテスト用
463        public static void methodTest() {
464                String path = "H:/tmp/test/newfile.txt";
465                FileOperation file = new DefaultFileOperation(path);
466                
467                String afPath = "H:/tmp/test/af.txt";
468                FileOperation af = new DefaultFileOperation(afPath);
469                
470                try {
471                        boolean rtn =
472                        //file.renameTo(af);
473                        file.createNewFile();
474                        //file.mkdirs();
475                        //file.getCanonicalFile().exists();
476                        System.out.println(rtn);
477                }catch(Exception e) {
478                        System.out.println(e.getMessage());
479                }
480        }
481        //*/
482}