A guide for developers who are doing a dipy release
There are some release utilities that come with nibabel. nibabel should install these as the nisext package, and the testing stuff is understandably in the testers module of that package. Dipy has Makefile targets for their use. The relevant targets are:
make check-version-info
make check-files
make sdist-tests
The first installs the code from a git archive, from the repository, and for in-place use, and runs the get_info() function to confirm that installation is working and information parameters are set correctly.
The second (sdist-tests) makes an sdist source distribution archive, installs it to a temporary directory, and runs the tests of that install.
If you have a version of nibabel trunk past February 11th 2011, there will also be a functional make target:
make bdist-egg-tests
This builds an egg (which is a zip file), hatches it (unzips the egg) and runs the tests from the resulting directory.
Review the open list of dipy issues. Check whether there are outstanding issues that can be closed, and whether there are any issues that should delay the release. Label them !
Review and update the release notes. Review and update the Changelog file. Get a partial list of contributors with something like:
git shortlog -ns 0.6.0..
where 0.6.0 was the last release tag name.
Then manually go over git shortlog 0.6.0.. to make sure the release notes are as complete as possible and that every contributor was recognized.
Use the opportunity to update the .mailmap file if there are any duplicate authors listed from git shortlog -ns.
Add any new authors to the AUTHORS file. Add any new entries to the THANKS file.
Check the copyright years in doc/conf.py and LICENSE
Check the examples - we really need an automated check here.
Check the pyx file doctests with:
./tools/doctest_extmods.py dipy
We really need an automated run of these using the buildbots, but we haven’t done it yet.
Check the long_description in dipy/info.py. Check it matches the README in the root directory, maybe with vim diffthis command. Check all the links are still valid.
Check all the dipy builds are green on the `nipy buildbot`_
If you have travis-ci_ building set up you might want to push the code in its current state to a branch that will build, e.g:
git branch -D pre-release-test # in case branch already exists
git co -b pre-release-test
Run the builder and review the output from http://nipy.bic.berkeley.edu/builders/dipy-release-checks This builder does not check the outputs - they will likely all be green - you have to check the stdio output for each step using the web interface.
The dipy-release-checks builder runs these tests:
make distclean
python -m compileall .
make sdist-tests
make bdist-egg-tests
make check-version-info
make check-files
make bdist-egg-tests may well fail because of a problem with the script tests; if you have a recent (>= March 31 2013) nibabel nisext package, you could try instead doing:
python -c 'from nisext.testers import bdist_egg_tests; bdist_egg_tests("dipy", label="not slow and not script_test")'
Eventually we should update the bdist-egg-tests makefile target.
make check-version-info checks how the commit hash is stored in the installed files. You should see something like this:
{'sys_version': '2.6.6 (r266:84374, Aug 31 2010, 11:00:51) \n[GCC 4.0.1 (Apple Inc. build 5493)]', 'commit_source': 'archive substitution', 'np_version': '1.5.0', 'commit_hash': '25b4125', 'pkg_path': '/var/folders/jg/jgfZ12ZXHwGSFKD85xLpLk+++TI/-Tmp-/tmpGPiD3E/pylib/dipy', 'sys_executable': '/Library/Frameworks/Python.framework/Versions/2.6/Resources/Python.app/Contents/MacOS/Python', 'sys_platform': 'darwin'}
/var/folders/jg/jgfZ12ZXHwGSFKD85xLpLk+++TI/-Tmp-/tmpGPiD3E/pylib/dipy/__init__.pyc
{'sys_version': '2.6.6 (r266:84374, Aug 31 2010, 11:00:51) \n[GCC 4.0.1 (Apple Inc. build 5493)]', 'commit_source': 'installation', 'np_version': '1.5.0', 'commit_hash': '25b4125', 'pkg_path': '/var/folders/jg/jgfZ12ZXHwGSFKD85xLpLk+++TI/-Tmp-/tmpGPiD3E/pylib/dipy', 'sys_executable': '/Library/Frameworks/Python.framework/Versions/2.6/Resources/Python.app/Contents/MacOS/Python', 'sys_platform': 'darwin'}
/Users/mb312/dev_trees/dipy/dipy/__init__.pyc
{'sys_version': '2.6.6 (r266:84374, Aug 31 2010, 11:00:51) \n[GCC 4.0.1 (Apple Inc. build 5493)]', 'commit_source': 'repository', 'np_version': '1.5.0', 'commit_hash': '25b4125', 'pkg_path': '/Users/mb312/dev_trees/dipy/dipy', 'sys_executable': '/Library/Frameworks/Python.framework/Versions/2.6/Resources/Python.app/Contents/MacOS/Python', 'sys_platform': 'darwin'}
make check-files checks if the source distribution is picking up all the library and script files. Look for output at the end about missed files, such as:
Missed script files: /Users/mb312/dev_trees/dipy/bin/nib-dicomfs, /Users/mb312/dev_trees/dipy/bin/nifti1_diagnose.py
Fix setup.py to carry across any files that should be in the distribution.
Clean and compile:
make distclean
git clean -fxd
python setup.py build_ext --inplace
Make sure all tests pass on your local machine (from the dipy root directory):
cd ..
nosetests --with-doctest dipy
cd dipy # back to the root directory
Check the documentation doctests:
cd doc
make doctest
cd ..
At the moment this generates lots of errors from the autodoc documentation running the doctests in the code, where the doctests pass when run in nose - we should find out why this is at some point, but leave it for now.
Trigger builds of all the binary build testers for dipy, using the web interface. You may need permissions set to do this - contact Matthew or Eleftherios if you do.
At the moment, the useful dipy binary build testers are:
The release should now be ready.
The trick here is to get all the testing, pushing to upstream done before you do the final release commit. There should be only one commit with the release version number, so you might want to make the release commit on your local machine, push to pypi_, review, fix, rebase, until all is good. Then and only then do you push to upstream on github.
Make the release commit. Edit dipy/info.py to set _version_extra to ''; commit
Build the release files:
make distclean
git clean -fxd
make source-release
Once everything looks good, upload the source release to PyPi. See setuptools intro:
python setup.py register
python setup.py sdist --formats=gztar,zip upload
Remember you’ll need your ~/.pypirc file set up right for this to work. See setuptools intro. The file should look something like this:
[distutils]
index-servers =
pypi
[pypi]
username:your.pypi.username
password:your-password
[server-login]
username:your.pypi.username
password:your-password
Check how everything looks on pypi - the description, the packages. If necessary delete the release and try again if it doesn’t look right.
Make an annotated tag for the release with tag of form 0.6.0:
git tag -am 'Second public release' 0.6.0
Set up maintenance / development branches
If this is this is a full release you need to set up two branches, one for further substantial development (often called ‘trunk’) and another for maintenance releases.
Branch to maintenance:
git co -b maint/0.6.x
Set _version_extra back to .dev and bump _version_micro by 1. Thus the maintenance series will have version numbers like - say - ‘0.6.1.dev’ until the next maintenance release - say ‘0.6.1’. Commit.
Push with something like git push upstream-rw maint/0.6.x --set-upstream
Start next development series:
git co main-master
then restore .dev to _version_extra, and bump _version_minor by 1. Thus the development series (‘trunk’) will have a version number here of ‘0.7.0.dev’ and the next full release will be ‘0.7.0’.
Next merge the maintenace branch with the “ours” strategy. This just labels the maintenance branch info.py edits as seen but discarded, so we can merge from maintenance in future without getting spurious merge conflicts:
git merge -s ours maint/0.6.x
Push with something like git push upstream-rw main-master:master
If this is just a maintenance release from maint/0.6.x or similar, just tag and set the version number to - say - 0.6.2.dev.
Push the tag with git push upstream-rw 0.6.0
By far the easiest way to do this is via the buildbots.
In order to do this, you need first to push the release commit and the release tag to github, so the buildbots can find the released code and build it.
In order to trigger the binary builds for the release commit, you need to go to the web interface for the binary builder, go to the “Force build” section, enter your username and password for the buildbot web service and enter the commit tag name in the revision field. For example, if the tag was 0.6.0 then you would enter 0.6.0 in the revision field of the form. This builds the exact commit labeled by the tag, which is what we want.
Trigger binary builds for Windows from the buildbots. See builders dipy-bdist32-26, dipy-bdist32-27. The exe builds will appear in http://nipy.bic.berkeley.edu/dipy-dist . Check that the binary build version numbers are release numbers (dipy-0.6.0.win32.exe rather than dipy-0.6.0.dev.win32.exe).
Download the builds and upload to pypi.
You can upload the exe files with the files interface for the new dipy release. Obviously you’ll need to log in to do this, and you’ll need to be an admin for the dipy pypi project.
For reference, if you need to do binary exe builds by hand, use something like:
make distclean
git clean -fxd
c:\Python26\python.exe setup.py bdist_egg upload
c:\Python26\python.exe setup.py bdist_wininst --target-version=2.6 register upload
Trigger binary builds for OSX from the buildbots dipy-bdist-mpkg-2.6, dipy-bdist-mpkg-2.7. egg and mpkg builds will appear in http://nipy.bic.berkeley.edu/dipy-dist . Download the eggs and upload to pypi.
Upload the dmg files with the files interface for the new dipy release.
Building OSX dmgs from the mpkg builds.
The buildbot binary builders build mpkg directories, which are installers for OSX.
These need their permissions to be fixed because the installers should install the files as the root user, group admin. The all need to be converted to OSX disk images. Use the ./tools/build_dmgs.py, with something like this command line:
./tools/build_dmgs "dipy-dist/dipy-0.6.0-py*.mpkg"
For this to work you’ll need several things:
- An account on a OSX box with sudo (Admin user) on which to run the script.
- ssh access to the buildbot server http://nipy.bic.berkeley.edu (ask Matthew or Eleftherios).
- a development version of bdist_mpkg installed from https://github.com/matthew-brett/bdist_mpkg. You need this second for the script reown_mpkg that fixes the permissions.
Upload the dmg files with the files interface for the new dipy release.
Checkout the tagged release, build the html docs and upload them to the github pages website:
make upload
You need to checkout the tagged version in order to get the version number correct for the doc build. The version number gets picked up from the info.py version.
Announce to the mailing lists. With fear and trembling.