Beispiel #1
0
        public void SplitAPathIntoNamesListOneName()
        {
            var pathSplitter = new PathSplitter();
            var result       = pathSplitter.SplitPath("/cam");

            Assert.Equal(new string[] { "cam" }, result);
        }
Beispiel #2
0
        public void ToStringTest()
        {
            var pathItem    = PathSplitter.SplitPath(ExpectedPath);
            var pathItemStr = pathItem.ToString();

            Assert.AreEqual(ExpectedPath, pathItemStr);
        }
Beispiel #3
0
        public void SplitAPathIntoNamesListNoNames()
        {
            var pathSplitter = new PathSplitter();
            var result       = pathSplitter.SplitPath("/");

            Assert.Equal(new string[0], result);
        }
Beispiel #4
0
        public void SplitAPathIntoNamesListTwoNames()
        {
            var pathSplitter = new PathSplitter();
            var result       = pathSplitter.SplitPath("/cam/jordan");

            Assert.Equal(new string[] { "cam", "jordan" }, result);
        }
Beispiel #5
0
        public void GetPathItemFromTest1()
        {
            var pathItem         = PathSplitter.SplitPath(ExpectedPath);
            var act              = pathItem.GetPathItemFrom("root");
            var expectedPathItem = PathSplitter.SplitPath("/dir/subdir");

            Assert.AreEqual(expectedPathItem, act);
        }
Beispiel #6
0
        public void GetLastTest()
        {
            var pathItem = PathSplitter.SplitPath(ExpectedPath);
            var expected = "subdir";
            var act      = pathItem.GetLast();

            Assert.AreEqual(expected, act);
        }
Beispiel #7
0
        public void PopTest()
        {
            var    pathItem = PathSplitter.SplitPath(ExpectedPath);
            string act      = pathItem.Pop();
            var    expected = "subdir";

            Assert.AreEqual(expected, act);
        }
Beispiel #8
0
        public void ToArrayTest()
        {
            var pathItem      = PathSplitter.SplitPath(ExpectedPath);
            var expectedArray = new string[] { "root", "dir", "subdir" };
            var actArray      = pathItem.ToArray();

            CollectionAssert.AreEqual(expectedArray, actArray);
        }
        public static (PathItem parent, string fileName) GetFilenameAndParent(this string fullPath)
        {
            var pathItem = PathSplitter.SplitPath(fullPath);
            var fileName = pathItem.GetLast();
            var parent   = new PathItem(pathItem.ToArray(1));

            return(parent, fileName);
        }
Beispiel #10
0
        public void CreateFile(string fileName, string parent, string inFilePath)
        {
            if (!File.Exists(inFilePath))
            {
                return;
            }

            var pId = GetDirectoryId(PathSplitter.SplitPath(parent));

            if (jsonStructureManager.ExistedFile(pId, fileName))
            {
                return;
            }

            var mimeType = MimeType.MimeTypeMap.GetMimeType(inFilePath);

            using (var stream = new FileStream(inFilePath, FileMode.Open, FileAccess.Read, FileShare.Read))
            {
                string hash = string.Empty;
                if (jsonStructureManager.IsCheckHash)
                {
                    hash = Crypto.Sha256.GetSha256(stream);
                }

                if (stream.Length > fManager.SplitSize)
                {
                    var(nextId, parentId) = ResolveTermParameters(fileName, parent);
                    var start = fManager.Write(stream, (writeStream) => {
                        while (true)
                        {
                            byte[] bs    = new byte[fManager.SplitSize];
                            int readSize = stream.Read(bs, 0, bs.Length);
                            if (readSize == 0)
                            {
                                break;
                            }
                            writeStream.Write(bs, 0, readSize);
                        }
                    }, LEN);
                    jsonStructureManager.CreateFile(nextId, parentId, fileName, start, hash, new Dictionary <string, string> {
                        { "MimeType", mimeType }
                    });
                }
                else
                {
                    var data = ByteLoader.FromFile(stream);
                    if (data != null)
                    {
                        CreateFile(fileName, parent, data, mimeType, hash);
                    }
                }
            }
        }
