re.compile("^(?P<version>v|V{0,1})(\.{0,1})(?P<major>0|[1-9]\d*)\.(?P<minor>0+|[1-9]\d*)(\.(?P<patch>0+|[1-9]\d*)(?:-(?P<prerelease>(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+(?P<buildmetadata>[0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?)?$"),
# non-sematic, e.g. 1.2.3.4
re.compile("^(?P<version>v|V{0,1})(\.{0,1})(?P<major>0|[1-9]\d*)\.(?P<minor>0+|[1-9]\d*)(\.(?P<patch>0+|[1-9]\d*)(\.(?P<subpatch>0|[1-9]\d*))?)$"),
- # non-sematic, e.g. 2023-05
+ # non-sematic, e.g. 2023-05[-dev]
re.compile("^(?P<year>[1-9]{1}[0-9]{3})\.(?P<month>[0-9]{2})(-dev){0,1}$"),
# non-semantic, e.g. abcdef0
re.compile("^[a-f0-9]{7}$"),
def remove_version(software: str) -> str:
# NOISY-DEBUG: print(f"DEBUG: software='{software}' - CALLED!")
- if not "." in software:
+ if not "." in software and " " not in software:
print(f"WARNING: software='{software}' does not contain a version number.")
return software
if type(software) is str and software == "":
# NOISY-DEBUG: print(f"DEBUG: Corrected empty string to None for software of domain='{domain}'")
software = None
- elif type(software) is str and "." in software:
+ elif type(software) is str and ("." in software or " " in software):
# NOISY-DEBUG: print(f"DEBUG: software='{software}' may contain a version number, domain='{domain}', removing it ...")
software = remove_version(software)
if str(software) == "":
# NOISY-DEBUG: print(f"DEBUG: software for '{domain}' was not detected, trying generator ...")
software = fetch_generator_from_path(domain)
- elif len(str(software)) > 0 and "." in software:
+ elif len(str(software)) > 0 and ("." in software or " " in software):
# NOISY-DEBUG: print(f"DEBUG: software='{software}' may contain a version number, domain='{domain}', removing it ...")
software = remove_version(software)