Imported from archive.
[mudpy.git] / lib / muff / muffuniv.py
1 # Copyright (c) 2005 mudpy, Jeremy Stanley <fungi@yuggoth.org>, all rights reserved.
2 # Licensed per terms in the LICENSE file distributed with this software.
3
4 # persistent variables are stored in ini-style files supported by ConfigParser
5 import ConfigParser
6
7 # need to know the directory separator
8 import os
9
10 # hack to load all modules in the muff package
11 import muff
12 for module in muff.__all__:
13         exec("import " + module)
14
15 class Element:
16         """An element of the universe."""
17         def __init__(self, key, origin, universe):
18                 """Default values for the in-memory element variables."""
19                 self.key = key
20                 if not origin.startswith(os.sep):
21                         origin = os.getcwd() + os.sep + origin
22                 self.origin = origin
23                 universe.contents[key] = self
24                 if key.find(":"):
25                         category = key.split(":", 1)
26                         if category[0] in universe.categories:
27                                 exec("universe." + category[0] + "s[category[1]] = self")
28                 if not origin in universe.files.keys():
29                         DataFile(origin, universe)
30                 if not universe.files[origin].data.has_section(key):
31                         universe.files[origin].data.add_section(key)
32         def facets(self):
33                 """Return a list of facets for this element."""
34                 return universe.files[self.origin].data.options(self.key)
35         def get(self, facet):
36                 """Retrieve values."""
37                 if facet in dir(self): return self.facet
38                 else:
39                         try:
40                                 return universe.files[self.origin].data.get(self.key, facet)
41                         except:
42                                 return None
43         def getint(self, facet):
44                 """Convenience method to coerce return values as type int."""
45                 value = self.get(facet)
46                 if not value: value = 0
47                 elif type(value) is str: value = value.rstrip("L")
48                 return int(value)
49         def set(self, facet, value):
50                 """Set values."""
51                 if facet in universe.files[self.origin].data.options(self.key):
52                         universe.files[self.origin].data.set(self.key, facet, repr(value))
53                 else: self.facet = value
54         def rec(self, facet, value):
55                 """Add initial values to the record."""
56                 universe.files[self.origin].data.set(self.key, facet, value)
57
58 class DataFile:
59         """A file containing universe elements."""
60         def __init__(self, filename, universe):
61                 filedir = os.sep.join(filename.split(os.sep)[:-1])
62                 data = ConfigParser.SafeConfigParser()
63                 data.read(filename)
64                 self.filename = filename
65                 self.data = data
66                 universe.files[filename] = self
67                 for section in data.sections():
68                         if section == "include":
69                                 for option in data.options(section):
70                                         includefile = data.get(section, option)
71                                         if not includefile.startswith(os.sep):
72                                                 includefile = filedir + os.sep + includefile
73                                         DataFile(includefile, universe)
74                         else:
75                                 Element(section, filename, universe)
76         def save(self):
77                 basedir = os.sep.join(self.filename.split(os.sep)[:-1])
78                 if not os.access(basedir, os.F_OK): os.makedirs(basedir)
79                 file_descriptor = file(self.filename, "w")
80                 self.data.write(file_descriptor)
81                 file_descriptor.flush()
82                 file_descriptor.close()
83
84 class Universe:
85         """The universe."""
86         def __init__(self):
87                 self.contents = {}
88                 self.files = {}
89                 self.categories = [ "account", "actor", "command", "internal", "item", "menu", "room" ]
90                 for item in self.categories: exec("self." + item + "s = {}")
91                 for item in [ "avatars", "commands", "internals", "universe" ]:
92                         filename = muffconf.get("files", item)
93                         if not filename.startswith(os.sep): filename = os.getcwd() + os.sep + filename
94                         DataFile(filename, self)
95         def save(self):
96                 for key in self.files.keys(): self.files[key].save()
97
98 def element_exists(key): return key in universe.contents.keys()
99
100 # reload the muffconf module if the files:data setting does not exist
101 try:
102         if muffconf.has_section("files"): pass
103 except AttributeError:
104         reload(muffconf)
105
106 # if there is no universe, create an empty one
107 if not "universe" in dir(): universe = Universe()
108