From 9b8f29011725917a5ddcb519b08d4bfd4309e224 Mon Sep 17 00:00:00 2001 From: Doug Hellmann Date: Tue, 20 Feb 2018 10:38:26 -0500 Subject: [PATCH] use packaging to determine the canonical name for projects on PyPI Rather than applying the rules ourselves, use the packaging project utility function to prepare the canonical name. Change-Id: I6310585ff14c376e954b0edc9def67cd65a5d550 Signed-off-by: Doug Hellmann --- openstack_releases/cmds/validate.py | 7 ------- openstack_releases/pythonutils.py | 20 ++++++++++++++++---- requirements.txt | 1 + 3 files changed, 17 insertions(+), 11 deletions(-) diff --git a/openstack_releases/cmds/validate.py b/openstack_releases/cmds/validate.py index 22d823e347..87325d840b 100644 --- a/openstack_releases/cmds/validate.py +++ b/openstack_releases/cmds/validate.py @@ -521,13 +521,6 @@ def validate_pypi_permissions(deliv, context): pypi_name = sdist uploaders = pythonutils.get_pypi_uploaders(pypi_name) - if not uploaders: - # Names like "openstack_requirements" are translated to - # "openstack-requirements" in the PyPI API. - alt_name = pypi_name.replace('_', '-') - LOG.debug('retrying with pypi_name name {!r}'.format(alt_name)) - uploaders = pythonutils.get_pypi_uploaders(alt_name) - if not uploaders: context.error( 'could not find users with permission to upload packages ' diff --git a/openstack_releases/pythonutils.py b/openstack_releases/pythonutils.py index ef02049189..f2951408dc 100644 --- a/openstack_releases/pythonutils.py +++ b/openstack_releases/pythonutils.py @@ -18,6 +18,7 @@ import os import os.path import xmlrpc.client +from packaging import utils as packaging_utils import requests from openstack_releases import processutils @@ -65,8 +66,9 @@ def guess_sdist_name(project): def get_pypi_info(dist_name): "Return PyPI information for the distribution." - LOG.debug('looking at PyPI for {}'.format(dist_name)) - url = 'https://pypi.python.org/pypi/{}/json'.format(dist_name) + canonical_name = packaging_utils.canonicalize_name(dist_name) + LOG.debug('looking at PyPI for {!r}'.format(canonical_name)) + url = 'https://pypi.python.org/pypi/{}/json'.format(canonical_name) LOG.debug(url) try: return requests.get(url).json() @@ -74,12 +76,22 @@ def get_pypi_info(dist_name): return {} -def get_pypi_uploaders(dist_name): +def _get_pypi_roles(dist_name): client = xmlrpc.client.ServerProxy('https://pypi.python.org/pypi') - roles = client.package_roles(dist_name) + LOG.debug('retrieving roles for {!r}'.format( + dist_name)) + return client.package_roles(dist_name) + + +def get_pypi_uploaders(dist_name): + roles = _get_pypi_roles(dist_name) + if not roles: + canonical_name = packaging_utils.canonicalize_name(dist_name) + roles = _get_pypi_roles(canonical_name) uploaders = set( acct for role, acct in roles if role in ('Owner', 'Maintainer') ) + LOG.debug('found: {}'.format(sorted(uploaders))) return uploaders diff --git a/requirements.txt b/requirements.txt index c08692f322..8fb8e2b118 100644 --- a/requirements.txt +++ b/requirements.txt @@ -32,3 +32,4 @@ sphinx>=1.6.2 # BSD pyfiglet>=0.7.5 appdirs +packaging>=16.5