| |
@@ -1,5 +1,6 @@
|
| |
import json
|
| |
import re
|
| |
+ from typing import List, Optional
|
| |
|
| |
from sqlalchemy import bindparam, Integer, func
|
| |
from sqlalchemy.sql import true, text
|
| |
@@ -13,6 +14,7 @@
|
| |
|
| |
from coprs.logic import users_logic
|
| |
from coprs.logic import builds_logic
|
| |
+ from coprs.models import Package
|
| |
from copr_common.enums import StatusEnum
|
| |
|
| |
log = app.logger
|
| |
@@ -131,7 +133,9 @@
|
| |
return package
|
| |
|
| |
@classmethod
|
| |
- def get_for_webhook_rebuild(cls, copr_id, webhook_secret, clone_url, commits, ref_type, ref):
|
| |
+ def get_for_webhook_rebuild(
|
| |
+ cls, copr_id, webhook_secret, clone_url, commits, ref_type, ref, pkg_name: Optional[str]
|
| |
+ ) -> List[Package]:
|
| |
clone_url_stripped = re.sub(r'(\.git)?/*$', '', clone_url)
|
| |
|
| |
packages = (models.Package.query.join(models.Copr)
|
| |
@@ -152,20 +156,60 @@
|
| |
if not package.copr.active_copr_chroots:
|
| |
continue
|
| |
|
| |
- if cls.commits_belong_to_package(package, commits, ref_type, ref):
|
| |
- result += [package]
|
| |
+ if cls._belongs_to_package(package, commits, ref_type, ref, pkg_name):
|
| |
+ result.append(package)
|
| |
|
| |
return result
|
| |
|
| |
@classmethod
|
| |
- def commits_belong_to_package(cls, package, commits, ref_type, ref):
|
| |
+ def _belongs_to_package(
|
| |
+ cls, package: Package, commits, ref_type: str, ref: str, pkg_name: Optional[str]
|
| |
+ ) -> bool:
|
| |
if ref_type == "tag":
|
| |
- matches = re.search(r'(.*)-[^-]+-[^-]+$', ref)
|
| |
- if matches and package.name != matches.group(1):
|
| |
+ return cls._tag_belongs_to_package(package, ref, pkg_name)
|
| |
+
|
| |
+ return cls.commits_belong_to_package(package, commits, ref)
|
| |
+
|
| |
+ @staticmethod
|
| |
+ def _ref_matches_copr_pkgname(ref: str, copr_pkg_name: str) -> bool:
|
| |
+ """
|
| |
+ We accept N-V-R and N-V. Version and Release needs to contain at least one
|
| |
+ digit.
|
| |
+ """
|
| |
+ separators = ["-", "_"]
|
| |
+
|
| |
+ def _parts_match(ref_parts):
|
| |
+ return any(separator.join(ref_parts) == copr_pkg_name for separator in separators)
|
| |
+
|
| |
+ def _has_a_version_part(ref_parts):
|
| |
+ if len(ref_parts) < 2:
|
| |
return False
|
| |
- else:
|
| |
- return True
|
| |
+ return any(char.isdigit() for char in ref_parts[-1])
|
| |
+
|
| |
+ for sep in separators:
|
| |
+ parts = ref.split(sep)
|
| |
+ # in case that ref has both version and release we need to do this twice
|
| |
+ for _ in range(2):
|
| |
+ if not _has_a_version_part(parts):
|
| |
+ break
|
| |
+ # drop the last version component, and compare
|
| |
+ parts.pop()
|
| |
+ if _parts_match(parts):
|
| |
+ return True
|
| |
+
|
| |
+ return False
|
| |
|
| |
+ @classmethod
|
| |
+ def _tag_belongs_to_package(
|
| |
+ cls, package: Package, ref: str, pkg_name: Optional[str]
|
| |
+ ) -> bool:
|
| |
+ if package.name == pkg_name:
|
| |
+ return True
|
| |
+
|
| |
+ return cls._ref_matches_copr_pkgname(ref, package.name)
|
| |
+
|
| |
+ @classmethod
|
| |
+ def commits_belong_to_package(cls, package: Package, commits, ref: str) -> bool:
|
| |
committish = package.source_json_dict.get("committish") or ''
|
| |
if committish and not ref.endswith(committish):
|
| |
return False
|
| |
see commit messages for reasoning
Fix #2213