def find_new_urls(vcs_type, vcs_url, package, maintainer_email, net_access=False): if net_access and ( vcs_url.startswith('https://') or vcs_url.startswith('http://')): headers = {'User-Agent': USER_AGENT} try: response = urlopen( Request(vcs_url, headers=headers), timeout=DEFAULT_URLLIB_TIMEOUT) except (urllib.error.HTTPError, urllib.error.URLError): pass except socket.timeout: pass else: redirected_url = response.geturl() if not is_on_obsolete_host(redirected_url): vcs_url = redirected_url vcs_browser = determine_browser_url(vcs_type, vcs_url) print("Update Vcs-* headers from URL redirect.") return (vcs_type, vcs_url, vcs_browser) # If possible, we use vcswatch to find the VCS repository URL if net_access: loop = asyncio.get_event_loop() try: (vcs_type, vcs_url, vcs_browser) = loop.run_until_complete( retrieve_vcswatch_urls(package)) except VcsWatchError as e: warn('vcswatch URL unusable: %s' % e.args[0]) except KeyError: pass else: if not is_on_obsolete_host(vcs_url): print("Update Vcs-* headers from vcswatch.") if is_on_obsolete_host(vcs_browser): vcs_browser = ( determine_browser_url(vcs_type, vcs_url) or vcs_browser) return (vcs_type, vcs_url, vcs_browser) warn('vcswatch URL %s is still on old infrastructure.' % vcs_url) # Otherwise, attempt to guess based on maintainer email. guessed_url = guess_repository_url(package, maintainer_email) if guessed_url is not None: vcs_type = "Git" vcs_url = guessed_url else: vcs_url = salsa_url_from_alioth_url(vcs_type, vcs_url) if vcs_url is None: raise NewRepositoryURLUnknown(vcs_type, vcs_url) vcs_type = "Git" # Verify that there is actually a repository there if net_access: if verify_salsa_repository(vcs_url) is False: raise NewRepositoryURLUnknown(vcs_type, vcs_url) print("Update Vcs-* headers to use salsa repository.") vcs_browser = determine_salsa_browser_url(vcs_url) return (vcs_type, vcs_url, vcs_browser)
def replace_full_license(para): license = para.license license_matched = find_common_license_from_fulltext(license.text) if license_matched is None: if os.path.exists(os.path.join(COMMON_LICENSES_DIR, license.synopsis)): warn('A common license shortname (%s) is used, but license ' 'text not recognized.' % license.synopsis) return # The full license text was found. Replace it with a blurb. canonical_id = canonical_license_id(license.synopsis) for shortname, blurb in _BLURB.items(): if canonical_id == canonical_license_id(shortname): break else: if license.synopsis in SPDX_RENAMES: renames[license.synopsis] = SPDX_RENAMES[license.synopsis] return else: warn('Found full license text for %s, but unknown synopsis %s (%s)' % (license_matched, license.synopsis, canonical_id)) return if license_matched == 'Apache-2.0': fixed_lintian_tag('source', 'copyright-file-contains-full-apache-2-license', info=()) if license_matched.startswith('GFDL-'): fixed_lintian_tag('source', 'copyright-file-contains-full-gfdl-license', info=()) if license_matched.startswith('GPL-'): fixed_lintian_tag('source', 'copyright-file-contains-full-gpl-license', info=()) para.license = License(license.synopsis, blurb) return license_matched
async def valid_bug(package, bug): if not net_access_allowed(): return None global debbugs if debbugs is None: from lintian_brush.debbugs import DebBugs _debbugs = DebBugs() try: await _debbugs.connect() except ImportError: # No asynpcg? return None except socket.gaierror as e: warn('Unable to connect to debbugs: %s' % e) return None debbugs = _debbugs return await debbugs.check_bug(package, bug)
def canonical_license_id(license_id): # From the standard: # For licenses that have multiple versions in use, the short name is # formed from the general short name of the license family, followed by a # dash and the version number. If the version number is omitted, the # lowest version number is implied. When the license grant permits using # the terms of any later version of that license, add a plus sign to the # end of the short name. For example, the short name GPL refers to the GPL # version 1 and is equivalent to GPL-1, although the latter is clearer and # therefore preferred. If the package may be distributed under the GPL # version 1 or any later version, use a short name of GPL-1+. # # For SPDX compatibility, versions with trailing dot-zeroes are considered # to be equivalent to versions without (e.g., “2.0.0” is considered equal # to “2.0” and “2”). m = re.fullmatch(r'([A-Za-z0-9]+)(\-[0-9\.]+)?(\+)?', license_id) if not m: warn('Unable to get canonical name for %r' % license_id) return license_id version = (m.group(2) or '-1')[1:] while version.endswith('.0'): version = version[:-2] return '%s-%s%s' % (m.group(1), version, m.group(3) or '')
if pgpsigurlmangle and has_keys: continue try: pgpmode = entry.get_option('pgpmode') except KeyError: pgpmode = 'default' else: if diligence() == 0: continue if pgpmode in ('gittag', 'previous', 'next', 'self'): sys.exit(2) try: releases = list( sorted(entry.discover(source_package_name()), reverse=True)) except HTTPError as e: warn('HTTP error accessing discovery URL %s: %s.' % (e.geturl(), e)) sys.exit(0) for r in releases[:RELEASES_TO_INSPECT]: if r.pgpsigurl: pgpsigurls = [(pgpsigurlmangle, r.pgpsigurl)] else: pgpsigurls = [(mangle, apply_url_mangle(mangle, r.url)) for mangle in COMMON_MANGLES] for mangle, pgpsigurl in pgpsigurls: # Try and download signatures from some predictable locations. try: resp = urlopen(pgpsigurl) except HTTPError: continue sig = resp.read() actual = urlopen(r.url).read()
'Files', 'License', 'Copyright', 'Comment', 'Upstream-Name', 'Format', 'Upstream-Contact', 'Source', 'Upstream', 'Contact', 'Name' } typo_fixed = set() case_fixed = set() try: with Deb822Editor('debian/copyright') as updater: for paragraph in updater.paragraphs: for field in paragraph: if field in valid_field_names: continue if (field.startswith('X-') and field[2:] in valid_field_names): if field[2:] in paragraph: warn('Both %s and %s exist.' % (field, field[2:])) continue value = paragraph[field] del paragraph[field] paragraph[field[2:]] = value typo_fixed.add((field, field[2:])) fixed_lintian_tag('source', 'field-name-typo-in-dep5-copyright', '%s (line XX)' % field) continue for option in valid_field_names: if distance(field, option) == 1: value = paragraph[field] del paragraph[field] paragraph[option] = value
#!/usr/bin/python3 import email.utils from debmutate.changelog import ChangelogEditor from lintian_brush.fixer import report_result, LintianIssue, warn versions = [] with ChangelogEditor() as updater: for block in updater.changelog: try: dt = email.utils.parsedate_to_datetime(block.date) except (TypeError, ValueError): warn('Invalid date %r for %s' % (block.date, block.version)) # parsedate_to_datetime is buggy and raises a TypeError # when the date is invalid. continue if dt is None: # Can't interpret the date. Just ignore.. continue newdate = email.utils.format_datetime(dt) issue = LintianIssue('source', 'debian-changelog-has-wrong-day-of-week', info='%04d-%02d-%02d is a %s' % (dt.year, dt.month, dt.day, dt.strftime('%A'))) if newdate[:3] != block.date[:3] and issue.should_fix(): block.date = newdate versions.append(block.version) issue.report_fixed()
except FileNotFoundError: return False return False if autoreconf_disabled(): try: with open('configure', 'rb') as f: for line in f: if b'runstatedir' in line: break else: new_debhelper_compat_version = min( new_debhelper_compat_version, 10) warn('Not upgrading beyond debhelper %d, since the package ' 'disables autoreconf but its configure does not provide ' '--runstatedir.' % new_debhelper_compat_version) except (IsADirectoryError, FileNotFoundError): pass if os.path.exists('debian/compat'): # Package currently stores compat version in debian/compat.. current_debhelper_compat_version = read_debhelper_compat_file( 'debian/compat') if current_debhelper_compat_version < new_debhelper_compat_version: with open('debian/compat', 'w') as cf: cf.write('%s\n' % new_debhelper_compat_version) else: # Nothing to do sys.exit(2)
if older_source_format_issue.should_fix(): if package_is_native(): format = '3.0 (native)' description = "Upgrade to newer source format %s." % format else: from lintian_brush.patches import ( tree_non_patches_changes, find_patches_directory, ) from breezy import errors from breezy.workingtree import WorkingTree patches_directory = find_patches_directory('.') if patches_directory not in ('debian/patches', None): # Non-standard patches directory. warn('Tree has non-standard patches directory %s.' % (patches_directory)) else: try: tree, path = WorkingTree.open_containing('.') except errors.NotBranchError as e: if not meets_minimum_certainty('possible'): warn('unable to open vcs to check for delta: %s' % e) sys.exit(0) format = "3.0 (quilt)" description = "Upgrade to newer source format %s." % format else: delta = list(tree_non_patches_changes(tree, patches_directory)) if delta: warn('Tree has non-quilt changes against upstream.') if opinionated(): format = "3.0 (quilt)"