Beispiel #11
0
        public void WriteToDir(string filePath, string outFilePath)
        {
            var(parent, fileName) = filePath.GetFilenameAndParent();
            int rootId = GetDirectoryId(parent);

            if (jsonStructureManager.ExistedDirectory(rootId, fileName))
            {
                var dirId = GetDirectoryId(PathSplitter.SplitPath(filePath));
                var dirs  = jsonStructureManager.GetDirectoryAllStructuresFromParent(dirId);
                var files = jsonStructureManager.GetFileAllStructuresFromParent(dirId);

                if (!Directory.Exists(outFilePath))
                {
                    Directory.CreateDirectory(outFilePath);
                }

                //Array.Sort(dirs);
                foreach (var dir in dirs)
                {
                    string path;
                    var    pathItem = PathSplitter.SplitPath(GetDirectoryPath(jsonStructureManager, dir.Id));
                    if (filePath.Equals("/"))
                    {
                        path = outFilePath + pathItem.ToString();
                    }
                    else
                    {
                        path = outFilePath + pathItem.GetPathItemFrom(filePath).ToString();
                    }
                    if (!Directory.Exists(path))
                    {
                        Directory.CreateDirectory(path);
                    }
                }

                foreach (var item in files.Select((value, index) => new { index, value }))
                {
                    string path;
                    var    pathItem = PathSplitter.SplitPath(GetFilePath(jsonStructureManager, item.value.Id));
                    if (filePath.Equals("/"))
                    {
                        path = outFilePath + pathItem.ToString();
                    }
                    else
                    {
                        path = outFilePath + pathItem.GetPathItemFrom(filePath).ToString();
                    }

                    var isOk = WriteToFile(item.value, path);
                    WriteToFilesProgress?.Invoke(this, new ReadWriteProgressEventArgs(item.index + 1, files.Length, item.value.Name, isOk));
                }
            }
        }
Beispiel #12
0
        public void AddPathTest()
        {
            var pathItem = new PathItem();

            pathItem.AddPath("root");
            pathItem.AddPath("dir");
            pathItem.AddPath("subdir");

            var expectPathItem = PathSplitter.SplitPath(ExpectedPath);

            var expected = "/root/dir/subdir";
            var act      = pathItem.ToString();

            Assert.AreEqual(expected, act);
            Assert.AreEqual(expectPathItem, pathItem);
        }
Beispiel #13
0
        public void GetPathTest()
        {
            var    pathItem = PathSplitter.SplitPath(ExpectedPath);
            var    act1     = pathItem.GetPath(0);
            var    act2     = pathItem.GetPath(1);
            var    act3     = pathItem.GetPath(2);
            var    act4     = pathItem.GetPath(3);
            var    exp1     = "root";
            var    exp2     = "dir";
            var    exp3     = "subdir";
            string exp4     = null;

            Assert.AreEqual(exp1, act1);
            Assert.AreEqual(exp2, act2);
            Assert.AreEqual(exp3, act3);
            Assert.AreEqual(exp4, act4);
        }
Beispiel #14
0
        /// <summary>
        /// Mounts a new file system.
        /// </summary>
        /// <param name="source">The source of the filesystem. This is usually a device name, but can also be another directory.</param>
        /// <param name="target">The path including the name of the mount point, where to mount the new filesystem.</param>
        public static void Mount(string source, string target)
        {
            // Retrieve the parent directory of the mount
            DirectoryEntry parent = PathResolver.Resolve(rootNode, ref target, PathResolutionFlags.RetrieveParent);

            if (parent == null)
            {
                throw new System.ArgumentException();
            }

            IFileSystem root = FileSystemFactory.CreateFileSystem(source);

            if (root == null)
            {
                throw new System.ArgumentException();
            }

            PathSplitter path = new PathSplitter(target);

            DirectoryEntry.Allocate(parent, path.Last, root.Root);
        }
        protected (int nextId, int parentId) ResolveTermParameters(string fileName, string parent)
        {
            var pathItem  = PathSplitter.SplitPath(parent);
            var fileArray = jsonStructureManager.GetFileStructures();
            int dirCount  = jsonStructureManager.NextFileId;           //fileArray.Length > 0 ? fileArray[fileArray.Length - 1].Id + 1 : 1;

            int parentRootId = GetDirectoryId(pathItem);
            var dirs         = jsonStructureManager.GetFileStructureFromParent(parentRootId, fileName);

            //var dirs = sqlite.GetValues(TABLE_FILES, "Parent = {0} and Name = '{1}'".FormatString(parentRootId, fileName));
            if (dirs != null)
            {
                throw new FileExistedException("Existed {0} on {1}".FormatString(fileName, parent));
            }
            if (parentRootId < 0)
            {
                throw new DirectoryNotFoundException("Not found {0}".FormatString(parent));
            }

            return(dirCount, parentRootId);
        }
