fuse4dbricks 0.7.5__tar.gz → 0.7.8__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/.github/workflows/test.yml +80 -80
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/CHANGELOG.md +13 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/PKG-INFO +2 -2
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/data_manager.py +10 -2
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/main.py +13 -1
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/pyproject.toml +1 -1
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/.env.example +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/.gitignore +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/README.md +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/__init__.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/api/__init__.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/api/errors.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/api/uc_client.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/auth/__init__.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/auth/provider.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/__init__.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/auth_manager.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/inode_manager.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/metadata_manager.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/operations.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/ram_cache.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/securable_filter.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/utils.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/fs/write_buffer.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/storage/__init__.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/fuse4dbricks/storage/persistence.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_auth_manager.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_auth_provider.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_data_manager.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_e2e_mount.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_inode_manager.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_main.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_metadata_manager.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_operations.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_persistence.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_securable_filter.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_uc_client.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_uc_client_consistency.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_uc_client_live.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_utils.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/tests/test_write_buffer.py +0 -0
- {fuse4dbricks-0.7.5 → fuse4dbricks-0.7.8}/uv.lock +0 -0
|
@@ -1,80 +1,80 @@
|
|
|
1
|
-
name: Test and lint
|
|
2
|
-
|
|
3
|
-
on:
|
|
4
|
-
push:
|
|
5
|
-
branches: [ main ]
|
|
6
|
-
tags: [ 'v*' ]
|
|
7
|
-
pull_request:
|
|
8
|
-
branches: [ main ]
|
|
9
|
-
|
|
10
|
-
# Security hardening: restricts the GITHUB_TOKEN to read-only access
|
|
11
|
-
permissions:
|
|
12
|
-
contents: read
|
|
13
|
-
|
|
14
|
-
jobs:
|
|
15
|
-
build:
|
|
16
|
-
runs-on: ubuntu-latest
|
|
17
|
-
|
|
18
|
-
steps:
|
|
19
|
-
- name: Checkout code
|
|
20
|
-
uses: actions/checkout@v6
|
|
21
|
-
|
|
22
|
-
- name: Set up Python 3.11
|
|
23
|
-
uses: actions/setup-python@v6
|
|
24
|
-
with:
|
|
25
|
-
python-version: "3.11"
|
|
26
|
-
# Caches pip packages to speed up subsequent runs
|
|
27
|
-
cache: 'pip'
|
|
28
|
-
|
|
29
|
-
- name: Install system dependencies for pyfuse3
|
|
30
|
-
run: |
|
|
31
|
-
sudo apt-get update
|
|
32
|
-
sudo apt-get install -y libfuse3-dev fuse3 pkg-config
|
|
33
|
-
|
|
34
|
-
- name: Install Python dependencies
|
|
35
|
-
run: |
|
|
36
|
-
python -m pip install --upgrade pip
|
|
37
|
-
# wheel is required to build the pyfuse3 C-extension correctly
|
|
38
|
-
pip install wheel flake8 pytest
|
|
39
|
-
pip install --group dev .
|
|
40
|
-
|
|
41
|
-
- name: Lint with flake8
|
|
42
|
-
run: |
|
|
43
|
-
# stop the build if there are Python syntax errors or undefined names
|
|
44
|
-
flake8 . --count --select=E9,F63,F7,F82 --show-source --statistics
|
|
45
|
-
# exit-zero treats all errors as warnings.
|
|
46
|
-
flake8 . --count --exit-zero --max-complexity=10 --max-line-length=127 --statistics
|
|
47
|
-
|
|
48
|
-
- name: Run tests
|
|
49
|
-
run: |
|
|
50
|
-
pytest .
|
|
51
|
-
|
|
52
|
-
- name: Install pypa/build
|
|
53
|
-
run: python3 -m pip install uv
|
|
54
|
-
- name: Build a binary wheel and a source tarball
|
|
55
|
-
run: uv build
|
|
56
|
-
- name: Store the distribution packages
|
|
57
|
-
uses: actions/upload-artifact@v7
|
|
58
|
-
with:
|
|
59
|
-
name: python-package-distributions
|
|
60
|
-
path: dist/
|
|
61
|
-
|
|
62
|
-
publish-to-pypi:
|
|
63
|
-
name: Publish package to PyPI
|
|
64
|
-
if: startsWith(github.ref, 'refs/tags/') # only publish to PyPI on tag pushes
|
|
65
|
-
needs:
|
|
66
|
-
- build
|
|
67
|
-
runs-on: ubuntu-latest
|
|
68
|
-
environment:
|
|
69
|
-
name: pypi
|
|
70
|
-
url: https://pypi.org/p/fuse4dbricks
|
|
71
|
-
permissions:
|
|
72
|
-
id-token: write
|
|
73
|
-
steps:
|
|
74
|
-
- name: Download all the dists
|
|
75
|
-
uses: actions/download-artifact@
|
|
76
|
-
with:
|
|
77
|
-
name: python-package-distributions
|
|
78
|
-
path: dist/
|
|
79
|
-
- name: Publish distribution to PyPI
|
|
80
|
-
uses: pypa/gh-action-pypi-publish@release/v1
|
|
1
|
+
name: Test and lint
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
branches: [ main ]
|
|
6
|
+
tags: [ 'v*' ]
|
|
7
|
+
pull_request:
|
|
8
|
+
branches: [ main ]
|
|
9
|
+
|
|
10
|
+
# Security hardening: restricts the GITHUB_TOKEN to read-only access
|
|
11
|
+
permissions:
|
|
12
|
+
contents: read
|
|
13
|
+
|
|
14
|
+
jobs:
|
|
15
|
+
build:
|
|
16
|
+
runs-on: ubuntu-latest
|
|
17
|
+
|
|
18
|
+
steps:
|
|
19
|
+
- name: Checkout code
|
|
20
|
+
uses: actions/checkout@v6
|
|
21
|
+
|
|
22
|
+
- name: Set up Python 3.11
|
|
23
|
+
uses: actions/setup-python@v6
|
|
24
|
+
with:
|
|
25
|
+
python-version: "3.11"
|
|
26
|
+
# Caches pip packages to speed up subsequent runs
|
|
27
|
+
cache: 'pip'
|
|
28
|
+
|
|
29
|
+
- name: Install system dependencies for pyfuse3
|
|
30
|
+
run: |
|
|
31
|
+
sudo apt-get update
|
|
32
|
+
sudo apt-get install -y libfuse3-dev fuse3 pkg-config
|
|
33
|
+
|
|
34
|
+
- name: Install Python dependencies
|
|
35
|
+
run: |
|
|
36
|
+
python -m pip install --upgrade pip
|
|
37
|
+
# wheel is required to build the pyfuse3 C-extension correctly
|
|
38
|
+
pip install wheel flake8 pytest
|
|
39
|
+
pip install --group dev .
|
|
40
|
+
|
|
41
|
+
- name: Lint with flake8
|
|
42
|
+
run: |
|
|
43
|
+
# stop the build if there are Python syntax errors or undefined names
|
|
44
|
+
flake8 . --count --select=E9,F63,F7,F82 --show-source --statistics
|
|
45
|
+
# exit-zero treats all errors as warnings.
|
|
46
|
+
flake8 . --count --exit-zero --max-complexity=10 --max-line-length=127 --statistics
|
|
47
|
+
|
|
48
|
+
- name: Run tests
|
|
49
|
+
run: |
|
|
50
|
+
pytest .
|
|
51
|
+
|
|
52
|
+
- name: Install pypa/build
|
|
53
|
+
run: python3 -m pip install uv
|
|
54
|
+
- name: Build a binary wheel and a source tarball
|
|
55
|
+
run: uv build
|
|
56
|
+
- name: Store the distribution packages
|
|
57
|
+
uses: actions/upload-artifact@v7
|
|
58
|
+
with:
|
|
59
|
+
name: python-package-distributions
|
|
60
|
+
path: dist/
|
|
61
|
+
|
|
62
|
+
publish-to-pypi:
|
|
63
|
+
name: Publish package to PyPI
|
|
64
|
+
if: startsWith(github.ref, 'refs/tags/') # only publish to PyPI on tag pushes
|
|
65
|
+
needs:
|
|
66
|
+
- build
|
|
67
|
+
runs-on: ubuntu-latest
|
|
68
|
+
environment:
|
|
69
|
+
name: pypi
|
|
70
|
+
url: https://pypi.org/p/fuse4dbricks
|
|
71
|
+
permissions:
|
|
72
|
+
id-token: write
|
|
73
|
+
steps:
|
|
74
|
+
- name: Download all the dists
|
|
75
|
+
uses: actions/download-artifact@v8
|
|
76
|
+
with:
|
|
77
|
+
name: python-package-distributions
|
|
78
|
+
path: dist/
|
|
79
|
+
- name: Publish distribution to PyPI
|
|
80
|
+
uses: pypa/gh-action-pypi-publish@release/v1
|
|
@@ -1,3 +1,16 @@
|
|
|
1
|
+
# 0.7.8 (2026-10-15)
|
|
2
|
+
|
|
3
|
+
- Fix typo in DataManager
|
|
4
|
+
|
|
5
|
+
# 0.7.7 (2026-10-01)
|
|
6
|
+
|
|
7
|
+
- Add --num-download-workers and --prefetch-mb to control prefetching
|
|
8
|
+
and parallel downloads.
|
|
9
|
+
|
|
10
|
+
# 0.7.6 (2026-08-07)
|
|
11
|
+
|
|
12
|
+
- Force push. Bump for traceability.
|
|
13
|
+
|
|
1
14
|
# 0.7.5 (2026-08-06)
|
|
2
15
|
|
|
3
16
|
- Fix fatal startup/runtime errors exiting with status 0 instead of 1.
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
Metadata-Version: 2.
|
|
1
|
+
Metadata-Version: 2.5
|
|
2
2
|
Name: fuse4dbricks
|
|
3
|
-
Version: 0.7.
|
|
3
|
+
Version: 0.7.8
|
|
4
4
|
Summary: FUSE driver for Databricks Unity Catalog Volumes.
|
|
5
5
|
Project-URL: Homepage, https://github.com/zeehio/fuse4dbricks
|
|
6
6
|
Author-email: Sergio Oller <sergioller@gmail.com>
|
|
@@ -116,7 +116,7 @@ class DownloadScheduler:
|
|
|
116
116
|
|
|
117
117
|
|
|
118
118
|
class DataManager:
|
|
119
|
-
def __init__(self, uc_client: UnityCatalogClient, persistence: DiskPersistence, ram_cache_mb = 512, num_workers=10):
|
|
119
|
+
def __init__(self, uc_client: UnityCatalogClient, persistence: DiskPersistence, ram_cache_mb = 512, num_workers=10, prefetch_mb=80):
|
|
120
120
|
"""
|
|
121
121
|
uc_client: client to download chunks from UC
|
|
122
122
|
persistence: where to store downloaded chunks on disk
|
|
@@ -129,6 +129,9 @@ class DataManager:
|
|
|
129
129
|
self._inflight_coalescer: InflightCoalescer[_CacheKey] = InflightCoalescer()
|
|
130
130
|
"Inflight coalescer for downloads identified by (fs_path, chunk_id, mtime, gen)"
|
|
131
131
|
|
|
132
|
+
if num_workers < 1:
|
|
133
|
+
raise ValueError("num_workers must be >= 1")
|
|
134
|
+
|
|
132
135
|
self._download_scheduler = DownloadScheduler(process_request=self._process_request, num_workers=num_workers)
|
|
133
136
|
|
|
134
137
|
# Per-path cache generation. Bumped on a local write so previously cached
|
|
@@ -138,6 +141,11 @@ class DataManager:
|
|
|
138
141
|
# max number of chunks to cache in memory
|
|
139
142
|
max_ram_chunks = int(ram_cache_mb*1024*1024 / self.chunk_size)
|
|
140
143
|
self._ram_cache: RamCache[_CacheKey] = RamCache(max_entries = max_ram_chunks)
|
|
144
|
+
prefetch_bytes = prefetch_mb * 1024 * 1024
|
|
145
|
+
chunks_to_prefetch = int(prefetch_bytes / self.chunk_size)
|
|
146
|
+
if chunks_to_prefetch < 0:
|
|
147
|
+
chunks_to_prefetch = 0
|
|
148
|
+
self._chunks_to_prefetch = chunks_to_prefetch
|
|
141
149
|
|
|
142
150
|
def close(self) -> None:
|
|
143
151
|
self._download_scheduler.close()
|
|
@@ -296,7 +304,7 @@ class DataManager:
|
|
|
296
304
|
self._read_chunk, fs_path, chunk_id, mtime, gen, chunk_size, ctx, chunks
|
|
297
305
|
)
|
|
298
306
|
# fetch ahead next 10 chunks once we are beyond chunk 0 (avoid prefetching too much on `head *` command)
|
|
299
|
-
num_chunks_to_prefetch =
|
|
307
|
+
num_chunks_to_prefetch = self._chunks_to_prefetch if end_chunk > 0 else min(1, self._chunks_to_prefetch)
|
|
300
308
|
chunks_to_prefetch = []
|
|
301
309
|
for i in range(num_chunks_to_prefetch):
|
|
302
310
|
chunk_to_prefetch = end_chunk + 1 + i
|
|
@@ -95,6 +95,18 @@ def parse_args():
|
|
|
95
95
|
default=30,
|
|
96
96
|
help="Default TTL for metadata cache entries in seconds",
|
|
97
97
|
)
|
|
98
|
+
parser.add_argument(
|
|
99
|
+
"--prefetch_mb",
|
|
100
|
+
type=int,
|
|
101
|
+
default=80,
|
|
102
|
+
help="Amount of data to prefetch in MB for each file",
|
|
103
|
+
)
|
|
104
|
+
parser.add_argument(
|
|
105
|
+
"--num-download-workers",
|
|
106
|
+
type=int,
|
|
107
|
+
default=10,
|
|
108
|
+
help="Number of concurrent download workers",
|
|
109
|
+
)
|
|
98
110
|
parser.add_argument(
|
|
99
111
|
"--metadata-cache-ttl-catalog-sec",
|
|
100
112
|
type=int,
|
|
@@ -242,7 +254,7 @@ async def async_main():
|
|
|
242
254
|
persistence = DiskPersistence(data_cache_dir, max_size_gb=args.disk_cache_gb, max_age_days=args.disk_cache_max_days)
|
|
243
255
|
|
|
244
256
|
inode_manager = InodeManager()
|
|
245
|
-
data_manager = DataManager(uc_client, persistence, ram_cache_mb=args.ram_cache_mb)
|
|
257
|
+
data_manager = DataManager(uc_client, persistence, ram_cache_mb=args.ram_cache_mb, num_workers=args.num_download_workers, prefetch_mb=args.prefetch_mb)
|
|
246
258
|
metadata_manager = MetadataManager(uc_client, ttl=args.metadata_cache_ttl_sec, max_entries=args.metadata_cache_max_entries, ttl_catalog=args.metadata_cache_ttl_catalog_sec, ttl_negative=args.metadata_cache_ttl_negative_sec, inode_manager=inode_manager)
|
|
247
259
|
# On a 401, the token is invalidated and re-resolved (possibly to a
|
|
248
260
|
# different principal); drop the cached principal so authz re-derives it.
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|