1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 from twisted.python import log
20 from twisted.internet import defer
21 from twisted.application import service
22 from buildbot import pbutil
25 """
26 Base class for services that manage users manually. This takes care
27 of the service.MultiService work needed by all the services that
28 subclass it.
29 """
30
34
37
40
42 """
43 Perspective registered in buildbot.pbmanager and contains the real
44 workings of `buildbot user` by working with the database when
45 perspective_commandline is called.
46 """
47
50
98
99 @defer.inlineCallbacks
101 """
102 This performs the requested operations from the `buildbot user`
103 call by calling the proper buildbot.db.users methods based on
104 the operation. It yields a deferred instance with the results
105 from the database methods.
106
107 @param op: operation to perform (add, remove, update, get)
108 @type op: string
109
110 @param bb_username: username portion of auth credentials
111 @type bb_username: string
112
113 @param bb_password: hashed password portion of auth credentials
114 @type bb_password: hashed string
115
116 @param ids: user identifiers used to find existing users
117 @type ids: list of strings or None
118
119 @param info: type/value pairs for each user that will be added
120 or updated in the database
121 @type info: list of dictionaries or None
122
123 @returns: results from db.users methods via deferred
124 """
125 log.msg("perspective_commandline called")
126 results = []
127
128 if ids:
129 for user in ids:
130
131
132 uid = yield self.master.db.users.identifierToUid(
133 identifier=user)
134
135 result = None
136 if op == 'remove':
137 if uid:
138 yield self.master.db.users.removeUser(uid)
139 result = user
140 else:
141 log.msg("Unable to find uid for identifier %s" % user)
142 elif op == 'get':
143 if uid:
144 result = yield self.master.db.users.getUser(uid)
145 else:
146 log.msg("Unable to find uid for identifier %s" % user)
147
148 results.append(result)
149 else:
150 for user in info:
151
152
153 ident = user.pop('identifier')
154 uid = yield self.master.db.users.identifierToUid(
155 identifier=ident)
156
157
158
159 if not user:
160 if uid:
161 result = yield self.master.db.users.updateUser(
162 uid=uid,
163 identifier=ident,
164 bb_username=bb_username,
165 bb_password=bb_password)
166 results.append(ident)
167 else:
168 log.msg("Unable to find uid for identifier %s"
169 % user)
170 else:
171
172 once_through = False
173 for attr in user:
174 if op == 'update' or once_through:
175 if uid:
176 result = yield self.master.db.users.updateUser(
177 uid=uid,
178 identifier=ident,
179 bb_username=bb_username,
180 bb_password=bb_password,
181 attr_type=attr,
182 attr_data=user[attr])
183 else:
184 log.msg("Unable to find uid for identifier %s"
185 % user)
186 elif op == 'add':
187 result = yield self.master.db.users.findUserByAttr(
188 identifier=ident,
189 attr_type=attr,
190 attr_data=user[attr])
191 once_through = True
192 results.append(ident)
193
194
195 if result:
196 results.append(result)
197 uid = result
198 results = self.formatResults(op, results)
199 defer.returnValue(results)
200
202 """
203 Service that runs to set up and register CommandlineUserManagerPerspective
204 so `buildbot user` calls get to perspective_commandline.
205 """
206
207 - def __init__(self, username=None, passwd=None, port=None):
208 UsersBase.__init__(self)
209 assert username and passwd, ("A username and password pair must be given "
210 "to connect and use `buildbot user`")
211 self.username = username
212 self.passwd = passwd
213
214 assert port, "A port must be specified for a PB connection"
215 self.port = port
216 self.registration = None
217
223 self.registration = self.master.pbmanager.register(self.port,
224 self.username,
225 self.passwd,
226 factory)
227
233 d.addCallback(unreg)
234 return d
235