summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorCoprDistGit <infra@openeuler.org>2023-04-11 16:39:51 +0000
committerCoprDistGit <infra@openeuler.org>2023-04-11 16:39:51 +0000
commit3e4e76422c02902c23edb143571b7926f57c21e1 (patch)
tree1a435578db51e242a36e0755e71a0f8f3c4722e0
parent11cb65ea43a579cdbca0598759753144a30c17fb (diff)
automatic import of python-scantree
-rw-r--r--.gitignore1
-rw-r--r--python-scantree.spec507
-rw-r--r--sources1
3 files changed, 509 insertions, 0 deletions
diff --git a/.gitignore b/.gitignore
index e69de29..18fe04a 100644
--- a/.gitignore
+++ b/.gitignore
@@ -0,0 +1 @@
+/scantree-0.0.1.tar.gz
diff --git a/python-scantree.spec b/python-scantree.spec
new file mode 100644
index 0000000..52e7d2e
--- /dev/null
+++ b/python-scantree.spec
@@ -0,0 +1,507 @@
+%global _empty_manifest_terminate_build 0
+Name: python-scantree
+Version: 0.0.1
+Release: 1
+Summary: Flexible recursive directory iterator: scandir meets glob("**", recursive=True)
+License: MIT
+URL: https://github.com/andhus/scantree
+Source0: https://mirrors.nju.edu.cn/pypi/web/packages/35/0a/8709b1516110e7b5e1ef796426d8e3fcdb96d83a0cc2639a3d559df1b7c7/scantree-0.0.1.tar.gz
+BuildArch: noarch
+
+
+%description
+[![Build Status](https://travis-ci.com/andhus/scantree.svg?branch=master)](https://travis-ci.com/andhus/scantree)
+[![codecov](https://codecov.io/gh/andhus/scantree/branch/master/graph/badge.svg)](https://codecov.io/gh/andhus/scantree)
+# scantree
+Recursive directory iterator supporting:
+- flexible filtering including wildcard path matching
+- in memory representation of file-tree (for repeated access)
+- efficient access to directory entry properties (`posix.DirEntry` interface) extended with real path and path relative to the recursion root directory
+- detection and handling of cyclic symlinks
+
+## Installation
+```commandline
+pip install scantree
+```
+
+## Usage
+See source code for full documentation, some generic examples below.
+
+Get matching file paths:
+```python
+from scantree import scantree, RecursionFilter
+
+tree = scantree('/path/to/dir', RecursionFilter(match=['*.txt']))
+print([path.relative for path in tree.filepaths()])
+print([path.real for path in tree.filepaths()])
+```
+```
+['d1/d2/file3.txt', 'd1/file2.txt', 'file1.txt']
+['/path/to/other_dir/file3.txt', '/path/to/dir/d1/file2.txt', '/path/to/dir/file1.txt']
+```
+
+Access metadata of directory entries in file tree:
+```python
+d2 = tree.directories[0].directories[0]
+print(type(d2))
+print(d2.path.absolute)
+print(d2.path.real)
+print(d2.path.is_symlink())
+print(d2.files[0].relative)
+```
+```
+scantree._node.DirNode
+/path/to/dir/d1/d2
+/path/to/other_dir
+True
+d1/d2/file3.txt
+```
+
+Aggregate information by operating on tree:
+```python
+hello_count = tree.apply(
+ file_apply=lambda path: sum([
+ w.lower() == 'hello' for w in
+ path.as_pathlib().read_text().split()
+ ]),
+ dir_apply=lambda dir_: sum(dir_.entries),
+)
+print(hello_count)
+```
+```
+3
+```
+
+```python
+hello_count_tree = tree.apply(
+ file_apply=lambda path: {
+ 'name': path.name,
+ 'count': sum([
+ w.lower() == 'hello'
+ for w in path.as_pathlib().read_text().split()
+ ])
+ },
+ dir_apply=lambda dir_: {
+ 'name': dir_.path.name,
+ 'count': sum(e['count'] for e in dir_.entries),
+ 'sub_counts': [e for e in dir_.entries]
+ },
+)
+from pprint import pprint
+pprint(hello_count_tree)
+```
+```
+{'count': 3,
+ 'name': 'dir',
+ 'sub_counts': [{'count': 2, 'name': 'file1.txt'},
+ {'count': 1,
+ 'name': 'd1',
+ 'sub_counts': [{'count': 1, 'name': 'file2.txt'},
+ {'count': 0,
+ 'name': 'd2',
+ 'sub_counts': [{'count': 0,
+ 'name': 'file3.txt'}]}]}]}
+```
+
+Flexible filtering:
+```python
+without_hidden_files = scantree('.', RecursionFilter(match=['*', '!.*']))
+
+without_palindrome_linked_dirs = scantree(
+ '.',
+ lambda paths: [
+ p for p in paths if not (
+ p.is_dir() and
+ p.is_symlink() and
+ p.name == p.name[::-1]
+ )
+ ]
+)
+```
+
+Comparison:
+```python
+tree = scandir('path/to/dir')
+# make some operations on filesystem, make sure file tree is the same:
+assert tree == scandir('path/to/dir')
+
+# tree contains absolute/real path info:
+import shutil
+shutil.copytree('path/to/dir', 'path/to/other_dir')
+new_tree = scandir('path/to/other_dir')
+assert tree != new_tree
+assert (
+ [p.relative for p in tree.leafpaths()] ==
+ [p.relative for p in new_tree.leafpaths()]
+)
+```
+
+Inspect symlinks:
+```python
+from scantree import CyclicLinkedDir
+
+file_links = []
+dir_links = []
+cyclic_links = []
+
+def file_apply(path):
+ if path.is_symlink():
+ file_links.append(path)
+
+def dir_apply(dir_node):
+ if dir_node.path.is_symlink():
+ dir_links.append(dir_node.path)
+ if isinstance(dir_node, CyclicLinkedDir):
+ cyclic_links.append((dir_node.path, dir_node.target_path))
+
+scantree('.', file_apply=file_apply, dir_apply=dir_apply)
+```
+
+%package -n python3-scantree
+Summary: Flexible recursive directory iterator: scandir meets glob("**", recursive=True)
+Provides: python-scantree
+BuildRequires: python3-devel
+BuildRequires: python3-setuptools
+BuildRequires: python3-pip
+%description -n python3-scantree
+[![Build Status](https://travis-ci.com/andhus/scantree.svg?branch=master)](https://travis-ci.com/andhus/scantree)
+[![codecov](https://codecov.io/gh/andhus/scantree/branch/master/graph/badge.svg)](https://codecov.io/gh/andhus/scantree)
+# scantree
+Recursive directory iterator supporting:
+- flexible filtering including wildcard path matching
+- in memory representation of file-tree (for repeated access)
+- efficient access to directory entry properties (`posix.DirEntry` interface) extended with real path and path relative to the recursion root directory
+- detection and handling of cyclic symlinks
+
+## Installation
+```commandline
+pip install scantree
+```
+
+## Usage
+See source code for full documentation, some generic examples below.
+
+Get matching file paths:
+```python
+from scantree import scantree, RecursionFilter
+
+tree = scantree('/path/to/dir', RecursionFilter(match=['*.txt']))
+print([path.relative for path in tree.filepaths()])
+print([path.real for path in tree.filepaths()])
+```
+```
+['d1/d2/file3.txt', 'd1/file2.txt', 'file1.txt']
+['/path/to/other_dir/file3.txt', '/path/to/dir/d1/file2.txt', '/path/to/dir/file1.txt']
+```
+
+Access metadata of directory entries in file tree:
+```python
+d2 = tree.directories[0].directories[0]
+print(type(d2))
+print(d2.path.absolute)
+print(d2.path.real)
+print(d2.path.is_symlink())
+print(d2.files[0].relative)
+```
+```
+scantree._node.DirNode
+/path/to/dir/d1/d2
+/path/to/other_dir
+True
+d1/d2/file3.txt
+```
+
+Aggregate information by operating on tree:
+```python
+hello_count = tree.apply(
+ file_apply=lambda path: sum([
+ w.lower() == 'hello' for w in
+ path.as_pathlib().read_text().split()
+ ]),
+ dir_apply=lambda dir_: sum(dir_.entries),
+)
+print(hello_count)
+```
+```
+3
+```
+
+```python
+hello_count_tree = tree.apply(
+ file_apply=lambda path: {
+ 'name': path.name,
+ 'count': sum([
+ w.lower() == 'hello'
+ for w in path.as_pathlib().read_text().split()
+ ])
+ },
+ dir_apply=lambda dir_: {
+ 'name': dir_.path.name,
+ 'count': sum(e['count'] for e in dir_.entries),
+ 'sub_counts': [e for e in dir_.entries]
+ },
+)
+from pprint import pprint
+pprint(hello_count_tree)
+```
+```
+{'count': 3,
+ 'name': 'dir',
+ 'sub_counts': [{'count': 2, 'name': 'file1.txt'},
+ {'count': 1,
+ 'name': 'd1',
+ 'sub_counts': [{'count': 1, 'name': 'file2.txt'},
+ {'count': 0,
+ 'name': 'd2',
+ 'sub_counts': [{'count': 0,
+ 'name': 'file3.txt'}]}]}]}
+```
+
+Flexible filtering:
+```python
+without_hidden_files = scantree('.', RecursionFilter(match=['*', '!.*']))
+
+without_palindrome_linked_dirs = scantree(
+ '.',
+ lambda paths: [
+ p for p in paths if not (
+ p.is_dir() and
+ p.is_symlink() and
+ p.name == p.name[::-1]
+ )
+ ]
+)
+```
+
+Comparison:
+```python
+tree = scandir('path/to/dir')
+# make some operations on filesystem, make sure file tree is the same:
+assert tree == scandir('path/to/dir')
+
+# tree contains absolute/real path info:
+import shutil
+shutil.copytree('path/to/dir', 'path/to/other_dir')
+new_tree = scandir('path/to/other_dir')
+assert tree != new_tree
+assert (
+ [p.relative for p in tree.leafpaths()] ==
+ [p.relative for p in new_tree.leafpaths()]
+)
+```
+
+Inspect symlinks:
+```python
+from scantree import CyclicLinkedDir
+
+file_links = []
+dir_links = []
+cyclic_links = []
+
+def file_apply(path):
+ if path.is_symlink():
+ file_links.append(path)
+
+def dir_apply(dir_node):
+ if dir_node.path.is_symlink():
+ dir_links.append(dir_node.path)
+ if isinstance(dir_node, CyclicLinkedDir):
+ cyclic_links.append((dir_node.path, dir_node.target_path))
+
+scantree('.', file_apply=file_apply, dir_apply=dir_apply)
+```
+
+%package help
+Summary: Development documents and examples for scantree
+Provides: python3-scantree-doc
+%description help
+[![Build Status](https://travis-ci.com/andhus/scantree.svg?branch=master)](https://travis-ci.com/andhus/scantree)
+[![codecov](https://codecov.io/gh/andhus/scantree/branch/master/graph/badge.svg)](https://codecov.io/gh/andhus/scantree)
+# scantree
+Recursive directory iterator supporting:
+- flexible filtering including wildcard path matching
+- in memory representation of file-tree (for repeated access)
+- efficient access to directory entry properties (`posix.DirEntry` interface) extended with real path and path relative to the recursion root directory
+- detection and handling of cyclic symlinks
+
+## Installation
+```commandline
+pip install scantree
+```
+
+## Usage
+See source code for full documentation, some generic examples below.
+
+Get matching file paths:
+```python
+from scantree import scantree, RecursionFilter
+
+tree = scantree('/path/to/dir', RecursionFilter(match=['*.txt']))
+print([path.relative for path in tree.filepaths()])
+print([path.real for path in tree.filepaths()])
+```
+```
+['d1/d2/file3.txt', 'd1/file2.txt', 'file1.txt']
+['/path/to/other_dir/file3.txt', '/path/to/dir/d1/file2.txt', '/path/to/dir/file1.txt']
+```
+
+Access metadata of directory entries in file tree:
+```python
+d2 = tree.directories[0].directories[0]
+print(type(d2))
+print(d2.path.absolute)
+print(d2.path.real)
+print(d2.path.is_symlink())
+print(d2.files[0].relative)
+```
+```
+scantree._node.DirNode
+/path/to/dir/d1/d2
+/path/to/other_dir
+True
+d1/d2/file3.txt
+```
+
+Aggregate information by operating on tree:
+```python
+hello_count = tree.apply(
+ file_apply=lambda path: sum([
+ w.lower() == 'hello' for w in
+ path.as_pathlib().read_text().split()
+ ]),
+ dir_apply=lambda dir_: sum(dir_.entries),
+)
+print(hello_count)
+```
+```
+3
+```
+
+```python
+hello_count_tree = tree.apply(
+ file_apply=lambda path: {
+ 'name': path.name,
+ 'count': sum([
+ w.lower() == 'hello'
+ for w in path.as_pathlib().read_text().split()
+ ])
+ },
+ dir_apply=lambda dir_: {
+ 'name': dir_.path.name,
+ 'count': sum(e['count'] for e in dir_.entries),
+ 'sub_counts': [e for e in dir_.entries]
+ },
+)
+from pprint import pprint
+pprint(hello_count_tree)
+```
+```
+{'count': 3,
+ 'name': 'dir',
+ 'sub_counts': [{'count': 2, 'name': 'file1.txt'},
+ {'count': 1,
+ 'name': 'd1',
+ 'sub_counts': [{'count': 1, 'name': 'file2.txt'},
+ {'count': 0,
+ 'name': 'd2',
+ 'sub_counts': [{'count': 0,
+ 'name': 'file3.txt'}]}]}]}
+```
+
+Flexible filtering:
+```python
+without_hidden_files = scantree('.', RecursionFilter(match=['*', '!.*']))
+
+without_palindrome_linked_dirs = scantree(
+ '.',
+ lambda paths: [
+ p for p in paths if not (
+ p.is_dir() and
+ p.is_symlink() and
+ p.name == p.name[::-1]
+ )
+ ]
+)
+```
+
+Comparison:
+```python
+tree = scandir('path/to/dir')
+# make some operations on filesystem, make sure file tree is the same:
+assert tree == scandir('path/to/dir')
+
+# tree contains absolute/real path info:
+import shutil
+shutil.copytree('path/to/dir', 'path/to/other_dir')
+new_tree = scandir('path/to/other_dir')
+assert tree != new_tree
+assert (
+ [p.relative for p in tree.leafpaths()] ==
+ [p.relative for p in new_tree.leafpaths()]
+)
+```
+
+Inspect symlinks:
+```python
+from scantree import CyclicLinkedDir
+
+file_links = []
+dir_links = []
+cyclic_links = []
+
+def file_apply(path):
+ if path.is_symlink():
+ file_links.append(path)
+
+def dir_apply(dir_node):
+ if dir_node.path.is_symlink():
+ dir_links.append(dir_node.path)
+ if isinstance(dir_node, CyclicLinkedDir):
+ cyclic_links.append((dir_node.path, dir_node.target_path))
+
+scantree('.', file_apply=file_apply, dir_apply=dir_apply)
+```
+
+%prep
+%autosetup -n scantree-0.0.1
+
+%build
+%py3_build
+
+%install
+%py3_install
+install -d -m755 %{buildroot}/%{_pkgdocdir}
+if [ -d doc ]; then cp -arf doc %{buildroot}/%{_pkgdocdir}; fi
+if [ -d docs ]; then cp -arf docs %{buildroot}/%{_pkgdocdir}; fi
+if [ -d example ]; then cp -arf example %{buildroot}/%{_pkgdocdir}; fi
+if [ -d examples ]; then cp -arf examples %{buildroot}/%{_pkgdocdir}; fi
+pushd %{buildroot}
+if [ -d usr/lib ]; then
+ find usr/lib -type f -printf "/%h/%f\n" >> filelist.lst
+fi
+if [ -d usr/lib64 ]; then
+ find usr/lib64 -type f -printf "/%h/%f\n" >> filelist.lst
+fi
+if [ -d usr/bin ]; then
+ find usr/bin -type f -printf "/%h/%f\n" >> filelist.lst
+fi
+if [ -d usr/sbin ]; then
+ find usr/sbin -type f -printf "/%h/%f\n" >> filelist.lst
+fi
+touch doclist.lst
+if [ -d usr/share/man ]; then
+ find usr/share/man -type f -printf "/%h/%f.gz\n" >> doclist.lst
+fi
+popd
+mv %{buildroot}/filelist.lst .
+mv %{buildroot}/doclist.lst .
+
+%files -n python3-scantree -f filelist.lst
+%dir %{python3_sitelib}/*
+
+%files help -f doclist.lst
+%{_docdir}/*
+
+%changelog
+* Tue Apr 11 2023 Python_Bot <Python_Bot@openeuler.org> - 0.0.1-1
+- Package Spec generated
diff --git a/sources b/sources
new file mode 100644
index 0000000..5fb843a
--- /dev/null
+++ b/sources
@@ -0,0 +1 @@
+e7b37d7292c0d4edc96246e8d681b2b5 scantree-0.0.1.tar.gz