Ejemplo n.º 1
0
 def _refresh_pulls(
     self,
     pull_requests_to_refresh: typing.List[
         github_types.GitHubPullRequestNumber],
 ) -> None:
     for pull in pull_requests_to_refresh:
         utils.async_run(
             github_events.send_refresh({
                 "number": pull,
                 "base": {
                     "repo": {
                         "name": self.repo,
                         "owner": {
                             "login": self.owner
                         },
                         "full_name": f"{self.owner}/{self.repo}",
                     }
                 },
             }  # type: ignore
                                        ))
Ejemplo n.º 2
0
def post_summary(ctxt, match, summary_check, conclusions,
                 previous_conclusions):
    summary_title, summary = gen_summary(ctxt, match)

    summary += doc.MERGIFY_PULL_REQUEST_DOC
    summary += serialize_conclusions(conclusions)

    summary_changed = (not summary_check
                       or summary_check["output"]["title"] != summary_title
                       or summary_check["output"]["summary"] != summary)

    if summary_changed:
        ctxt.log.info(
            "summary changed",
            summary={
                "title": summary_title,
                "name": ctxt.SUMMARY_NAME,
                "summary": summary,
            },
            sources=_filterred_sources_for_logging(ctxt.sources),
            conclusions=conclusions,
            previous_conclusions=previous_conclusions,
        )

        utils.async_run(
            ctxt.set_summary_check(
                check_api.Result(check_api.Conclusion.SUCCESS,
                                 title=summary_title,
                                 summary=summary)))
    else:
        ctxt.log.info(
            "summary unchanged",
            summary={
                "title": summary_title,
                "name": ctxt.SUMMARY_NAME,
                "summary": summary,
            },
            sources=_filterred_sources_for_logging(ctxt.sources),
            conclusions=conclusions,
            previous_conclusions=previous_conclusions,
        )
Ejemplo n.º 3
0
    def pull_request_auto_refresher(self, pull_number):
        # NOTE(sileht): we need to refresh PR for two reasons:
        # * sync the first one from its base branch if needed
        # * update all summary with the new queues

        old_pull_requests = self.get_pulls()
        try:
            yield
        finally:
            new_pull_requests = self.get_pulls()
            if new_pull_requests == old_pull_requests:
                return

            pull_requests_to_refresh = [
                p for p in new_pull_requests if p != pull_number
            ]
            if not pull_requests_to_refresh:
                return

            self.log.info(
                "queue changed, refreshing all pull requests",
                _from=old_pull_requests,
                _to=new_pull_requests,
                _to_refresh=pull_requests_to_refresh,
            )

            for pull in pull_requests_to_refresh:
                utils.async_run(
                    github_events.send_refresh({
                        "number": pull,
                        "base": {
                            "repo": {
                                "name": self.repo,
                                "owner": {
                                    "login": self.owner
                                },
                                "full_name": f"{self.owner}/{self.repo}",
                            }
                        },
                    }))
Ejemplo n.º 4
0
def report(
    url: str,
) -> typing.Union[context.Context, github.GithubInstallationClient, None]:
    path = url.replace("https://github.com/", "")

    pull_number: typing.Optional[str]
    repo: typing.Optional[str]

    try:
        owner, repo, _, pull_number = path.split("/")
    except ValueError:
        pull_number = None
        try:
            owner, repo = path.split("/")
        except ValueError:
            owner = path
            repo = None

    try:
        client = github.get_client(owner)
    except exceptions.MergifyNotInstalled:
        print(f"* Mergify is not installed on account {owner}")
        return None

    print("* INSTALLATION ID: %s" % client.auth.installation["id"])

    cached_sub, db_sub = utils.async_run(
        subscription.Subscription.get_subscription(client.auth.owner_id),
        subscription.Subscription._retrieve_subscription_from_db(
            client.auth.owner_id),
    )

    if repo is None:
        slug = None
    else:
        slug = owner + "/" + repo

    print("* SUBSCRIBED (cache/db): %s / %s" %
          (cached_sub.active, db_sub.active))
    print("* Features (cache):")
    for f in cached_sub.features:
        print(f"  - {f.value}")
    report_sub(client.auth.installation["id"], cached_sub, "ENGINE-CACHE",
               slug)
    report_sub(client.auth.installation["id"], db_sub, "DASHBOARD", slug)

    utils.async_run(report_worker_status(client.auth.owner))

    if repo is not None:

        repo_info = client.item(f"/repos/{owner}/{repo}")
        print(
            f"* REPOSITORY IS {'PRIVATE' if repo_info['private'] else 'PUBLIC'}"
        )

        print("* CONFIGURATION:")
        mergify_config = None
        try:
            filename, mergify_config_content = rules.get_mergify_config_content(
                client, repo)
        except rules.NoRules:  # pragma: no cover
            print(".mergify.yml is missing")
        else:
            print(f"Config filename: {filename}")
            print(mergify_config_content.decode())
            try:
                mergify_config = rules.UserConfigurationSchema(
                    mergify_config_content)
            except rules.InvalidRules as e:  # pragma: no cover
                print("configuration is invalid %s" % str(e))
            else:
                mergify_config["pull_request_rules"].rules.extend(
                    engine.DEFAULT_PULL_REQUEST_RULES.rules)

        if pull_number is None:
            for branch in client.items(f"/repos/{owner}/{repo}/branches"):
                q = queue.Queue(
                    utils.get_redis_for_cache(),
                    client.auth.installation["id"],
                    client.auth.owner,
                    repo,
                    branch["name"],
                )
                pulls = q.get_pulls()
                if not pulls:
                    continue

                print(f"* QUEUES {branch['name']}:")

                for priority, grouped_pulls in itertools.groupby(
                        pulls, key=lambda v: q.get_config(v)["priority"]):
                    try:
                        fancy_priority = helpers.PriorityAliases(priority).name
                    except ValueError:
                        fancy_priority = priority
                    formatted_pulls = ", ".join(
                        (f"#{p}" for p in grouped_pulls))
                    print(f"** {formatted_pulls} (priority: {fancy_priority})")
        else:
            pull_raw = client.item(
                f"/repos/{owner}/{repo}/pulls/{pull_number}")
            ctxt = context.Context(
                client,
                pull_raw,
                cached_sub,
                [{
                    "event_type": "mergify-debugger",
                    "data": {}
                }],
            )

            # FIXME queues could also be printed if no pull number given
            q = queue.Queue.from_context(ctxt)
            print("* QUEUES: %s" % ", ".join([f"#{p}" for p in q.get_pulls()]))
            print("* PULL REQUEST:")
            pr_data = dict(ctxt.pull_request.items())
            pprint.pprint(pr_data, width=160)

            print("is_behind: %s" % ctxt.is_behind)

            print("mergeable_state: %s" % ctxt.pull["mergeable_state"])

            print("* MERGIFY LAST CHECKS:")
            for c in ctxt.pull_engine_check_runs:
                print("[%s]: %s | %s" %
                      (c["name"], c["conclusion"], c["output"].get("title")))
                print("> " +
                      "\n> ".join(c["output"].get("summary").split("\n")))

            if mergify_config is not None:
                print("* MERGIFY LIVE MATCHES:")
                match = mergify_config[
                    "pull_request_rules"].get_pull_request_rule(ctxt)
                summary_title, summary = actions_runner.gen_summary(
                    ctxt, match)
                print("> %s" % summary_title)
                print(summary)

            return ctxt

    return client
