Skip to content

Commit 2f38f34

Browse files
authored
ci: Add automatic pull request labeler (#15)
This PR includes several unrelated improvements to be able to do the first open source release: Project metadata and packaging: - Move project metadata/config to pyproject.toml - Add extra metadata to pyproject.toml - Exclude supporting files from the distribution Automation improvements: - Add automatic pull request labeler - Bump action versions - Run the workflow for all branches - Test using all supported Python versions Releasing: - Publish distribution files to PyPI - Create GitHub Release automatically - Create contributing guide - Add releasing instruction to CONTRIBUTING.md
2 parents e9ca0e3 + 4cddd24 commit 2f38f34

File tree

11 files changed

+313
-48
lines changed

11 files changed

+313
-48
lines changed

.github/RELEASE_NOTES.template.md

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
# Frequenz Channels Release Notes
2+
3+
## Summary
4+
5+
<!-- Here goes a general summary of what this release is about -->
6+
7+
## Upgrading
8+
9+
<!-- Here goes notes on how to upgrade from previous versions, including if there are any depractions and what they should be replaced with -->
10+
11+
## New Features
12+
13+
<!-- Here goes the main new features and examples or instructions on how to use them -->
14+
15+
## Bug Fixes
16+
17+
<!-- Here goes notable bug fixes that are worth a special mention or explanation -->

.github/labeler.yml

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
# Configuration for the Labeler GitHub action, executed by
2+
# .github/workflows/labeler.yml.
3+
#
4+
# The basic syntax is [label]: [path patterns].
5+
#
6+
# For more details on the configuration please see:
7+
# https://github.com/marketplace/actions/labeler
8+
9+
"part:docs":
10+
- "**/*.md"
11+
- LICENSE
12+
13+
"part:tests":
14+
- "tests/**"
15+
16+
"part:tooling":
17+
- ".git*"
18+
- ".git*/**"
19+
- "**/*.toml"
20+
- "**/*.ini"
21+
- CODEOWNERS
22+
- MANIFEST.in
23+
- "*requirements*.txt"
24+
- setup.py
25+
26+
"part:channels":
27+
- "src/frequenz/channels/**"

.github/workflows/ci.yaml

Lines changed: 109 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,34 +1,36 @@
11
name: frequenz-channels-python
22

3-
on:
4-
push:
5-
branches: [ v0.x.x ]
6-
7-
pull_request:
8-
9-
workflow_dispatch:
3+
on: [pull_request, push, workflow_dispatch]
104

115
jobs:
126
test:
13-
runs-on: ubuntu-20.04
7+
strategy:
8+
matrix:
9+
os:
10+
- ubuntu-20.04
11+
python-version:
12+
- "3.8"
13+
- "3.9"
14+
- "3.10"
15+
runs-on: ${{ matrix.os }}
1416

1517
steps:
1618
- name: Fetch sources
17-
uses: actions/checkout@v2
19+
uses: actions/checkout@v3
1820
with:
1921
submodules: true
2022

2123
- name: Set up Python
22-
uses: actions/setup-python@v2
24+
uses: actions/setup-python@v4
2325
with:
24-
python-version: "3.8"
26+
python-version: ${{ matrix.python-version }}
2527

26-
- uses: actions/cache@v2
28+
- uses: actions/cache@v3
2729
with:
2830
path: ~/.cache/pip
29-
key: ${{ runner.os }}-pip-${{ hashFiles('**/setup.cfg') }}
31+
key: ${{ runner.os }}-${{ matrix.python-version }}-pip-${{ hashFiles('pyproject.toml') }}
3032
restore-keys: |
31-
${{ runner.os }}-pip-
33+
${{ runner.os }}-${{ matrix.python-version }}-pip-
3234
3335
- name: Install required Python packages
3436
run: |
@@ -38,3 +40,96 @@ jobs:
3840
- name: run nox
3941
run: nox
4042
timeout-minutes: 10
43+
44+
build-dist:
45+
runs-on: ubuntu-20.04
46+
steps:
47+
- name: Fetch sources
48+
uses: actions/checkout@v3
49+
with:
50+
submodules: true
51+
52+
- name: Set up Python
53+
uses: actions/setup-python@v4
54+
with:
55+
python-version: "3.10"
56+
57+
- name: Install build dependencies
58+
run: |
59+
python -m pip install -U pip
60+
python -m pip install -U build
61+
62+
- name: Build the source and binary distribution
63+
run: python -m build
64+
65+
- name: Upload dist files
66+
uses: actions/upload-artifact@v3
67+
with:
68+
name: frequenz-channels-python-dist
69+
path: dist/
70+
if-no-files-found: error
71+
72+
create-github-release:
73+
needs: ["test", "build-dist"]
74+
# Create a release only on tags creation
75+
if: github.event_name == 'push' && startsWith(github.ref, 'refs/tags')
76+
permissions:
77+
# We need write permissions on contents to create GitHub releases and on
78+
# discussions to create the release announcement in the discussion forums
79+
contents: write
80+
discussions: write
81+
runs-on: ubuntu-20.04
82+
steps:
83+
- name: Download dist files
84+
uses: actions/download-artifact@v3
85+
with:
86+
name: frequenz-channels-python-dist
87+
path: dist
88+
89+
- name: Download RELEASE_NOTES.md
90+
run: |
91+
set -ux
92+
gh api \
93+
-X GET \
94+
-f ref=$REF \
95+
-H "Accept: application/vnd.github.raw" \
96+
"/repos/$REPOSITORY/contents/RELEASE_NOTES.md" \
97+
> RELEASE_NOTES.md
98+
env:
99+
REF: ${{ github.ref }}
100+
REPOSITORY: ${{ github.repository }}
101+
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
102+
103+
- name: Create GitHub release
104+
run: |
105+
set -ux
106+
extra_opts=
107+
if echo "$REF_NAME" | grep -- -; then extra_opts=" --prerelease"; fi
108+
gh release create \
109+
-R "$REPOSITORY" \
110+
--discussion-category announcements \
111+
--notes-file RELEASE_NOTES.md \
112+
--generate-notes \
113+
$extra_opts \
114+
$REF_NAME \
115+
dist/*
116+
env:
117+
REF_NAME: ${{ github.ref_name }}
118+
REPOSITORY: ${{ github.repository }}
119+
GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
120+
121+
publish-to-pypi:
122+
needs: ["create-github-release"]
123+
runs-on: ubuntu-20.04
124+
steps:
125+
- name: Download dist files
126+
uses: actions/download-artifact@v3
127+
with:
128+
name: frequenz-channels-python-dist
129+
path: dist
130+
131+
- name: Publish the Python distribution to PyPI
132+
uses: pypa/gh-action-pypi-publish@release/v1
133+
with:
134+
password: ${{ secrets.PYPI_API_TOKEN }}
135+
skip_existing: true

.github/workflows/labeler.yml

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
name: Pull Request Labeler
2+
3+
# XXX: !!! SECURITY WARNING !!!
4+
# pull_request_target has write access to the repo, and can read secrets. We
5+
# need to audit any external actions executed in this workflow and make sure no
6+
# checked out code is run (not even installing dependencies, as installing
7+
# dependencies usually can execute pre/post-install scripts). We should also
8+
# only use hashes to pick the action to execute (instead of tags or branches).
9+
# For more details read:
10+
# https://securitylab.github.com/research/github-actions-preventing-pwn-requests/
11+
on: [pull_request_target]
12+
13+
jobs:
14+
Label:
15+
permissions:
16+
contents: read
17+
pull-requests: write
18+
runs-on: ubuntu-latest
19+
steps:
20+
- name: Labeler
21+
# Only use hashes, see the security comment above
22+
uses: actions/labeler@e54e5b338fbd6e6cdb5d60f51c22335fc57c401e # 4.0.1
23+
with:
24+
repo-token: "${{ secrets.GITHUB_TOKEN }}"

CONTRIBUTING.md

Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
Contributing to `frequenz-channels`
2+
===================================
3+
4+
5+
Build
6+
=====
7+
8+
You can use `build` to simply build the source and binary distribution:
9+
10+
```sh
11+
python -m pip install build
12+
python -m build
13+
```
14+
15+
Local development
16+
=================
17+
18+
You can use editable installs to develop the project locally (it will install
19+
all the dependencies too):
20+
21+
```sh
22+
python -m pip install -e .
23+
```
24+
25+
You can also use `nox` to run the tests and other checks:
26+
27+
```sh
28+
python -m pip install nox
29+
nox
30+
```
31+
32+
Releasing
33+
=========
34+
35+
These are the steps to create a new release:
36+
37+
1. Get the latest head you want to create a release from.
38+
39+
2. Update the `RELEASE_NOTES.md` file if it is not complete, up to date, and
40+
clean from template comments (`<!-- ... ->`) and empty sections. Submit
41+
a pull request if an update is needed, wait until it is merged, and update
42+
the latest head you want to create a release from to get the new merged pull
43+
request.
44+
45+
3. Create a new signed tag using the release notes and
46+
a [semver](https://semver.org/) compatible version number with a `v` prefix,
47+
for example:
48+
49+
```sh
50+
git tag -s -F RELEASE_NOTES.md v0.0.1
51+
```
52+
53+
4. Push the new tag.
54+
55+
5. A GitHub action will test the tag and if all goes well it will create
56+
a [GitHub
57+
Release](https://github.com/frequenz-floss/frequenz-channels/releases),
58+
create a new
59+
[announcement](https://github.com/frequenz-floss/frequenz-channels/discussions/categories/announcements)
60+
about the release, and upload a new package to
61+
[PyPI](https://pypi.org/project/frequenz-channels/) automatically.
62+
63+
6. Once this is done, reset the `RELEASE_NOTES.md` with the template:
64+
65+
```sh
66+
cp .github/RELEASE_NOTES.template.md RELEASE_NOTES.md
67+
```
68+
69+
Commit the new release notes and create a PR (this step should be automated
70+
eventually too).
71+
72+
7. Celebrate!

MANIFEST.in

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
exclude .gitignore
2+
exclude .darglint
3+
exclude noxfile.py
4+
exclude CODEOWNERS
5+
recursive-exclude .github *
6+
recursive-exclude tests *
7+
recursive-exclude benchmarks *

README.md

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
11
# Frequenz channels
22

33
This repository contains channel implementations for python.
4+
5+
## Contributing
6+
7+
If you want to know how to build this project and contribute to it, please
8+
check out the [Contributing
9+
Guide](https://github.com/frequenz-floss/frequenz-channels/CONTRIBUTING.md).

RELEASE_NOTES.md

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
# `frequenz-channels` Release Notes
2+
3+
## Summary
4+
5+
This is the first public open source release based on the internal SDK version v0.9.0. There are no breaking changes in this release, only changes to the project structure, metadata, and automation. Packages are also now uploaded to PyPI as [`frequenz-channels`](https://pypi.org/project/frequenz-channels/), so this project now can be installed normally via `pip`:
6+
7+
```sh
8+
python -m pip install frequenz-channels
9+
```
10+
11+
The GitHub issues were also improved, adding templates for [reporting issues](https://github.com/frequenz-floss/frequenz-channels/issues/new?assignees=&labels=priority%3A%E2%9D%93%2C+type%3Abug&template=bug.yml) and [requesting features](https://github.com/frequenz-floss/frequenz-channels/issues/new?assignees=&labels=part%3A%E2%9D%93%2C+priority%3A%E2%9D%93%2C+type%3Aenhancement&template=feature.yml). Users are also pointed to the [Discussion forums](https://github.com/frequenz-floss/frequenz-channels/issues/new/choose) when trying to open an issue if they have questions instead. Also many labels are assigned automatically on issue and pull request creation.

pyproject.toml

Lines changed: 40 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,46 @@ requires = [
66
]
77
build-backend = "setuptools.build_meta"
88

9+
10+
[project]
11+
name = "frequenz-channels"
12+
description = "Channel implementations for Python"
13+
readme = "README.md"
14+
license = { text = "MIT" }
15+
keywords = [ "frequenz", "channel" ]
16+
classifiers = [
17+
"Development Status :: 3 - Alpha",
18+
"Intended Audience :: Developers",
19+
"License :: OSI Approved :: MIT License",
20+
"Programming Language :: Python :: 3",
21+
"Programming Language :: Python :: 3 :: Only",
22+
"Programming Language :: Python :: 3.8",
23+
"Programming Language :: Python :: 3.9",
24+
"Programming Language :: Python :: 3.10",
25+
"Topic :: Software Development :: Libraries",
26+
]
27+
requires-python = ">= 3.8, < 4"
28+
dependencies = [
29+
"watchfiles >= 0.15.0",
30+
]
31+
dynamic = [ "version" ]
32+
33+
[[project.authors]]
34+
name ="Frequenz Energy-as-a-Service GmbH"
35+
36+
37+
[project.urls]
38+
Changelog = "https://github.com/frequenz-floss/frequenz-channels-pytyhon/releases"
39+
Repository = "https://github.com/frequenz-floss/frequenz-channels-pytyhon"
40+
Issues = "https://github.com/frequenz-floss/frequenz-channels-pytyhon/issues"
41+
Support = "https://github.com/frequenz-floss/frequenz-channels-pytyhon/discussions/categories/support"
42+
43+
[tool.setuptools]
44+
include-package-data = true
45+
46+
[tool.setuptools_scm]
47+
version_scheme = "post-release"
48+
949
[tool.pylint.similarities]
1050
ignore-comments=['yes']
1151
ignore-docstrings=['yes']
@@ -18,9 +58,6 @@ disable = ["too-few-public-methods", "wrong-import-order", "ungrouped-imports"]
1858
[tool.pylint.'DESIGN']
1959
max-attributes=12
2060

21-
[tool.setuptools_scm]
22-
version_scheme = "post-release"
23-
2461
[tool.isort]
2562
profile = "black"
2663
line_length = 88

setup.cfg

Lines changed: 0 additions & 18 deletions
This file was deleted.

0 commit comments

Comments
 (0)