You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@fluss.apache.org by ja...@apache.org on 2026/09/18 02:10:36 UTC
(fluss) branch release-1.0 updated: [build] Give Python release candidates distinct versions (#4412)
This is an automated email from the ASF dual-hosted git repository.
wuchong pushed a commit to branch release-1.0
in repository https://gitbox.apache.org/repos/asf/fluss.git
The following commit(s) were added to refs/heads/release-1.0 by this push:
new e25f7464ff [build] Give Python release candidates distinct versions (#4412)
e25f7464ff is described below
commit e25f7464fffe5dc0e84efcdd071c2de2360a3b54
Author: Jark Wu <ja...@apache.org>
AuthorDate: Fri Sep 18 10:10:32 2026 +0800
[build] Give Python release candidates distinct versions (#4412)
---
.github/workflows/python-release.yml | 12 +++++
fluss-rust/bindings/python/DEVELOPMENT.md | 7 +++
tools/releasing/set_python_release_version.py | 63 +++++++++++++++++++++++++++
3 files changed, 82 insertions(+)
diff --git a/.github/workflows/python-release.yml b/.github/workflows/python-release.yml
index dc58d892e6..c6fa693caa 100644
--- a/.github/workflows/python-release.yml
+++ b/.github/workflows/python-release.yml
@@ -48,6 +48,12 @@ jobs:
needs: [version-check]
steps:
- uses: actions/checkout@v6
+ - name: Set Python release version
+ shell: bash
+ env:
+ RELEASE_TAG: ${{ github.ref_name }}
+ run: python tools/releasing/set_python_release_version.py "$RELEASE_TAG"
+
- uses: dtolnay/rust-toolchain@4cda84d5c5c54efe2404f9d843567869ab1699d4
with:
toolchain: stable
@@ -80,6 +86,12 @@ jobs:
- { os: ubuntu-latest, target: "aarch64", manylinux: "manylinux_2_28", license-target: "aarch64-unknown-linux-gnu" }
steps:
- uses: actions/checkout@v6
+ - name: Set Python release version
+ shell: bash
+ env:
+ RELEASE_TAG: ${{ github.ref_name }}
+ run: python tools/releasing/set_python_release_version.py "$RELEASE_TAG"
+
- uses: dtolnay/rust-toolchain@4cda84d5c5c54efe2404f9d843567869ab1699d4
with:
toolchain: stable
diff --git a/fluss-rust/bindings/python/DEVELOPMENT.md b/fluss-rust/bindings/python/DEVELOPMENT.md
index 8a916ce4e9..c756b796bb 100644
--- a/fluss-rust/bindings/python/DEVELOPMENT.md
+++ b/fluss-rust/bindings/python/DEVELOPMENT.md
@@ -92,6 +92,13 @@ uv run pdoc fluss
## Release
+The tag-triggered Python release workflow publishes each release candidate to
+TestPyPI with its own PEP 440 version: `v1.0.0-rc3` builds `pyfluss==1.0.0rc3`.
+Before building both the sdist and wheels, it sets the Python package version in
+`pyproject.toml`; Rust workspace versions and lockfiles remain unchanged. The
+sdist retains this version when rebuilt. Final tags such as `v1.0.0` keep the
+Cargo-derived `1.0.0` version and publish to PyPI.
+
```bash
# Build wheel
uv run maturin build --release
diff --git a/tools/releasing/set_python_release_version.py b/tools/releasing/set_python_release_version.py
new file mode 100644
index 0000000000..14cf5ae4ff
--- /dev/null
+++ b/tools/releasing/set_python_release_version.py
@@ -0,0 +1,63 @@
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+
+"""Give each TestPyPI candidate its own version before running maturin."""
+
+import argparse
+import re
+from pathlib import Path
+
+
+def set_release_version(pyproject: Path, tag: str) -> str:
+ """Set PEP 440 RC metadata; final releases keep the Cargo-derived version."""
+ match = re.fullmatch(r"v([0-9]+\.[0-9]+\.[0-9]+)(?:-rc\.?([0-9]+))?", tag)
+ if match is None:
+ raise ValueError(f"Expected vX.Y.Z or vX.Y.Z-rcN, got {tag!r}")
+
+ version, candidate = match.groups()
+ if candidate is None:
+ return version
+
+ version = f"{version}rc{int(candidate)}"
+ content = pyproject.read_text(encoding="utf-8")
+ # Keep the Rust workspace and lockfile at the final version. Static Python
+ # metadata takes precedence in maturin and survives rebuilding the sdist.
+ content, count = re.subn(
+ r'^dynamic[ \t]*=[ \t]*\["version"\][ \t]*$',
+ f'version = "{version}"',
+ content,
+ flags=re.MULTILINE,
+ )
+ if count != 1:
+ raise ValueError(f"Expected exactly one dynamic version field in {pyproject}")
+ pyproject.write_text(content, encoding="utf-8")
+ return version
+
+
+def main() -> None:
+ parser = argparse.ArgumentParser(description=__doc__)
+ parser.add_argument("tag", help="Release tag already checked against Cargo.toml")
+ args = parser.parse_args()
+ root = Path(__file__).resolve().parents[2]
+ version = set_release_version(
+ root / "fluss-rust/bindings/python/pyproject.toml", args.tag
+ )
+ print(f"Python distribution version: {version}")
+
+
+if __name__ == "__main__":
+ main()