diff --git a/ATXCommon/FsUtils.cs b/ATXCommon/FsUtils.cs index 67e15c6ce1f4194de0a135bd42f2ca54da44fbff..710d41e01ed253f81d6d2636681b99c02c7aa9c5 100644 --- a/ATXCommon/FsUtils.cs +++ b/ATXCommon/FsUtils.cs @@ -11,6 +11,49 @@ namespace ATXCommon { private static readonly Logger Log = LogManager.GetCurrentClassLogger(); + /// <summary> + /// Create a directory with the given name if it doesn't exist yet, otherwise + /// (optionally) create a new one using a date suffix to distinguish it from + /// the existing one. + /// </summary> + /// <param name="dirPath">The full path of the directory to be created.</param> + /// <param name="unique">Add a time-suffix to the name if the directory exists.</param> + /// <returns>The name of the (created or pre-existing) directory. This will only + /// differ from the input parameter "dirPath" if the "unique" parameter is set + /// to true (then it will give the newly generated name) or if an error occured + /// (in which case it will return an empty string).</returns> + public static string CreateNewDirectory(string dirPath, bool unique) { + try { + if (Directory.Exists(dirPath)) { + // if unique was not requested, return the name of the existing dir: + if (unique == false) + return dirPath; + + dirPath = dirPath + "_" + TimeUtils.Timestamp(); + } + Directory.CreateDirectory(dirPath); + Log.Debug("Created directory: [{0}]", dirPath); + return dirPath; + } + catch (Exception ex) { + Log.Error("Error in CreateNewDirectory({0}): {1}", dirPath, ex.Message); + } + return ""; + } + + /// <summary> + /// Helper method to check if a directory exists, trying to create it if not. + /// </summary> + /// <param name="path">The full path of the directory to check / create.</param> + /// <returns>True if existing or creation was successful, false otherwise.</returns> + public static bool CheckForDirectory(string path) { + if (string.IsNullOrWhiteSpace(path)) { + Log.Error("ERROR: CheckForDirectory() parameter must not be empty!"); + return false; + } + return FsUtils.CreateNewDirectory(path, false) == path; + } + /// <summary> /// Recursively sum up size of all files under a given path. /// </summary> @@ -111,5 +154,36 @@ namespace ATXCommon // if nothing triggered before, we pretend the dir is empty: return true; } + + /// <summary> + /// Collect individual files in the root of a given directory tree in a specific + /// sub-directory. A file name given as "ignoredName" will be skipped in the checks. + /// </summary> + /// <param name="userDir">The user directory to check for individual files.</param> + /// <param name="ignoredName">A filename that will be ignored.</param> + public static void CollectOrphanedFiles(DirectoryInfo userDir, string ignoredName) { + var fileList = userDir.GetFiles(); + var orphanedDir = Path.Combine(userDir.FullName, "orphaned"); + try { + if (fileList.Length > 1 || + (string.IsNullOrEmpty(ignoredName) && fileList.Length > 0)) { + if (Directory.Exists(orphanedDir)) { + Log.Info("Orphaned directory already exists, skipping individual files."); + return; + } + Log.Debug("Found individual files, collecting them in 'orphaned' folder."); + CreateNewDirectory(orphanedDir, false); + } + foreach (var file in fileList) { + if (file.Name.Equals(ignoredName)) + continue; + Log.Debug("Collecting orphan: [{0}]", file.Name); + file.MoveTo(Path.Combine(orphanedDir, file.Name)); + } + } + catch (Exception ex) { + Log.Error("Error collecting orphaned files: {0}\n{1}", ex.Message, ex.StackTrace); + } + } } } diff --git a/AutoTx/AutoTx.cs b/AutoTx/AutoTx.cs index 9223121e5cf0ed16361ea41475c4e7cf572551ed..c4581c15f1a049b3024e51aeee27c59cd818258f 100644 --- a/AutoTx/AutoTx.cs +++ b/AutoTx/AutoTx.cs @@ -676,45 +676,17 @@ namespace AutoTx #region filesystem tasks (check, move, ...) - /// <summary> - /// Collect individual files in a user dir in a specific sub-directory. If a marker - /// file is set in the configuration, this will be skipped in the checks. - /// </summary> - /// <param name="userDir">The user directory to check for individual files.</param> - private void CollectOrphanedFiles(DirectoryInfo userDir) { - var fileList = userDir.GetFiles(); - var orphanedDir = Path.Combine(userDir.FullName, "orphaned"); - try { - if (fileList.Length > 1 || - (string.IsNullOrEmpty(_config.MarkerFile) && fileList.Length > 0)) { - if (Directory.Exists(orphanedDir)) { - Log.Info("Orphaned directory already exists, skipping individual files."); - return; - } - Log.Debug("Found individual files, collecting them in 'orphaned' folder."); - CreateNewDirectory(orphanedDir, false); - } - foreach (var file in fileList) { - if (file.Name.Equals(_config.MarkerFile)) - continue; - Log.Debug("Collecting orphan: [{0}]", file.Name); - file.MoveTo(Path.Combine(orphanedDir, file.Name)); - } - } - catch (Exception ex) { - Log.Error("Error collecting orphaned files: {0}\n{1}", ex.Message, ex.StackTrace); - } - } - /// <summary> /// Check the incoming directory for files and directories, move them over /// to the "processing" location (a sub-directory of ManagedDirectory). /// </summary> + /// CAUTION: this method is called as a consequence of the main timer being triggered, so + /// be aware that any message dispatched here could potentially show up every second! private void MoveToManagedLocation(DirectoryInfo userDir) { string errMsg; try { // first check for individual files and collect them: - CollectOrphanedFiles(userDir); + FsUtils.CollectOrphanedFiles(userDir, _config.MarkerFile); // the default subdir inside the managed directory, where folders will be // picked up later by the actual transfer method: @@ -793,7 +765,7 @@ namespace AutoTx try { // make sure the target directory that should hold all subdirectories to // be moved is existing: - if (string.IsNullOrEmpty(CreateNewDirectory(destPath, false))) { + if (string.IsNullOrEmpty(FsUtils.CreateNewDirectory(destPath, false))) { Log.Warn("WARNING: destination path doesn't exist: {0}", destPath); return false; } @@ -828,62 +800,16 @@ namespace AutoTx return true; } - /// <summary> - /// Create a directory with the given name if it doesn't exist yet, otherwise - /// (optionally) create a new one using a date suffix to distinguish it from - /// the existing one. - /// </summary> - /// <param name="dirPath">The full path of the directory to be created.</param> - /// <param name="unique">Add a time-suffix to the name if the directory exists.</param> - /// <returns>The name of the (created or pre-existing) directory. This will only - /// differ from the input parameter "dirPath" if the "unique" parameter is set - /// to true (then it will give the newly generated name) or if an error occured - /// (in which case it will return an empty string).</returns> - private string CreateNewDirectory(string dirPath, bool unique) { - try { - if (Directory.Exists(dirPath)) { - // if unique was not requested, return the name of the existing dir: - if (unique == false) - return dirPath; - - dirPath = dirPath + "_" + TimeUtils.Timestamp(); - } - Directory.CreateDirectory(dirPath); - Log.Debug("Created directory: [{0}]", dirPath); - return dirPath; - } - catch (Exception ex) { - // TODO / FIXME: combine log and admin-email! - var msg = string.Format("Error in CreateNewDirectory({0}): {1}", dirPath, ex.Message); - Log.Error(msg); - SendAdminEmail(msg); - } - return ""; - } - - /// <summary> - /// Helper method to check if a directory exists, trying to create it if not. - /// </summary> - /// <param name="path">The full path of the directory to check / create.</param> - /// <returns>True if existing or creation was successful, false otherwise.</returns> - private bool CheckForDirectory(string path) { - if (string.IsNullOrWhiteSpace(path)) { - Log.Error("ERROR: CheckForDirectory() parameter must not be empty!"); - return false; - } - return CreateNewDirectory(path, false) == path; - } - /// <summary> /// Ensure the required spooling directories (managed/incoming) exist. /// </summary> /// <returns>True if all dirs exist or were created successfully.</returns> private bool CheckSpoolingDirectories() { - var retval = CheckForDirectory(_incomingPath); - retval &= CheckForDirectory(_managedPath); - retval &= CheckForDirectory(Path.Combine(_managedPath, "PROCESSING")); - retval &= CheckForDirectory(Path.Combine(_managedPath, "DONE")); - retval &= CheckForDirectory(Path.Combine(_managedPath, "UNMATCHED")); + var retval = FsUtils.CheckForDirectory(_incomingPath); + retval &= FsUtils.CheckForDirectory(_managedPath); + retval &= FsUtils.CheckForDirectory(Path.Combine(_managedPath, "PROCESSING")); + retval &= FsUtils.CheckForDirectory(Path.Combine(_managedPath, "DONE")); + retval &= FsUtils.CheckForDirectory(Path.Combine(_managedPath, "UNMATCHED")); return retval; } @@ -911,7 +837,7 @@ namespace AutoTx if (!_remoteUserDirs.Contains(userDir)) continue; - CreateNewDirectory(Path.Combine(_incomingPath, userDir), false); + FsUtils.CreateNewDirectory(Path.Combine(_incomingPath, userDir), false); } _lastUserDirCheck = DateTime.Now; } diff --git a/AutoTx/RoboCommand.cs b/AutoTx/RoboCommand.cs index cb9dc03010bceded7f0d9509b36feeb6827abb1c..9fa02ede1c2c4f747d0fa870ded49bc3fc96fb73 100644 --- a/AutoTx/RoboCommand.cs +++ b/AutoTx/RoboCommand.cs @@ -28,7 +28,7 @@ namespace AutoTx // the user name is expected to be the last part of the path: _status.CurrentTargetTmp = new DirectoryInfo(sourcePath).Name; - CreateNewDirectory(_status.CurrentTargetTmpFull(), false); + FsUtils.CreateNewDirectory(_status.CurrentTargetTmpFull(), false); _transferState = TxState.Active; _status.TransferInProgress = true;