-
Notifications
You must be signed in to change notification settings - Fork 572
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Better releases #593
Better releases #593
Changes from 7 commits
08b0d79
82f87ea
f1a8e8f
6503dd4
696b08c
044cc7f
c43eff3
b3193e4
a762528
ab3715e
601174c
45f44ce
911065c
fa4959a
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,80 @@ | ||
.. _nbconvert_release: | ||
|
||
Making an ``nbconvert`` release | ||
=============================== | ||
|
||
This document guides a contributor through creating a release of ``nbconvert``. | ||
|
||
|
||
Assign all merged PRs to milestones | ||
----------------------------------- | ||
|
||
Go to GitHub and assign all PRs that have been merged to milestones. | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. We can provide a handy link here to PRs merged with no milestone: There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Great idea. |
||
This will be helpful when you update the changelog. | ||
|
||
Check installed tools | ||
--------------------- | ||
|
||
Review ``CONTRIBUTING.md``, particularly the testing and release sections. | ||
|
||
Clean the repository | ||
-------------------- | ||
|
||
You can remove all non-tracked files with: | ||
|
||
.. code:: bash | ||
|
||
git clean -xfdi | ||
|
||
This would ask you for confirmation before removing all untracked files. | ||
|
||
Make sure the ``dist/`` folder is clean and avoid stale builds from | ||
previous attempts. | ||
|
||
Create the release | ||
------------------ | ||
|
||
#. Update the changelog to account for all the PRs assigned to this milestone. | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Should this explicitly mention where the changelog file is? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Relative to the top level? or relative to the location of this file? |
||
|
||
#. Update version number in ``notebook/_version.py``. | ||
|
||
#. Commit and tag the release with the current version number: | ||
|
||
.. code:: bash | ||
|
||
git commit -am "release $VERSION" | ||
git tag $VERSION | ||
|
||
#. You are now ready to build the ``sdist`` and ``wheel``: | ||
|
||
.. code:: bash | ||
|
||
python setup.py sdist | ||
python setup.py bdist_wheel | ||
|
||
#. You can now test the ``wheel`` and the ``sdist`` locally before uploading | ||
to PyPI. Make sure to use `twine <https://github.com/pypa/twine>`_ to | ||
upload the archives over SSL. | ||
|
||
.. code:: bash | ||
|
||
twine upload dist/* | ||
|
||
Release the new version | ||
----------------------- | ||
|
||
#. Push directly on master, including --tags separately | ||
|
||
.. code:: bash | ||
|
||
git push upstream | ||
git push upstream --tags | ||
|
||
#. Push tages on master forgetting to push ``--tags`` too. | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This looks like a confused copy of the point immediately above? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. yes i think I was in the middle of splitting one thing in the original notebook, but then realised that I could just have the raw code as two lines. |
||
|
||
|
||
Return to development state | ||
--------------------------- | ||
|
||
#. If all went well, change the ``notebook/_version.py`` back adding the | ||
``.dev`` suffix. |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,7 @@ | ||
version_info = (5, 2, 0,'.dev') | ||
__version__ = '.'.join(map(str, version_info[0:3])) + ''.join(version_info[3:]) | ||
from nbconvert._version_tools import create_valid_version | ||
|
||
version_info = (5, 2, 0) | ||
pre_info = '' | ||
dev_info = '.dev' | ||
__version__ = create_valid_version(version_info, pre_input=pre_info, dev_input=dev_info) | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,83 @@ | ||
# import pep440 # cannot be imported as described below | ||
import re | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This file looks like it's copied from somewhere - can we have a comment at the top clearly saying where, including what version (or commit, if necessary)? We may also need to include a copyright notice and license text. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. It's @Carreau's There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Also I should mention I thought that I had included that comment at the top and in the main text, I guess the only thing that's missing is a github link I will fix that. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yeah, put an explicit Github link and a commit ID, for good measure. I don't personally mind about the copyright notice & license text, and @Carreau may well not mind either. In general, though, if we're including code from another project, we should include those things - it's a typical condition of the licenses which allow you to redistribute that code. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. You may also just copy past the I'll make my pep440 easier to vendor. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Got it from pep440 itself Appendix B. |
||
|
||
def create_valid_version(release_info, epoch=None, pre_input='', dev_input=''): | ||
''' | ||
Creates a pep440 valid version of version number given a tuple integers | ||
and optional epoch, prerelease and developmental info. | ||
|
||
Parameters | ||
---------- | ||
release_info : Tuple(Int) | ||
epoch : Int, default None | ||
pre_input : Str, default '' | ||
dev_input : Str, default '' | ||
''' | ||
|
||
pep440_err = "The version number is not a pep 440 compliant version number" | ||
|
||
|
||
if epoch is not None: | ||
epoch_seg = str(epoch) + '!' | ||
else: | ||
epoch_seg = '' | ||
|
||
release_seg = '.'.join(map(str, release_info)) | ||
|
||
_magic_pre = ['a','b','rc'] | ||
if pre_input!='' and not any([pre_input.startswith(prefix) for prefix in _magic_pre]): | ||
raise ValueError(pep440_err + "\n please fix your prerelease segment.") | ||
else: | ||
pre_seg = pre_input | ||
|
||
if dev_input=='': | ||
dev_seg = dev_input | ||
elif not dev_input.startswith('.') and dev_input.startswith('dev'): | ||
dev_seg = ''.join(['.', dev_input]) | ||
elif dev_input.startswith('.dev'): | ||
dev_seg = dev_input | ||
elif dev_input!='': | ||
raise ValueError(pep440_err + "\n please fix your development segment.") | ||
|
||
if dev_input!='' and not any([dev_seg.endswith(str(n)) for n in range(10)]): | ||
dev_seg = ''.join([dev_seg,'0']) | ||
|
||
out_version = ''.join([epoch_seg, release_seg, pre_seg, dev_seg]) | ||
|
||
if is_canonical(out_version): | ||
return out_version | ||
else: | ||
raise ValueError(pep440_err) | ||
|
||
# This has been ported directly from the pep440 package since it cannot be | ||
# installed as part of a setuptools based install without using pyproject.toml | ||
|
||
posint = '(0|[1-9]\d*)' | ||
|
||
# 0!0.0.0rc0.post0.dev0 | ||
|
||
tpl_string_re = ('^' # Start | ||
'([1-9]\d*!)?' # [N!] | ||
'{posint}' # N | ||
'(\.{posint})*' # (.N)* | ||
'((a|b|rc){posint})?' # [{a|b|rc}N] | ||
'(\.post{posint})?' # [.postN] | ||
'(\.dev{postdev})?' # [.devN] | ||
'$') | ||
string_re = tpl_string_re.format(posint=posint, postdev=posint) | ||
loose440re = re.compile(tpl_string_re.format(posint=posint, postdev=(posint+'?'))) | ||
pep440re = re.compile(string_re) | ||
|
||
def is_canonical(version, loosedev=False): | ||
""" | ||
Return whether or not the version string is canonical according to Pep 440 | ||
""" | ||
if loosedev: | ||
return loose440re.match(version) is not None | ||
return pep440re.match(version) is not None | ||
|
||
|
||
# this is the end of the direct port from pep440 | ||
|
||
|
||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -197,13 +197,20 @@ def run(self): | |
'testpath', | ||
] | ||
|
||
extras_require = setuptools_args['extras_require'] = { | ||
extra_requirements = { | ||
# FIXME: tests still require nose for some utility calls, | ||
# but we are running with pytest | ||
'test': ['pytest', 'pytest-cov', 'nose', 'ipykernel', 'jupyter_client'], | ||
'test': ['pytest', 'pytest-cov', 'nose', 'ipykernel', 'jupyter_client>=4.2'], | ||
'serve': ['tornado>=4.0'], | ||
'execute': ['jupyter_client>=4.2'], | ||
} | ||
s = [] | ||
[s.extend(values) for values in extra_requirements.values()] | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I don't like using list comprehensions for side effects. I'd either do this with a regular for loop: for reqs in extra_requirements.values():
s.extend(reqs) Or get clever with s = sum(extra_requirements.values(), []) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I did not know that sum could be applied to lists. I'm intrigued because that could allow: There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Yep, I think that would be OK. I believe that sum can accept anything which you can combine with the |
||
extra_requirements['all'] = list(set(s)) | ||
|
||
extras_require = setuptools_args['extras_require'] = { | ||
**extra_requirements | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This syntax is new in Python 3.5. If we need a copy of the dictionary, I think |
||
} | ||
|
||
if 'setuptools' in sys.modules: | ||
from setuptools.command.develop import develop | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Have you checked a built copy of this? I can't remember if backticks in headings work.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, they do work.