Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 31 additions & 0 deletions .github/workflows/package-contents.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
name: Package contents

# The sdist once shipped an entire agent working directory because it had no
# include list and the build backend defaults to "everything not ignored".
# This fails the build if anything outside the package ever ships again.
on:
pull_request:
push:
branches: [master, main]

jobs:
sdist-scope:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-python@v5
with:
python-version: '3.11'
- run: pip install build
- name: Plant a stray directory the way an agent would
run: mkdir -p .claude/worktrees/probe && echo leak > .claude/worktrees/probe/leak.rs
- run: python -m build --sdist --outdir dist-check
- name: The sdist must contain only the package and its metadata
run: |
set -euo pipefail
tar tzf dist-check/*.tar.gz | sed 's|^[^/]*/||' | grep -v '^$' \
| awk -F/ '{print $1}' | sort -u > /tmp/top.txt
echo "top-level entries in the sdist:"; cat /tmp/top.txt
if grep -qE '^\.claude|^\.codex|^backend|^crates|^migrations' /tmp/top.txt; then
echo "::error::the sdist contains files from outside the package"; exit 1
fi
5 changes: 5 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -76,3 +76,8 @@ dmypy.json
# OS
.DS_Store
Thumbs.db

# Agent working directories. These are not source and must never be packaged;
# an unscoped sdist published one to PyPI once already.
.claude/
.codex/
13 changes: 13 additions & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,19 @@ Issues = "https://github.com/0xArchiveIO/sdk-python/issues"
[tool.hatch.build.targets.wheel]
packages = ["oxarchive"]

# The wheel is scoped to the package, but the sdist had no scope at all, so
# hatchling swept in every non-gitignored file in the directory. That published
# an agent working directory, and with it a copy of the private backend, inside
# oxarchive 1.8.0's sdist. List what ships instead of trusting the default.
[tool.hatch.build.targets.sdist]
include = [
"/oxarchive",
"/README.md",
"/CHANGELOG.md",
"/LICENSE",
"/pyproject.toml",
]

[tool.ruff]
line-length = 100
target-version = "py39"
Expand Down
Loading