Esempio n. 1
0
        private static (FullPath path, FullPath innerPath, Stream lockFile) CreateUniqueDirectory(FullPath folderPath)
        {
            /*
             * Structure
             * - temp/<folder>/lock => allows to detect concurrency
             * - temp/<folder>/<returned_value>/
             */

            var count = 1;

            while (true)
            {
                Stream?lockFileStream = null;
                try
                {
                    var tempPath = folderPath.Value + "_";
                    while (Directory.Exists(folderPath))
                    {
                        folderPath = FullPath.FromPath(tempPath + count.ToString(CultureInfo.InvariantCulture));

                        if (count == int.MaxValue)
                        {
                            throw new InvalidOperationException("Cannot create a temporary directory");
                        }

                        count++;
                    }

                    Directory.CreateDirectory(folderPath);
                    var lockFilePath = folderPath / LockFileName;
                    lockFileStream = new FileStream(lockFilePath, FileMode.CreateNew, FileAccess.ReadWrite, FileShare.None);
                    var innerFolderPath = folderPath / DirectoryName;
                    if (Directory.Exists(innerFolderPath))
                    {
                        lockFileStream.Dispose();
                        continue;
                    }

                    Directory.CreateDirectory(innerFolderPath);

                    // Assert folder is empty
                    if (Directory.EnumerateFileSystemEntries(innerFolderPath).Any())
                    {
                        lockFileStream.Dispose();
                        continue;
                    }

                    return(folderPath, innerFolderPath, lockFileStream);
                }
                catch (IOException)
                {
                    // The folder may already in use
                }
                catch
                {
                    lockFileStream?.Dispose();
                    throw;
                }

                lockFileStream?.Dispose();
            }
        }
Esempio n. 2
0
 private TemporaryDirectory(FullPath path, FullPath innerPath, Stream lockFile)
 {
     _path     = path;
     FullPath  = innerPath;
     _lockFile = lockFile;
 }