Identity Workflow
In this article you will learn about the software development process for the IOTA Identity repository as well as key terms, functions, and the overall operability of the workflow components.
Issues
Issues are opened when a certain task or problem is noted but cannot immediately be fixed. Issues may contain bug reports, requests, or larger topics. Please use the correct GitHub issue template for your issue type. Only IOTA Foundation members should use the task templates flagged for maintainers. You should make sure to label the issue correctly. As a contributor, you may also add issues to a certain project.
Git
Pull Requests
New branches should be pushed to the GitHub repository as soon as possible, making them public to all contributors. In addition, a pull request (PR) should be opened in draft status, describing the goals and any requirements of the changes. To generate good changelogs, a PR title must be written in a way that is suitable as a changelog entry while the PR must be labeled correctly.
Any code written should frequently be committed and pushed back to the GitHub branch. This acts as both a back-up mechanism and provides transparency towards other contributors and the community. You should also pull from the origin branch of the PR regularly to prevent merge conflicts.
Other contributors are encouraged to provide feedback on a PR during its development. A PR should be flagged as 'ready for review' once the PR has implemented all changes and no further commits are planned by the main contributors. The repository requires a review to be provided by at least one (other) developer in the team that works in the same language or has knowledge of the work before it can be merged. For larger PRs, the review of two maintainers is recommended.
Once a PR is approved, the preferred method is "squash-and-merge" for non-epic branches to keep the destination branch clean and allow for many small commits while work is in-progress. Epic branches must instead be merged with the merge commits of included PRs intact, so the changelog generator can detect included changes. Once merged in, the source branch may be deleted.
Branches
IOTA Identity always has two permanent branches: main
and dev
. Both branches are protected and disallow direct commits; the only changes allowed are from pull requests approved and merged by maintainers.
Main (main)
The main
branch contains a stable version of the code that is released towards package managers such as crates.io
and npm
. This branch only accepts PRs that merge from release
or hotfix
branches.
Dev (dev)
The dev
branch contains a frequently updated version of the code that is released towards package managers under a development flag. These releases may contain breaking changes without a strong notice towards developers using them. While the dev
branch may get frequent updates, it may not contain unfinished features. Any large, multi-PR feature should be committed to a long-lived epic
branch created specifically for that feature.
Work Branches
These are branches that developers work on directly. Their names should be prefixed appropriately with one of the following categories. For example, a PR fixing a null pointer bug in the Wasm bindings might be created from a branch called fix/client-non-null
.
Feature (feat/, doc/, chore/, fix/)
Singular PR contributions should create either a feat
, doc
, chore
, or fix
branch, depending on the type of changes. These may be branched from either the dev
branch or an epic
branch. If the number of lines of code are going to be relatively small and the work completed in a single PR, the branch should be created from dev
and merged back into dev
once completed. Otherwise, the branches should be created from their associated epic
branch and be merged back into the same epic
branch.
feat
branches should contain changes to the code that expand or modify functionality. They should also include updates to the documentation and examples related to the feature, thoughdoc
branches may be used to catch up on documenting a feature.doc
branches contain changes to code documentation or the wiki. These PRs should be kept relatively small to avoid burdening a reviewer with too many documentation updates at once. For example, during a documentation catch-up, we will have a branch or PR per documentation page.chore
branches are short-lived branches that contain no significant features or functionality changes, but rather smaller fixes such as typos, code fixes, minor refactors, and CI changes.fix
branches correct bugs such as compilation errors or where existing features do not behave as expected, generally without introducing any new functionality or breaking changes.
We recommend integrating dev
or epic
regularly, depending on where the branch started, to reduce the possibility and potential size of merge conflicts.
Epic (epic/)
Long-lived epic
branches should be created as soon as a feature is expected to require more than one PR. The epic
branch should be branched from dev
and should only accept merges that are related to the feature being developed. A PR should be opened as soon as the branch is created to publicly notify contributors about the development, the goals and requirements of the feature, and the existence of the branch. It is recommended you integrate dev
often to reduce the possibility and potential size of merge conflicts. Epic branches must not be squash-merged, otherwise the changelog generator will not detect its constituent PRs.
Semantic Versioning
Semantic Versioning (SemVer) describes a methodology for versioning of software to convey meaning and guarantees through the version string. A typical version string looks like 2.3.1
, where 2
is called the major version, 3
the minor version and 1
the patch or bugfix version.
The central idea is that every part of the version string conveys meaning. A major change introduces behavior that is incompatible with previous versions of the software, while a minor change adds backwards-compatible functionality and a patch simply fixes a problem. So just by looking at the version string, an implementer will understand the effort needed to integrate a new version.
For more detailed information and an overview of advanced features, see Semantic Versioning 2.0.0. Though this is not to be confused with Sentimental Versioning.
Changelog
A changelog is a file describing a software project for humans to grasp the type and content of changes from version to version. Changelogs are closely related to the versioning of software, since individual changes are grouped into versions that are, in our case, referenced by a SemVer string. We generally follow the recommendations from keepachangelog. The changelog in this project is generated from the titles and labels of pull requests.
PR labels
Labels are used to categorize changes in pull requests. Adding a label will include the labeled PR title in the related section of the generated changelog.
Changelogs are generated for the core Rust library and each binding separately. To attach a PR to a specific changelog, use the following labels:
Rust
This includes the PR in the core Rust library changelog.
Wasm
This includes the PR in the WASM bindings changelog.
It is also necessary to add an appropriate label for the type of change in the PR. The following labels determine in which section a PR title will appear:
Changed
Maps to the major version of Semantic Versioning.
labels: Breaking change
Added
Maps to the minor version of Semantic Versioning.
labels: Added
Patch
Maps to the patch version of Semantic Versioning.
labels: Patch
Deprecated
Marks features that will be removed in the feature. No special version consideration should apply here, since the feature did not change yet.
labels: Deprecated
Removed
Marks features as being removed. Typically the features should have been deprecated in the previous version. This maps to the major version of Semantic Versioning.
labels: Removed
Excluded tags
Marks changes that should not be part of the changelog. This should only be used for documentation and rare exceptions.
labels: Documentation
, No changelog
Please note that a PR can only be listed in one section of a changelog. So attaching the labels Rust
Added
Patch
to a PR, for example, is invalid because Added
and Patch
conflict.
Release summary
To attach a release summary to a version in the changelog, an issue with the label release-summary
must be created. Create a GitHub milestone matching the version you want to describe and attach it to the issue. The issue can be closed immediately. The text of the issue will be included in the changelog as the release summary.
Issue Labels
The following labels are used to categorize issues but do not have any effect on changelogs: Request
, Enhancement
, Bug
, Chore
, Dependencies
, Help wanted
, Duplicate
, Wontfix
.
Release
With the release process, we can deliver versions of our software to the community. We use sensible automation where it helps to remove tedium. However, some steps that require active decision-making remain manual.
The final list of changes from the changelog informs the version of the release. If at least one change mapping to a major version is included, the major version needs to be incremented. In that case, the minor and patch versions are set to 0
. If there are no changes related to a major version, but changes related to a minor version are present, the minor version needs to be incremented while the patch version is set to 0
. Otherwise, only the patch version is incremented. Determining the version of the release is the responsibility of the person performing the release.
The determined version of the release is used to create the hotfix or release branch. For example, a major release from the previous version v2.3.1
will create the release/v3.0.0
branch.
Notice the v
in front of the version. We tag all release in git in the form of vMAJOR.MINOR.PATCH
. For bindings, we prefix the tag with the binding name, so a tag for Wasm would look like wasm-v1.2.3
. Bindings and the core Rust library are versioned and released independently.
Additionally, we may release dev
versions separately for both bindings and the core Rust library. These releases are meant as a preview of upcoming versions. For example, if the current version is 1.2.3
with the tag v1.2.3
, we may release v1.3.0-dev.1
which is then superseded by the actual 1.3.0
release.
You should follow these steps to create a release:
- Ensure all the changes you want to release are on the
dev
branch. - Select the appropriate GitHub Actions workflow, e.g.
Rust Create Release PR
. 2.1. Decide if you want to create adev
ormain
release. 2.2. Determine the next version string. 2.3. Run the workflow. The workflow will create a PR fromdev
targetingdev
with release related changes. - Review the PR. 3.1. The PR will update the changelog, check that it has all expected entries in the appropriate sections and the determined version matches the changelog according to SemVer. 3.2. The PR will update project version strings, ensure these are correct and match the expected version. 3.3. Refer to Troubleshooting if anything is incorrect.
- Merge the PR.
4.1. On merging to
dev
, an automatic workflow is triggered that builds and publishes artifacts to the appropriate package manager (crates.io
for Rust,npm
for the WASM bindings), and creates a GitHub Release (only formain
version releases of the core Rust library). - For
main
version releases, merge thedev
branch into themain
branch.
Troubleshooting
The changelog entries have the wrong description in the release PR
Update the titles of the relevant PRs, then re-run the workflow with the same parameters. The release PR will be updated with the new changelog.
The changelog in the release PR is missing entries, has unrelated entries, or entries in the wrong section
Fix the labels on the relevant PRs, then re-run the workflow with the same parameters. The release PR will be updated with the new changelog.
The release description in the release PR is missing or wrong
Fix the issue description, milestone, and label according to the release summaries guide and re-run the workflow with the same parameters. The release PR will be updated with the new changelog.
Features or code are missing from the release
Merge the code into the dev
branch, then re-run the workflow with the same parameters. The release PR will be updated with the changes.
I want to abort the release for any reason
Close the PR. You can reopen it later. // TODO: can I just re-run the workflow? Maybe that needs an "I want to resume an aborted release" section?