You are viewing an old version of this page. View the current version.

Compare with Current View Page History

« Previous Version 49 Next »

This page describes the process of releasing a new version of Mynewt through the ASF.

Overview

A Mynewt release consists of three pieces:

  1. Core
  2. Newt, Newtvm
  3. newtmgr
  4. Blinky


Each of these pieces has its own git repository:

 

 

When you are ready to release a new version of Mynewt, use the below steps to guide you through the process.

 

Step 0: Create the branch

The first step in the release process is creating the branch.The branch is created off of the develop branch, so make sure you have the latest from develop:

    git checkout develop
    git pull origin develop

To create the branch, use the following git command:

    git branch <branch_name>

Generally, you want to switch to the branch after you have created it. To switch to the branch, use the following git command:

    git checkout <branch_name>

The shorthand way to do both of these (create and switch to the branch):

    git checkout -b <branch_name>

The naming convention for the branch is based on the release number. The naming convention is the release number separated by underscores followed by _dev.

Examples:

  1. Release 1.0.0 beta 2: git branch 1_0_0_b2_dev
  2. Release 1.0.0: git branch 1_0_0_dev
  3. Release 2.1.2: git branch 2_1_2_dev

You now need to push the branch to the remote. You should be in that branch currently when doing this with the command listed here.

    git push origin <branch_name>

Always a good idea to see if it all worked. To view both local and remote branches:

    git branch -a

Step 1: Review github pull requests

There may be some changes intended for the release that never made it in.  Review the outstanding pull requests in the three github mirrors and make sure none of them need to make it into the release.  If any of them should be in the release, they need to be merged before you can proceed with the release process.

Pull request URLs

Step 2: Ensure all tests pass

The Mynewt testing procedure is underdeveloped.  Testing consists of two steps:

  1. Run the core unit tests (see example output below).  Run the unit tests under both OS X and Linux.
  2. Manually execute the Apache Mynewt Test Plan.

$ newt test all
...lots of compiling and testing...
...about 2 minutes later ...
Archiving bootutil.a
Linking test_bootutil
Executing test: /Users/ccollins/tmp/myproj/bin/unittest/libs/bootutil/test_bootutil
Passed tests: [net/nimble/host fs/nffs libs/os hw/hal libs/mbedtls libs/util sys/config libs/bootutil]
All tests passed

Step 3: Audit licenses of third-party code

Every third-party library included in a release that is not Apache-licensed has to be accounted for.  For information about what licenses are Apache-compatible, see the following pages:


Download Rat

To perform a license audit, you will need to use a tool called Apache Rat.  Download Rat here: http://creadur.apache.org/rat/download_rat.cgi

Rat Usage

Rat checks all the files in the specified path for something resembling an Apache license.  Files that do not contain an Apache licensed get flagged.  A .rat-excludes file is used to indicate which files should be ignored by Rat.  Once a non-Apache file has been accounted for, its name can be added to the excludes file.

To execute the Rat tool from the command-line:

  1. Change to the base directory of the repository you wish to audit (e.g., ~/dev/core).
  2. Run the following command:
      java -jar <rat-directory>/apache-rat-0.11.jar -E .rat-excludes -d .

Where <rat-directory> is the location where you unpacked the rat tool.

Example:

[ccollins@ccollins-mac:~/repos/core]$ java -jar ~/Downloads/apache-rat-0.11/apache-rat-0.11.jar -E .rat-excludes -d .
*****************************************************
Summary
-------
Generated at: 2016-03-03T19:28:50-08:00
Notes: 4
Binaries: 2268
Archives: 0
Standards: 3926
[...lots of output snipped...]