Beispiel #16
0
        /// <summary>
        /// Performs an iterative lookup of the given path starting from the root and obeying to the specified flags.
        /// </summary>
        /// <param name="path">The path to lookup. This can be a relative or absolute path. Path.DirectorySeparatorChar or Path.AltDirectorySeparatorChar are valid delimiters.</param>
        /// <param name="flags">The lookup flags, which control the lookup process.</param>
        /// <returns>The directory entry of the resolved path.</returns>
        /// <exception cref="System.Security.SecurityException">The caller does not have access to the path or a component. For example the caller does not have the right to traverse the path.</exception>
        /// <exception cref="System.IO.PathTooLongException">The path is too long to traverse. This can be the result of circular symbolic links in the path.</exception>
        /// <exception cref="System.IO.FileNotFoundException">The path or a component was not found. This exception can be prevented by specifying PathResolutionFlags.DoNotThrowNotFoundException.</exception>
        /// <exception cref="System.IO.DirectoryNotFoundException">A path component was not found. This exception can be prevented by specifying PathResolutionFlags.DoNotThrowNotFoundException.</exception>
        /// <remarks>
        /// This call may result in other exceptions not specified in the above list. Other exceptions can be thrown by IVfsNode implementations, which are visited during the traversal
        /// process. For example a network file system node may throw an exception, if the server is unreachable.
        /// </remarks>
        private DirectoryEntry Resolve(ref string path, PathResolutionFlags flags)
        {
            // DirectoryNode entry found by stepping through the path
            DirectoryEntry entry = null;

            // Split the given path to its components
            PathSplitter dirs = new PathSplitter(path);

            // Determine the number of path components
            int max = dirs.Length;

            // Current path component
            string item;
            // Loop index
            int index = 0;
            // Perform an access check on the root directory
            AccessCheck.Perform(currentDirectory, AccessMode.Traverse, AccessCheckFlags.None);

            // Do not resolve the last name, if we want the parent directory.
            if (PathResolutionFlags.RetrieveParent == (flags & PathResolutionFlags.RetrieveParent)) {
                path = dirs[dirs.Length - 1];
                max--;
            }

            // Check if this is an absolute path?
            if (dirs[0].Length == 0) {
                // Yes, replace the current directory
                currentDirectory = rootDirectory;
                index++;
            }

            // Iterate over the remaining path components
            while ((currentDirectory != null) && (index < max)) {
                item = dirs[index];
                entry = null;
                if (currentDirectory.Node.NodeType == VfsNodeType.SymbolicLink) {
                    SymbolicLinkNode link = (SymbolicLinkNode)currentDirectory.Node;
                    if (0 != depth--) {
                        // The symlink stores a relative path, use it for a current relative lookup.
                        string target = link.Target;

                        // Build a new flags set for symlink lookups, as we do not want all of them.
                        PathResolutionFlags symflags = (flags & PathResolutionFlags.SymLinkLookupSafe);
                        entry = Resolve(ref target, symflags);
                    }
                    else {
                        if (PathResolutionFlags.DoNotThrowNotFoundException != (PathResolutionFlags.DoNotThrowNotFoundException & flags)) {
                            // FIXME: Provide a MUI resource string for the exception
            #if VFS_EXCEPTIONS
                            throw new PathTooLongException();
            #endif // #if !VFS_EXCEPTIONS
                        }
                    }
                }
                else {
                    // Pass the lookup to the DirectoryEntry (and ultimately to the inode itself.)
                    entry = currentDirectory.Lookup(item);

                    // If lookup in the directory entry failed, ask the real INode to perform the lookup.
                    if (entry == null) {
                        IVfsNode node = currentDirectory.Node.Lookup(item);
                        if (node != null) {
                            entry = DirectoryEntry.Allocate(currentDirectory, item, node);
                        }
                    }
                }

                // Increment the path component index
                index++;

                // Check if we have a new path component?
                if ((entry == null) && (PathResolutionFlags.DoNotThrowNotFoundException != (PathResolutionFlags.DoNotThrowNotFoundException & flags))) {
                    // FIXME: Move exception messages to MUI resources
            #if VFS_EXCEPTIONS
                    if (index == max)
                        throw new FileNotFoundException(@"Failed to resolve the path.", path);
                    else
                        throw new DirectoryNotFoundException(@"Failed to resolve the path.");
            #endif // #if VFS_EXCEPTIONS
                }

                // Set the current resolution directory
                currentDirectory = entry;

                // Check if the caller has traverse access to the directory
                AccessCheck.Perform(currentDirectory, AccessMode.Traverse, AccessCheckFlags.None);
            }

            return currentDirectory;
        }
