Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/code-specialist/pypi-poetry-publish
Opinionated GitHub action to fully automate publishing packages to PyPI - using Poetry and GitHub releases
https://github.com/code-specialist/pypi-poetry-publish
automation github-action github-actions package packaging packaging-python poetry publishing pypi pypi-package python workflow
Last synced: about 1 month ago
JSON representation
Opinionated GitHub action to fully automate publishing packages to PyPI - using Poetry and GitHub releases
- Host: GitHub
- URL: https://github.com/code-specialist/pypi-poetry-publish
- Owner: code-specialist
- License: mit
- Created: 2022-11-16T19:33:45.000Z (about 2 years ago)
- Default Branch: main
- Last Pushed: 2023-04-09T15:31:49.000Z (almost 2 years ago)
- Last Synced: 2024-11-30T12:15:35.785Z (about 2 months ago)
- Topics: automation, github-action, github-actions, package, packaging, packaging-python, poetry, publishing, pypi, pypi-package, python, workflow
- Homepage:
- Size: 48.8 KB
- Stars: 11
- Watchers: 1
- Forks: 4
- Open Issues: 4
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# pypi-poetry-publish
Opinionated GitHub action to fully automate publishing packages to PyPI - using Poetry and GitHub releases.
We published this action because we use it in our projects and thought it would be useful to others as well. This action is **open to any kind of
collaboration and contribution** - We're happy to receive feedback, issues, pull requests or just kudos.## Features
- Automatically publish your package to PyPI when you create a new release on GitHub
- Publish to the public PyPI, the TestPyPI, or a custom PyPI registry
- Runs on private GitHub Actions runners
- Support for private PyPI repository dependencies
- Configurable **Python version**, **Poetry**, and **Poetry Core version** for specific needs
- Configurable branch e.g. `main`, `master`, `beta`, etc.Jump to example:
- [Publish to public PyPI](#publish-to-public-pypi)
- [With private dependencies](#with-private-dependencies)
- [To a private PyPI](#publish-to-a-private-pypi)
- [With private dependencies](#with-private-dependencies)## Prerequisites
This action assumes you use [poetry](https://python-poetry.org/) as your package manager and have the `pyproject.toml` and `poetry.lock` files in the root directory of your
repository.```
my_project/
├─ example_package/
│ ├─ __init__.py
├─ pyproject.toml
├─ poetry.lock
```> :information_source: If you do not use a custom runner, you may use the builtin functionality `GITHUB_TOKEN` with write permissions as the `ACCESS_TOKEN` as seen in the first
> example.
> See [https://docs.github.com/en/actions/security-guides/automatic-token-authentication#using-the-github_token-in-a-workflow](https://docs.github.
> com/en/actions/security-guides/automatic-token-authentication#using-the-github_token-in-a-workflow)> :warning: We recommend you to use this workflow with the test PyPI registry e.g. `PUBLISH_REGISTRY: "https://test.pypi.org/simple/"` until you can confirm your workflow works as
> expected.## Minimal example
```yaml
name: Build and publish python packageon:
release:
types: [ published ]jobs:
publish-service-client-package:
runs-on: ubuntu-latest
permissions:
contents: write
steps:
- name: Publish PyPi package
uses: code-specialist/pypi-poetry-publish@v1
with:
ACCESS_TOKEN: ${{ secrets.GITHUB_TOKEN }}
PUBLISH_REGISTRY_PASSWORD: ${{ secrets.PYPI_TOKEN }}
```## Process
1. You create a new Release and Tag e.g. `1.0.0` (Trigger)
2. The action will:
1. build your package
2. adjust the version in the `pyproject.toml` and `__init__.py` in the package directory according to the tag
3. publish the package to a PyPI registry## Example process
### Before the release
**./pyproject.toml**
```toml
[tool.poetry]
name = "code-specialist-example-package"
version = "0.1.0"
description = "Example package"
authors = ["Code Specialist"]
packages = [{include = "example_package"}][tool.poetry.dependencies]
python = "^3.10"
```**./example_package/__init__.py**
```python
__version__ = "0.1.0"
```### After GitHub Release 1.0.0
The action will alter the content of your repository to avoid conflicts and version mismatches:
**pyproject.toml**
```toml
[tool.poetry]
name = "code-specialist-example-package"
version = "1.0.0" # adjusted to 1.0.0
description = "Example package"
authors = ["Code Specialist"]
packages = [{include = "example_package"}][tool.poetry.dependencies]
python = "^3.10"
```**./example_package/__init__.py**
```python
__version__ = "1.0.0" # adjusted to 1.0.0
```## Inputs
> The inputs marked with (✓) are required if the `POETRY_DEPENDENCY_REGISTRY_URL` is set.| Name | Description | Mandatory | Default |
|---------------------------------------|-------------------------------------------------------------------------------------------------------------------------------------|-----------|----------------------------|
| `ACCESS_TOKEN` | GitHub token with write access to the repository, to adjust the version | ✓ | |
| `PUBLISH_REGISTRY_PASSWORD` | Either a password for the registry user or a token in combination with `__token__` as the `PUBLISH_REGISTRY_USERNAME` | ✓ | |
| `PUBLISH_REGISTRY_USERNAME` | The username for the pypi registry | | `__token__` |
| `PACKAGE_DIRECTORY` | The directory the package is located in e.g. `./src/`, `./example_package` | | './' |
| `POETRY_VERSION` | The Poetry version to perform the build with | | `1.1.8` |
| `POETRY_CORE_VERSION` | The Poetry Code version to perform the build with | | `1.0.4` |
| `PYTHON_VERSION` | The Python version to perform the build with | | `3.10` |
| `BRANCH` | The branch to publish from | | `master` |
| `PUBLISH_REGISTRY` | The registry to publish to e.g.`https://test.pypi.org/simple/` | | `https://pypi.org/simple/` |
| `POETRY_DEPENDENCY_REGISTRY_URL` | Allows to define a custom registry to be used by Poetry for dependency installation e.g. `https://pypi.code-specialist.com/simple/` | | |
| `POETRY_DEPENDENCY_REGISTRY_NAME` | The name used for the custom registry in the dependencies. Must match the name in the `pyproject.toml` | (✓) | |
| `POETRY_DEPENDENCY_REGISTRY_USERNAME` | The username for the custom registry | (✓) | |
| `POETRY_DEPENDENCY_REGISTRY_PASSWORD` | The password for the custom registry | (✓) | |
| `POETRY_CUSTOM_REGISTRY_AUTH` | The authentication type for the custom registry | | `http-basic` |## Examples
Each example requires you to:
1. Create a workflow file e.g. `.github/workflows/publish.yaml`
2. Create a new release and tag e.g. `1.0.0` and the action will be triggered and publishes your package> :information_source: If there is a use case you would like to see, please open an issue or a pull request.
### Publish to Public PyPI
- Requires GitHub secrets:
- `PUBLISH_REGISTRY_PASSWORD` with a valid tokenIn order to use the `GITHUB_TOKEN` you also have to provide permissions for the token. In this case you require the `contents:write` permission.
**publish.yaml**
```yaml
name: Build and publish python packageon:
release:
types: [ published ]jobs:
publish-service-client-package:
runs-on: ubuntu-latest
permissions:
contents: write
steps:
- name: Publish PyPi package
uses: code-specialist/pypi-poetry-publish@v1
with:
PACKAGE_DIRECTORY: "./example-package/"
PYTHON_VERSION: "3.10"
ACCESS_TOKEN: ${{ secrets.GITHUB_TOKEN }}
PUBLISH_REGISTRY_PASSWORD: ${{ secrets.PUBLISH_REGISTRY_PASSWORD }}
```### Publish Test PyPI
- Requires GitHub secrets:
- `PUBLISH_REGISTRY_PASSWORD` with a valid token
- `ACCESS_TOKEN` access token with write access to the GitHub repository
**publish.yaml**
```yaml
name: Build and publish python packageon:
release:
types: [ published ]jobs:
publish-service-client-package:
runs-on: ubuntu-latest
steps:
- name: Publish PyPi package
uses: code-specialist/pypi-poetry-publish@v1
with:
PACKAGE_DIRECTORY: "./example-package/"
PYTHON_VERSION: "3.10"
ACCESS_TOKEN: ${{ secrets.ACCESS_TOKEN }}
PUBLISH_REGISTRY_PASSWORD: ${{ secrets.PUBLISH_REGISTRY_PASSWORD }}
PUBLISH_REGISTRY: "https://test.pypi.org/legacy/"
```### Publish to a Private PyPI
- Requires GitHub secrets:
- `PUBLISH_REGISTRY_USER` username for the PyPI registry
- `PUBLISH_REGISTRY_PASSWORD` with the password for the `PUBLISH_REGISTRY_USER` user
- `ACCESS_TOKEN` access token with write access to the GitHub repository**publish.yaml**
```yaml
name: Build and publish python packageon:
release:
types: [ published ]jobs:
publish-service-client-package:
runs-on: ubuntu-latest
steps:
- name: Publish PyPI package
uses: code-specialist/pypi-poetry-publish@v1
with:
PACKAGE_DIRECTORY: "./example-package/"
PYTHON_VERSION: "3.10"
ACCESS_TOKEN: ${{ secrets.ACCESS_TOKEN }}
PUBLISH_REGISTRY_PASSWORD: ${{ secrets.PUBLISH_REGISTRY_PASSWORD }}
PUBLISH_REGISTRY_USER: ${{ secrets.PUBLISH_REGISTRY_USER }}
PUBLISH_REGISTRY: "https://pypi.code-specialist.com/simple/"
```### With Private Dependencies
- Requires GitHub secrets:
- `ACCESS_TOKEN` access token with write access to the GitHub repository
- `PUBLISH_REGISTRY_USER` username for the PyPI registry
- `PUBLISH_REGISTRY_PASSWORD` with the password for the `PUBLISH_REGISTRY_USER` user
- `POETRY_DEPENDENCY_REGISTRY_USERNAME` username for the custom registry
- `POETRY_DEPENDENCY_REGISTRY_PASSWORD` password for the custom registry**publish.yaml**
```yaml
name: Build and publish python packageon:
release:
types: [ published ]jobs:
publish-service-client-package:
runs-on: ubuntu-latest
steps:
- name: Publish PyPI package
uses: code-specialist/pypi-poetry-publish@v1
with:
ACCESS_TOKEN: ${{ secrets.ACCESS_TOKEN }}
PUBLISH_REGISTRY_USER: ${{ secrets.PUBLISH_REGISTRY_USER }}
PUBLISH_REGISTRY_PASSWORD: ${{ secrets.PUBLISH_REGISTRY_PASSWORD }}
PUBLISH_REGISTRY: "https://pypi.code-specialist.com"
POETRY_DEPENDENCY_REGISTRY_URL: "https://pypi.code-specialist.com"
POETRY_DEPENDENCY_REGISTRY_NAME: "codespecialist"
POETRY_DEPENDENCY_REGISTRY_USERNAME: ${{ secrets.CUSTOM_PUBLISH_REGISTRY_USERNAME }}
POETRY_DEPENDENCY_REGISTRY_PASSWORD: ${{ secrets.CUSTOM_PUBLISH_REGISTRY_PASSWORD }}
```For this to install the dependency `private-code-specialist-example-package` from `https://pypi.code-specialist.com/simple/`, the corresponding `pyproject.toml` would look like
this:```toml
[tool.poetry]
name = "code-specialist-example-package"
version = "1.0.0" # adjusted to 1.0.0
description = "Example package"
authors = ["Code Specialist"]
packages = [{include = "example_package"}][[tool.poetry.source]]
name = "codespecialist"
url = "https://pypi.code-specialist.com"[tool.poetry.dependencies]
python = "^3.10"
private-code-specialist-example-package = {version = "^1.0.0", source = "codespecialist"}
```