2 from time import strftime
5 from re import compile as re_compile
7 class AutoTimerComponent(object):
8 """AutoTimer Component which also handles validity checks"""
10 def __init__(self, id, *args, **kwargs):
13 self.setValues(*args, **kwargs)
15 def __eq__(self, other):
17 return self.id == other.id
18 except AttributeError:
21 def __ne__(self, other):
22 return not self.__eq__(other)
24 def setValues(self, name, match, enabled, timespan = None, services = None, offset = None, \
25 afterevent = [], exclude = None, maxduration = None, destination = None, \
26 include = None, matchCount = 0, matchLeft = 0, matchLimit = '', matchFormatString = '', \
27 lastBegin = 0, justplay = False, avoidDuplicateDescription = False):
30 self.timespan = timespan
31 self.services = services
33 self.afterevent = afterevent
34 self.exclude = exclude
35 self.include = include
36 self.maxduration = maxduration
37 self.enabled = enabled
38 self.destination = destination
39 self.matchCount = matchCount
40 self.matchLeft = matchLeft
41 self.matchLimit = matchLimit
42 self.matchFormatString = matchFormatString
43 self.lastBegin = lastBegin
44 self.justplay = justplay
45 self.avoidDuplicateDescription = avoidDuplicateDescription
47 def calculateDayspan(self, begin, end):
48 if end[0] < begin[0] or (end[0] == begin[0] and end[1] <= begin[1]):
49 return (begin, end, True)
51 return (begin, end, False)
53 def setTimespan(self, timespan):
55 self._timespan = (None,)
57 self._timespan = self.calculateDayspan(*timespan)
59 def getTimespan(self):
62 timespan = property(getTimespan, setTimespan)
64 def setExclude(self, exclude):
67 [re_compile(x) for x in exclude[0]],
68 [re_compile(x) for x in exclude[1]],
69 [re_compile(x) for x in exclude[2]],
73 self._exclude = ([], [], [], [])
78 exclude = property(getExclude, setExclude)
80 def setInclude(self, include):
83 [re_compile(x) for x in include[0]],
84 [re_compile(x) for x in include[1]],
85 [re_compile(x) for x in include[2]],
89 self._include = ([], [], [], [])
94 include = property(getInclude, setInclude)
96 def setServices(self, services):
98 self._services = services
102 def getServices(self):
103 return self._services
105 services = property(getServices, setServices)
107 def setAfterEvent(self, afterevent):
108 del self._afterevent[:]
110 for definition in afterevent:
111 action, timespan = definition
113 self._afterevent.append((action, (None,)))
115 self._afterevent.append((action, self.calculateDayspan(*timespan)))
117 def getCompleteAfterEvent(self):
118 return self._afterevent
120 afterevent = property(getCompleteAfterEvent, setAfterEvent)
122 def hasTimespan(self):
123 return self.timespan[0] is not None
125 def getTimespanBegin(self):
126 return '%02d:%02d' % (self.timespan[0][0], self.timespan[0][1])
128 def getTimespanEnd(self):
129 return '%02d:%02d' % (self.timespan[1][0], self.timespan[1][1])
131 def checkAnyTimespan(self, time, begin = None, end = None, haveDayspan = False):
135 # Check if we span a day
137 # Check if begin of event is later than our timespan starts
138 if time.tm_hour > begin[0] or (time.tm_hour == begin[0] and time.tm_min >= begin[1]):
139 # If so, event is in our timespan
141 # Check if begin of event is earlier than our timespan end
142 if time.tm_hour < end[0] or (time.tm_hour == end[0] and time.tm_min <= end[1]):
143 # If so, event is in our timespan
147 # Check if event begins earlier than our timespan starts
148 if time.tm_hour < begin[0] or (time.tm_hour == begin[0] and time.tm_min < begin[1]):
149 # Its out of our timespan then
151 # Check if event begins later than our timespan ends
152 if time.tm_hour > end[0] or (time.tm_hour == end[0] and time.tm_min > end[1]):
153 # Its out of our timespan then
157 def checkTimespan(self, begin):
158 return self.checkAnyTimespan(begin, *self.timespan)
160 def hasDuration(self):
161 return self.maxduration is not None
163 def getDuration(self):
164 return self.maxduration/60
166 def checkDuration(self, length):
167 if self.maxduration is None:
169 return length > self.maxduration
171 def checkServices(self, service):
172 if not len(self.services):
174 return service not in self.services
176 def getExcludedTitle(self):
177 return [x.pattern for x in self.exclude[0]]
179 def getExcludedShort(self):
180 return [x.pattern for x in self.exclude[1]]
182 def getExcludedDescription(self):
183 return [x.pattern for x in self.exclude[2]]
185 def getExcludedDays(self):
186 return self.exclude[3]
188 def getIncludedTitle(self):
189 return [x.pattern for x in self.include[0]]
191 def getIncludedShort(self):
192 return [x.pattern for x in self.include[1]]
194 def getIncludedDescription(self):
195 return [x.pattern for x in self.include[2]]
197 def getIncludedDays(self):
198 return self.include[3]
200 def checkExcluded(self, title, short, extended, dayofweek):
201 if len(self.exclude[3]):
202 list = [x for x in self.exclude[3]]
203 if "weekend" in list:
204 list.extend(["5", "6"])
205 if "weekday" in list:
206 list.extend(["0", "1", "2", "3", "4"])
207 if dayofweek in list:
210 for exclude in self.exclude[0]:
211 if exclude.search(title):
213 for exclude in self.exclude[1]:
214 if exclude.search(short):
216 for exclude in self.exclude[2]:
217 if exclude.search(extended):
221 def checkIncluded(self, title, short, extended, dayofweek):
222 if len(self.include[3]):
223 list = [x for x in self.include[3]]
224 if "weekend" in list:
225 list.extend(["5", "6"])
226 if "weekday" in list:
227 list.extend(["0", "1", "2", "3", "4"])
228 if dayofweek not in list:
231 for include in self.include[0]:
232 if not include.search(title):
234 for include in self.include[1]:
235 if not include.search(short):
237 for include in self.include[2]:
238 if not include.search(extended):
243 def checkFilter(self, title, short, extended, dayofweek):
244 if self.checkExcluded(title, short, extended, dayofweek):
247 return self.checkIncluded(title, short, extended, dayofweek)
250 return self.offset is not None
252 def isOffsetEqual(self):
253 return self.offset[0] == self.offset[1]
255 def applyOffset(self, begin, end):
256 if self.offset is None:
258 return (begin - self.offset[0], end + self.offset[1])
260 def getOffsetBegin(self):
261 return self.offset[0]/60
263 def getOffsetEnd(self):
264 return self.offset[1]/60
266 def hasAfterEvent(self):
267 return len(self.afterevent)
269 def hasAfterEventTimespan(self):
270 for afterevent in self.afterevent:
271 if afterevent[1][0] is not None:
275 def getAfterEventTimespan(self, end):
276 for afterevent in self.afterevent:
277 if not self.checkAnyTimespan(end, *afterevent[1]):
281 def getAfterEvent(self):
282 for afterevent in self.afterevent:
283 if afterevent[1][0] is None:
287 def getEnabled(self):
288 return self.enabled and "yes" or "no"
290 def getJustplay(self):
291 return self.justplay and "1" or "0"
293 def hasDestination(self):
294 return self.destination is not None
296 def hasCounter(self):
297 return self.matchCount != 0
299 def hasCounterFormatString(self):
300 return self.matchFormatString != ''
302 def getCounter(self):
303 return self.matchCount
305 def getCounterLeft(self):
306 return self.matchLeft
308 def getCounterLimit(self):
309 return self.matchLimit
311 def getCounterFormatString(self):
312 return self.matchFormatString
314 def checkCounter(self, timestamp):
315 # 0-Count is considered "unset"
316 if self.matchCount == 0:
319 # Check if event is in current timespan (we can only manage one!)
320 limit = strftime(self.matchFormatString, timestamp)
321 if limit != self.matchLimit:
324 if self.matchLeft > 0:
329 def update(self, begin, timestamp):
330 # Only update limit when we have new begin
331 if begin > self.lastBegin:
332 self.lastBegin = begin
335 # %m is Month, %U is week (sunday), %W is week (monday)
336 newLimit = strftime(self.matchFormatString, timestamp)
338 if newLimit != self.matchLimit:
339 self.matchLeft = self.matchCount
340 self.matchLimit = newLimit
342 def getLastBegin(self):
343 return self.lastBegin
345 def getAvoidDuplicateDescription(self):
346 return self.avoidDuplicateDescription
358 str(self.afterevent),
360 str(self.maxduration),
362 str(self.destination),
363 str(self.matchCount),
365 str(self.matchLimit),
366 str(self.matchFormatString),