# vi: encoding=utf-8 ts=8 sts=4 sw=4 et import re import gzip import time import StringIO import os import fcntl import string import tempfile # PLD_Builder: import gpg import request import util import log class B_Queue: def __init__(self, filename): self.name = filename self.requests = [] self.fd = None def dump(self, fname): (fdno, tmpfname) = tempfile.mkstemp(dir=os.path.dirname(fname)) f = os.fdopen(fdno, "w") self.requests.reverse() for r in self.requests: r.dump(f) self.requests.reverse() f.flush() os.fsync(f.fileno()) f.close() os.chmod(tmpfname, 0644) os.rename(tmpfname, fname) def dump_html(self, fname): (fdno, tmpfname) = tempfile.mkstemp(dir=os.path.dirname(fname)) f = os.fdopen(fdno, "w") f.write(""" PLD builder queue \n""" ) self.requests.reverse() for r in self.requests: r.dump_html(f) self.requests.reverse() f.write("\n") f.flush() os.fsync(f.fileno()) f.close() os.chmod(tmpfname, 0644) os.rename(tmpfname, fname) # read possibly compressed, signed queue def read_signed(self): if re.search(r"\.gz$", self.name): f = gzip.open(self.name) else: f = open(self.name) (signers, body) = gpg.verify_sig(f.read()) self.signers = signers self.requests = request.parse_requests(body) def _open(self): if self.fd == None: if os.access(self.name, os.F_OK): self.fd = open(self.name, "r+") else: self.fd = open(self.name, "w+") def read(self): self._open() self.signers = [] body = self.fd.read() if string.strip(body) == "": # empty file, don't choke self.requests = [] return try: self.requests = request.parse_requests(body) except Exception, e: log.panic("error parsing %s: %s" % (self.name, e)) pass def _write_to(self, f): f.write("\n") for r in self.requests: r.write_to(f) f.write("\n") def write(self): self._open() self.fd.seek(0) self.fd.truncate(0) self._write_to(self.fd) self.fd.flush() def lock(self, no_block): self._open() op = fcntl.LOCK_EX if no_block: op = op + fcntl.LOCK_NB try: fcntl.flock(self.fd, op) return 1 except IOError: return 0 def unlock(self): fcntl.flock(self.fd, fcntl.LOCK_UN) def write_signed(self, name): sio = StringIO.StringIO() self._write_to(sio) sio.seek(0) sio.write(gpg.sign(sio.read())) sio.seek(0) (fdno, tmpname) = tempfile.mkstemp(dir=os.path.dirname(name)) f = os.fdopen(fdno, "w") if re.search(r"\.gz$", name): fgz = gzip.GzipFile(filename=name, mode="w", compresslevel=6, fileobj=f) util.sendfile(sio, fgz) fgz.close() else: util.sendfile(sio, f) f.flush() os.fsync(f.fileno()) f.close() os.chmod(tmpname, 0644) os.rename(tmpname, name) def add(self, req): self.requests.append(req) def value(self): return self.requests