1
2 """Analyze OpenFOAM logs"""
3
4 from TimeLineAnalyzer import TimeLineAnalyzer
5 from PyFoam.Basics.LineReader import LineReader
6 from PyFoam.Error import error
7
8 from PyFoam.Basics.ProgressOutput import ProgressOutput
9
10 from sys import stdout
11
13 """Base class for all analyzers
14
15 Administrates and calls a number of LogLineAnlayzers for each
16 line"""
17
19 """
20 @param progress: Print time progress on console?
21 """
22 self.analyzers={}
23 self.time=""
24 self.oDir=""
25 self.line=LineReader()
26 self.timeListeners=[]
27 self.timeTriggers=[]
28
29 self.progressOut=None
30 if progress:
31 self.progressOut=ProgressOutput(stdout)
32
33 tm=TimeLineAnalyzer(progress=progress)
34 self.addAnalyzer("Time",tm)
35 tm.addListener(self.setTime)
36
38 """Remove reference to self in children (hoping to remove
39 circular dependencies)"""
40
41 for a in self.analyzers.values():
42 a.tearDown()
43 a.setParent(None)
44
46 """Sets the time and alert all the LineAnalyzers that the time has changed
47 @param time: the new value of the time
48 """
49 if time!=self.time:
50 if self.progressOut:
51 self.progressOut.reset()
52
53 self.time=time
54 for listener in self.timeListeners:
55 listener.timeChanged()
56 for nm in self.analyzers:
57 self.analyzers[nm].timeChanged()
58 self.checkTriggers()
59
61 """Write a message to the progress output"""
62 if self.progressOut:
63 self.progressOut(msg)
64
66 """@param listener: An object that is notified when the time changes. Has to
67 implement a timeChanged method"""
68 if not 'timeChanged' in dir(listener):
69 error("Error. Object has no timeChanged-method:"+str(listener))
70 else:
71 self.timeListeners.append(listener)
72
74 """@returns: A list with the names of the Analyzers"""
75 return self.analyzers.keys()
76
78 """Is this LogLineAnalyzer name there"""
79 return self.analyzers.has_key(name)
80
82 """Get the LogLineAnalyzer name"""
83 if self.analyzers.has_key(name):
84 return self.analyzers[name]
85 else:
86 return None
87
89 """Adds an analyzer
90
91 obj - A LogLineAnalyzer
92 name - the name of the analyzer"""
93
94 obj.setParent(self)
95 self.analyzers[name]=obj
96
98 """Calls all the anlyzers for a line"""
99 for nm in self.analyzers:
100 self.analyzers[nm].doAnalysis(line)
101
103 """Analyzes a file (one line at a time)
104
105 fh - handle of the file"""
106 while(self.line.read(fh)):
107 self.analyzeLine(self.line.line)
108
110 """Checks with all the analyzers
111
112 If one analyzer returns False it returns False"""
113 result=True
114
115 for nm in self.analyzers:
116
117 result=result and self.analyzers[nm].goOn()
118
119 return result
120
122 """Gets the current time"""
123 return str(self.time)
124
126 """Sets the output directory for all the analyzers"""
127 self.oDir=d
128 for nm in self.analyzers:
129 self.analyzers[nm].setDirectory(self.oDir)
130
132 """Gets the output directory"""
133 return self.oDir
134
135 - def addTrigger(self,time,func,once=True,until=None):
136 """Adds a trigger function that is to be called as soon as
137 the simulation time exceeds a certain value
138 @param time: the time at which the function should be triggered
139 @param func: the trigger function
140 @param once: Should this function be called once or at every time-step
141 @param until: The time until which the trigger should be called"""
142
143 data={}
144 data["time"]=float(time)
145 data["func"]=func
146 if until!=None:
147 data["until"]=float(until)
148 once=False
149 data["once"]=once
150
151 self.timeTriggers.append(data)
152
154 """Check for and execute the triggered functions"""
155
156 remove=[]
157 for i in range(len(self.timeTriggers)):
158 t=self.timeTriggers[i]
159 if t["time"]<=self.time:
160 t["func"]()
161 if t["once"]:
162 remove.append(i)
163 elif "until" in t:
164 if t["until"]<=self.time:
165 remove.append(i)
166
167 remove.reverse()
168
169 for i in remove:
170 self.timeTriggers.pop(i)
171