Audit Procedure

  1. Run the Rat tool from the base directory of the repository being audited.
  2. Look at the source files flagged by Rat.  For each file:
    1. If the file was created for Mynewt (i.e., not third-party), then it is missing the Apache license text.  Copy the text from another Mynewt source file and paste it at the top of the problematic file.  You can verify that the license text is correct by comparing it to the text at the bottom of this page: http://www.apache.org/licenses/LICENSE-2.0
    2. If the file is third-party and it uses a license that is not Apache-compatible (http://www.apache.org/legal/resolved.html#category-x), then the files must be removed from the release.
    3. If the file is third-party and it uses a license that is Apache-compatible:
      1. Add a pointer at the end of the repository's LICENSE file indicating that the library is included in the product and that it is licensed in an Apache-compatible way.  The LICENSE file should be located in the root of the repository.  A single pointer can account for an entire library if the library is isolated in the directory tree.  If Mynewt sources files are intermixed with third-party files, each third-party file must be specified in the LICENSE file.
      2. Add the filename to the repository's .rat-excludes file. This file should be in the repository's base directory. Preface the addition with a comment explaining which library the files are from and how they are licensed.  This change prevents Rat from flagging the same files during subsequent executions.

Note

Unfortunately, Rat does not appear to support more than one directory in filename paths in the exclude file.  I.e., the following entries are OK:

  • crc16.*
  • system_nrf52.h
  • libs/baselibc


But these aren't:

  • fs/nffs/src/crc16.c
  • hw/mcu/nordic/nrf52xxx/include/mcu/system_nrf52.h


This could become problematic if a repository contains two files with the same name.

Step 4: Update the newt version numbers

Update the newt tool so that:

  • "newt version" reports the new version number
  • "newt new" downloads the correct version of blinky

The version strings are defined at the top of newt/newtutil/newtutil.go in the newt repository:

var NewtVersionStr string = "Apache Newt (incubating) version: 0.9.0"
var NewtBlinkyTag string = "mynewt_0_9_0_tag"

Getting the NewtBlinkyTag string right is a bit tricky, since you have not created the new tag yet.  Refer to step 6 to see how the tag will be named.

Make sure you commit and push the change!

Step 5: Update README.md and RELEASE_NOTES.md files

Each of the main repositories (core, newt, blinky) contains a README.md file in its root directory.  Most of the repositories also contain a RELEASE_NOTES.md file in the same location.  Make sure these files contain up to date information.  In particular, ensure these files:

  • Don't contain old dates or version numbers
  • Mention TODO items which are complete in this release
  • Mention upcoming releases which have already been released (or are in the process of being released).

Step 6: Tag the Repositories

Each git repository must be tagged with the name of the release.  Tagging the repositories makes it easy to determine exactly what went into the release.  The tag should be named as follows:

  • mynewt_<version-number>_rc<#>_tag


The rc<#> is the release candidate number.  Start with an rc of 1; increment this number each time you have to cancel and restart the release process.  Replace periods in the version number with underscores.  If this is a beta release, append b<number> to the version-number.  For example, 0.8.0 beta 2 rc3 should have the following tag:

  • mynewt_0_8_0_b2_rc3_tag

Tag the repository with the following git commands:

    git tag -a <tag-name> -m <commit-message>
    git push origin --tags

The first command creates a tag in your local repository.  The second pushes the tag to the remote server.

You will also want to create a second tag that doesn't specify an rc number.  This tag is necessary so that the release can be properly tested.  For example, the core repository contains a repository.yml file mapping version numbers to tag names.  This file has to be accurate both during and after the release process, so it needs to specify the final tag name from the start.

If something goes wrong and you need to delete the tag here are the commands to do this. Note that the first command deletes it from the remote, the second locally.

git push --delete origin <tag_name>

git tag --delete <tag_name>


Example:

[ccollins@ccollins-mac:~/repos/core]$ git tag -a mynewt_0_8_0_b2_rc3_tag -m 'Mynewt 0.8.0 B2, rc3'
[ccollins@ccollins-mac:~/repos/core]$ git tag -a mynewt_0_8_0_b2_tag -m 'Mynewt 0.8.0 B2'
[ccollins@ccollins-mac:~/repos/core]$ git push origin --tags

Repeat this procedure for each of the following repositories:

Step 7: Expose the new release in the repository.yml files

People will need a way to try out the new release while it is being voted on.  You should update each repo's repository.yml file with a pointer to the corresponding tag.  A repo's repository.yml file is only contained in the master branch; that is the branch you must modify.  Since the release is not approved yet, the old tags should still be used by default.  In other words, don't modify any pointers, just add new ones.  Here is the git diff showing the changes that were made to the core repository.yml file for the 0.9.0 release:

 repo.name: apache-mynewt-core
 repo.versions:
     "0.0.0": "develop"
     "0.7.9": "mynewt_0_8_0_b2_tag"
     "0.8.0": "mynewt_0_8_0_tag"
+    "0.9.0": "mynewt_0_9_0_tag"
     "0-latest": "0.8.0"
     "0-dev": "0.0.0"
     "0.8-latest": "0.8.0"
+    "0.9-latest": "0.9.0"

Repeat this procedure for each of the repositories:

Step 8: Create the source release artifacts

Note: To complete this step you will need to publish a GPG code signing key.  This something you only have to do once.  If you have not done this, see: Code Signing Keys.

Each source release consists of three artifacts:

  1. Gzipped tarball.
  2. A SHA512 hash of the gzipped tarball.
  3. A detached signature generated by signing the gzipped tarball with your code signing key.

Source release artifacts must be named as follows (file extension excluded):

  • apache-<product>-<version>[-b#]-incubating

The intermediate -b# is only included if this is a beta release.

For example, for 0.8.0 beta 2 rc3, the three source artifacts would have the following names:

  • apache-mynewt-core-0.8.0-b2-incubating
  • apache-mynewt-newt-0.8.0-b2-incubating
  • apache-mynewt-blinky-0.8.0-b2-incubating


The following procedure can be used to produce the source artifacts:

  1. Grab the mynewt-archive-src.sh script (https://github.com/runtimeinc/mynewt_tools/raw/master/mynewt-archive-src.sh) if you don't already have it.  Put it somewhere in your PATH, or adjust the following steps as needed.
  2. Change to the base directory of the git clone.
  3. mynewt-archive-src.sh <destination-dir/artifact-name> <tag-name> (note: you will be prompted for your key password)

The <tag-name> is the name of the tag you created in step 3.  The <destination-dir/artifact-name> field is best illustrated with an example:

[ccollins@ccollins-mac:~/repos/core]$ mynewt-archive-src.sh ~/releases/0.8.0-b2/rc3/apache-mynewt-core-0.8.0-b2-incubating mynewt_0_8_0_b2_rc3_tag


The above invocation will create the following three files:

# Source tarball.
~/releases/0.8.0-b2/rc3/apache-mynewt-core-0.8.0-b2-incubating.tgz

# Detached signature.
~/releases/0.8.0-b2/rc3/apache-mynewt-core-0.8.0-b2-incubating.tgz.asc

# SHA512.
~/releases/0.8.0-b2/rc3/apache-mynewt-core-0.8.0-b2-incubating.tgz.sha

Apply this process to each repository (core, newt, and blinky).  Do not include the rc-number in the artifact names.

Note: You do not need to make a fresh git clone for the above procedure.  The mynewt-archive-src.sh script uses the git archive command, which packages the source files exactly as they were tagged in git.

Step 9: Create the binary release artifacts

Note: To complete this step you will need to publish a GPG code signing key.  This something you only have to do once.  If you have not done this, see: Code Signing Keys.

Binary releases contain the same artifacts as source releases:

  1. Gzipped tarball.
  2. A SHA512 hash of the gzipped tarball.
  3. A detached signature generated by signing the gzipped tarball with your code signing key.

Binary release artifacts must be named as follows (file extension excluded):

  • apache-<product>-bin-<platform>-<version>[-b#]-incubating

The intermediate -b# is only included if this is a beta release.

For example, for 0.8.0 beta 2 rc3, the two binary artifacts would have the following names:

  • apache-mynewt-newt-bin-osx-0.8.0-b2-incubating
  • apache-mynewt-newt-bin-linux-0.8.0-b2-incubating

The following procedure can be used to produce the binary artifacts:

  1. Grab the mynewt-archive-bin.sh script (https://github.com/runtimeinc/mynewt_tools/raw/master/mynewt-archive-bin.sh) if you don't already have it.  Put it somewhere in your PATH, or adjust the following steps as needed.
  2. Build the binary from the appropriate source artifact for the appropriate platform (more details TBD).
  3. mynewt-archive-bin.sh <destination-dir/artifact-name> <file-1> [file-2] [file-3] [...] (note: you will be prompted for your key password)

The file list should consist of the following:

  • newt
  • LICENSE
  • NOTICE
  • DISCLAIMER
  • README.md
  • RELEASE_NOTES.md

The LICENSE, NOTICE, DISCLAIMER, README.md, and RELEASE_NOTES.md files should be exactly those from the corresponding source release.

Example:

[ccollins@ccollins-mac:~/repos/newt]$ mynewt-archive-bin.sh ~/releases/0.8.0-b2/rc3/apache-mynewt-newt-bin-osx-0.8.0-b2-incubating newt LICENSE NOTICE DISCLAIMER


The above invocation will create the following three files:

# Binary tarball.
~/releases/0.8.0-b2/rc3/apache-mynewt-newt-bin-osx-0.8.0-b2-incubating.tgz

# Detached signature.
~/releases/0.8.0-b2/rc3/apache-mynewt-newt-bin-osx-0.8.0-b2-incubating.tgz.asc

# SHA512.
~/releases/0.8.0-b2/rc3/apache-mynewt-newt-bin-osx-0.8.0-b2-incubating.tgz.sha

Apply this process for each platform (osx and linux).  Do not include the rc-number in the artifact names.

Step 10: Verify the signatures

The mynewt-archive.sh script verifies the signatures after they are created, but you might want to double-check that everything is good.  Run the following command for each detached signature (.asc) file:

    gpg2 --verify "<tgz-file>" "<asc-file>"


The output will indicate that the signature matches the tarball (or not!).

If all your artifacts are in the same directory, you can simplify the process with a script, e.g.,

    for i in *.asc ; do echo ">>> $i <<<" && gpg2 --verify "$i" "${i%.asc}" ; done

Step 11: Upload the artifacts to the release candidate svn server

1. Check out the dev/incubator/mynewt directory from the svn server:

    svn co https://dist.apache.org/repos/dist/dev/incubator/mynewt

2. Make sure the KEYS file is up to date

If you used a new key to sign the release, you need to append the text representation of your key to the KEYS file.  The KEYS file is located in the base mynewt path of the svn server.

    cat <your-key-file> >> KEYS

3. Create a new subdirectory for the release in the mynewt directory

The directory should be named as follows:

  • apache-mynewt-<version>[-b#]-incubating/rc<#>
[ccollins@ccollins-mac:~/repos/dist.apache.org/repos/dist/dev/incubator/mynewt]$ mkdir -p apache-mynewt-0.8.0-b2-incubating/rc3

4. Add the build artifacts to the new subdirectory

[ccollins@ccollins-mac:~/repos/dist.apache.org/repos/dist/dev/incubator/mynewt]$ cp ~/releases/0.8.0-b2/rc3/* apache-mynewt-0.8.0-b2-incubating/rc3/
[ccollins@ccollins-mac:~/repos/dist.apache.org/repos/dist/dev/incubator/mynewt]$ svn add apache-mynewt-0.8.0-b2-incubating

5. Commit

[ccollins@ccollins-mac:~/repos/dist.apache.org/repos/dist/dev/incubator/mynewt]$ svn ci

Step 12: Send [VOTE] and [DISCUSS] emails to the dev list

Call for a vote for the new release by sending an email to dev@mynewt.incubator.apache.org.  A separate "[DISCUSS]" thread should also be opened to allow for discussion of the pros and cons of the release.  These threads are kept separate so that the vote thread is not polluted with discussion.

[VOTE]

[DISCUSS]


The vote must remain open for at least 72 hours.  You can keep the vote open longer if you wish (e.g., if the necessary number of +1 votes have not been accumulated yet).  The vote passes if the following two criteria are met:

  • At least three binding +1 votes.
  • The total vote tally is >= half the number of binding votes (i.e., majority consensus).

Before sending the email, it is a good idea to test every URL that it references.  Broken links won't look good!

Step 13: Send a [RESULT][VOTE] email to the dev list


If the vote doesn't pass, the process ends here.  You will need to restart the process after the problems are fixed.  If the vote does pass, proceed to step 14.

Step 14: Send a [VOTE] email to the gen list

This is similar to the dev vote email.  The differences are:

  • Email recipient is: general@incubator.apache.org
  • A different set of people have binding votes.
  • There is no need for a separate [DISCUSS] email.

Some resources for writing this email:

The pass criteria are the same as those of the dev vote:

  • At least three binding +1 votes.
  • The total vote tally is >= half the number of binding votes (i.e., majority consensus).

Before sending the email, it is a good idea to test every URL that it references.  Broken links won't look good!

Step 15: Send a [RESULT][VOTE] email to the gen list

If the vote doesn't pass, the process ends here.  You will need to restart the process after the problems are fixed.  If the vote does pass, proceed to step 15.

Step 16: Move the release artifacts to the release directory on the svn server

The release directory is: https://dist.apache.org/repos/dist/release/incubator/mynewt

The release subdirectory (and the KEYS file, if you changed it) should be moved to the above directory.  Be sure to use the svn mv command to move the files from dev to release; don't make local copies of the dev files and add them separately with svn add.  If you moved the files properly with svn mv, their svn logs should be augmented with a new entry corresponding to the move operation.  In other words, svn history should not be lost during the move.

 

Example:

[ccollins@ccollins-mac:~/repos/dist/release/incubator/mynewt]$ mkdir apache-mynewt-1.0.0-b1-incubating
[ccollins@ccollins-mac:~/repos/dist/release/incubator/mynewt]$ svn add apache-mynewt-1.0.0-b1-incubating/
A         apache-mynewt-1.0.0-b1-incubating
[ccollins@ccollins-mac:~/repos/dist/release/incubator/mynewt]$ cd apache-mynewt-1.0.0-b1-incubating
[ccollins@ccollins-mac:~/repos/dist/release/incubator/mynewt/apache-mynewt-apache-mynewt-1.0.0-b1-incubating]$ svn mv ~/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/* .
A         apache-mynewt-blinky-1.0.0-b1-incubating.tgz
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-blinky-1.0.0-b1-incubating.tgz
A         apache-mynewt-blinky-1.0.0-b1-incubating.tgz.asc
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-blinky-1.0.0-b1-incubating.tgz.asc
A         apache-mynewt-blinky-1.0.0-b1-incubating.tgz.sha
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-blinky-1.0.0-b1-incubating.tgz.sha
A         apache-mynewt-core-1.0.0-b1-incubating.tgz
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-core-1.0.0-b1-incubating.tgz
A         apache-mynewt-core-1.0.0-b1-incubating.tgz.asc
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-core-1.0.0-b1-incubating.tgz.asc
A         apache-mynewt-core-1.0.0-b1-incubating.tgz.sha
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-core-1.0.0-b1-incubating.tgz.sha
A         apache-mynewt-newt-1.0.0-b1-incubating.tgz
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-newt-1.0.0-b1-incubating.tgz
A         apache-mynewt-newt-1.0.0-b1-incubating.tgz.asc
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-newt-1.0.0-b1-incubating.tgz.asc
A         apache-mynewt-newt-1.0.0-b1-incubating.tgz.sha
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-newt-1.0.0-b1-incubating.tgz.sha
A         apache-mynewt-newt-bin-linux-1.0.0-b1-incubating.tgz
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-newt-bin-linux-1.0.0-b1-incubating.tgz
A         apache-mynewt-newt-bin-linux-1.0.0-b1-incubating.tgz.asc
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-newt-bin-linux-1.0.0-b1-incubating.tgz.asc
A         apache-mynewt-newt-bin-linux-1.0.0-b1-incubating.tgz.sha
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-newt-bin-linux-1.0.0-b1-incubating.tgz.sha
A         apache-mynewt-newt-bin-osx-1.0.0-b1-incubating.tgz
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-newt-bin-osx-1.0.0-b1-incubating.tgz
A         apache-mynewt-newt-bin-osx-1.0.0-b1-incubating.tgz.asc
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-newt-bin-osx-1.0.0-b1-incubating.tgz.asc
A         apache-mynewt-newt-bin-osx-1.0.0-b1-incubating.tgz.sha
D         /Users/ccollins/repos/dist/dev/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating/rc2/apache-mynewt-newt-bin-osx-1.0.0-b1-incubating.tgz.sha
[ccollins@ccollins-mac:~/repos/dist/release/incubator/mynewt/apache-mynewt-1.0.0-b1-incubating]$ svn ci
Adding         .
Adding  (bin)  apache-mynewt-blinky-1.0.0-b1-incubating.tgz
Adding         apache-mynewt-blinky-1.0.0-b1-incubating.tgz.asc
Adding         apache-mynewt-blinky-1.0.0-b1-incubating.tgz.sha
Adding  (bin)  apache-mynewt-core-1.0.0-b1-incubating.tgz
Adding         apache-mynewt-core-1.0.0-b1-incubating.tgz.asc
Adding         apache-mynewt-core-1.0.0-b1-incubating.tgz.sha
Adding  (bin)  apache-mynewt-newt-1.0.0-b1-incubating.tgz
Adding         apache-mynewt-newt-1.0.0-b1-incubating.tgz.asc
Adding         apache-mynewt-newt-1.0.0-b1-incubating.tgz.sha
Adding  (bin)  apache-mynewt-newt-bin-linux-1.0.0-b1-incubating.tgz
Adding         apache-mynewt-newt-bin-linux-1.0.0-b1-incubating.tgz.asc
Adding         apache-mynewt-newt-bin-linux-1.0.0-b1-incubating.tgz.sha
Adding  (bin)  apache-mynewt-newt-bin-osx-1.0.0-b1-incubating.tgz
Adding         apache-mynewt-newt-bin-osx-1.0.0-b1-incubating.tgz.asc
Adding         apache-mynewt-newt-bin-osx-1.0.0-b1-incubating.tgz.sha
Committed revision 17368.

Step 17: Send an [ANNOUNCE] email to the dev and announce lists

Wait at least 24 hours so that the release can propagate to most apache mirrors.  Then, send a release announcement to the following two recipients using your apache.org address.

Some resources for writing this email:

Notes:

  • Be sure to include the incubation disclaimer at the bottom of the email (present in the template).
  • The announce list is moderated; you won't see your email in the archives until it is approved by the moderator.
  • Send this email from your apache.org email address (announce@apache.org destination bounces otherwise)

Step 18: Update the default tags in the repository.yml files

Now that the release is out, it should be the version that new users get by default.  Update the appropriate labels in each repo's repository.yml file.  The below git diff shows what was done for the 0.9.0 release:

 repo.name: apache-mynewt-core
 repo.versions:
     "0.0.0": "develop"
     "0.7.9": "mynewt_0_8_0_b2_tag"
     "0.8.0": "mynewt_0_8_0_tag"
     "0.9.0": "mynewt_0_9_0_tag"
-    "0-latest": "0.8.0"
+    "0-latest": "0.9.0"
     "0-dev": "0.0.0"
     "0.8-latest": "0.8.0"
     "0.9-latest": "0.9.0"

Repeat this procedure for each of the repositories:

  • No labels