Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
38 commits
Select commit Hold shift + click to select a range
85ebe7c
fix: upload of wheels
tmathern May 30, 2025
bf1b7c1
fix: upload of wheels
tmathern May 30, 2025
8f8361d
fix: upload of wheels
tmathern May 30, 2025
4b77a03
fix: upload of wheels
tmathern May 30, 2025
2fe7ad9
fix: upload of wheels
tmathern May 30, 2025
5da91d5
fix: upload of wheels
tmathern May 30, 2025
211ceeb
fix: upload of wheels
tmathern May 30, 2025
1e4c374
fix: upload of wheels
tmathern May 30, 2025
3f69012
fix: upload of wheels
tmathern May 30, 2025
091758a
fix: upload of wheels
tmathern May 30, 2025
184584d
fix: upload of wheels
tmathern May 30, 2025
b981e45
fix: upload of wheels
tmathern May 30, 2025
71a1d8b
fix: upload of wheels
tmathern May 31, 2025
1a631ed
fix: upload of wheels
tmathern May 31, 2025
c40da61
fix: Update test setup
tmathern May 31, 2025
0a4c347
fix: upload of wheels
tmathern May 31, 2025
b2b3603
fix: merge commit
tmathern May 31, 2025
64deb67
fix: upload of wheels
tmathern May 31, 2025
b9a8f97
fix: upload of wheels
tmathern May 31, 2025
c4e36d4
fix: upload of wheels
tmathern May 31, 2025
f58304c
fix: upload of wheels
tmathern May 31, 2025
0f94d4c
fix: upload of wheels
tmathern May 31, 2025
ee12132
fix: Test
tmathern May 31, 2025
b3371b7
fix: Add test
tmathern May 31, 2025
f5623ab
fix: Refactor tests
tmathern May 31, 2025
bfdca20
fix: Reader test
tmathern May 31, 2025
1cc2e29
fix: Update readme
tmathern May 31, 2025
83f8af0
fix: Docs
tmathern May 31, 2025
15e0e22
fix: Refactor
tmathern May 31, 2025
905e4b2
fix: benchmark
tmathern May 31, 2025
2c9e44b
fix: CLeaning up
tmathern May 31, 2025
5ad9392
fix: Stream tests
tmathern May 31, 2025
d17f373
fix: Reader tests
tmathern May 31, 2025
4de674b
fix: Builder double close test
tmathern May 31, 2025
050ca3c
ci: Merge branch 'mathern/pypitest-setup' into mathern/manywheels
tmathern May 31, 2025
a47891a
fix: Remove debug logs
tmathern May 31, 2025
bd148f2
fix: Fix typo
tmathern May 31, 2025
dcb862c
fix: Stream exception
tmathern May 31, 2025
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
14 changes: 14 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -4,27 +4,35 @@
# Pre-requisite: Python virtual environment is active (source .venv/bin/activate)
# Run Pytest tests in virtualenv: .venv/bin/pytest tests/test_unit_tests.py -v

# Removes build artifacts, distribution files, and other generated content
clean:
rm -rf artifacts/ build/ dist/

# Performs a complete cleanup including uninstalling the c2pa package and clearing pip cache
clean-c2pa-env: clean
python3 -m pip uninstall -y c2pa
python3 -m pip cache purge

# Installs all required dependencies from requirements.txt and requirements-dev.txt
install-deps:
python3 -m pip install -r requirements.txt
python3 -m pip install -r requirements-dev.txt
pip install -e .

# Installs the package in development mode
build-python:
pip install -e .

# Performs a complete rebuild of the development environment
rebuild: clean-c2pa-env install-deps download-native-artifacts build-python
@echo "Development rebuild done!"

# Runs the unit tests
test:
python3 ./tests/test_unit_tests.py

