annotate roundup/roundupdb.py @ 44:c1f3e058c58d

Moved the database backends off into backends.
author Richard Jones <richard@users.sourceforge.net>
date Mon, 23 Jul 2001 07:14:41 +0000
parents c7c14960f413
children a55c1301ba1f
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
44
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
1 # $Id: roundupdb.py,v 1.3 2001-07-23 07:14:41 richard Exp $
25
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
2
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
3 import re, os, smtplib, socket
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
4
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
5 import hyperdb, date
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
6
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
7 def splitDesignator(designator, dre=re.compile(r'([^\d]+)(\d+)')):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
8 ''' Take a foo123 and return ('foo', 123)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
9 '''
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
10 m = dre.match(designator)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
11 return m.group(1), m.group(2)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
12
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
13 class Database:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
14 def getuid(self):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
15 """Return the id of the "user" node associated with the user
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
16 that owns this connection to the hyperdatabase."""
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
17 return self.user.lookup(self.journaltag)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
18
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
19 def uidFromAddress(self, address):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
20 ''' address is from the rfc822 module, and therefore is (name, addr)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
21
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
22 user is created if they don't exist in the db already
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
23 '''
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
24 (realname, address) = address
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
25 users = self.user.stringFind(address=address)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
26 if users: return users[0]
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
27 return self.user.create(username=address, address=address,
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
28 realname=realname)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
29
44
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
30 # XXX: added the 'creator' faked attribute
25
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
31 class Class(hyperdb.Class):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
32 # Overridden methods:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
33 def __init__(self, db, classname, **properties):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
34 hyperdb.Class.__init__(self, db, classname, **properties)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
35 self.auditors = {'create': [], 'set': [], 'retire': []}
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
36 self.reactors = {'create': [], 'set': [], 'retire': []}
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
37
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
38 def create(self, **propvalues):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
39 """These operations trigger detectors and can be vetoed. Attempts
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
40 to modify the "creation" or "activity" properties cause a KeyError.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
41 """
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
42 if propvalues.has_key('creation') or propvalues.has_key('activity'):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
43 raise KeyError, '"creation" and "activity" are reserved'
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
44 for audit in self.auditors['create']:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
45 audit(self.db, self, None, propvalues)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
46 nodeid = hyperdb.Class.create(self, **propvalues)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
47 for react in self.reactors['create']:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
48 react(self.db, self, nodeid, None)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
49 return nodeid
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
50
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
51 def set(self, nodeid, **propvalues):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
52 """These operations trigger detectors and can be vetoed. Attempts
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
53 to modify the "creation" or "activity" properties cause a KeyError.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
54 """
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
55 if propvalues.has_key('creation') or propvalues.has_key('activity'):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
56 raise KeyError, '"creation" and "activity" are reserved'
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
57 for audit in self.auditors['set']:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
58 audit(self.db, self, nodeid, propvalues)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
59 oldvalues = self.db.getnode(self.classname, nodeid)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
60 hyperdb.Class.set(self, nodeid, **propvalues)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
61 for react in self.reactors['set']:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
62 react(self.db, self, nodeid, oldvalues)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
63
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
64 def retire(self, nodeid):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
65 """These operations trigger detectors and can be vetoed. Attempts
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
66 to modify the "creation" or "activity" properties cause a KeyError.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
67 """
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
68 for audit in self.auditors['retire']:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
69 audit(self.db, self, nodeid, None)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
70 hyperdb.Class.retire(self, nodeid)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
71 for react in self.reactors['retire']:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
72 react(self.db, self, nodeid, None)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
73
44
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
74 def get(self, nodeid, propname):
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
75 """Attempts to get the "creation" or "activity" properties should
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
76 do the right thing
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
77 """
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
78 if propname == 'creation':
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
79 journal = self.db.getjournal(self.classname, nodeid)
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
80 if journal:
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
81 return self.db.getjournal(self.classname, nodeid)[0][1]
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
82 else:
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
83 # on the strange chance that there's no journal
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
84 return date.Date()
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
85 if propname == 'activity':
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
86 journal = self.db.getjournal(self.classname, nodeid)
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
87 if journal:
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
88 return self.db.getjournal(self.classname, nodeid)[-1][1]
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
89 else:
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
90 # on the strange chance that there's no journal
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
91 return date.Date()
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
92 if propname == 'creator':
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
93 journal = self.db.getjournal(self.classname, nodeid)
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
94 if journal:
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
95 name = self.db.getjournal(self.classname, nodeid)[0][2]
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
96 else:
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
97 return None
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
98 return self.db.user.lookup(name)
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
99 return hyperdb.Class.get(self, nodeid, propname)
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
100
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
101 def getprops(self):
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
102 """In addition to the actual properties on the node, these
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
103 methods provide the "creation" and "activity" properties."""
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
104 d = hyperdb.Class.getprops(self).copy()
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
105 d['creation'] = hyperdb.Date()
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
106 d['activity'] = hyperdb.Date()
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
107 d['creator'] = hyperdb.Link("user")
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
108 return d
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
109
25
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
110 # New methods:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
111
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
112 def audit(self, event, detector):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
113 """Register a detector
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
114 """
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
115 self.auditors[event].append(detector)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
116
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
117 def react(self, event, detector):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
118 """Register a detector
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
119 """
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
120 self.reactors[event].append(detector)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
121
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
122 class FileClass(Class):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
123 def create(self, **propvalues):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
124 ''' snaffle the file propvalue and store in a file
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
125 '''
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
126 content = propvalues['content']
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
127 del propvalues['content']
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
128 newid = Class.create(self, **propvalues)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
129 self.setcontent(self.classname, newid, content)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
130 return newid
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
131
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
132 def filename(self, classname, nodeid):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
133 # TODO: split into multiple files directories
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
134 return os.path.join(self.db.dir, 'files', '%s%s'%(classname, nodeid))
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
135
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
136 def setcontent(self, classname, nodeid, content):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
137 ''' set the content file for this file
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
138 '''
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
139 open(self.filename(classname, nodeid), 'wb').write(content)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
140
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
141 def getcontent(self, classname, nodeid):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
142 ''' get the content file for this file
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
143 '''
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
144 return open(self.filename(classname, nodeid), 'rb').read()
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
145
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
146 def get(self, nodeid, propname):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
147 ''' trap the content propname and get it from the file
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
148 '''
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
149 if propname == 'content':
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
150 return self.getcontent(self.classname, nodeid)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
151 return Class.get(self, nodeid, propname)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
152
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
153 def getprops(self):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
154 ''' In addition to the actual properties on the node, these methods
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
155 provide the "content" property.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
156 '''
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
157 d = Class.getprops(self).copy()
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
158 d['content'] = hyperdb.String()
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
159 return d
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
160
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
161 # XXX deviation from spec - was called ItemClass
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
162 class IssueClass(Class):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
163 # Overridden methods:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
164
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
165 def __init__(self, db, classname, **properties):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
166 """The newly-created class automatically includes the "messages",
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
167 "files", "nosy", and "superseder" properties. If the 'properties'
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
168 dictionary attempts to specify any of these properties or a
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
169 "creation" or "activity" property, a ValueError is raised."""
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
170 if not properties.has_key('title'):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
171 properties['title'] = hyperdb.String()
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
172 if not properties.has_key('messages'):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
173 properties['messages'] = hyperdb.Multilink("msg")
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
174 if not properties.has_key('files'):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
175 properties['files'] = hyperdb.Multilink("file")
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
176 if not properties.has_key('nosy'):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
177 properties['nosy'] = hyperdb.Multilink("user")
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
178 if not properties.has_key('superseder'):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
179 properties['superseder'] = hyperdb.Multilink("issue")
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
180 if (properties.has_key('creation') or properties.has_key('activity')
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
181 or properties.has_key('creator')):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
182 raise ValueError, '"creation", "activity" and "creator" are reserved'
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
183 Class.__init__(self, db, classname, **properties)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
184
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
185 # New methods:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
186
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
187 def addmessage(self, nodeid, summary, text):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
188 """Add a message to an issue's mail spool.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
189
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
190 A new "msg" node is constructed using the current date, the user that
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
191 owns the database connection as the author, and the specified summary
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
192 text.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
193
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
194 The "files" and "recipients" fields are left empty.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
195
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
196 The given text is saved as the body of the message and the node is
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
197 appended to the "messages" field of the specified issue.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
198 """
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
199
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
200 def sendmessage(self, nodeid, msgid):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
201 """Send a message to the members of an issue's nosy list.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
202
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
203 The message is sent only to users on the nosy list who are not
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
204 already on the "recipients" list for the message.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
205
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
206 These users are then added to the message's "recipients" list.
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
207 """
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
208 # figure the recipient ids
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
209 recipients = self.db.msg.get(msgid, 'recipients')
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
210 r = {}
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
211 for recipid in recipients:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
212 r[recipid] = 1
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
213 authid = self.db.msg.get(msgid, 'author')
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
214 r[authid] = 1
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
215
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
216 # now figure the nosy people who weren't recipients
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
217 sendto = []
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
218 nosy = self.get(nodeid, 'nosy')
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
219 for nosyid in nosy:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
220 if not r.has_key(nosyid):
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
221 sendto.append(nosyid)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
222 recipients.append(nosyid)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
223
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
224 if sendto:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
225 # update the message's recipients list
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
226 self.db.msg.set(msgid, recipients=recipients)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
227
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
228 # send an email to the people who missed out
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
229 sendto = [self.db.user.get(i, 'address') for i in recipients]
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
230 cn = self.classname
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
231 title = self.get(nodeid, 'title') or '%s message copy'%cn
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
232 m = ['Subject: [%s%s] %s'%(cn, nodeid, title)]
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
233 m.append('To: %s'%', '.join(sendto))
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
234 m.append('Reply-To: %s'%self.ISSUE_TRACKER_EMAIL)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
235 m.append('')
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
236 m.append(self.db.msg.get(msgid, 'content'))
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
237 # TODO attachments
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
238 try:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
239 smtp = smtplib.SMTP(self.MAILHOST)
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
240 smtp.sendmail(self.ISSUE_TRACKER_EMAIL, sendto, '\n'.join(m))
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
241 except socket.error, value:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
242 return "Couldn't send confirmation email: mailhost %s"%value
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
243 except smtplib.SMTPException, value:
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
244 return "Couldn't send confirmation email: %s"%value
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
245
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
246 #
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
247 # $Log: not supported by cvs2svn $
44
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
248 # Revision 1.2 2001/07/22 12:09:32 richard
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
249 # Final commit of Grande Splite
c1f3e058c58d Moved the database backends off into backends.
Richard Jones <richard@users.sourceforge.net>
parents: 26
diff changeset
250 #
26
c7c14960f413 Final commit of Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents: 25
diff changeset
251 # Revision 1.1 2001/07/22 11:58:35 richard
c7c14960f413 Final commit of Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents: 25
diff changeset
252 # More Grande Splite
25
4cf1daf2f2eb More Grande Splite
Richard Jones <richard@users.sourceforge.net>
parents:
diff changeset
253 #

Roundup Issue Tracker: http://roundup-tracker.org/