From cd73f7c027ebda43ab3f3e01c6ffcd58eaf3aa53 Mon Sep 17 00:00:00 2001 From: Ben Soares Date: Wed, 24 Oct 2018 13:23:27 +0100 Subject: [PATCH] JAL-3141 Code checkout. Not compiling. --- src/jalview/io/BackupFilenameFilter.java | 115 +++++++++++++++++++++++------- src/jalview/io/BackupFiles.java | 86 +++++++++++++++++++--- 2 files changed, 169 insertions(+), 32 deletions(-) diff --git a/src/jalview/io/BackupFilenameFilter.java b/src/jalview/io/BackupFilenameFilter.java index 647e250..8cf7cbf 100644 --- a/src/jalview/io/BackupFilenameFilter.java +++ b/src/jalview/io/BackupFilenameFilter.java @@ -3,7 +3,7 @@ package jalview.io; import java.io.File; import java.io.FilenameFilter; -public class BackupFileFilter implements FilenameFilter +public class BackupFilenameFilter implements FilenameFilter { public String base; @@ -14,7 +14,7 @@ public class BackupFileFilter implements FilenameFilter public String extension; - public BackupFileFilter(String base, String template, int digits, + public BackupFilenameFilter(String base, String template, int digits, String extension) { this.base = base; @@ -26,35 +26,102 @@ public class BackupFileFilter implements FilenameFilter @Override public boolean accept(File file, String filename) { + // CHECK THIS IS NOT ALWAYS THE PARENT DIR if (file.isDirectory()) { return true; } else { - int numcharstart = template.indexOf(BackupFiles.NUM_PLACEHOLDER); - String templateStart = template; - String templateEnd = ""; - if (numcharstart > -1) - { - templateStart = template.substring(0, numcharstart); - templateEnd = template.substring(numcharstart + BackupFiles.NUM_PLACEHOLDER.length()); - } - int startLength = base.length() + templateStart.length(); - int endLength = templateEnd.length() + extension.length(); - if (filename.length() == startLength + digits + endLength - && filename.startsWith(base + templateStart) - && filename.endsWith(templateEnd + extension) - && filename - .substring(startLength, - filename.length() - endLength + 1) - .matches("[0-9]+")) - { - return true; - } - + BackupFilenameParts bffp = new BackupFilenameParts(filename, base, + template, digits, extension); + return bffp.isBackupFile(); } - return false; } } + +class BackupFilenameParts +{ + File file; + + String base; + + String templateStart; + + int num; + + int digits; + + String templateEnd; + + String extension; + + boolean isBackupFile; + + public BackupFilenameParts(File file, String base, String template, int digits, + String extension) + { + this(file.getName(), base, template, digits, extension); + } + + public BackupFilenameParts(String filename, String base, String template, + int digits, String extension) + { + this.isBackupFile = false; + + if (!(filename.startsWith(base) && filename.endsWith(extension))) + { + return; + } + + int numcharstart = template.indexOf(BackupFiles.NUM_PLACEHOLDER); + String templateStart = template; + String templateEnd = ""; + if (numcharstart > -1) + { + templateStart = template.substring(0, numcharstart); + templateEnd = template.substring(numcharstart + BackupFiles.NUM_PLACEHOLDER.length()); + } + int startLength = base.length() + templateStart.length(); + int endLength = templateEnd.length() + extension.length(); + String numString = filename.substring(startLength, filename.length() - endLength + 1); + + if (filename.length() >= startLength + digits + endLength + && filename.startsWith(base + templateStart) + && filename.endsWith(templateEnd + extension) + && numString.matches("[0-9]+")) + { + this.file = file; + this.base = base; + this.templateStart = templateStart; + this.num = Integer.parseInt(numString); + this.digits = digits; + this.templateStart = templateStart; + this.templateEnd = templateEnd; + this.isBackupFile = true; + } + + } + + public static String getBackupFilename(int index, String base, + String template, + int digits, String extension) + { + String numString = String.format("%0" + digits + "d", index); + String backupSuffix = template.replaceAll(BackupFiles.NUM_PLACEHOLDER, + numString); + String backupfilename = base + backupSuffix + extension; + return backupfilename; + } + + public boolean isBackupFile() + { + return this.isBackupFile; + } + + public int indexNum() + { + return this.num; + } +} \ No newline at end of file diff --git a/src/jalview/io/BackupFiles.java b/src/jalview/io/BackupFiles.java index da5209b..39cd23e 100644 --- a/src/jalview/io/BackupFiles.java +++ b/src/jalview/io/BackupFiles.java @@ -4,6 +4,19 @@ import jalview.bin.Cache; import java.io.File; import java.io.IOException; +import java.util.Arrays; +import java.util.HashMap; +import java.util.TreeMap; + +/* + * BackupFiles used for manipulating (naming rolling/deleting) backup/version files when an alignment or project file is saved. + * User configurable options are: + * BACKUPFILES_ENABLED - boolean flag as to whether to use this mechanism or act as before, including overwriting files as saved. + * BACKUPFILES_SUFFIX - a template to insert just before the file extension. Use '%n' to be replaced by a 0-led SUFFIX_DIGITS long integer. + * BACKUPFILES_ROLL_MAX - the maximum number of backupfiles to keep for any one alignment or project file. + * BACKUPFILES_SUFFIX_DIGITS - the number of digits to insert replace %n with (e.g. BACKUPFILES_SUFFIX_DIGITS = 3 would make "001", "002", etc) + * BACKUPFILES_REVERSE_ORDER - if true then "logfile" style numbering and file rolling will occur. If false then ever-increasing version numbering will occur, but old files will still be deleted if there are more than ROLL_MAX backup files. + */ public class BackupFiles { @@ -159,13 +172,21 @@ public class BackupFiles if (reverseOrder) { // backup style numbering - for (int m = 0; m < max; m++) + + int tempMax = max; + // max == -1 means no limits + if (max == -1) { - int n = max - m; - numString = String.format("%0" + digits + "d", n); - String backupSuffix = suffix.replaceAll(NUM_PLACEHOLDER, numString); - String backupfilename = dir + File.separatorChar + basename - + backupSuffix + extension; + // do something cleverer here (possibly)! + tempMax = 10000; + } + + for (int m = 0; m < tempMax; m++) + { + int n = tempMax - m; + String backupfilename = dir + File.separatorChar + + BackupFilenameParts.getBackupFilename(n, basename, suffix, + digits, extension); File backupfile_n = new File(backupfilename); if (!backupfile_n.exists()) @@ -209,11 +230,60 @@ public class BackupFiles // reached) // find existing backup files - BackupFileFilter bff = new BackupFileFilter(basename, suffix, digits, + BackupFilenameFilter bff = new BackupFilenameFilter(basename, suffix, + digits, extension); File[] backupFiles = dirFile.listFiles(bff); - + int nextIndexNum; + if (backupFiles.length == 0) + { + nextIndexNum = 1; + } else { + + // and sort them (based on integer found in the suffix) using a + // precomputed Hashmap for speed + HashMap bfHashMap = new HashMap(); + for (int i = 0; i < backupFiles.length; i++) + { + File f = backupFiles[i]; + BackupFilenameParts bfp = new BackupFilenameParts(f, basename, suffix, digits, extension); + bfHashMap.put(bfp.indexNum(), f); + } + TreeMap bfTreeMap = new TreeMap<>(); + bfTreeMap.putAll(bfHashMap); + + bfTreeMap.values().toArray(backupFiles); + + // max value of -1 means keep all backup files + if (bfTreeMap.size() >= max && max != -1) + { + // need to delete some files to keep number of backups to designated + // max + int numToDelete = bfTreeMap.size() - max; + File[] filesToDelete = Arrays.copyOfRange(backupFiles, 0, + numToDelete - 1); + + /****************************************** + * CONFIRM THESE DELETIONS WITH THE USER! * + ******************************************/ + for (int i = 0; i < filesToDelete.length; i++) + { + File toDelete = filesToDelete[i]; + toDelete.delete(); + } + + } + + nextIndexNum = bfTreeMap.lastKey() + 1; + + // Let's make the new backup file!! yay, got there at last! + String nextBackupFilename = dir + File.separatorChar + + BackupFilenameParts.getBackupFilename(nextIndexNum, + basename, suffix, digits, extension); + File nextBackupFile = new File(nextBackupFilename); + ret = ret && file.renameTo(nextBackupFile); + } } return ret; -- 1.7.10.2