This is an automated email from the ASF dual-hosted git repository.
JingsongLi pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/paimon-mosaic.git
The following commit(s) were added to refs/heads/main by this push:
new d481ff1 Prepare release yml and tools (#11)
d481ff1 is described below
commit d481ff1628ce97894b02b637314e2e13354b2c21
Author: Jingsong Lee <[email protected]>
AuthorDate: Wed May 20 13:54:18 2026 +0800
Prepare release yml and tools (#11)
---
.github/workflows/publish_snapshot.yml | 91 +++++++++++++--
.github/workflows/release-cpp.yml | 105 +++++++++++++++++
.github/workflows/release-java.yml | 145 +++++++++++++++++++++++
.github/workflows/release-python.yml | 195 +++++++++++++++++++++++++++++++
.github/workflows/release-rust.yml | 54 +++++++++
python/setup.py | 27 ++++-
tools/releasing/create_release_branch.sh | 57 +++++++++
tools/releasing/create_source_release.sh | 77 ++++++++++++
tools/releasing/update_branch_version.sh | 66 +++++++++++
9 files changed, 803 insertions(+), 14 deletions(-)
diff --git a/.github/workflows/publish_snapshot.yml
b/.github/workflows/publish_snapshot.yml
index 947fdc1..bdae106 100644
--- a/.github/workflows/publish_snapshot.yml
+++ b/.github/workflows/publish_snapshot.yml
@@ -30,12 +30,39 @@ concurrency:
cancel-in-progress: true
jobs:
- publish-snapshot:
- if: github.repository == 'apache/paimon-mosaic'
- runs-on: ubuntu-latest
+ build-native:
+ runs-on: ${{ matrix.os }}
+ strategy:
+ fail-fast: false
+ matrix:
+ include:
+ - os: ubuntu-latest
+ target: x86_64-unknown-linux-gnu
+ os_name: linux
+ arch: x86_64
+ lib_name: libmosaic_jni.so
+ - os: ubuntu-24.04-arm
+ target: aarch64-unknown-linux-gnu
+ os_name: linux
+ arch: aarch64
+ lib_name: libmosaic_jni.so
+ - os: macos-13
+ target: x86_64-apple-darwin
+ os_name: macos
+ arch: x86_64
+ lib_name: libmosaic_jni.dylib
+ - os: macos-latest
+ target: aarch64-apple-darwin
+ os_name: macos
+ arch: aarch64
+ lib_name: libmosaic_jni.dylib
+ - os: windows-latest
+ target: x86_64-pc-windows-msvc
+ os_name: windows
+ arch: x86_64
+ lib_name: mosaic_jni.dll
steps:
- - name: Checkout code
- uses: actions/checkout@v4
+ - uses: actions/checkout@v4
- name: Setup Rust toolchain
run: |
@@ -49,18 +76,58 @@ jobs:
~/.cargo/registry
~/.cargo/git
target
- key: ${{ runner.os }}-cargo-${{ hashFiles('**/Cargo.lock') }}
+ key: ${{ runner.os }}-${{ matrix.target }}-cargo-${{
hashFiles('**/Cargo.lock') }}
restore-keys: |
- ${{ runner.os }}-cargo-
+ ${{ runner.os }}-${{ matrix.target }}-cargo-
- name: Build JNI library
run: cargo build --release -p mosaic-jni
- - name: Prepare native resources
- run: |
- RESOURCE_DIR=java/src/main/resources/native/linux/x86_64
- mkdir -p "$RESOURCE_DIR"
- cp target/release/libmosaic_jni.so "$RESOURCE_DIR/"
+ - name: Upload native library
+ uses: actions/upload-artifact@v4
+ with:
+ name: native-${{ matrix.os_name }}-${{ matrix.arch }}
+ path: target/release/${{ matrix.lib_name }}
+
+ publish-snapshot:
+ if: github.repository == 'apache/paimon-mosaic'
+ runs-on: ubuntu-latest
+ needs: [build-native]
+ steps:
+ - uses: actions/checkout@v4
+
+ - name: Download linux x86_64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-linux-x86_64
+ path: java/src/main/resources/native/linux/x86_64
+
+ - name: Download linux aarch64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-linux-aarch64
+ path: java/src/main/resources/native/linux/aarch64
+
+ - name: Download macOS x86_64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-macos-x86_64
+ path: java/src/main/resources/native/macos/x86_64
+
+ - name: Download macOS aarch64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-macos-aarch64
+ path: java/src/main/resources/native/macos/aarch64
+
+ - name: Download windows x86_64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-windows-x86_64
+ path: java/src/main/resources/native/windows/x86_64
+
+ - name: Verify native libraries
+ run: find java/src/main/resources/native -type f | sort
- name: Set up JDK ${{ env.JDK_VERSION }}
uses: actions/setup-java@v4
diff --git a/.github/workflows/release-cpp.yml
b/.github/workflows/release-cpp.yml
new file mode 100644
index 0000000..b01020a
--- /dev/null
+++ b/.github/workflows/release-cpp.yml
@@ -0,0 +1,105 @@
+# 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.
+
+# Build and publish C/C++ SDK as GitHub Release assets.
+#
+# Trigger: push a version tag (e.g. v0.1.0, v0.1.0-rc1).
+# Creates a GitHub Release with per-platform tarballs containing headers +
shared library.
+
+name: Release C++
+
+on:
+ push:
+ tags:
+ - "v[0-9]+.[0-9]+.[0-9]+"
+ - "v[0-9]+.[0-9]+.[0-9]+-rc[0-9]+"
+ workflow_dispatch:
+
+permissions:
+ contents: write
+
+jobs:
+ build:
+ runs-on: ${{ matrix.os }}
+ strategy:
+ fail-fast: false
+ matrix:
+ include:
+ - os: ubuntu-latest
+ target: x86_64-unknown-linux-gnu
+ lib_name: libmosaic_ffi.so
+ archive_suffix: linux-x86_64
+ - os: ubuntu-24.04-arm
+ target: aarch64-unknown-linux-gnu
+ lib_name: libmosaic_ffi.so
+ archive_suffix: linux-aarch64
+ - os: macos-13
+ target: x86_64-apple-darwin
+ lib_name: libmosaic_ffi.dylib
+ archive_suffix: macos-x86_64
+ - os: macos-latest
+ target: aarch64-apple-darwin
+ lib_name: libmosaic_ffi.dylib
+ archive_suffix: macos-aarch64
+ steps:
+ - uses: actions/checkout@v6
+
+ - name: Setup Rust toolchain
+ run: |
+ rustup update stable
+ rustup default stable
+
+ - name: Build FFI library
+ run: cargo build --release -p mosaic-ffi
+
+ - name: Package tarball
+ shell: bash
+ run: |
+ VERSION=${GITHUB_REF_NAME:-dev}
+ ARCHIVE_NAME="mosaic-cpp-${VERSION}-${{ matrix.archive_suffix }}"
+ mkdir -p "$ARCHIVE_NAME/lib" "$ARCHIVE_NAME/include"
+ cp include/mosaic.h include/mosaic.hpp include/arrow_c_data.h
"$ARCHIVE_NAME/include/"
+ cp target/release/${{ matrix.lib_name }} "$ARCHIVE_NAME/lib/"
+ tar czf "${ARCHIVE_NAME}.tar.gz" "$ARCHIVE_NAME"
+
+ - name: Upload tarball
+ uses: actions/upload-artifact@v7
+ with:
+ name: cpp-${{ matrix.archive_suffix }}
+ path: "*.tar.gz"
+
+ release:
+ needs: build
+ runs-on: ubuntu-latest
+ if: startsWith(github.ref, 'refs/tags/')
+ steps:
+ - uses: actions/download-artifact@v8
+ with:
+ pattern: cpp-*
+ merge-multiple: true
+ path: dist
+
+ - name: Create GitHub Release
+ env:
+ GH_TOKEN: ${{ github.token }}
+ TAG: ${{ github.ref_name }}
+ run: |
+ gh release create "$TAG" \
+ --repo "${{ github.repository }}" \
+ --title "Release $TAG" \
+ --generate-notes \
+ dist/*.tar.gz
diff --git a/.github/workflows/release-java.yml
b/.github/workflows/release-java.yml
new file mode 100644
index 0000000..b00f51a
--- /dev/null
+++ b/.github/workflows/release-java.yml
@@ -0,0 +1,145 @@
+################################################################################
+# 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.
+################################################################################
+
+name: Release Java
+
+on:
+ push:
+ tags:
+ - "v[0-9]+.[0-9]+.[0-9]+"
+ - "v[0-9]+.[0-9]+.[0-9]+-rc[0-9]+"
+ workflow_dispatch:
+
+env:
+ JDK_VERSION: 8
+
+concurrency:
+ group: ${{ github.workflow }}-${{ github.ref }}
+ cancel-in-progress: true
+
+jobs:
+ build-native:
+ runs-on: ${{ matrix.os }}
+ strategy:
+ fail-fast: false
+ matrix:
+ include:
+ - os: ubuntu-latest
+ target: x86_64-unknown-linux-gnu
+ os_name: linux
+ arch: x86_64
+ lib_name: libmosaic_jni.so
+ - os: ubuntu-24.04-arm
+ target: aarch64-unknown-linux-gnu
+ os_name: linux
+ arch: aarch64
+ lib_name: libmosaic_jni.so
+ - os: macos-13
+ target: x86_64-apple-darwin
+ os_name: macos
+ arch: x86_64
+ lib_name: libmosaic_jni.dylib
+ - os: macos-latest
+ target: aarch64-apple-darwin
+ os_name: macos
+ arch: aarch64
+ lib_name: libmosaic_jni.dylib
+ - os: windows-latest
+ target: x86_64-pc-windows-msvc
+ os_name: windows
+ arch: x86_64
+ lib_name: mosaic_jni.dll
+ steps:
+ - uses: actions/checkout@v4
+
+ - name: Setup Rust toolchain
+ run: |
+ rustup update stable
+ rustup default stable
+
+ - name: Build JNI library
+ run: cargo build --release -p mosaic-jni
+
+ - name: Upload native library
+ uses: actions/upload-artifact@v4
+ with:
+ name: native-${{ matrix.os_name }}-${{ matrix.arch }}
+ path: target/release/${{ matrix.lib_name }}
+
+ deploy-staging:
+ if: github.repository == 'apache/paimon-mosaic' && startsWith(github.ref,
'refs/tags/')
+ runs-on: ubuntu-latest
+ needs: [build-native]
+ steps:
+ - uses: actions/checkout@v4
+
+ - name: Download linux x86_64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-linux-x86_64
+ path: java/src/main/resources/native/linux/x86_64
+
+ - name: Download linux aarch64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-linux-aarch64
+ path: java/src/main/resources/native/linux/aarch64
+
+ - name: Download macOS x86_64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-macos-x86_64
+ path: java/src/main/resources/native/macos/x86_64
+
+ - name: Download macOS aarch64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-macos-aarch64
+ path: java/src/main/resources/native/macos/aarch64
+
+ - name: Download windows x86_64 native library
+ uses: actions/download-artifact@v4
+ with:
+ name: native-windows-x86_64
+ path: java/src/main/resources/native/windows/x86_64
+
+ - name: Verify native libraries
+ run: find java/src/main/resources/native -type f | sort
+
+ - name: Set up JDK ${{ env.JDK_VERSION }}
+ uses: actions/setup-java@v4
+ with:
+ java-version: ${{ env.JDK_VERSION }}
+ distribution: 'temurin'
+ server-id: apache.releases.https
+ server-username: MAVEN_USERNAME
+ server-password: MAVEN_PASSWORD
+ gpg-private-key: ${{ secrets.GPG_SECRET_KEY }}
+ gpg-passphrase: MAVEN_GPG_PASSPHRASE
+
+ - name: Deploy to Apache Nexus staging
+ working-directory: java
+ run: |
+ mvn clean deploy \
+ -Prelease \
+ -DskipTests \
+ -DretryFailedDeploymentCount=10
+ env:
+ MAVEN_USERNAME: ${{ secrets.NEXUS_STAGE_DEPLOYER_USER }}
+ MAVEN_PASSWORD: ${{ secrets.NEXUS_STAGE_DEPLOYER_PW }}
+ MAVEN_GPG_PASSPHRASE: ${{ secrets.GPG_PASSPHRASE }}
diff --git a/.github/workflows/release-python.yml
b/.github/workflows/release-python.yml
new file mode 100644
index 0000000..8ed5a34
--- /dev/null
+++ b/.github/workflows/release-python.yml
@@ -0,0 +1,195 @@
+# 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.
+
+# Publish the mosaic-format Python package to PyPI.
+#
+# Trigger: push a version tag (e.g. v0.1.0, v0.1.0-rc1).
+# Pre-release tags (containing '-') publish to TestPyPI; release tags publish
to PyPI.
+#
+# Token auth: add secrets PYPI_API_TOKEN / TEST_PYPI_API_TOKEN for publishing.
+
+name: Release Python
+
+on:
+ push:
+ tags:
+ - "v[0-9]+.[0-9]+.[0-9]+"
+ - "v[0-9]+.[0-9]+.[0-9]+-rc[0-9]+"
+ workflow_dispatch:
+
+concurrency:
+ group: ${{ github.workflow }}-${{ github.ref }}-${{ github.event_name }}
+ cancel-in-progress: true
+
+permissions:
+ contents: read
+
+jobs:
+ wheels-linux:
+ runs-on: ${{ matrix.os }}
+ strategy:
+ fail-fast: false
+ matrix:
+ include:
+ - os: ubuntu-latest
+ arch: x86_64
+ - os: ubuntu-24.04-arm
+ arch: aarch64
+ steps:
+ - uses: actions/checkout@v4
+
+ - name: Set up Python
+ uses: actions/setup-python@v5
+ with:
+ python-version: "3.12"
+
+ - name: Build wheels via cibuildwheel
+ uses: pypa/[email protected]
+ with:
+ package-dir: python
+ output-dir: wheelhouse
+ env:
+ CIBW_BUILD: "cp39-manylinux_${{ matrix.arch }}"
+ CIBW_MANYLINUX_X86_64_IMAGE: manylinux_2_28
+ CIBW_MANYLINUX_AARCH64_IMAGE: manylinux_2_28
+ CIBW_BEFORE_ALL_LINUX: >
+ curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh -s
-- -y &&
+ source $HOME/.cargo/env &&
+ cargo build --release -p mosaic-ffi &&
+ cp target/release/libmosaic_ffi.so {package}/mosaic/
+
+ - name: Upload wheels
+ uses: actions/upload-artifact@v4
+ with:
+ name: wheels-linux-${{ matrix.arch }}
+ path: wheelhouse/*.whl
+
+ wheels-macos:
+ runs-on: ${{ matrix.os }}
+ strategy:
+ fail-fast: false
+ matrix:
+ include:
+ - os: macos-13
+ target: x86_64-apple-darwin
+ lib_name: libmosaic_ffi.dylib
+ - os: macos-latest
+ target: aarch64-apple-darwin
+ lib_name: libmosaic_ffi.dylib
+ steps:
+ - uses: actions/checkout@v4
+
+ - name: Setup Rust toolchain
+ run: |
+ rustup update stable
+ rustup default stable
+
+ - name: Build native library
+ run: cargo build --release -p mosaic-ffi
+
+ - name: Copy native library into package
+ run: cp target/release/${{ matrix.lib_name }} python/mosaic/
+
+ - name: Set up Python
+ uses: actions/setup-python@v5
+ with:
+ python-version: "3.12"
+
+ - name: Install build tools
+ run: pip install build wheel setuptools delocate
+
+ - name: Build wheel
+ working-directory: python
+ run: python -m build --wheel
+
+ - name: Repair wheel
+ run: |
+ delocate-wheel -w python/dist/repaired python/dist/*.whl
+ rm python/dist/*.whl
+ mv python/dist/repaired/*.whl python/dist/
+
+ - name: Upload wheel
+ uses: actions/upload-artifact@v4
+ with:
+ name: wheels-${{ matrix.os }}-${{ matrix.target }}
+ path: python/dist/*.whl
+
+ wheels-windows:
+ runs-on: windows-latest
+ steps:
+ - uses: actions/checkout@v4
+
+ - name: Setup Rust toolchain
+ run: |
+ rustup update stable
+ rustup default stable
+
+ - name: Build native library
+ run: cargo build --release -p mosaic-ffi
+
+ - name: Copy native library into package
+ shell: bash
+ run: cp target/release/mosaic_ffi.dll python/mosaic/
+
+ - name: Set up Python
+ uses: actions/setup-python@v5
+ with:
+ python-version: "3.12"
+
+ - name: Install build tools
+ run: pip install build wheel setuptools
+
+ - name: Build wheel
+ working-directory: python
+ run: python -m build --wheel
+
+ - name: Upload wheel
+ uses: actions/upload-artifact@v4
+ with:
+ name: wheels-windows-x86_64
+ path: python/dist/*.whl
+
+ release:
+ name: Publish to PyPI
+ runs-on: ubuntu-latest
+ permissions:
+ contents: read
+ needs: [wheels-linux, wheels-macos, wheels-windows]
+ if: startsWith(github.ref, 'refs/tags/')
+ steps:
+ - uses: actions/download-artifact@v4
+ with:
+ pattern: wheels-*
+ merge-multiple: true
+ path: dist
+
+ - name: Publish to TestPyPI
+ if: contains(github.ref, '-')
+ uses: pypa/gh-action-pypi-publish@release/v1
+ with:
+ repository-url: https://test.pypi.org/legacy/
+ skip-existing: true
+ packages-dir: dist
+ password: ${{ secrets.TEST_PYPI_API_TOKEN }}
+
+ - name: Publish to PyPI
+ if: ${{ !contains(github.ref, '-') }}
+ uses: pypa/gh-action-pypi-publish@release/v1
+ with:
+ skip-existing: true
+ packages-dir: dist
+ password: ${{ secrets.PYPI_API_TOKEN }}
diff --git a/.github/workflows/release-rust.yml
b/.github/workflows/release-rust.yml
new file mode 100644
index 0000000..13d8331
--- /dev/null
+++ b/.github/workflows/release-rust.yml
@@ -0,0 +1,54 @@
+# 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.
+
+# Publish mosaic-core crate to crates.io.
+#
+# Trigger: push a version tag (e.g. v0.1.0, v0.1.0-rc1).
+# Pre-release tags (containing '-') only run dry-run checks without publishing.
+#
+# Token auth: add secret CARGO_REGISTRY_TOKEN for crates.io publishing.
+
+name: Release Rust
+
+on:
+ push:
+ tags:
+ - "v[0-9]+.[0-9]+.[0-9]+"
+ - "v[0-9]+.[0-9]+.[0-9]+-rc[0-9]+"
+ workflow_dispatch:
+
+jobs:
+ publish:
+ runs-on: ubuntu-latest
+ permissions:
+ contents: read
+ steps:
+ - uses: actions/checkout@v6
+
+ - name: Setup Rust toolchain
+ run: |
+ rustup update stable
+ rustup default stable
+
+ - name: Dry run
+ run: cargo publish -p mosaic-core --dry-run
+
+ - name: Publish mosaic-core to crates.io
+ if: startsWith(github.ref, 'refs/tags/') && !contains(github.ref, '-')
+ run: cargo publish -p mosaic-core
+ env:
+ CARGO_REGISTRY_TOKEN: ${{ secrets.CARGO_REGISTRY_TOKEN }}
diff --git a/python/setup.py b/python/setup.py
index 9c8724f..0725345 100644
--- a/python/setup.py
+++ b/python/setup.py
@@ -21,8 +21,9 @@ import os
import platform
import shutil
-from setuptools import setup
+from setuptools import Distribution, setup
from setuptools.command.build_py import build_py
+from wheel.bdist_wheel import bdist_wheel
def _lib_name():
@@ -63,4 +64,26 @@ class BuildPyWithNativeLib(build_py):
super().run()
-setup(cmdclass={"build_py": BuildPyWithNativeLib})
+class PlatformWheel(bdist_wheel):
+ """Tag wheel as py3-none-{platform} since this is a ctypes package."""
+
+ def finalize_options(self):
+ bdist_wheel.finalize_options(self)
+ self.root_is_pure = False
+
+ def get_tag(self):
+ _, _, plat = bdist_wheel.get_tag(self)
+ return "py3", "none", plat
+
+
+class BinaryDistribution(Distribution):
+ """Force the wheel to be platform-specific."""
+
+ def has_ext_modules(self):
+ return True
+
+
+setup(
+ cmdclass={"build_py": BuildPyWithNativeLib, "bdist_wheel": PlatformWheel},
+ distclass=BinaryDistribution,
+)
diff --git a/tools/releasing/create_release_branch.sh
b/tools/releasing/create_release_branch.sh
new file mode 100755
index 0000000..71fd87c
--- /dev/null
+++ b/tools/releasing/create_release_branch.sh
@@ -0,0 +1,57 @@
+#!/usr/bin/env bash
+
+#
+# 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.
+#
+
+##
+## Variables with defaults (if not overwritten by environment)
+##
+RELEASE_CANDIDATE=${RELEASE_CANDIDATE:-none}
+MVN=${MVN:-mvn}
+
+# fail immediately
+set -o errexit
+set -o nounset
+# print command before executing
+set -o xtrace
+
+CURR_DIR=`pwd`
+if [[ `basename ${CURR_DIR}` != "tools" ]] ; then
+ echo "You have to call the script from the tools/ dir"
+ exit 1
+fi
+
+###########################
+
+if [ -z "${RELEASE_VERSION}" ]; then
+ echo "RELEASE_VERSION is unset"
+ exit 1
+fi
+
+cd ..
+
+target_branch=release-${RELEASE_VERSION}
+if [ "${RELEASE_CANDIDATE}" != "none" ]; then
+ target_branch=${target_branch}-rc${RELEASE_CANDIDATE}
+fi
+
+git checkout -b ${target_branch}
+
+RELEASE_HASH=`git rev-parse HEAD`
+echo "Echo created release hash $RELEASE_HASH"
+
+echo "Done. Don't forget to create the release tag on GitHub and push the
changes."
diff --git a/tools/releasing/create_source_release.sh
b/tools/releasing/create_source_release.sh
new file mode 100755
index 0000000..816a775
--- /dev/null
+++ b/tools/releasing/create_source_release.sh
@@ -0,0 +1,77 @@
+#!/usr/bin/env bash
+
+#
+# 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.
+#
+
+##
+## Variables with defaults (if not overwritten by environment)
+##
+MVN=${MVN:-mvn}
+
+# fail immediately
+set -o errexit
+set -o nounset
+# print command before executing
+set -o xtrace
+
+CURR_DIR=`pwd`
+if [[ `basename $CURR_DIR` != "tools" ]] ; then
+ echo "You have to call the script from the tools/ dir"
+ exit 1
+fi
+
+if [ "$(uname)" == "Darwin" ]; then
+ SHASUM="shasum -a 512"
+else
+ SHASUM="sha512sum"
+fi
+
+###########################
+
+RELEASE_VERSION=${RELEASE_VERSION}
+
+if [ -z "${RELEASE_VERSION}" ]; then
+ echo "RELEASE_VERSION is unset"
+ exit 1
+fi
+
+rm -rf release
+mkdir release
+cd ..
+
+echo "Creating source package"
+
+# create a temporary git clone to ensure that we have a pristine source release
+git clone . tools/release/paimon-mosaic-tmp-clone
+cd tools/release/paimon-mosaic-tmp-clone
+
+trap 'cd ${CURR_DIR};rm -rf release' ERR
+
+rsync -a \
+ --exclude ".git" --exclude ".gitignore" --exclude ".gitattributes" \
+ --exclude ".asf.yaml" --exclude ".github" \
+ --exclude "deploysettings.xml" --exclude "target" \
+ --exclude ".idea" --exclude "*.iml" --exclude ".DS_Store" \
+ . paimon-mosaic-$RELEASE_VERSION
+
+tar czf apache-paimon-mosaic-${RELEASE_VERSION}-src.tgz
paimon-mosaic-$RELEASE_VERSION
+gpg --armor --detach-sig apache-paimon-mosaic-$RELEASE_VERSION-src.tgz
+$SHASUM apache-paimon-mosaic-$RELEASE_VERSION-src.tgz >
apache-paimon-mosaic-$RELEASE_VERSION-src.tgz.sha512
+
+mv apache-paimon-mosaic-$RELEASE_VERSION-src.* ../
+cd ..
+rm -rf paimon-mosaic-tmp-clone
diff --git a/tools/releasing/update_branch_version.sh
b/tools/releasing/update_branch_version.sh
new file mode 100755
index 0000000..31e591f
--- /dev/null
+++ b/tools/releasing/update_branch_version.sh
@@ -0,0 +1,66 @@
+#!/usr/bin/env bash
+
+#
+# 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.
+#
+
+##
+## Variables with defaults (if not overwritten by environment)
+##
+MVN=${MVN:-mvn}
+
+# fail immediately
+set -o errexit
+set -o nounset
+# print command before executing
+set -o xtrace
+
+CURR_DIR=`pwd`
+if [[ `basename $CURR_DIR` != "tools" ]] ; then
+ echo "You have to call the script from the tools/ dir"
+ exit 1
+fi
+
+###########################
+
+OLD_VERSION=${OLD_VERSION}
+NEW_VERSION=${NEW_VERSION}
+
+
+if [ -z "${OLD_VERSION}" ]; then
+ echo "OLD_VERSION is unset"
+ exit 1
+fi
+
+if [ -z "${NEW_VERSION}" ]; then
+ echo "NEW_VERSION is unset"
+ exit 1
+fi
+
+cd ..
+
+#change version in all pom files
+find . -name 'pom.xml' -type f -exec perl -pi -e
's#<version>'$OLD_VERSION'</version>#<version>'$NEW_VERSION'</version>#' {} \;
+
+#change version in Cargo.toml files
+find . -name 'Cargo.toml' -not -path '*/target/*' -type f -exec perl -pi -e
's#^version = "'$OLD_VERSION'"#version = "'$NEW_VERSION'"#' {} \;
+
+#change version in pyproject.toml
+perl -pi -e 's#^version = "'$OLD_VERSION'"#version = "'$NEW_VERSION'"#'
python/pyproject.toml
+
+git commit -am "Update version to $NEW_VERSION"
+
+echo "Don't forget to push the change."