lib_ci.py 4.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154
  1. # -*- coding: utf-8 -*-
  2. """
  3. (c) 2016 - Copyright Red Hat Inc
  4. Authors:
  5. Lubomír Sedlář <lubomir.sedlar@gmail.com>
  6. Farhaan Bukhsh <farhaan.bukhsh@gmail.com>
  7. Pierre-Yves Chibon <pingou@pingoured.fr>
  8. """
  9. from __future__ import unicode_literals, absolute_import
  10. # pylint: disable=too-many-locals
  11. import logging
  12. import time
  13. import pagure.exceptions
  14. import pagure.lib.query
  15. from pagure.config import config as pagure_config
  16. _log = logging.getLogger(__name__)
  17. BUILD_STATS = {
  18. "SUCCESS": ("Build successful", pagure_config["FLAG_SUCCESS"], 100),
  19. "FAILURE": ("Build failed", pagure_config["FLAG_FAILURE"], 0),
  20. "ABORTED": ("Build aborted", "error", 0),
  21. "BUILDING": ("Build in progress", pagure_config["FLAG_PENDING"], 0),
  22. }
  23. def process_jenkins_build(session, project, build_id, iteration=0):
  24. """ Gets the build info from jenkins and flags that particular
  25. pull-request.
  26. """
  27. import jenkins
  28. # This import is needed as pagure.lib relies on Project.ci_hook to be
  29. # defined and accessible and this happens in pagure.hooks.pagure_ci
  30. from pagure.hooks import pagure_ci # noqa: E402,F401
  31. # Jenkins Base URL
  32. _log.info("Querying jenkins at: %s", project.ci_hook.ci_url)
  33. jenk = jenkins.Jenkins(project.ci_hook.ci_url)
  34. jenkins_name = project.ci_hook.ci_job
  35. _log.info(
  36. "Querying jenkins for project: %s, build: %s", jenkins_name, build_id
  37. )
  38. try:
  39. build_info = jenk.get_build_info(jenkins_name, build_id)
  40. except jenkins.NotFoundException:
  41. _log.debug("Could not find build %s at: %s", build_id, jenkins_name)
  42. raise pagure.exceptions.PagureException(
  43. "Could not find build %s at: %s" % (build_id, jenkins_name)
  44. )
  45. if build_info.get("building") is True:
  46. if iteration < 5:
  47. _log.info("Build is still going, let's wait a sec and try again")
  48. time.sleep(1)
  49. return process_jenkins_build(
  50. session, project, build_id, iteration=iteration + 1
  51. )
  52. _log.info(
  53. "We've been waiting for 5 seconds and the build is still "
  54. "not finished, so let's keep going."
  55. )
  56. result = build_info.get("result")
  57. if not result and build_info.get("building") is True:
  58. result = "BUILDING"
  59. _log.info("Result from jenkins: %s", result)
  60. url = build_info["url"]
  61. _log.info("URL from jenkins: %s", url)
  62. pr_id = None
  63. for action in build_info["actions"]:
  64. for cause in action.get("causes", []):
  65. try:
  66. pr_id = int(cause["note"])
  67. except (KeyError, ValueError):
  68. continue
  69. if not pr_id:
  70. raise pagure.exceptions.NoCorrespondingPR("No corresponding PR found")
  71. if not result or result not in BUILD_STATS:
  72. raise pagure.exceptions.PagureException(
  73. "Unknown build status: %s" % result
  74. )
  75. request = pagure.lib.query.search_pull_requests(
  76. session, project_id=project.id, requestid=pr_id
  77. )
  78. if not request:
  79. raise pagure.exceptions.PagureException("Request not found")
  80. comment, state, percent = BUILD_STATS[result]
  81. # Adding build ID to the CI type
  82. username = "%s #%s" % (project.ci_hook.ci_type, build_id)
  83. if request.commit_stop:
  84. comment += " (commit: %s)" % (request.commit_stop[:8])
  85. uid = None
  86. for flag in request.flags:
  87. if (
  88. flag.status == pagure_config["FLAG_PENDING"]
  89. and flag.username == username
  90. ):
  91. uid = flag.uid
  92. break
  93. _log.info("Flag's UID: %s", uid)
  94. pagure.lib.query.add_pull_request_flag(
  95. session,
  96. request=request,
  97. username=username,
  98. percent=percent,
  99. comment=comment,
  100. url=url,
  101. status=state,
  102. uid=uid,
  103. user=project.user.username,
  104. token=None,
  105. )
  106. session.commit()
  107. def trigger_jenkins_build(project_path, url, job, token, branch, cause):
  108. """ Trigger a build on a jenkins instance."""
  109. try:
  110. import jenkins
  111. except ImportError:
  112. _log.error("Pagure-CI: Failed to load the jenkins module, bailing")
  113. return
  114. _log.info("Jenkins CI")
  115. repo = "%s/%s" % (pagure_config["GIT_URL_GIT"].rstrip("/"), project_path)
  116. data = {"cause": cause, "REPO": repo, "BRANCH": branch}
  117. server = jenkins.Jenkins(url)
  118. _log.info(
  119. "Pagure-CI: Triggering at: %s for: %s - data: %s", url, job, data
  120. )
  121. try:
  122. server.build_job(name=job, parameters=data, token=token)
  123. _log.info("Pagure-CI: Build triggered")
  124. except Exception as err:
  125. _log.info("Pagure-CI:An error occured: %s", err)