Beispiel #17
0
        /// <summary>
        /// Performs an iterative lookup of the given path starting from the root and obeying to the specified flags.
        /// </summary>
        /// <param name="path">The path to lookup. This can be a relative or absolute path. Path.DirectorySeparatorChar or Path.AltDirectorySeparatorChar are valid delimiters.</param>
        /// <param name="flags">The lookup flags, which control the lookup process.</param>
        /// <returns>The directory entry of the resolved path.</returns>
        /// <exception cref="System.Security.SecurityException">The caller does not have access to the path or a component. For example the caller does not have the right to traverse the path.</exception>
        /// <exception cref="System.IO.PathTooLongException">The path is too long to traverse. This can be the result of circular symbolic links in the path.</exception>
        /// <exception cref="System.IO.FileNotFoundException">The path or a component was not found. This exception can be prevented by specifying PathResolutionFlags.DoNotThrowNotFoundException.</exception>
        /// <exception cref="System.IO.DirectoryNotFoundException">A path component was not found. This exception can be prevented by specifying PathResolutionFlags.DoNotThrowNotFoundException.</exception>
        /// <remarks>
        /// This call may result in other exceptions not specified in the above list. Other exceptions can be thrown by IVfsNode implementations, which are visited during the traversal
        /// process. For example a network file system node may throw an exception, if the server is unreachable.
        /// </remarks>
        private DirectoryEntry Resolve(ref string path, PathResolutionFlags flags)
        {
            // DirectoryNode entry found by stepping through the path
            DirectoryEntry entry = null;

            // Split the given path to its components
            PathSplitter dirs = new PathSplitter(path);

            // Determine the number of path components
            int max = dirs.Length;

            // Current path component
            string item;

            // Loop index
            int index = 0;

            // Perform an access check on the root directory
            AccessCheck.Perform(currentDirectory, AccessMode.Traverse, AccessCheckFlags.None);

            // Do not resolve the last name, if we want the parent directory.
            if (PathResolutionFlags.RetrieveParent == (flags & PathResolutionFlags.RetrieveParent))
            {
                path = dirs[dirs.Length - 1];
                max--;
            }

            // Check if this is an absolute path?
            if (dirs[0].Length == 0)
            {
                // Yes, replace the current directory
                currentDirectory = rootDirectory;
                index++;
            }

            // Iterate over the remaining path components
            while ((currentDirectory != null) && (index < max))
            {
                item  = dirs[index];
                entry = null;
                if (currentDirectory.Node.NodeType == VfsNodeType.SymbolicLink)
                {
                    SymbolicLinkNode link = (SymbolicLinkNode)currentDirectory.Node;
                    if (0 != depth--)
                    {
                        // The symlink stores a relative path, use it for a current relative lookup.
                        string target = link.Target;

                        // Build a new flags set for symlink lookups, as we do not want all of them.
                        PathResolutionFlags symflags = (flags & PathResolutionFlags.SymLinkLookupSafe);
                        entry = Resolve(ref target, symflags);
                    }
                    else
                    {
                        if (PathResolutionFlags.DoNotThrowNotFoundException != (PathResolutionFlags.DoNotThrowNotFoundException & flags))
                        {
                            // FIXME: Provide a MUI resource string for the exception
#if VFS_EXCEPTIONS
                            throw new PathTooLongException();
#endif // #if !VFS_EXCEPTIONS
                        }
                    }
                }
                else
                {
                    // Pass the lookup to the DirectoryEntry (and ultimately to the inode itself.)
                    entry = currentDirectory.Lookup(item);

                    // If lookup in the directory entry failed, ask the real INode to perform the lookup.
                    if (entry == null)
                    {
                        IVfsNode node = currentDirectory.Node.Lookup(item);
                        if (node != null)
                        {
                            entry = DirectoryEntry.Allocate(currentDirectory, item, node);
                        }
                    }
                }

                // Increment the path component index
                index++;

                // Check if we have a new path component?
                if ((entry == null) && (PathResolutionFlags.DoNotThrowNotFoundException != (PathResolutionFlags.DoNotThrowNotFoundException & flags)))
                {
                    // FIXME: Move exception messages to MUI resources
#if VFS_EXCEPTIONS
                    if (index == max)
                    {
                        throw new FileNotFoundException(@"Failed to resolve the path.", path);
                    }
                    else
                    {
                        throw new DirectoryNotFoundException(@"Failed to resolve the path.");
                    }
#endif // #if VFS_EXCEPTIONS
                }

                // Set the current resolution directory
                currentDirectory = entry;

                // Check if the caller has traverse access to the directory
                AccessCheck.Perform(currentDirectory, AccessMode.Traverse, AccessCheckFlags.None);
            }

            return(currentDirectory);
        }
Beispiel #18
0
        /// <summary>
        /// Mounts a new file system.
        /// </summary>
        /// <param name="source">The source of the filesystem. This is usually a device name, but can also be another directory.</param>
        /// <param name="target">The path including the name of the mount point, where to mount the new filesystem.</param>
        public static void Mount(string source, string target)
        {
            // Retrieve the parent directory of the mount
            DirectoryEntry parent = PathResolver.Resolve(rootNode, ref target, PathResolutionFlags.RetrieveParent);

            if (parent == null)
                throw new System.ArgumentException();

            IFileSystem root = FileSystemFactory.CreateFileSystem(source);

            if (root == null)
                throw new System.ArgumentException();

            PathSplitter path = new PathSplitter(target);
            DirectoryEntry.Allocate(parent, path.Last, root.Root);
        }