]> mj.ucw.cz Git - moe.git/blob - t/moe/status.py
Changed pipeline.insert syntax - now guesses the function name
[moe.git] / t / moe / status.py
1 #!/usr/bin/env python
2
3 import sys
4 import types
5 import re
6
7 key_pattern = re.compile("^[A-Za-z0-9_-]+$")
8
9 class MoeStatusInvalid(Exception):
10     pass
11
12 class Status:
13     """Moe status file."""
14
15     def __init__(self):
16         self.stat = {}
17
18     def __getitem__(self, k):
19         if not self.stat.has_key(k): return None
20         v = self.stat[k]
21         if type(v) == types.ListType:
22             if len(v) > 0: return v[0]
23             else: return None
24         else: return v
25
26     def __setitem__(self, k, v):
27         self.stat[k] = v
28
29     def keys(self):
30         return self.stat.keys()
31
32     def get_list(self, k):
33         m = self.stat
34         if not m.has_key(k):
35             m[k] = []
36         elif type(m[k]) != types.ListType:
37             m[k] = [m[k]]
38         return m[k]
39
40     def dump(self, prefix=""):
41         """
42         Dump status in metafile format.
43         Return a list of lines, `prefix` is indent prefix.
44         """
45         l = []
46         for k,v in self.stat.items():
47             if type(v) == types.ListType: vals = v
48             else: vals = [v]
49             for w in vals:
50                 if isinstance(w, Status):
51                     l.append(prefix + k + "(\n")
52                     l.extend(self.str_lines(prefix+"  "))
53                     l.append(prefix + ")\n")
54                 else:
55                     l.append(prefix + k + ":" + str(w) + "\n")
56         return l
57         
58     def write(self, f=None, name=None):
59         """
60         Write status (as a metafile) to `f` or file `name` or `stdout`
61         """
62         if not f and name is not None:
63             with open(name, "w") as f:
64                 for l in self.dump():
65                     f.write(l+"\n")
66         else:
67             if not f: 
68                 f = sys.stdout
69             for l in self.dump():
70                 f.write(l+"\n")
71
72     def read(self, file=None, name=None):
73         if file is None:
74             if name is not None:
75                 file = open(name, "r")
76             else:
77                 file = sys.stdin
78         self.stat = {}
79         self.do_read(file)
80
81     def read_val(self, k, v):
82         if not key_pattern.match(k):
83             raise MoeStatusInvalid, "Parse error: invalid key syntax"
84         m = self.stat
85         if not m.has_key(k):
86             m[k] = v
87         else:
88             self.get_list(k).append(v)
89
90     def do_read(self, file):
91         stk = []
92         this = self
93         for x in file.readlines():
94             x = x.rstrip("\n").lstrip(" \t")
95             if x=="" or x.startswith("#"):
96                 pass
97             else:
98                 sep = x.find(":")
99                 if sep >= 0:
100                     k = x[:sep]
101                     v = x[sep+1:]
102                     this.read_val(k, v)
103                 elif x.endswith("("):
104                     k = x[:-1]
105                     new = Status()
106                     this.read_val(k, new)
107                     stk.append(this)
108                     this = new
109                 elif x == ")":
110                     if len(stk) == 0:
111                         raise MoeStatusInvalid, "Parse error: incorrect nesting"
112                     else:
113                         this = stk.pop()
114                 else:
115                     raise MoeStatusInvalid, "Parse error: malformed line"