]> TLD Linux GIT Repositories - tld-builder.git/blob - TLD_Builder/bqueue.py
- python 3.x fixes
[tld-builder.git] / TLD_Builder / bqueue.py
1 # vi: encoding=utf-8 ts=8 sts=4 sw=4 et
2
3 import re
4 import gzip
5 import time
6 import sys
7 if sys.version_info[0] == 2:
8     import StringIO
9 else:
10     from io import StringIO
11 import os
12 import fcntl
13 import string
14 import tempfile
15
16 # TLD_Builder:
17 import gpg
18 import request
19 import util
20 import log
21
22 class B_Queue:
23     def __init__(self, filename):
24         self.name = filename
25         self.requests = []
26         self.fd = None
27
28     def dump(self, fname):
29         (fdno, tmpfname) = tempfile.mkstemp(dir=os.path.dirname(fname))
30         f = os.fdopen(fdno, "w")
31         self.requests.reverse()
32         for r in self.requests:
33             r.dump(f)
34         self.requests.reverse()
35         f.flush()
36         os.fsync(f.fileno())
37         f.close()
38         os.chmod(tmpfname, 0o0644)
39         os.rename(tmpfname, fname)
40
41     def dump_html(self, fname):
42         (fdno, tmpfname) = tempfile.mkstemp(dir=os.path.dirname(fname))
43         f = os.fdopen(fdno, "w")
44         f.write("""
45 <html>
46     <head>
47     <link rel="Shortcut Icon" href="//www.tld-linux.org/favicon.ico"/>
48         <title>TLD builder queue</title>
49         <link rel="stylesheet" type="text/css" charset="utf-8" media="all" href="style.css">
50         <script src="//ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
51         <script src="//cdnjs.cloudflare.com/ajax/libs/jquery-timeago/1.4.3/jquery.timeago.min.js"></script>
52         <script type="text/javascript" src="script.js"></script>
53     </head>
54 <body>
55 <div id="header">
56     <div id="requesters-filter">Filter by requesters:<br></div>
57 </div>
58 <div id="content">
59 """
60         )
61         self.requests.reverse()
62         for r in self.requests:
63             r.dump_html(f)
64         self.requests.reverse()
65         f.write("</div></body></html>\n")
66         f.flush()
67         os.fsync(f.fileno())
68         f.close()
69         os.chmod(tmpfname, 0o0644)
70         os.rename(tmpfname, fname)
71
72     # read possibly compressed, signed queue
73     def read_signed(self):
74         if re.search(r"\.gz$", self.name):
75             f = gzip.open(self.name)
76         else:
77             f = open(self.name)
78         (signers, body) = gpg.verify_sig(f.read())
79         self.signers = signers
80         self.requests = request.parse_requests(body)
81
82     def _open(self):
83         if self.fd == None:
84             if os.access(self.name, os.F_OK):
85                 self.fd = open(self.name, "r+")
86             else:
87                 self.fd = open(self.name, "w+")
88
89     def read(self):
90         self._open()
91         self.signers = []
92         body = self.fd.read()
93         if body.strip() == "":
94             # empty file, don't choke
95             self.requests = []
96             return
97         try:
98             self.requests = request.parse_requests(body)
99         except Exception as e:
100             log.panic("error parsing %s: %s" % (self.name, e))
101             pass
102
103     def _write_to(self, f):
104         f.write("<queue>\n")
105         for r in self.requests:
106             r.write_to(f)
107         f.write("</queue>\n")
108
109     def write(self):
110         self._open()
111         self.fd.seek(0)
112         self.fd.truncate(0)
113         self._write_to(self.fd)
114         self.fd.flush()
115
116     def lock(self, no_block):
117         self._open()
118         op = fcntl.LOCK_EX
119         if no_block:
120             op = op + fcntl.LOCK_NB
121         try:
122             fcntl.flock(self.fd, op)
123             return 1
124         except IOError:
125             return 0
126
127     def unlock(self):
128         fcntl.flock(self.fd, fcntl.LOCK_UN)
129
130     def write_signed(self, name):
131         sio = StringIO.StringIO()
132         self._write_to(sio)
133         sio.seek(0)
134         sio.write(gpg.sign(sio.read()))
135         sio.seek(0)
136         (fdno, tmpname) = tempfile.mkstemp(dir=os.path.dirname(name))
137         f = os.fdopen(fdno, "w")
138         if re.search(r"\.gz$", name):
139             fgz = gzip.GzipFile(filename=name, mode="w", compresslevel=6, fileobj=f)
140             util.sendfile(sio, fgz)
141             fgz.close()
142         else:
143             util.sendfile(sio, f)
144         f.flush()
145         os.fsync(f.fileno())
146         f.close()
147         os.chmod(tmpname, 0o0644)
148         os.rename(tmpname, name)
149
150     def add(self, req):
151         self.requests.append(req)
152
153     def value(self):
154         return self.requests