Ejemplo n.º 5
0
def report(url):
    path = url.replace("https://github.com/", "")
    try:
        owner, repo, _, pull_number = path.split("/")
    except ValueError:
        print(f"Wrong URL: {url}")
        return
    slug = owner + "/" + repo

    try:
        client = github.get_client(owner, repo)
    except exceptions.MergifyNotInstalled:
        print("* Mergify is not installed there")
        return

    print("* INSTALLATION ID: %s" % client.auth.installation["id"])

    cached_sub, db_sub = utils.async_run(
        sub_utils.get_subscription(client.auth.owner_id),
        sub_utils._retrieve_subscription_from_db(client.auth.owner_id),
    )
    print("* SUBSCRIBED (cache/db): %s / %s" %
          (cached_sub["subscription_active"], db_sub["subscription_active"]))
    report_sub(client.auth.installation["id"], slug, cached_sub,
               "ENGINE-CACHE")
    report_sub(client.auth.installation["id"], slug, db_sub, "DASHBOARD")

    utils.async_run(report_worker_status(client.auth.owner))

    pull_raw = client.item(f"pulls/{pull_number}")
    ctxt = context.Context(client, pull_raw, cached_sub, [{
        "event_type": "mergify-debugger",
        "data": {}
    }])

    q = queue.Queue.from_context(ctxt)
    print("QUEUES: %s" % ", ".join([f"#{p}" for p in q.get_pulls()]))

    print("* REPOSITORY IS %s" %
          "PRIVATE" if ctxt.pull["base"]["repo"]["private"] else "PUBLIC")

    print("* CONFIGURATION:")
    try:
        filename, mergify_config_content = rules.get_mergify_config_content(
            ctxt)
    except rules.NoRules:  # pragma: no cover
        print(".mergify.yml is missing")
        pull_request_rules = None
    else:
        print(f"Config filename: {filename}")
        print(mergify_config_content.decode())
        try:
            mergify_config = rules.UserConfigurationSchema(
                mergify_config_content)
        except rules.InvalidRules as e:  # pragma: no cover
            print("configuration is invalid %s" % str(e))
        else:
            pull_request_rules_raw = mergify_config[
                "pull_request_rules"].as_dict()
            pull_request_rules = rules.PullRequestRules.from_list(
                pull_request_rules_raw["rules"] + engine.MERGIFY_RULE["rules"])

    print("* PULL REQUEST:")
    pr_data = dict(ctxt.pull_request.items())
    pprint.pprint(pr_data, width=160)

    print("is_behind: %s" % ctxt.is_behind)

    print("mergeable_state: %s" % ctxt.pull["mergeable_state"])

    print("* MERGIFY LAST CHECKS:")
    for c in ctxt.pull_engine_check_runs:
        print("[%s]: %s | %s" %
              (c["name"], c["conclusion"], c["output"].get("title")))
        print("> " + "\n> ".join(c["output"].get("summary").split("\n")))

    if pull_request_rules is not None:
        print("* MERGIFY LIVE MATCHES:")
        match = pull_request_rules.get_pull_request_rule(ctxt)
        summary_title, summary = actions_runner.gen_summary(ctxt, match)
        print("> %s" % summary_title)
        print(summary)

    return ctxt