Mercurial > treepkg
view contrib/sawmill/web/details.py @ 570:44c0f8404983
Refactor git pull command out of update
Tag MUST NOT use update because therefore it always changes the current local branch!
For listing the tags it's enough to pull the latest repo changes
author | Bjoern Ricks <bricks@intevation.de> |
---|---|
date | Fri, 02 Sep 2011 11:46:29 +0000 |
parents | 73a2e603a23b |
children |
line wrap: on
line source
# -*- coding: UTF-8 -*- # # Copyright (C) 2010 by Intevation GmbH # Authors: # Sascha L. Teichmann <sascha.teichmann@intevation.de> # # This program is free software under the GPL (>=v2) # Read the file COPYING coming with the software for details. from mod_python import apache, psp, util import os import re import datetime import time from lxml import etree BASE_DIR = "treepkgs" TREEPKG_DIR = os.path.join(os.path.dirname(__file__), BASE_DIR) STATUS_LINE = re.compile(r"^([^:]+):(.+)") UNDER_SCORE = re.compile(r"_+(\w)") INVALID_LABEL = re.compile(r"[^a-zA-Z0-9_]") def _create_time(s, format="%Y-%m-%d %H:%M:%S"): return datetime.datetime(*(time.strptime(s, format)[0:6])) def _pretty_log_name(log): log = log.replace(".txt", "").replace(".gz", "").capitalize() return UNDER_SCORE.sub(lambda x: " %s" % x.group(1).upper(), log) def _make_valid_label(label): return INVALID_LABEL.sub("_", label) class TrackItem(object): def __init__(self, treepkg, track, revision, status_file): self.treepkg = treepkg self.track = track self.revision = revision self.status_file = status_file self.loaded = False self.status = None self.start = None self.stop = None self.logs = None self.tags = None def check_loaded(self): if not self.loaded: f = open(self.status_file) try: for line in f: m = STATUS_LINE.match(line) if not m: continue key, value = [x.strip() for x in m.groups()] if key == 'status': self.status = value elif key == 'start': self.start = _create_time(value) elif key == 'stop': self.stop = _create_time(value) elif key == 'tags': self.tags = value finally: f.close() self.loaded = True def get_build_status(self): self.check_loaded() return self.status def get_build_start(self): self.check_loaded() return self.start def get_build_stop(self): self.check_loaded() return self.stop def get_tags(self): self.check_loaded() return self.tags def get_label(self): self.check_loaded() out = [ _make_valid_label(self.track), _make_valid_label(self.revision) ] if self.start: out.append(self.start.strftime("%Y%m%d%H%M%S")) return ''.join(out) def log_path(self, log): return "%s/tracks/%s/pkg/%s/log/%s" % ( self.treepkg, self.track, self.revision, log) def get_build_logs(self): oj = os.path.join if self.logs is None: log_dir = oj(os.path.dirname(self.status_file), "log") if not os.path.isdir(log_dir): self.logs = [] else: self.logs =[(_pretty_log_name(f), self.log_path(f)) for f in os.listdir(log_dir) if os.path.isfile(oj(log_dir, f)) and f.find("txt") >= 0] return self.logs build_status = property(get_build_status) build_start = property(get_build_start) build_stop = property(get_build_stop) build_logs = property(get_build_logs) build_tags = property(get_tags) build_label = property(get_label) def __scan_track_items(treepkg, path): items = [] tracks_path = os.path.join(path, "tracks") if os.path.isdir(tracks_path): for track in os.listdir(tracks_path): track_path = os.path.join(tracks_path, track) if not os.path.isdir(track_path): continue revisions_path = os.path.join(track_path, "pkg") if not os.path.isdir(revisions_path): continue for revision in os.listdir(revisions_path): revision_path = os.path.join(revisions_path, revision) if not os.path.isdir(revision_path): continue status_file = os.path.join(revision_path, "status") if not os.path.isfile(status_file): continue items.append(TrackItem(treepkg, track, revision, status_file)) return items def __description_header(treepkg): treepkg_xml = os.path.join(treepkg, "treepkg.xml") if os.path.isfile(treepkg_xml): xml = None try: xml = open(treepkg_xml, "rb") dom = etree.parse(xml) finally: if xml: xml.close() description = ''.join(dom.xpath("//description/text()")) header = ''.join([etree.tostring(x, encoding="UTF-8", method="html") for x in dom.xpath("//header/*")]) return description, header return "unknown", "" def index(req, treepkg=''): if not treepkg: util.redirect(req, "index.py") package_dir = None for d in os.listdir(TREEPKG_DIR): dp = os.path.join(TREEPKG_DIR, d) if d == treepkg and os.path.isdir(dp): package_dir = dp break if not package_dir: req.status = apache.HTTP_NOT_FOUND return "requested TreePkg not found" description, header = __description_header(package_dir) track_items = __scan_track_items(treepkg, package_dir) parameters = { 'page_title' : description, 'back_link' : 'index.py', 'base_dir' : BASE_DIR, 'description': description, 'header' : header, 'track_items': track_items } if os.path.isfile(os.path.join(package_dir, "rss.xml")): parameters['syndicate'] = ( 'Build error feed', 'treepkgs/%s/rss.xml' % treepkg) req.content_type = 'text/html;charset=utf-8' template = psp.PSP(req, filename='templates/details.html') template.run(parameters)