Release management
This document explains how CESNET manages releases of Invenio- and OArepo-related packages, and what to do for each release type.
Package layers
invenio-app-rdm
CESNET Invenio is built on InvenioRDM packages, with invenio-app-rdm as the root package.
In the InvenioRDM ecosystem, dependencies follow pinned major versions.
For example, if invenio-app-rdm depends on invenio-rdm-records, the requirement looks like:
invenio-rdm-records>=12.3.0,<13.0.0
CESNET patches to invenio-* packages
CESNET patches invenio-app-rdm and other Invenio packages to add CESNET features (for example, multiple models and workflows).
These patched packages keep the same package names (for example, invenio-rdm-records) but are published to the CESNET pip registry , not global PyPI.
Patched versions use a suffix such as:
27.0.0+oarepo.3.3yojwri2nobgwy5x
Meaning:
- base upstream version:
27.0.0 - CESNET patch number:
3 - trailing hash: identifies the exact CESNET patch set
oarepo package
After patching, CESNET publishes oarepo to the CESNET pip registry.
This package contains fully pinned dependencies, so installing a specific oarepo version always produces the same dependency set (Invenio packages + CESNET patches).
oarepo versioning tracks invenio-app-rdm. Example:
14.2.1b9.dev0+6.rdm.14.0.0b9.dev0
This means it is the 6th build based on invenio-app-rdm==14.0.0b9.dev0.
Because CESNET changes can be backward-incompatible, these rules apply:
- major version follows
invenio-app-rdmmajor version - minor version increases when:
- CESNET introduces backward-incompatible changes (only during upstream development), or
invenio-app-rdmincreases its minor version
- patch version increases when:
- upstream patch version increases, or
- CESNET patch content changes
oarepo-* packages
Extra CESNET functionality (for example, multiple metadata schemas, vocabulary hierarchy, workflows) is delivered via oarepo-* packages.
These packages follow semantic versioning:
- major = backward-incompatible change
- minor = new feature or larger backward-compatible change
- patch = bugfix/chore
If an oarepo-* package depends on a package whose major version changes, CESNET applies a release train and bumps the dependent package’s major version as well.
For example, oarepo-vocabularies dependencies:
[project]
name = "oarepo-vocabularies"
version = "4.0.0"
dependencies = [
"oarepo[rdm,tests]>=14,<15",
"oarepo-runtime>=3.0.0,<4.0.0",
"oarepo-ui>=8.0.0,<9.0.0",
# invenio dependencies
"invenio-search>=3.0.0,<4.0.0",
"invenio-vocabularies>=11.0.0,<12.0.0",
]If invenio-vocabularies moves from 11 to 12, oarepo-vocabularies moves from 4 to 5.
Likewise, if oarepo-ui moves from 8 to 9, oarepo-vocabularies major version also increases.
oarepo-app package
oarepo-app combines:
oarepo(pinned Invenio stack)- CESNET extensions (
oarepo-*packages)
Its major version changes whenever the major version of any core invenio-* or oarepo-* dependency changes.
oarepo-app has two variants:
- development
Pins only major versions of CESNET packages. Useful for active development because newer compatible versions are installed. - production
Fully pins CESNET and Invenio packages. Intended for production repositories that prioritize stability.
Repositories typically include both oarepo and oarepo-app as a consistency check:
[project]
name = "datarepo"
version = "1.0.0"
dependencies = [
"oarepo[s3,rdm]>=14.0.0,<15.0.0",
"oarepo-app[development]>=1.0.0,<2.0.0",
]
requires-python = ">=3.14,<3.15"oarepo-app provides an extensive changelog covering Invenio and CESNET package changes since the previous oarepo-app release.
The link above points to rdm-14; switch branches for other InvenioRDM versions.
Compatibility matrix
oarepo-app version | oarepo version | invenio-app-rdm version | Suggested range |
|---|---|---|---|
| 1.0.0 | 14.2.1b9.dev0 | 14.0.0b9.dev0 | oarepo[s3,rdm]>=14.0.0,<15.0.0 |
oarepo-app[production]>=1.0.0,<2.0.0 | |||
python>=3.14,<3.15 |
Release train reference (step-by-step)
For oarepo-* PRs, always check whether the PR introduces a new dependency on InvenioRDM or another oarepo-* package.
If yes, treat it as a major release.
Always run the testrig with your PRs, even if the PR only includes patch-level changes.
It usually takes about 30 minutes, but it can prevent broken releases.
1) Release oarepo (base of the train)
- Open invenio-integration-tests workflow .
- Click Run workflow.
- Select the correct branch and Python version.
- Start the workflow.
The workflow will:
- download and patch Invenio packages with CESNET patches
- run the testrig for patched packages
- run API tests on a reference InvenioRDM repository
- run smoke UI tests on a reference InvenioRDM repository
- create and publish a new
oarepoversion
Potential problem: patches cannot be applied to an Invenio package
If patch application fails, follow this sequence:
- In the workflow output, identify the failing package (for example,
invenio-communities). - Clone the package repository:
gh repo clone oarepo/invenio-communities - Check out the upstream tag used by the release:
git checkout vX.Y.Z - Switch to the existing feature branch:
git switch oarepo-feature-featurename - Create a new branch rebased for the new upstream tag:
git switch -c oarepo-feature-featurename-from-X.Y.Z - Rebase onto the upstream tag:
git rebase vX.Y.Z - Resolve conflicts, then commit and push the new branch.
Next, update the feature branch reference in oarepo/invenio-integration-tests. Example:
- name: invenio-communities
features:
# updated branch for newer upstream base
- name: oarepo-feature-disable-communities-ui-from-25.0.0
base: v25.0.0
invenio-version: ">=25.0.0"
# original branch kept for older base
- name: oarepo-feature-disable-communities-ui
base: v21.0.0
# added version constraint here so that it is not used for >=25.0.0
invenio-version: ">=21.0.0,<25.0.0"After updating invenio-forks.yaml, re-run the workflow.
2) Release oarepo-* packages
OARepo packages must declare version-ranged dependencies for both:
- other
oarepo-*packages they use - Invenio packages referenced in source imports or tests
Dependencies used only in tests must be placed in the tests optional dependency group in pyproject.toml. For example:
[project]
name = "oarepo-vocabularies"
version = "4.0.0"
dependencies = [
"oarepo[rdm,tests]>=14,<15",
"oarepo-runtime>=3.0.0,<4.0.0",
"oarepo-ui>=8.0.0,<9.0.0",
# invenio dependencies referenced from sources
"invenio-search>=3.0.0,<4.0.0",
"invenio-vocabularies>=11.0.0,<12.0.0",
]
[project.optional-dependencies]
tests = [
# extra invenio dependencies referenced from tests
"invenio-app>=3.0.0,<4.0.0",
]Use resolve_invenio.sh to get a list of Invenio packages and recommended version ranges for dependency declarations. Whenever you add a new import, run this tool to check whether a new dependency is required.
patch release (vX.Y.Z)
Use this for bug fixes and chores.
- Create a PR with the change.
- Get approval and merge.
- Create a GitHub release with tag
vX.Y.Z:- keep
X.Yunchanged - increment
Z
- keep
- The release is created by the person who approved and merged the PR.
minor release (vX.Y.0)
Use this for backward-compatible new features.
- Create a PR with the change.
- Get approval and merge.
- Create a GitHub release with tag
vX.Y.0:- keep
Xunchanged - increment
Y - reset patch to
0
- keep
- The release is created by the person who approved and merged the PR.
major release (vX.0.0)
Use this for backward-incompatible changes or release-train dependency propagation.
- Create a PR with the change. Inside the PR, set package version to
X.0.0(where X is incremented) - TODO: Open oarepo-app actions and run the dependency checker.
- Provide:
- target
oarepoversion (empty means the latest version) - list of
oarepo-*packages (the checker will suppose that major version of these packages will be changed, that is the PR of the change IS NOT MERGED yet)
- target
- Use the generated dependency graph to identify all packages that require a major bump.
- Create PRs for all affected packages:
- set package version to
X.0.0 - update dependency constraints in
pyproject.tomlto new major ranges where needed
- set package version to
- Run the testrig with all related PRs:
uvx run \
--from git+https://github.com/oarepo/invenio-testrig@master invenio-testrig \
github \
--config-file https://raw.githubusercontent.com/oarepo/oarepo/refs/heads/main/tools/testrig.yaml \
<pr1> <pr2> ...- Continue only if all testrig checks are green.
- Merge and release in dependency order:
- first merge a PR that has no pending bumped dependencies
- create GitHub release tag matching
pyproject.toml(vX.0.0) - rerun testrig with remaining PRs
- repeat until all affected packages are released
3) Release ccmm-invenio
Warning: CCMM does not follow semantic versioning at the XML serialization level, so ccmm-invenio cannot reliably follow semantic versioning either.
For example, ccmm-invenio 1.1.x maps to CCMM 1.1.y, while CCMM 1.2.0 may still introduce backward-incompatible XML serialization changes.
Because of this, oarepo-app version guardrails do not reliably detect compatibility changes for ccmm-invenio.
When releasing ccmm-invenio:
- prefer backward-compatible changes whenever possible
- increment the patch version even for minor functional changes
- do not increment major or minor versions in normal releases
If a backward-incompatible change is necessary:
- Clearly describe the change and its impact in the pull request.
- Add
[breaking]to the PR title. - Communicate the change to the team before release.
Warning: If oarepo-app is released after a breaking ccmm-invenio change, the break is not detected automatically.
You must manually increase the oarepo-app major version in the release branch.
4) Release oarepo-app (final train aggregation)
- Open oarepo-app create release branch workflow .
- Run create a release branch.
- Review the generated release branch and PR:
- version is computed automatically
- major version is increased automatically if any major bumps are present
- Review the changelog in the release branch.
- Run testrig on the release PR.
- If checks pass, merge the PR.
After merge, the release process starts automatically and publishes the new oarepo-app version to the CESNET pip registry.
5) Update this file
Finally, update the compatibility matrix in this file and merge PR with this change.
6) Update the app copier template
When making a major release of oarepo-app, update the
pyproject.toml template in the app copier
to contain the new oarepo-app version range.