def leaf(self, atom): """ Get the leaf defined by the given atom :param atom: Atom defining the leaf contents :type atom: Atom :return: Leaf defined by the atom :rtype: Leaf """ atom = Atom.elf(atom) folder = self._branch(atom) file_name = File.make_file_name(str(atom), self.extension, is_compressed=self.compress_all, is_encrypted=self.encrypt_all) file = File.join(folder, file_name) return Leaf(file)
def __init__(self, folder): self._root = None self._folder = Folder.elf(folder) if not self._folder.exists(): raise NotRootException(f'Folder does not exists: {self._folder}') self._file = File.join(self._folder, self._file_name(self._folder)) if not self._file.exists(): raise NotRootException(f'Description file does ' f'not exist: {self._file}') self.read() if self.key() != self._folder.name(): raise NotRootException(f'Key/folder mismatch. ' f'key={self._root.key}, ' f'folder={self._folder}, ' f'file={self._file}')
def elf(cls, folder, **kwargs): """ Converts an existing folder to root, tolerating missing file but not invalid key. If a folder already is a valid root, it will be returned as root. The folder name must be a valid :class:`.Key` :raise RootError: If file already exists, but does not have the right key, or if it has an invalid format :param folder: Folder to convert to root :type folder: Folder :param kwargs: Attributes to add to root file :return: New or existing root :rtype: Root """ if cls.is_root(folder): return cls(folder) folder = Folder.elf(folder) file = File.join(folder, cls._file_name(folder)) if file.exists(): try: dic = file.read() if isinstance(dic['_root'], Atom): key = dic['_root'].key if key == folder.name(): raise RootError(f'This seems to be a valid root, but ' f'is_root said otherwise. Contact ' f'the rather incompetent developer of ' f'this module.') else: raise RootError(f'Root file already exists, but has ' f'the wrong key. ' f'Expected: key={folder.name()}, ' f'Found: key={key}') else: raise RootError(f'Root file already exists, but has ' f'invalid format. Should be atom, but ' f'contents is instead: {dic}') except FileError as fe: raise RootError(f'Root file exists, does not seem to be a ' f'valid JSON file. ' f'Original error from read: {fe}') else: folder.touch() file.write(cls._dic(folder, **kwargs)) return cls(folder)
def test_not_ground(tmp_folder): ground = Ground.settle(tmp_folder, 'test_ground') folder = Folder(ground) g = folder.list('.*')[0] c = g.list()[0] cf = File(c.list('.*')[0]) dic = cf.read() dic['ground_key'] = 'rubbish' cf.write(dic) with pytest.raises(NoGround): Ground(tmp_folder) cf.delete() with pytest.raises(NotRootException): Ground(tmp_folder)
def find_all(cls, folder): """ Find all roots in folder :param folder: Folder to search :type folder: Folder :return: List of roots found in folder :rtype: [Root] """ path = Path.elf(folder) paths = path.glob(cls._FILE_WILDCARD, recursive=True) roots = [] for path in paths: if path.is_file(): file = File.elf(path) folder = file.folder() if file.stub() == folder.name(): if cls.is_root(folder): cls._append_if_root(roots, folder) return roots
def _files(self, pattern='*', recursive=True): paths = self._folder.files(pattern=pattern, recursive=recursive) return [File(x) for x in paths]
def grow(self, native, atom=None, force_extension=False, delete_native=False): """ Add a file to the tree. A file outside of the tree is called ``native`` while a file in the tree is called ``leaf`` :param native: File to add to the tree :type native: File :param atom: Atom defining the contents of the file, if the file name is not a valid atom string :type atom: Atom :param force_extension: Flags forcing file extension to be the extension inherent in tree :type force_extension: bool :param delete_native: Flags whether to delete the native file after file has been copied to the tree structure :type delete_native: bool :return: New leaf in tree :rtype: Leaf """ native = File.elf(native) if not native.exists(): raise TreeError(f'Cannot grow Leaf from non existent ' f'path: {native}') if not native.is_file(): raise TreeError(f'Native is not a file: {native}') if not force_extension and len(native.extensions()) != 1: raise TreeError(f'Leaves must have one extension, this native ' f'has none or multiple: {native.extensions()}. ' f'Use force_extension to set it to ' f'tree inherent: \'{self.extension}\'') if not atom: try: atom = Atom(native.stub()) except AtomError as se: raise TreeError(f'File name is not a valid ' f'atom: {native.name()}. ' f'Add atom as parameter to override ' f'file name.') from se if force_extension: extension = self.extension else: extension = native.extension() new_name = File.make_file_name(str(atom), extension, is_compressed=native.is_compressed(), is_encrypted=native.is_encrypted()) if native.name() == new_name: new_name = None folder = self._branch(atom) if delete_native: file = native.move(folder, new_name) else: file = native.copy(folder, new_name) leaf = Leaf(file) logger.debug(f'Added leaf: {leaf}') leaf = self._shape(leaf) return leaf
def __init__(self, file): File.__init__(self) Atom.__init__(self, self.stub()) if not self.exists(): raise LeafError(f'Leaf path does not exist: {self}')
def _get_file(cls, folder): return File.join(folder, cls._file_name(folder))