Transfer a local directory across a network boundary by packaging it as a synthetic PyPI wheel
Project description
repak
Transfer the contents of a local directory across a network boundary by packaging it as a PyPI wheel.
Some environments are isolated from the public internet but mirror PyPI
automatically into the isolated side. repak abuses that channel as a
transport: it packs a directory into a synthetic wheel, you upload it to
public PyPI, the internal mirror replicates it, and on the far side
pip install + a generated unpak-* command reproduces the directory.
Only transfer public-domain data.
repakdoes not and cannot enforce this — it is your responsibility.
How it works
Upload side
- The directory name is normalized to a PyPI name:
repak-{folder}. - PyPI is queried; a new package starts at
0.1, an existing repak package is bumped (0.1 → … → 0.99). You confirm before overwriting. - The directory contents are tarred (
.git/.hg/.svn/.bzrexcluded), gzipped, and SHA-256'd. - A self-contained wheel is built containing the tar blob, the checksum, and
an
unpak-{folder}console-script entry point. - The wheel size is checked against PyPI's 100 MiB per-file limit, then
uploaded with
twine.
Download side (isolated environment)
pip install repak-myproject
unpak-myproject /target/landing/folder
The entry point verifies the SHA-256 before writing anything, then
reproduces the directory. It is fully self-contained — repak itself does
not need to be installed on the destination.
Install
pip install repak
Usage
The PyPI token is read from the environment (never a flag, so it stays out of shell history and process listings):
export PYPI_TOKEN="pypi-..." # or TWINE_PASSWORD
repak --path /path/to/folder
# or, from inside the folder:
repak
# non-interactive (skip confirmation prompts):
repak --path /path/to/folder --yes
Then on the isolated side, once the mirror has synced:
pip install repak-<folder>
unpak-<folder> /target/landing/folder
Behavior & constraints
- Extract is overwrite/merge in place: existing unrelated files are left untouched; re-running with the same payload is idempotent.
- Safety: tar entries with absolute paths or
..traversal are rejected; a checksum mismatch aborts before any file is written. - Versioning runs
0.1–0.99(99 uploads per package name). PyPI does not allow re-uploading an existing version. - Name collisions: if
repak-{folder}already exists on PyPI but was not created by repak (no repak marker), upload is refused. - Mirror lag: propagation from public PyPI to the internal mirror is not immediate and the delay is environment-specific.
- Mirror limits: a private mirror may impose size limits below PyPI's 100 MiB.
Non-goals
No dependency resolution, no "correct" packaging (the wheel is a transport container), no git integration (clone/prepare the directory yourself), and no repak install required on the destination side.
Development
pip install -e ".[dev]"
pytest -q # full suite, incl. venv install + roundtrip e2e
License
MIT
Project details
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file repak-0.3.0.tar.gz.
File metadata
- Download URL: repak-0.3.0.tar.gz
- Upload date:
- Size: 14.4 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
cfd693d65fdaffdbc2e7d2377695151076a4fc52713d038b9e548935353523aa
|
|
| MD5 |
d2c0561500b39a2f78ac24f1fb055ea3
|
|
| BLAKE2b-256 |
92090c27ea539fe0694ca9199dc14245b63790ee8e9ebbc9799120715038cb9d
|
Provenance
The following attestation bundles were made for repak-0.3.0.tar.gz:
Publisher:
release.yml on dlfelps/repak
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
repak-0.3.0.tar.gz -
Subject digest:
cfd693d65fdaffdbc2e7d2377695151076a4fc52713d038b9e548935353523aa - Sigstore transparency entry: 1563859581
- Sigstore integration time:
-
Permalink:
dlfelps/repak@4942718f0e3c4cfb2bcb6f55dc85913a9482bd0b -
Branch / Tag:
refs/tags/v0.3.0 - Owner: https://github.com/dlfelps
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@4942718f0e3c4cfb2bcb6f55dc85913a9482bd0b -
Trigger Event:
release
-
Statement type:
File details
Details for the file repak-0.3.0-py3-none-any.whl.
File metadata
- Download URL: repak-0.3.0-py3-none-any.whl
- Upload date:
- Size: 12.1 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/6.1.0 CPython/3.13.12
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
82333eb94eaafd85c4f75565256c48e9114070f1590be933c2661d18cd5c346b
|
|
| MD5 |
491de904ab2303a18bdf153ba8a0d0a9
|
|
| BLAKE2b-256 |
b55b3985d40d22cfa842d692438a8f50349f7743f35c4beaecbc3639385df67c
|
Provenance
The following attestation bundles were made for repak-0.3.0-py3-none-any.whl:
Publisher:
release.yml on dlfelps/repak
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
repak-0.3.0-py3-none-any.whl -
Subject digest:
82333eb94eaafd85c4f75565256c48e9114070f1590be933c2661d18cd5c346b - Sigstore transparency entry: 1563859605
- Sigstore integration time:
-
Permalink:
dlfelps/repak@4942718f0e3c4cfb2bcb6f55dc85913a9482bd0b -
Branch / Tag:
refs/tags/v0.3.0 - Owner: https://github.com/dlfelps
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@4942718f0e3c4cfb2bcb6f55dc85913a9482bd0b -
Trigger Event:
release
-
Statement type: