class Boss(threading.Thread): def __init__(self): threading.Thread.__init__(self) self.log = logging.getLogger(__name__) self.config = Config() self.database = Database(self.config) self.build_queue = Queue(1) def run(self): workers = [] for worker_location in self.config.get("workers"): worker = Worker(worker_location, "image", self.build_queue) worker.start() workers.append(worker) self.log.info("Active workers are %s", workers) while True: build_job = self.database.get_build_job() if build_job: self.log.info("Found build job %s", build_job) self.build_queue.put(build_job) else: time.sleep(10)
class Worker(threading.Thread): def __init__(self): threading.Thread.__init__(self) self.log = logging.getLogger(__name__) self.log.info("log initialized") self.config = Config() self.log.info("config initialized") self.database = Database(self.config) self.log.info("database initialized") self.worker_id = None self.imagebuilders = [] def worker_register(self): self.worker_name = gethostname() self.worker_address = "" self.worker_pubkey = get_pubkey() self.log.info("register worker '%s' '%s' '%s'", self.worker_name, self.worker_address, self.worker_pubkey) self.worker_id = str( self.database.worker_register(self.worker_name, self.worker_address, self.worker_pubkey)) def worker_add_skill(self, imagebuilder): self.database.worker_add_skill(self.worker_id, *imagebuilder, 'ready') def add_imagebuilder(self, distro, release, target, subtarget): self.log.info("adding imagebuilder") self.log.info("worker serves %s %s %s %s", distro, release, target, subtarget) imagebuilder = ImageBuilder(distro, str(release), target, subtarget) self.log.info("initializing imagebuilder") if imagebuilder.run(): self.log.info("register imagebuilder") self.worker_add_skill(imagebuilder.as_array()) self.imagebuilders.append(imagebuilder.as_array()) self.log.info("imagebuilder initialzed") else: # manage failures # add in skill status pass self.log.info("added imagebuilder") def destroy(self, signal=None, frame=None): self.log.info("destroy worker %s", self.worker_id) self.database.worker_destroy(self.worker_id) sys.exit(0) def run(self): self.log.info("register worker") self.worker_register() self.log.debug("setting up gnupg") setup_gnupg() while True: self.log.debug("severing %s", self.imagebuilders) build_job_request = None for imagebuilder in self.imagebuilders: if ImageBuilder(*imagebuilder).created(): build_job_request = self.database.get_build_job( *imagebuilder) if build_job_request: break else: self.add_imagebuilder(*imagebuilder) if build_job_request: self.log.debug("found build job") self.last_build_id = build_job_request[0] image = Image(*build_job_request[2:9]) self.log.debug(image.as_array()) if not image.build(): self.log.warn("build failed for %s", image.as_array()) else: # heartbeat should be more less than 5 seconds if len(self.imagebuilders) < MAX_TARGETS or MAX_TARGETS == 0: imagebuilder_request = None while not imagebuilder_request: imagebuilder_request = self.database.worker_needed() if not imagebuilder_request: self.heartbeat() time.sleep(5) continue self.log.info("found worker_needed %s", imagebuilder_request) if not imagebuilder_request in self.imagebuilders: self.add_imagebuilder(*imagebuilder_request) self.heartbeat() time.sleep(5) def heartbeat(self): self.log.debug("heartbeat %s", self.worker_id) self.database.worker_heartbeat(self.worker_id)