def _fetch(hostname, username, port, gerrit_query): """ Fetch changes from gerrit by executing given query Connects to gerrit at given hostname with given username via SSH and uses given gerrit query to fetch changes :arg str hostname: gerrit server hostname :arg str username: gerrit username :arg int port: port for gerrit service :arg str gerrit_query: gerrit query to be executed via SSH :Return: List of Change objects if any, empty list on error """ try: logging.info("Connecting to %s@%s:%d", username, hostname, port) gerrit_client = GerritClient(host=hostname, username=username, port=port) logging.info("Connected to Gerrit version [%s]", gerrit_client.gerrit_version()) except GerritError as err: logging.error("Gerrit error: %s", err) return [] logging.info("Fetching changes with %s", gerrit_query) changes = [] try: changes = gerrit_client.query(gerrit_query) except ValueError as value_error: # should not happen as query above should have no errors logging.error("Query %s failed: %s!", gerrit_query, value_error) logging.info("Number of changes fetched: %d", len(changes)) return changes
def search_projects(self, name): client = GerritClient("gerrit") results = client.run_command("ls-projects --format json") projects = json.load(results.stdout) clyde_projects = [] for name, contents in projects.iteritems(): if name.startswith('clyde/packages'): clyde_projects.append(name.split('/')[2]) return clyde_projects
class SimpleActionExecutor: def __init__(self, action, filter): self.gerrit_client = GerritClient("gerrit-host") self.action = action self.filter = filter self.gerrit_client.gerrit_version() def do_work(self): self.gerrit_client.start_event_stream() while True: event = self.gerrit_client.get_event() if self.filter.filter_event(event): self.action.execute_for_event(event)
def __init__(self, gerrit_host="gerrit.mmt.com"): self.client = None self.ELK_HOST = "127.0.0.1:9200" # elastic search self.index_name = datetime.datetime.now().strftime('gerrit-stats-%Y-%m') url = "http://127.0.0.1:8080" # gerrit servers auth = HTTPDigestAuth('admin', 'pass') self.rest_client = GerritRestAPI(url=url, auth=auth) # establish connection with jira self.jira = JIRA(basic_auth=('jira', 'pass'), options = {'server': '127.0.0.1'}) # Jira server self.regex = r'([A-Z]+-[0-9]+)' log.info("creating a new connection with %s" % (gerrit_host)) self.client = GerritClient(gerrit_host) log.info("Gerrit version is %s" % (self.client.gerrit_version())) self.start_event_stream()
def activate(self): """Triggers on plugin activation You should delete it if you're not using it to override any default behaviour""" self.client = GerritClient("gerritssh") self.client.gerrit_version() self.client.start_event_stream() self.start_poller(2, self._poll_event) super(Gerrit, self).activate()
class GerritClientEventStream(GerritClient): def __init__(self, host, username=None, port=None, keepalive=None): super(GerritClientEventStream, self).__init__(host, username, port, keepalive) self.client = GerritClient(host, username, port, keepalive) def __str__(self): return def __enter__(self): # Needed to make event stream to be connected to server not_connected = True while not_connected: try: self.client.gerrit_version() not_connected = False except GerritError as e: logger.error(e) sleep(3) self.client.start_event_stream() return self.client def __exit__(self, exc_type, exc_val, exc_tb): self.client.stop_event_stream()
def _main(): usage = "usage: %prog [options]" parser = optparse.OptionParser(usage=usage) parser.add_option('-g', '--gerrit-hostname', dest='hostname', default='review', help='gerrit server hostname (default: %default)') parser.add_option('-b', '--blocking', dest='blocking', action='store_true', help='block on event get (default: False)') parser.add_option('-t', '--timeout', dest='timeout', default=None, type='int', help='timeout (seconds) for blocking event get ' '(default: None)') (options, _args) = parser.parse_args() if options.timeout and not options.blocking: parser.error('Can only use --timeout with --blocking') logging.basicConfig(format='%(message)s', level=logging.INFO) try: gerrit = GerritClient(host=options.hostname) logging.info("Connected to Gerrit version [%s]", gerrit.gerrit_version()) gerrit.start_event_stream() except GerritError as err: logging.error("Gerrit error: %s", err) return 1 errors = Event() try: while True: event = gerrit.get_event(block=options.blocking, timeout=options.timeout) if event: logging.info("Event: %s", str(event)) if isinstance(event, GerritStreamErrorEvent): logging.error(event.error) errors.set() break else: logging.info("No event") if not options.blocking: time.sleep(1) except KeyboardInterrupt: logging.info("Terminated by user") finally: gerrit.stop_event_stream() if errors.isSet(): logging.error("Exited with error") return 1
class Gerrit(BotPlugin): """An Err plugin skeleton""" min_err_version = '1.6.0' # Optional, but recommended max_err_version = '2.0.0' # Optional, but recommended def activate(self): """Triggers on plugin activation You should delete it if you're not using it to override any default behaviour""" self.client = GerritClient("gerritssh") self.client.gerrit_version() self.client.start_event_stream() self.start_poller(2, self._poll_event) super(Gerrit, self).activate() def deactivate(self): """Triggers on plugin deactivation You should delete it if you're not using it to override any default behaviour""" logging.warn('Calling Stop Poller') self.stop_poller(self._poll_event) logging.warn('Calling Stop event stream') self.client.stop_event_stream() logging.warn('Calling super deavtivate') super(Gerrit, self).deactivate() def _poll_event(self): logging.warn('Starting to listen for event') event = self.client.get_event(block=True, timeout=1) if event: self.send('#mugsie-test', 'Got an Event', message_type='groupchat') logging.warn('Stopped listening for event') # Passing split_args_with=None will cause arguments to be split on any kind # of whitespace, just like Python's split() does @botcmd(split_args_with=None) def example(self, mess, args): """A command which simply returns 'Example'""" return "Example"
class GerritClientEventStream(GerritClient): def __init__(self, host, username=None, port=None, keepalive=None): super(GerritClientEventStream, self).__init__(host, username, port, keepalive) self.client = GerritClient(host, username, port, keepalive) def __str__(self): return def __enter__(self): # Needed to make event stream to be connected to server self.client.gerrit_version() self.client.start_event_stream() return self.client def __exit__(self, exc_type, exc_val, exc_tb): self.client.stop_event_stream()
def _main(): usage = "usage: %prog [options]" parser = optparse.OptionParser(usage=usage) # 198.101.231.251 is review.openstack.org. For some vague reason the dns entry from inside pygerrit is not resolved. # It throws an error "ERROR Gerrit error: Failed to connect to server: [Errno 101] Network is unreachable" parser.add_option( "-g", "--gerrit-hostname", dest="hostname", default="198.101.231.251", help="gerrit server hostname (default: %default)", ) parser.add_option("-p", "--port", dest="port", type="int", default=29418, help="port number (default: %default)") parser.add_option("-u", "--username", dest="username", help="username", default="vijayvenkatachalam") parser.add_option( "-b", "--blocking", dest="blocking", action="store_true", help="block on event get (default: False)" ) parser.add_option( "-t", "--timeout", dest="timeout", default=None, type="int", help="timeout (seconds) for blocking event get " "(default: None)", ) parser.add_option( "-v", "--verbose", dest="verbose", action="store_true", default=False, help="enable verbose (debug) logging" ) parser.add_option( "-i", "--ignore-stream-errors", dest="ignore", action="store_true", help="do not exit when an error event is received", ) parser.add_option( "-c", "--change-ref", dest="change_ref", action="store", type="string", help="to be provided if required to do one time job on a change-ref", ) parser.add_option( "-x", "--commit-id", dest="commitid", action="callback", callback=check_for_change_ref, type="string", help="to be provided if required to do one time job on a change-id", ) parser.add_option( "-j", "--project", dest="project", action="callback", callback=check_for_change_ref, type="string", help="project of the change-ref provided", ) parser.add_option( "-n", "--vote-num", dest="vote", action="callback", callback=check_for_change_ref, type="string", help="the vote, should be either '+1' or '-1'", ) parser.add_option( "-m", "--vote-message", dest="message", action="callback", callback=check_for_vote, type="string", help="the message that has to be sent for voting", ) (options, _args) = parser.parse_args() if options.timeout and not options.blocking: parser.error("Can only use --timeout with --blocking") if options.change_ref and not options.project: parser.error("Can only use --change_ref with --project") if options.vote and not options.message: parser.error("Can only use --vote with --vote-message") if options.vote and not options.commitid: parser.error("Can only use --vote with --commit-id") level = logging.DEBUG if options.verbose else logging.INFO logging.basicConfig(format="%(asctime)s %(levelname)s %(message)s", level=level) if options.change_ref: # One time job needs to be performed. if options.vote: # Just voting needs to be done, no need of testing vote(options.commitid, options.vote, options.message) else: # Execute tests and vote if options.project not in CONSTANTS.PROJECT_CONFIG: logging.info("Project specified does not match criteria") return project_config = CONSTANTS.PROJECT_CONFIG[options.project] files_matched, commitid = are_files_matching_criteria( project_config["repo_path"], project_config["review_repo"], project_config["files_to_check"], options.change_ref, ) if files_matched: test_changes(options.change_ref, options.project, commitid, "RUN") else: logging.error("Changeref specified does not match file match criteria") return # Starting the loop for listening to Gerrit events try: logging.info("Connecting to gerrit host " + options.hostname) logging.info("Connecting to gerrit username " + options.username) logging.info("Connecting to gerrit port " + str(options.port)) gerrit = GerritClient(host=options.hostname, username=options.username, port=options.port) logging.info("Connected to Gerrit version [%s]", gerrit.gerrit_version()) gerrit.start_event_stream() except GerritError as err: logging.error("Gerrit error: %s", err) return 1 errors = Event() try: while True: event = gerrit.get_event(block=options.blocking, timeout=options.timeout) if event: logging.debug("Event: %s", event) """ Logic starts here """ if is_event_matching_criteria(event): if are_files_matching_criteria_event(event): record_event_details(event) inform_builder(event) if isinstance(event, ErrorEvent) and not options.ignore: logging.error(event.error) errors.set() break else: logging.debug("No event") if not options.blocking: time.sleep(1) except KeyboardInterrupt: logging.info("Terminated by user") finally: logging.debug("Stopping event stream...") gerrit.stop_event_stream() if errors.isSet(): logging.error("Exited with error") return 1
def _main(): usage = "usage: %prog [options]" parser = optparse.OptionParser(usage=usage) parser.add_option('-g', '--gerrit-hostname', dest='hostname', default='review', help='gerrit server hostname (default: %default)') parser.add_option('-p', '--port', dest='port', type='int', default=29418, help='port number (default: %default)') parser.add_option('-u', '--username', dest='username', help='username') parser.add_option('-b', '--blocking', dest='blocking', action='store_true', help='block on event get (default: False)') parser.add_option('-t', '--timeout', dest='timeout', default=None, type='int', help='timeout (seconds) for blocking event get ' '(default: None)') parser.add_option('-v', '--verbose', dest='verbose', action='store_true', help='enable verbose (debug) logging') parser.add_option('-i', '--ignore-stream-errors', dest='ignore', action='store_true', help='do not exit when an error event is received') (options, _args) = parser.parse_args() if options.timeout and not options.blocking: parser.error('Can only use --timeout with --blocking') level = logging.DEBUG if options.verbose else logging.INFO logging.basicConfig(format='%(asctime)s %(levelname)s %(message)s', level=level) try: gerrit = GerritClient(host=options.hostname, username=options.username, port=options.port) logging.info("Connected to Gerrit version [%s]", gerrit.gerrit_version()) gerrit.start_event_stream() except GerritError as err: logging.error("Gerrit error: %s", err) return 1 errors = Event() try: while True: event = gerrit.get_event(block=options.blocking, timeout=options.timeout) if event: logging.info("Event: %s", event) if isinstance(event, ErrorEvent) and not options.ignore: logging.error(event.error) errors.set() break else: logging.info("No event") if not options.blocking: time.sleep(1) except KeyboardInterrupt: logging.info("Terminated by user") finally: logging.debug("Stopping event stream...") gerrit.stop_event_stream() if errors.isSet(): logging.error("Exited with error") return 1
def setUp(self): self.gerrit = GerritClient("review")
class TestGerritEvents(unittest.TestCase): def setUp(self): self.gerrit = GerritClient("review") def test_patchset_created(self): _create_event("patchset-created-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, PatchsetCreatedEvent)) self.assertEquals(event.name, "patchset-created") self.assertEquals(event.change.project, "project-name") self.assertEquals(event.change.branch, "branch-name") self.assertEquals(event.change.topic, "topic-name") self.assertEquals(event.change.change_id, "Ideadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.change.number, "123456") self.assertEquals(event.change.subject, "Commit message subject") self.assertEquals(event.change.url, "http://review.example.com/123456") self.assertEquals(event.change.owner.name, "Owner Name") self.assertEquals(event.change.owner.email, "*****@*****.**") self.assertEquals(event.patchset.number, "4") self.assertEquals(event.patchset.revision, "deadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.patchset.ref, "refs/changes/56/123456/4") self.assertEquals(event.patchset.uploader.name, "Uploader Name") self.assertEquals(event.patchset.uploader.email, "*****@*****.**") self.assertEquals(event.uploader.name, "Uploader Name") self.assertEquals(event.uploader.email, "*****@*****.**") def test_draft_published(self): _create_event("draft-published-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, DraftPublishedEvent)) self.assertEquals(event.name, "draft-published") self.assertEquals(event.change.project, "project-name") self.assertEquals(event.change.branch, "branch-name") self.assertEquals(event.change.topic, "topic-name") self.assertEquals(event.change.change_id, "Ideadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.change.number, "123456") self.assertEquals(event.change.subject, "Commit message subject") self.assertEquals(event.change.url, "http://review.example.com/123456") self.assertEquals(event.change.owner.name, "Owner Name") self.assertEquals(event.change.owner.email, "*****@*****.**") self.assertEquals(event.patchset.number, "4") self.assertEquals(event.patchset.revision, "deadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.patchset.ref, "refs/changes/56/123456/4") self.assertEquals(event.patchset.uploader.name, "Uploader Name") self.assertEquals(event.patchset.uploader.email, "*****@*****.**") self.assertEquals(event.uploader.name, "Uploader Name") self.assertEquals(event.uploader.email, "*****@*****.**") def test_ref_updated(self): _create_event("ref-updated-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, RefUpdatedEvent)) self.assertEquals(event.name, "ref-updated") self.assertEquals(event.ref_update.project, "project-name") self.assertEquals(event.ref_update.oldrev, "0000000000000000000000000000000000000000") self.assertEquals(event.ref_update.newrev, "deadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.ref_update.refname, "refs/tags/refname") self.assertEquals(event.submitter.name, "Submitter Name") self.assertEquals(event.submitter.email, "*****@*****.**") def test_change_merged(self): _create_event("change-merged-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, ChangeMergedEvent)) self.assertEquals(event.name, "change-merged") self.assertEquals(event.change.project, "project-name") self.assertEquals(event.change.branch, "branch-name") self.assertEquals(event.change.topic, "topic-name") self.assertEquals(event.change.change_id, "Ideadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.change.number, "123456") self.assertEquals(event.change.subject, "Commit message subject") self.assertEquals(event.change.url, "http://review.example.com/123456") self.assertEquals(event.change.owner.name, "Owner Name") self.assertEquals(event.change.owner.email, "*****@*****.**") self.assertEquals(event.patchset.number, "4") self.assertEquals(event.patchset.revision, "deadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.patchset.ref, "refs/changes/56/123456/4") self.assertEquals(event.patchset.uploader.name, "Uploader Name") self.assertEquals(event.patchset.uploader.email, "*****@*****.**") self.assertEquals(event.submitter.name, "Submitter Name") self.assertEquals(event.submitter.email, "*****@*****.**") def test_merge_failed(self): _create_event("merge-failed-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, MergeFailedEvent)) self.assertEquals(event.name, "merge-failed") self.assertEquals(event.change.project, "project-name") self.assertEquals(event.change.branch, "branch-name") self.assertEquals(event.change.topic, "topic-name") self.assertEquals(event.change.change_id, "Ideadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.change.number, "123456") self.assertEquals(event.change.subject, "Commit message subject") self.assertEquals(event.change.url, "http://review.example.com/123456") self.assertEquals(event.change.owner.name, "Owner Name") self.assertEquals(event.change.owner.email, "*****@*****.**") self.assertEquals(event.patchset.number, "4") self.assertEquals(event.patchset.revision, "deadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.patchset.ref, "refs/changes/56/123456/4") self.assertEquals(event.patchset.uploader.name, "Uploader Name") self.assertEquals(event.patchset.uploader.email, "*****@*****.**") self.assertEquals(event.submitter.name, "Submitter Name") self.assertEquals(event.submitter.email, "*****@*****.**") self.assertEquals(event.reason, "Merge failed reason") def test_comment_added(self): _create_event("comment-added-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, CommentAddedEvent)) self.assertEquals(event.name, "comment-added") self.assertEquals(event.change.project, "project-name") self.assertEquals(event.change.branch, "branch-name") self.assertEquals(event.change.topic, "topic-name") self.assertEquals(event.change.change_id, "Ideadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.change.number, "123456") self.assertEquals(event.change.subject, "Commit message subject") self.assertEquals(event.change.url, "http://review.example.com/123456") self.assertEquals(event.change.owner.name, "Owner Name") self.assertEquals(event.change.owner.email, "*****@*****.**") self.assertEquals(event.patchset.number, "4") self.assertEquals(event.patchset.revision, "deadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.patchset.ref, "refs/changes/56/123456/4") self.assertEquals(event.patchset.uploader.name, "Uploader Name") self.assertEquals(event.patchset.uploader.email, "*****@*****.**") self.assertEquals(len(event.approvals), 2) self.assertEquals(event.approvals[0].category, "CRVW") self.assertEquals(event.approvals[0].description, "Code Review") self.assertEquals(event.approvals[0].value, "1") self.assertEquals(event.approvals[1].category, "VRIF") self.assertEquals(event.approvals[1].description, "Verified") self.assertEquals(event.approvals[1].value, "1") self.assertEquals(event.author.name, "Author Name") self.assertEquals(event.author.email, "*****@*****.**") def test_reviewer_added(self): _create_event("reviewer-added-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, ReviewerAddedEvent)) self.assertEquals(event.name, "reviewer-added") self.assertEquals(event.change.project, "project-name") self.assertEquals(event.change.branch, "branch-name") self.assertEquals(event.change.topic, "topic-name") self.assertEquals(event.change.change_id, "Ideadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.change.number, "123456") self.assertEquals(event.change.subject, "Commit message subject") self.assertEquals(event.change.url, "http://review.example.com/123456") self.assertEquals(event.change.owner.name, "Owner Name") self.assertEquals(event.change.owner.email, "*****@*****.**") self.assertEquals(event.patchset.number, "4") self.assertEquals(event.patchset.revision, "deadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.patchset.ref, "refs/changes/56/123456/4") self.assertEquals(event.patchset.uploader.name, "Uploader Name") self.assertEquals(event.patchset.uploader.email, "*****@*****.**") self.assertEquals(event.reviewer.name, "Reviewer Name") self.assertEquals(event.reviewer.email, "*****@*****.**") def test_change_abandoned(self): _create_event("change-abandoned-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, ChangeAbandonedEvent)) self.assertEquals(event.name, "change-abandoned") self.assertEquals(event.change.project, "project-name") self.assertEquals(event.change.branch, "branch-name") self.assertEquals(event.change.topic, "topic-name") self.assertEquals(event.change.change_id, "Ideadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.change.number, "123456") self.assertEquals(event.change.subject, "Commit message subject") self.assertEquals(event.change.url, "http://review.example.com/123456") self.assertEquals(event.change.owner.name, "Owner Name") self.assertEquals(event.change.owner.email, "*****@*****.**") self.assertEquals(event.abandoner.name, "Abandoner Name") self.assertEquals(event.abandoner.email, "*****@*****.**") self.assertEquals(event.reason, "Abandon reason") def test_change_restored(self): _create_event("change-restored-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, ChangeRestoredEvent)) self.assertEquals(event.name, "change-restored") self.assertEquals(event.change.project, "project-name") self.assertEquals(event.change.branch, "branch-name") self.assertEquals(event.change.topic, "topic-name") self.assertEquals(event.change.change_id, "Ideadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.change.number, "123456") self.assertEquals(event.change.subject, "Commit message subject") self.assertEquals(event.change.url, "http://review.example.com/123456") self.assertEquals(event.change.owner.name, "Owner Name") self.assertEquals(event.change.owner.email, "*****@*****.**") self.assertEquals(event.restorer.name, "Restorer Name") self.assertEquals(event.restorer.email, "*****@*****.**") self.assertEquals(event.reason, "Restore reason") def test_topic_changed(self): _create_event("topic-changed-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, TopicChangedEvent)) self.assertEquals(event.name, "topic-changed") self.assertEquals(event.change.project, "project-name") self.assertEquals(event.change.branch, "branch-name") self.assertEquals(event.change.topic, "topic-name") self.assertEquals(event.change.change_id, "Ideadbeefdeadbeefdeadbeefdeadbeefdeadbeef") self.assertEquals(event.change.number, "123456") self.assertEquals(event.change.subject, "Commit message subject") self.assertEquals(event.change.url, "http://review.example.com/123456") self.assertEquals(event.change.owner.name, "Owner Name") self.assertEquals(event.change.owner.email, "*****@*****.**") self.assertEquals(event.changer.name, "Changer Name") self.assertEquals(event.changer.email, "*****@*****.**") self.assertEquals(event.oldtopic, "old-topic") def test_user_defined_event(self): _create_event("user-defined-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, UserDefinedEvent)) self.assertEquals(event.title, "Event title") self.assertEquals(event.description, "Event description") def test_unhandled_event(self): data = _create_event("unhandled-event", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, UnhandledEvent)) self.assertEquals(event.json, json.loads(data)) def test_invalid_json(self): _create_event("invalid-json", self.gerrit) event = self.gerrit.get_event(False) self.assertTrue(isinstance(event, ErrorEvent)) def test_add_duplicate_event(self): try: @GerritEventFactory.register("user-defined-event") class AnotherUserDefinedEvent(GerritEvent): pass except: return self.fail("Did not raise exception when duplicate event registered")
def _main(): usage = "usage: %prog [options]" parser = optparse.OptionParser(usage=usage) parser.add_option('-g', '--gerrit-hostname', dest='hostname', default='review', help='gerrit server hostname (default: %default)') parser.add_option('-p', '--port', dest='port', type='int', default=29418, help='port number (default: %default)') parser.add_option('-u', '--username', dest='username', help='username') parser.add_option('-b', '--blocking', dest='blocking', action='store_true', help='block on event get (default: False)') parser.add_option('-t', '--timeout', dest='timeout', default=None, type='int', help='timeout (seconds) for blocking event get ' '(default: None)') parser.add_option('-v', '--verbose', dest='verbose', action='store_true', help='enable verbose (debug) logging') parser.add_option('-i', '--ignore-stream-errors', dest='ignore', action='store_true', help='do not exit when an error event is received') (options, _args) = parser.parse_args() if options.timeout and not options.blocking: parser.error('Can only use --timeout with --blocking') level = logging.DEBUG if options.verbose else logging.INFO logging.basicConfig(format='%(asctime)s %(levelname)s %(message)s', level=level) try: gerrit = GerritClient(host=options.hostname, username=options.username, port=options.port) logging.info("Connected to Gerrit version [%s]", gerrit.gerrit_version()) gerrit.start_event_stream() except GerritError as err: logging.error("Gerrit error: %s", err) return 1 try: r = redis.Redis() except Exception as err: logging.error("Redis error", exc_info=True) return 2 errors = Event() try: while True: event = gerrit.get_event(block=options.blocking, timeout=options.timeout) if event: logging.info("Event: %s", event) if isinstance(event, ErrorEvent) and not options.ignore: logging.error(event.error) errors.set() break elif isinstance(event, CommentAddedEvent): is_reviewed = False if event.change.owner.email != event.author.email: continue for approval in event.approvals: if int(approval.value) == 1 and approval.category == 'Code-Review': is_reviewed = True if is_reviewed: data = {'project': event.change.project, 'changeid': event.change.change_id, 'subject': event.change.subject, 'ref': event.patchset.ref, 'revision': event.patchset.revision, 'url': event.change.url} r.lpush('omnibuild', json.dumps(data)) elif isinstance(event, ReviewerAddedEvent): if event.reviewer.email == '*****@*****.**': data = {'project': event.change.project, 'changeid': event.change.change_id, 'ref': event.patchset.ref, 'revision': event.patchset.revision, 'url': event.change.url} r.lpush('omnibuild', json.dumps(data)) else: # logging.info("No event") if not options.blocking: time.sleep(1) except KeyboardInterrupt: logging.info("Terminated by user") except Exception: logging.error("Error during processing", exc_info=True) errors.set() finally: logging.warning("Stopping event stream...") gerrit.stop_event_stream() if errors.isSet(): logging.error("Exited with error") return 1
def __init__(self, host, username=None, port=None, keepalive=None): super(GerritClientEventStream, self).__init__(host, username, port, keepalive) self.client = GerritClient(host, username, port, keepalive)
class DGerritHandler(): def __init__(self, gerrit_host="gerrit.mmt.com"): self.client = None self.ELK_HOST = "127.0.0.1:9200" # elastic search self.index_name = datetime.datetime.now().strftime('gerrit-stats-%Y-%m') url = "http://127.0.0.1:8080" # gerrit servers auth = HTTPDigestAuth('admin', 'pass') self.rest_client = GerritRestAPI(url=url, auth=auth) # establish connection with jira self.jira = JIRA(basic_auth=('jira', 'pass'), options = {'server': '127.0.0.1'}) # Jira server self.regex = r'([A-Z]+-[0-9]+)' log.info("creating a new connection with %s" % (gerrit_host)) self.client = GerritClient(gerrit_host) log.info("Gerrit version is %s" % (self.client.gerrit_version())) self.start_event_stream() def start_event_stream(self): # start listening to event stream log.info("initiating listening to event stream") self.client.start_event_stream() def event_listen(self): iter = 0 while True: try: elog = {} event = self.client.get_event() log.info("==============START=====================================") log.info("got a new event %s -- %s" % (event.name, type(event.json))) log.info("actual event is %s" % pformat(event.json)) elog['type'] = event.name if event.name == "error-event": log.info("got an error-event, exiting the script.............") sys.exit() elog['gerrit_id'] = event.change.number log.info(dir(event)) if hasattr(event, 'author'): elog['author_username'] = event.author.username if hasattr(event, 'author') else None elog['author_email'] = event.author.email if hasattr(event, 'author') else None elif hasattr(event, 'patchset'): elog['author_username'] = event.patchset.author.username if hasattr(event.patchset, 'author') else None elog['author_email'] = event.patchset.author.email if hasattr(event.patchset, 'author') else None elog['project'] = event.change.project elog['owner'] = event.change.owner.username elog['branch'] = event.change.branch elog['patchset_number'] = event.patchset.number elog['patchset_size_deletions'] = event.json.get('patchSet').get('sizeDeletions') elog['patchset_size_insertions'] = event.json.get('patchSet').get('sizeInsertions') elog['subject'] = event.change.subject if event.name == 'reviewer-added': elog['reviewers'] = event.reviewer.username elif event.name == 'change-merged': elog['submitter'] = event.submitter.username elif event.name == 'comment-added' and 'approvals' in event.json.keys(): for i in event.json.get('approvals'): log.info(i) if 'oldValue' in i: log.info("----found old value----") elog['approval_approver'] = event.author.username elog['approver_type'] = i.get('type') elog['approval_value'] = i.get('value') elog['approval_description'] = i.get('description') break else: elog['approval_approver'] = event.author.username elog['approver_type'] = 'comment-added' elog['approval_value'] = '0' elog['approval_description'] = 'comment-added' log.info("~~~~~~~~~~~~~~~~~~~ Start JIRA Analysis ~~~~~~~~~~~~~~~~~~~") issue_type = [] elog['issue_id'] = re.findall(self.regex, elog['subject']) for issue in elog['issue_id']: issue_type.append(self.jira.issue(issue).fields.issuetype.name) elog['issue_id_type'] = issue_type log.info("~~~~~~~~~~~~~~~~~~~ End JIRA Analysis ~~~~~~~~~~~~~~~~~~~") log.info("~~~~~~~~~~~~~~~~~~~ Start Gerrit File Actions ~~~~~~~~~~~~~~~~~~~") files_info = { "ADDED": { "lines_added": 0, "lines_removed": 0, "count": 0 }, "MODIFIED": { "lines_added": 0, "lines_removed": 0, "count": 0 }, "DELETED": { "lines_added": 0, "lines_removed": 0, "count": 0 }, "RENAMED": { "lines_added": 0, "lines_removed": 0, "count": 0 }, "COPIED": { "lines_added": 0, "lines_removed": 0, "count": 0 }, "REWRITE": { "lines_added": 0, "lines_removed": 0, "count": 0 } } query_result = self.client.run_command("query --current-patch-set --format JSON --files change:{}".format(elog['gerrit_id'])) output = query_result.stdout.read() output = output.split('\n') files = json.loads(output[0]) log.info(elog['project']) for file in files['currentPatchSet']['files']: if file['file'] not in ['/COMMIT_MSG', '/MERGE_LIST']: files_info[file['type']]['lines_added'] += file['insertions'] files_info[file['type']]['lines_removed'] += file['deletions'] files_info[file['type']]['count'] += 1 elog['files'] = files_info log.info("~~~~~~~~~~~~~~~~~~~ End Gerrit File Actions ~~~~~~~~~~~~~~~~~~~") log.info("elk message %d is %s" % (iter, json.dumps(elog, indent=2))) log.info("==============END=====================================") self.log_to_elk(elog) except Exception as e: log.exception(e) if event: log.info(str(event.json)) finally: iter += 1 def stop_event_stream(self): # stop listening to gerrit event stream log.info("stop listening to event stream") self.client.stop_event_stream() def log_to_elk(self, log): log['timestamp'] = datetime.datetime.now() elk = Elasticsearch(self.ELK_HOST) elk.index(index=self.index_name, doc_type='gerrit_info', body=log) def get_reviewer_list(self, change_id): endpoint = "/changes/%s/reviewers/" % change_id data = self.rest_client.get(endpoint) reviewers = [] for i in data: if i.get('username') is not None: reviewers.append(i.get('username')) return reviewers
def __init__(self, action, filter): self.gerrit_client = GerritClient("gerrit-host") self.action = action self.filter = filter self.gerrit_client.gerrit_version()
def _main(): descr = 'Send request using Gerrit ssh API' parser = argparse.ArgumentParser( description=descr, formatter_class=argparse.ArgumentDefaultsHelpFormatter) parser.add_argument('-g', '--gerrit-hostname', dest='hostname', default='review', help='gerrit server hostname') parser.add_argument('-p', '--port', dest='port', type=int, default=29418, help='port number') parser.add_argument('-u', '--username', dest='username', help='username') parser.add_argument('-b', '--blocking', dest='blocking', action='store_true', help='block on event get') parser.add_argument('-t', '--timeout', dest='timeout', default=None, type=int, metavar='SECONDS', help='timeout for blocking event get') parser.add_argument('-v', '--verbose', dest='verbose', action='store_true', help='enable verbose (debug) logging') parser.add_argument('-i', '--ignore-stream-errors', dest='ignore', action='store_true', help='do not exit when an error event is received') options = parser.parse_args() if options.timeout and not options.blocking: parser.error('Can only use --timeout with --blocking') level = logging.DEBUG if options.verbose else logging.INFO logging.basicConfig(format='%(asctime)s %(levelname)s %(message)s', level=level) try: gerrit = GerritClient(host=options.hostname, username=options.username, port=options.port) logging.info("Connected to Gerrit version [%s]", gerrit.gerrit_version()) gerrit.start_event_stream() except GerritError as err: logging.error("Gerrit error: %s", err) return 1 errors = Event() try: while True: event = gerrit.get_event(block=options.blocking, timeout=options.timeout) if event: logging.info("Event: %s", event) if isinstance(event, ErrorEvent) and not options.ignore: logging.error(event.error) errors.set() break else: logging.info("No event") if not options.blocking: time.sleep(1) except KeyboardInterrupt: logging.info("Terminated by user") finally: logging.debug("Stopping event stream...") gerrit.stop_event_stream() if errors.isSet(): logging.error("Exited with error") return 1