# Tests building and installing a local wheel package
# Downloads required artifacts, builds the wheel, installs it, and verifies the installation
test-local-wheel-build:
# Clean any existing builds
rm -rf build/ dist/
Expand All @@ -41,6 +49,8 @@ test-local-wheel-build:
# Verify wheel structure
twine check dist/*

# Tests building and installing a local source distribution package
# Downloads required artifacts, builds the sdist, installs it, and verifies the installation
test-local-sdist-build:
# Clean any existing builds
rm -rf build/ dist/
Expand All @@ -58,17 +68,21 @@ test-local-sdist-build:
# Verify sdist structure
twine check dist/*

# Verifies the wheel build process and checks the built package and its metadata
verify-wheel-build:
rm -rf build/ dist/ src/*.egg-info/
python -m build
twine check dist/*

# Manually publishes the package to PyPI after creating a release
publish: release
python3 -m pip install twine
python3 -m twine upload dist/*

# Formats Python source code using autopep8 with aggressive settings
format:
autopep8 --aggressive --aggressive --in-place src/c2pa/*.py

# Downloads the required native artifacts for the specified version
download-native-artifacts:
python3 scripts/download_artifacts.py c2pa-v0.55.0
64 changes: 42 additions & 22 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,26 +12,29 @@ This project provides a Python API for working with [C2PA](https://c2pa.org/) (C
## Project Structure

```bash
python_api/
├── examples/ # Example scripts demonstrating usage
├── src/ # Source code for the C2PA Python API
│ └── c2pa/ # Main package directory
│ └── libs/ # Platform-specific libraries
├── tests/ # Unit tests and benchmarks
├── artifacts/ # Platform-specific libraries for building
│ ├── win_amd64/ # Windows x64 libraries
│ ├── win_arm64/ # Windows ARM64 libraries
│ ├── macosx_x86_64/ # macOS x64 libraries
│ ├── macosx_arm64/ # macOS ARM64 libraries
│ ├── linux_x86_64/ # Linux x64 libraries
│ └── linux_aarch64/ # Linux ARM64 libraries
├── requirements.txt # Python dependencies
└── README.md # Project documentation
.
├── .github/ # GitHub configuration files
├── artifacts/ # Platform-specific libraries for building (per subfolder)
│ └── linux_x86_64/ # Linux ARM64 libraries
├── docs/ # Project documentation
├── examples/ # Example scripts demonstrating usage
├── scripts/ # Utility scripts (eg. artifacts download)
├── src/ # Source code
│ └── c2pa/ # Main package directory
│ └── libs/ # Platform-specific libraries
├── tests/ # Unit tests and benchmarks
├── .gitignore # Git ignore rules
├── Makefile # Build and development commands
├── pyproject.toml # Python project configuration
├── requirements.txt # Python dependencies
├── requirements-dev.txt # Development dependencies
└── setup.py # Package setup script
```

## Development Setup

1. Create and activate a virtual environment:

```bash
# Create virtual environment
python -m venv .venv
Expand All @@ -43,19 +46,20 @@ python -m venv .venv
source .venv/bin/activate

# load project dependencies
pip install -r requirements.txt
pip install -r requirements.txt

# download library artifacts for the current version you want
python scripts/download_artifacts.py c2pa-v0.49.5
# download library artifacts for the current version you want, eg v0.55.0
python scripts/download_artifacts.py c2pa-v0.55.0
```


2. Install the package in development mode:

```bash
pip install -e .
```

This will:

- Copy the appropriate libraries for your platform from `artifacts/` to `src/c2pa/libs/`
- Install the package in development mode, allowing you to make changes to the Python code without reinstalling

Expand All @@ -67,26 +71,42 @@ To build wheels for all platforms that have libraries in the `artifacts/` direct
python setup.py bdist_wheel
```

You can use `twine` to verify the wheels have correct metadata:

```bash
twine check dist/*
```

This will create platform-specific wheels in the `dist/` directory.

## Running Tests

Install pytest (if not already installed):
Run the tests:

```bash
make test
```

Alternatively, install pytest (if not already installed):

```bash
pip install pytest
```

Run the tests:
And run:

```bash
pytest
```

## Examples

### Adding a "Do Not Train" Assertion

The `examples/training.py` script demonstrates how to add a "Do Not Train" assertion to an asset and verify it.

### Signing and Verifying Assets

The `examples/test.py` script shows how to sign an asset with a C2PA manifest and verify it.

## Contributing
Expand All @@ -95,4 +115,4 @@ Contributions are welcome! Please fork the repository and submit a pull request.

## License

This project is licensed under the Apache License 2.0 or the MIT License. See the LICENSE-MIT and LICENSE-APACHE files for details.
This project is licensed under the Apache License 2.0 or the MIT License. See the LICENSE-MIT and LICENSE-APACHE files for details.
59 changes: 0 additions & 59 deletions README_saved.md

This file was deleted.

3 changes: 2 additions & 1 deletion requirements-dev.txt
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,8 @@ build==1.0.3 # For building packages using PEP 517/518
toml==0.10.2 # For reading pyproject.toml files

# Testing dependencies
pytest==7.4.0
pytest>=8.1.0
pytest-benchmark>=5.1.0

# for downloading the library artifacts
requests>=2.0.0
Expand Down
12 changes: 0 additions & 12 deletions setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -103,19 +103,13 @@ def copy_platform_libraries(platform_name, clean_first=False):
clean_first: If True, remove existing files in PACKAGE_LIBS_DIR first
"""
platform_dir = ARTIFACTS_DIR / platform_name
print(" ")
print('##### Found platform dir: ', platform_dir)
print(" ")

# Ensure the platform directory exists and contains files
if not platform_dir.exists():
raise ValueError(f"Platform directory not found: {platform_dir}")

# Get list of all files in the platform directory
platform_files = list(platform_dir.glob('*'))
print(" ")
print('##### Platform files: ', platform_files)
print(" ")
if not platform_files:
raise ValueError(f"No files found in platform directory: {platform_dir}")

Expand All @@ -124,9 +118,6 @@ def copy_platform_libraries(platform_name, clean_first=False):
shutil.rmtree(PACKAGE_LIBS_DIR)

# Ensure the package libs directory exists
print(" ")
print('##### Package libs dir will be in: ', PACKAGE_LIBS_DIR)
print(" ")
PACKAGE_LIBS_DIR.mkdir(parents=True, exist_ok=True)

# Copy files from platform-specific directory to the package libs directory
Expand Down Expand Up @@ -189,9 +180,6 @@ def find_available_platforms():
print(f"\nBuilding wheel for {platform_name}...")
try:
# Copy libraries for this platform (cleaning first)
print(" ")
print('##### Preparing to copy libraries to where they belong')
print(" ")
copy_platform_libraries(platform_name, clean_first=True)

# Build the wheel
Expand Down
4 changes: 3 additions & 1 deletion src/c2pa/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
C2paSigningAlg,
C2paSignerInfo,
Signer,
Stream,
sdk_version
) # NOQA

Expand All @@ -18,5 +19,6 @@
'C2paSigningAlg',
'C2paSignerInfo',
'Signer',
'Stream',
'sdk_version'
]
]
25 changes: 21 additions & 4 deletions src/c2pa/build.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,15 @@
GITHUB_API_BASE = "https://api.github.com"
ARTIFACTS_DIR = Path("artifacts")


def get_latest_release() -> dict:
"""Get the latest release information from GitHub."""
url = f"{GITHUB_API_BASE}/repos/{REPO_OWNER}/{REPO_NAME}/releases/latest"
response = requests.get(url)
response.raise_for_status()
return response.json()


def download_artifact(url: str, platform_name: str) -> None:
"""Download and extract an artifact to the appropriate platform directory."""
print(f"Downloading artifact for {platform_name}...")
Expand All @@ -37,7 +39,9 @@ def download_artifact(url: str, platform_name: str) -> None:
# Extract all files to the platform directory
zip_ref.extractall(platform_dir)

print(f"Successfully downloaded and extracted artifacts for {platform_name}")
print(f"Successfully downloaded and extracted artifacts for {
platform_name}")


def download_artifacts() -> None:
"""Main function to download artifacts. Can be called as a script or from hatch."""
Expand Down Expand Up @@ -72,11 +76,22 @@ def download_artifacts() -> None:
print(f"Unexpected error: {e}", file=sys.stderr)
sys.exit(1)


def inject_version():
"""Inject the version from pyproject.toml into src/c2pa/__init__.py as __version__."""
import toml
pyproject_path = os.path.abspath(os.path.join(os.path.dirname(__file__), "..", "..", "pyproject.toml"))
init_path = os.path.abspath(os.path.join(os.path.dirname(__file__), "..", "c2pa", "__init__.py"))
pyproject_path = os.path.abspath(
os.path.join(
os.path.dirname(__file__),
"..",
"..",
"pyproject.toml"))
init_path = os.path.abspath(
os.path.join(
os.path.dirname(__file__),
"..",
"c2pa",
"__init__.py"))
with open(pyproject_path, "r") as f:
pyproject = toml.load(f)
version = pyproject["project"]["version"]
Expand All @@ -89,11 +104,13 @@ def inject_version():
with open(init_path, "w") as f:
f.writelines(lines)


def initialize_build() -> None:
"""Initialize the build process by downloading artifacts."""
inject_version()
download_artifacts()


if __name__ == "__main__":
inject_version()
download_artifacts()
download_artifacts()
Loading