예제 #1
0
    def _get_attached_bugs(self, advisories):
        # get bugs attached to all advisories
        bugs = set()
        try:
            for advisory in advisories:
                green_print(f"Retrieving bugs for advisory {advisory}")
                bugs.update(errata.get_bug_ids(advisory))
        except GSSError:
            exit_unauthenticated()
        green_print(f"Found {len(bugs)} bugs")

        return list(bzutil.get_bugs(self.bzapi, list(bugs)).values())
예제 #2
0
    async def run(self):
        self.working_dir.mkdir(parents=True, exist_ok=True)
        build_data_repo = self.working_dir / "ocp-build-data-push"
        shutil.rmtree(build_data_repo, ignore_errors=True)
        shutil.rmtree(self.elliott_working_dir, ignore_errors=True)
        shutil.rmtree(self.doozer_working_dir, ignore_errors=True)

        release_config = None
        group_config = await self.load_group_config()

        if self.assembly != "stream":
            releases_config = await self.load_releases_config()
            release_config = releases_config.get("releases",
                                                 {}).get(self.assembly, {})
            if not release_config:
                raise ValueError(
                    f"Assembly {self.assembly} is not defined in releases.yml for group {self.group_name}."
                )
            group_config = assembly_group_config(
                Model(releases_config), self.assembly,
                Model(group_config)).primitive()
            asssembly_type = release_config.get("assembly",
                                                {}).get("type", "standard")
            if asssembly_type == "standard":
                self.release_name = self.assembly
                self.release_version = tuple(
                    map(int, self.release_name.split(".", 2)))
            elif asssembly_type == "custom":
                self.release_name = f"{self.release_version[0]}.{self.release_version[1]}.0-assembly.{self.assembly}"
            elif asssembly_type == "candidate":
                self.release_name = f"{self.release_version[0]}.{self.release_version[1]}.0-{self.assembly}"
            nightlies = release_config.get("assembly", {}).get(
                "basis", {}).get("reference_releases", {}).values()
            self.candidate_nightlies = self.parse_nighties(nightlies)

        if release_config and asssembly_type != "standard":
            _LOGGER.warning("No need to check Blocker Bugs for assembly %s",
                            self.assembly)
        else:
            _LOGGER.info("Checking Blocker Bugs for release %s...",
                         self.release_name)
            self.check_blockers()

        advisories = {}

        if self.default_advisories:
            advisories = group_config.get("advisories", {})
        else:
            _LOGGER.info("Creating advisories for release %s...",
                         self.release_name)
            if release_config:
                advisories = group_config.get("advisories", {}).copy()

            if self.release_version[2] == 0:  # GA release
                if advisories.get("rpm", 0) <= 0:
                    advisories["rpm"] = self.create_advisory(
                        "RHEA", "rpm", "ga")
                if advisories.get("image", 0) <= 0:
                    advisories["image"] = self.create_advisory(
                        "RHEA", "image", "ga")
            else:  # z-stream release
                if advisories.get("rpm", 0) <= 0:
                    advisories["rpm"] = self.create_advisory(
                        "RHBA", "rpm", "standard")
                if advisories.get("image", 0) <= 0:
                    advisories["image"] = self.create_advisory(
                        "RHBA", "image", "standard")
            if self.release_version[0] > 3:
                if advisories.get("extras", 0) <= 0:
                    advisories["extras"] = self.create_advisory(
                        "RHBA", "image", "extras")
                if advisories.get("metadata", 0) <= 0:
                    advisories["metadata"] = self.create_advisory(
                        "RHBA", "image", "metadata")

        _LOGGER.info("Ensuring JIRA ticket for release %s...",
                     self.release_name)
        jira_issue_key = group_config.get("release_jira")
        jira_template_vars = {
            "release_name": self.release_name,
            "x": self.release_version[0],
            "y": self.release_version[1],
            "z": self.release_version[2],
            "release_date": self.release_date,
            "advisories": advisories,
            "candidate_nightlies": self.candidate_nightlies,
        }
        if jira_issue_key:
            _LOGGER.info("Reusing existing release JIRA %s", jira_issue_key)
            jira_issue = self._jira_client.get_issue(jira_issue_key)
            subtasks = [
                self._jira_client.get_issue(subtask.key)
                for subtask in jira_issue.fields.subtasks
            ]
            self.update_release_jira(jira_issue, subtasks, jira_template_vars)
        else:
            _LOGGER.info("Creating a release JIRA...")
            jira_issues = self.create_release_jira(jira_template_vars)
            jira_issue = jira_issues[0] if jira_issues else None
            jira_issue_key = jira_issue.key if jira_issue else None

        _LOGGER.info("Updating ocp-build-data...")
        build_data_changed = await self.update_build_data(
            advisories, jira_issue_key)

        _LOGGER.info("Sweep builds into the the advisories...")
        for kind, advisory in advisories.items():
            if not advisory:
                continue
            if kind == "rpm":
                self.sweep_builds("rpm", advisory)
            elif kind == "image":
                self.sweep_builds("image",
                                  advisory,
                                  only_payload=self.release_version[0] >= 4)
            elif kind == "extras":
                self.sweep_builds("image", advisory, only_non_payload=True)
            elif kind == "metadata":
                await self.build_and_attach_bundles(advisory)

        # bugs should be swept after builds to have validation
        # for only those bugs to be attached which have corresponding brew builds
        # attached to the advisory
        # currently for rpm advisory and cves only
        _LOGGER.info("Sweep bugs into the the advisories...")
        self.sweep_bugs(check_builds=True)

        _LOGGER.info("Adding placeholder bugs...")
        for kind, advisory in advisories.items():
            bug_ids = get_bug_ids(advisory)
            if not bug_ids:  # Only create placeholder bug if the advisory has no attached bugs
                _LOGGER.info("Create placeholder bug for %s advisory %s...",
                             kind, advisory)
                self.create_and_attach_placeholder_bug(kind, advisory)

        # Verify the swept builds match the nightlies
        if self.release_version[0] < 4:
            _LOGGER.info("Don't verify payloads for OCP3 releases")
        else:
            _LOGGER.info("Verify the swept builds match the nightlies...")
            for _, payload in self.candidate_nightlies.items():
                self.verify_payload(payload, advisories["image"])

        if build_data_changed or self.candidate_nightlies:
            _LOGGER.info("Sending a notification to QE and multi-arch QE...")
            if self.dry_run:
                jira_issue_link = "https://jira.example.com/browse/FOO-1"
            else:
                jira_issue_link = jira_issue.permalink()
            self.send_notification_email(advisories, jira_issue_link)

        # Move advisories to QE
        for kind, advisory in advisories.items():
            try:
                if kind == "metadata":
                    # Verify attached operators
                    await self.verify_attached_operators(
                        advisories["image"], advisories["extras"],
                        advisories["metadata"])
                self.change_advisory_state(advisory, "QE")
            except CalledProcessError as ex:
                _LOGGER.warning(
                    f"Unable to move {kind} advisory {advisory} to QE: {ex}")