Source code for pyjen.build

"""Primitives for interacting with Jenkins builds"""
from datetime import datetime
import logging
from urllib.parse import urljoin
from pyjen.changeset import Changeset


[docs]class Build: """information about a single build / run of a :class:`~.job.Job`""" def __init__(self, api): """ Args: api (JenkinsAPI): Pre-initialized connection to the Jenkins REST API """ super().__init__() self._api = api self._log = logging.getLogger(__name__) def __eq__(self, obj): if not isinstance(obj, Build): return False if obj.uid != self.uid: return False return True def __ne__(self, obj): if not isinstance(obj, Build): return True if obj.uid != self.uid: return True return False def __hash__(self): return hash(self.uid) @property def url(self): """str: URL of this build""" return self._api.url @property def number(self): """int: sequentially assigned numeric ID for the build""" data = self._api.get_api_data() return data['number'] @property def start_time(self): """datetime.datetime: time stamp of when this build was started""" data = self._api.get_api_data() time_in_seconds = data['timestamp'] * 0.001 return datetime.fromtimestamp(time_in_seconds) @property def is_building(self): """bool: True if the build is currently executing otherwise False""" data = self._api.get_api_data() return data['building'] @property def console_output(self): """str: raw console output for this build as plain text""" return self._api.get_text("/consoleText") @property def result(self): """str: state of the associated job upon completion of this build. Typically one of the following: * "SUCCESS" * "UNSTABLE" * "FAILURE" * "ABORTED" """ data = self._api.get_api_data() return data['result'] @property def changeset(self): """Changeset: Description of 0 or more SCM revisions associated with / included in this build""" data = self._api.get_api_data() return Changeset(self._api, data['changeSet']) @property def description(self): """str: Gets the descriptive text associated with this build. May be an empty string if no description given.""" data = self._api.get_api_data() retval = data["description"] if retval is None: return "" return retval @description.setter def description(self, value): args = { 'params': { 'description': value, 'Submit': "Submit" } } self._api.post(self.url + '/submitDescription', args=args) @property def uid(self): """str: internal, unique identifier associated with this build""" data = self._api.get_api_data() return data["id"] @property def artifact_urls(self): """list (): list of 0 or more URLs to download published build artifacts """ data = self._api.get_api_data() artifacts_node = data['artifacts'] retval = [] for node in artifacts_node: url = urljoin( self._api.url, "artifact/" + node['fileName']) retval.append(url) return retval @property def duration(self): """int: total runtime of the build, in milliseconds. Returns 0 if build hasn't finished""" data = self._api.get_api_data() return data['duration'] @property def estimated_duration(self): """int: Estimated runtime for a running build, in milliseconds. Estimate is based off average duration of previous builds""" data = self._api.get_api_data() return data['estimatedDuration']
[docs] def abort(self): """Aborts this build before it completes""" self._api.post(self._api.url + "stop")
[docs] def kill(self): """Performs hard kill on this build""" self._api.post(self._api.url + "kill")
if __name__ == "__main__": # pragma: no cover pass