forked from LBRYCommunity/lbry-sdk
updated release script with unittests and ability to go from rc to final release
This commit is contained in:
parent
0e90c4b611
commit
75f82b107e
1 changed files with 101 additions and 38 deletions
|
@ -4,6 +4,7 @@ import io
|
|||
import sys
|
||||
import json
|
||||
import argparse
|
||||
import unittest
|
||||
from datetime import date
|
||||
from getpass import getpass
|
||||
|
||||
|
@ -52,6 +53,14 @@ def get_label(pr, prefix):
|
|||
return label
|
||||
|
||||
|
||||
def get_previous_final(repo, current_release):
|
||||
assert current_release.rc is not None, "Need an rc to find the previous final release."
|
||||
previous = None
|
||||
for release in repo.releases(current_release.rc + 1):
|
||||
previous = release
|
||||
return previous
|
||||
|
||||
|
||||
class Version:
|
||||
|
||||
def __init__(self, major=0, minor=0, micro=0, rc=None):
|
||||
|
@ -73,21 +82,25 @@ class Version:
|
|||
version = re.search('__version__ = "(.*?)"', src).group(1)
|
||||
return cls.from_string(version)
|
||||
|
||||
def increment(self, part):
|
||||
def increment(self, action):
|
||||
cls = self.__class__
|
||||
if part == 'major':
|
||||
return cls(self.major+1)
|
||||
elif part == 'minor':
|
||||
return cls(self.major, self.minor+1)
|
||||
elif part == 'micro':
|
||||
return cls(self.major, self.minor, self.micro+1)
|
||||
elif part == 'rc':
|
||||
if self.rc is None:
|
||||
return cls(self.major, self.minor, self.micro+1, 1)
|
||||
else:
|
||||
|
||||
if action == '*-rc':
|
||||
assert self.rc is not None, f"Can't drop rc designation because {self} is already not an rc."
|
||||
return cls(self.major, self.minor, self.micro)
|
||||
elif action == '*+rc':
|
||||
assert self.rc is not None, "Must already be an rc to increment."
|
||||
return cls(self.major, self.minor, self.micro, self.rc+1)
|
||||
else:
|
||||
raise ValueError(f'unknown version part: {part}')
|
||||
|
||||
assert self.rc is None, f"Can't start a new rc because {self} is already an rc."
|
||||
if action == 'major+rc':
|
||||
return cls(self.major+1, rc=1)
|
||||
elif action == 'minor+rc':
|
||||
return cls(self.major, self.minor+1, rc=1)
|
||||
elif action == 'micro+rc':
|
||||
return cls(self.major, self.minor, self.micro+1, 1)
|
||||
|
||||
raise ValueError(f'unknown action: {action}')
|
||||
|
||||
@property
|
||||
def tag(self):
|
||||
|
@ -107,16 +120,22 @@ def release(args):
|
|||
|
||||
current_version = Version.from_content(version_file)
|
||||
print(f'Current Version: {current_version}')
|
||||
new_version = current_version.increment(args.increment)
|
||||
new_version = current_version.increment(args.action)
|
||||
print(f' New Version: {new_version}')
|
||||
print()
|
||||
|
||||
current_release = repo.release_from_tag(current_version.tag)
|
||||
if args.action == '*-rc':
|
||||
previous_release = get_previous_final(repo, current_version)
|
||||
else:
|
||||
previous_release = repo.release_from_tag(current_version.tag)
|
||||
|
||||
areas = {}
|
||||
for pr in gh.search_issues(f"merged:>={current_release._json_data['created_at']} repo:lbryio/lbry"):
|
||||
for pr in gh.search_issues(f"merged:>={previous_release._json_data['created_at']} repo:lbryio/lbry"):
|
||||
for area_name in get_labels(pr, 'area'):
|
||||
area = areas.setdefault(area_name, [])
|
||||
area.append(f' * [{get_label(pr, "type")}] {pr.title} ({pr.html_url})')
|
||||
type_label = get_label(pr, "type")
|
||||
if not (args.action == '*-rc' and type_label == 'fixup'):
|
||||
area.append(f' * [{type_label}] {pr.title} ({pr.html_url})')
|
||||
|
||||
area_names = list(areas.keys())
|
||||
area_names.sort()
|
||||
|
@ -133,6 +152,10 @@ def release(args):
|
|||
for pr in prs:
|
||||
w(pr)
|
||||
|
||||
print(body.getvalue())
|
||||
|
||||
if not args.dry_run:
|
||||
|
||||
commit = version_file.update(
|
||||
new_version.tag,
|
||||
version_file.decoded.decode('utf-8').replace(str(current_version), str(new_version)).encode()
|
||||
|
@ -155,10 +178,50 @@ def release(args):
|
|||
)
|
||||
|
||||
|
||||
class TestReleaseTool(unittest.TestCase):
|
||||
|
||||
def test_version_parsing(self):
|
||||
self.assertTrue(str(Version.from_string('1.2.3')), '1.2.3')
|
||||
self.assertTrue(str(Version.from_string('1.2.3rc4')), '1.2.3rc4')
|
||||
|
||||
def test_version_increment(self):
|
||||
v = Version.from_string('1.2.3')
|
||||
self.assertTrue(str(v.increment('major+rc')), '2.0.0rc1')
|
||||
self.assertTrue(str(v.increment('minor+rc')), '1.3.0rc1')
|
||||
self.assertTrue(str(v.increment('micro+rc')), '1.2.4rc1')
|
||||
with self.assertRaisesRegex(AssertionError, "Must already be an rc to increment."):
|
||||
v.increment('*+rc')
|
||||
with self.assertRaisesRegex(AssertionError, "Can't drop rc designation"):
|
||||
v.increment('*-rc')
|
||||
|
||||
v = Version.from_string('1.2.3rc3')
|
||||
self.assertTrue(str(v.increment('*+rc')), '1.2.3rc4')
|
||||
self.assertTrue(str(v.increment('*-rc')), '1.2.3')
|
||||
with self.assertRaisesRegex(AssertionError, "already an rc"):
|
||||
v.increment('major+rc')
|
||||
with self.assertRaisesRegex(AssertionError, "already an rc"):
|
||||
v.increment('minor+rc')
|
||||
with self.assertRaisesRegex(AssertionError, "already an rc"):
|
||||
v.increment('micro+rc')
|
||||
|
||||
|
||||
def test():
|
||||
runner = unittest.TextTestRunner(verbosity=2)
|
||||
loader = unittest.TestLoader()
|
||||
suite = loader.loadTestsFromTestCase(TestReleaseTool)
|
||||
runner.run(suite)
|
||||
|
||||
|
||||
def main():
|
||||
parser = argparse.ArgumentParser()
|
||||
parser.add_argument("increment", choices=['major', 'minor', 'micro', 'rc'])
|
||||
release(parser.parse_args())
|
||||
parser.add_argument("--test", default=False, action="store_true", help="run unit tests")
|
||||
parser.add_argument("--dry-run", default=False, action="store_true", help="show what will be done")
|
||||
parser.add_argument("action", nargs="?", choices=['major+rc', 'minor+rc', 'micro+rc', '*+rc', '*-rc'])
|
||||
args = parser.parse_args()
|
||||
if args.test:
|
||||
test()
|
||||
else:
|
||||
release(args)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
|
|
Loading…
Reference in a new issue