1 package org.apache.turbine.services.security;
2
3
4 /*
5 * Licensed to the Apache Software Foundation (ASF) under one
6 * or more contributor license agreements. See the NOTICE file
7 * distributed with this work for additional information
8 * regarding copyright ownership. The ASF licenses this file
9 * to you under the Apache License, Version 2.0 (the
10 * "License"); you may not use this file except in compliance
11 * with the License. You may obtain a copy of the License at
12 *
13 * http://www.apache.org/licenses/LICENSE-2.0
14 *
15 * Unless required by applicable law or agreed to in writing,
16 * software distributed under the License is distributed on an
17 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
18 * KIND, either express or implied. See the License for the
19 * specific language governing permissions and limitations
20 * under the License.
21 */
22
23
24 import java.util.ArrayList;
25 import java.util.List;
26
27 import org.apache.commons.configuration.Configuration;
28 import org.apache.fulcrum.security.acl.AccessControlList;
29 import org.apache.fulcrum.security.model.turbine.TurbineUserManager;
30 import org.apache.fulcrum.security.model.turbine.entity.TurbineUser;
31 import org.apache.fulcrum.security.util.DataBackendException;
32 import org.apache.fulcrum.security.util.EntityExistsException;
33 import org.apache.fulcrum.security.util.PasswordMismatchException;
34 import org.apache.fulcrum.security.util.UnknownEntityException;
35 import org.apache.fulcrum.security.util.UserSet;
36 import org.apache.turbine.om.security.DefaultUserImpl;
37 import org.apache.turbine.om.security.User;
38 import org.apache.turbine.services.ServiceManager;
39 import org.apache.turbine.services.TurbineServices;
40 import org.apache.turbine.util.ObjectUtils;
41
42 /**
43 * Default user manager.
44 *
45 * The user manager wraps Fulcrum security user objects into
46 * Turbine-specific ones.
47 *
48 * @author <a href="mailto:tv@apache.org">Thomas Vandahl</a>
49 * @version $Id: PassiveUserManager.java 1096130 2011-04-23 10:37:19Z ludwig $
50 */
51 public class DefaultUserManager implements UserManager
52 {
53 /** Fulcrum user manager instance to delegate to */
54 private TurbineUserManager umDelegate = null;
55
56 /**
57 * Wrap a Fulcrum user object into a Turbine user object
58 *
59 * @param user the user object to delegate to
60 *
61 * @return the wrapped object
62 */
63 protected <U extends User> U wrap(TurbineUser user)
64 {
65 @SuppressWarnings("unchecked")
66 U u = (U)new DefaultUserImpl(user);
67 return u;
68 }
69
70 /**
71 * Initializes the UserManager
72 *
73 * @param conf A Configuration object to init this Manager
74 */
75 @Override
76 public void init(Configuration conf)
77 {
78 ServiceManager manager = TurbineServices.getInstance();
79 this.umDelegate = (TurbineUserManager)manager.getService(TurbineUserManager.ROLE);
80 }
81
82 /**
83 * Check whether a specified user's account exists.
84 *
85 * The login name is used for looking up the account.
86 *
87 * @param user The user to be checked.
88 * @return true if the specified account exists
89 * @throws DataBackendException if there was an error accessing the data backend.
90 */
91 @Override
92 public boolean accountExists(User user)
93 throws DataBackendException
94 {
95 return umDelegate.checkExists(user);
96 }
97
98 /**
99 * Check whether a specified user's account exists.
100 *
101 * The login name is used for looking up the account.
102 *
103 * @param userName The name of the user to be checked.
104 * @return true if the specified account exists
105 * @throws DataBackendException if there was an error accessing the data backend.
106 */
107 @Override
108 public boolean accountExists(String userName)
109 throws DataBackendException
110 {
111 return umDelegate.checkExists(userName);
112 }
113
114 /**
115 * Retrieve a user from persistent storage using username as the
116 * key.
117 *
118 * @param username the name of the user.
119 * @return an User object.
120 * @exception UnknownEntityException if the user's record does not
121 * exist in the database.
122 * @exception DataBackendException if there is a problem accessing the
123 * storage.
124 */
125 @Override
126 public <U extends User> U retrieve(String username)
127 throws UnknownEntityException, DataBackendException
128 {
129 TurbineUser u = umDelegate.getUser(username);
130 return wrap(u);
131 }
132
133 /**
134 * Retrieve a set of users that meet the specified criteria.
135 *
136 * As the keys for the criteria, you should use the constants that
137 * are defined in {@link User} interface, plus the names
138 * of the custom attributes you added to your user representation
139 * in the data storage. Use verbatim names of the attributes -
140 * without table name prefix in case of DB implementation.
141 *
142 * @param criteria The criteria of selection.
143 * @return a List of users meeting the criteria.
144 * @throws DataBackendException if there is a problem accessing the
145 * storage.
146 */
147 @Override
148 public List<? extends User> retrieveList(Object criteria)
149 throws DataBackendException
150 {
151 UserSet uset = umDelegate.getAllUsers();
152 List<User> userList = new ArrayList<User>();
153
154 for (org.apache.fulcrum.security.entity.User u : uset)
155 {
156 TurbineUser tu = (TurbineUser)u;
157 userList.add(wrap(tu));
158 }
159
160 return userList;
161 }
162
163 /**
164 * Retrieve a user from persistent storage using username as the
165 * key, and authenticate the user. The implementation may chose
166 * to authenticate to the server as the user whose data is being
167 * retrieved.
168 *
169 * @param username the name of the user.
170 * @param password the user supplied password.
171 * @return an User object.
172 * @exception PasswordMismatchException if the supplied password was
173 * incorrect.
174 * @exception UnknownEntityException if the user's record does not
175 * exist in the database.
176 * @exception DataBackendException if there is a problem accessing the
177 * storage.
178 */
179 @Override
180 public <U extends User> U retrieve(String username, String password)
181 throws PasswordMismatchException, UnknownEntityException,
182 DataBackendException
183 {
184 TurbineUser u = umDelegate.getUser(username, password);
185 return wrap(u);
186 }
187
188 /**
189 * Save an User object to persistent storage. User's record is
190 * required to exist in the storage.
191 *
192 * @param user an User object to store.
193 * @exception UnknownEntityException if the user's record does not
194 * exist in the database.
195 * @exception DataBackendException if there is a problem accessing the
196 * storage.
197 */
198 @Override
199 public void store(User user)
200 throws UnknownEntityException, DataBackendException
201 {
202 try
203 {
204 user.setObjectdata(ObjectUtils.serializeMap(user.getPermStorage()));
205 }
206 catch (Exception e)
207 {
208 throw new DataBackendException("Could not serialize permanent storage", e);
209 }
210
211 umDelegate.saveUser(((DefaultUserImpl)user).getUserDelegate());
212 }
213
214 /**
215 * Saves User data when the session is unbound. The user account is required
216 * to exist in the storage.
217 *
218 * LastLogin, AccessCounter, persistent pull tools, and any data stored
219 * in the permData hashtable that is not mapped to a column will be saved.
220 *
221 * @exception UnknownEntityException if the user's account does not
222 * exist in the database.
223 * @exception DataBackendException if there is a problem accessing the
224 * storage.
225 */
226 @Override
227 public void saveOnSessionUnbind(User user)
228 throws UnknownEntityException, DataBackendException
229 {
230 store(user);
231 }
232
233 /**
234 * Authenticate an User with the specified password. If authentication
235 * is successful the method returns nothing. If there are any problems,
236 * exception was thrown.
237 *
238 * @param user an User object to authenticate.
239 * @param password the user supplied password.
240 * @exception PasswordMismatchException if the supplied password was
241 * incorrect.
242 * @exception UnknownEntityException if the user's record does not
243 * exist in the database.
244 * @exception DataBackendException if there is a problem accessing the
245 * storage.
246 */
247 @Override
248 public void authenticate(User user, String password)
249 throws PasswordMismatchException, UnknownEntityException,
250 DataBackendException
251 {
252 umDelegate.authenticate(user, password);
253 }
254
255 /**
256 * Creates new user account with specified attributes.
257 *
258 * @param user the object describing account to be created.
259 * @param initialPassword The password to use for the object creation
260 *
261 * @throws DataBackendException if there was an error accessing the data backend.
262 * @throws EntityExistsException if the user account already exists.
263 */
264 @Override
265 public void createAccount(User user, String initialPassword)
266 throws EntityExistsException, DataBackendException
267 {
268 umDelegate.addUser(user, initialPassword);
269 }
270
271 /**
272 * Removes an user account from the system.
273 *
274 * @param user the object describing the account to be removed.
275 * @throws DataBackendException if there was an error accessing the data backend.
276 * @throws UnknownEntityException if the user account is not present.
277 */
278 @Override
279 public void removeAccount(User user)
280 throws UnknownEntityException, DataBackendException
281 {
282 umDelegate.removeUser(user);
283 }
284
285 /**
286 * Change the password for an User.
287 *
288 * @param user an User to change password for.
289 * @param oldPassword the current password supplied by the user.
290 * @param newPassword the current password requested by the user.
291 * @exception PasswordMismatchException if the supplied password was
292 * incorrect.
293 * @exception UnknownEntityException if the user's record does not
294 * exist in the database.
295 * @exception DataBackendException if there is a problem accessing the
296 * storage.
297 */
298 @Override
299 public void changePassword(User user, String oldPassword,
300 String newPassword)
301 throws PasswordMismatchException, UnknownEntityException,
302 DataBackendException
303 {
304 umDelegate.changePassword(
305 ((DefaultUserImpl)user).getUserDelegate(),
306 oldPassword, newPassword);
307 }
308
309 /**
310 * Forcibly sets new password for an User.
311 *
312 * This is supposed by the administrator to change the forgotten or
313 * compromised passwords. Certain implementations of this feature
314 * would require administrative level access to the authenticating
315 * server / program.
316 *
317 * @param user an User to change password for.
318 * @param password the new password.
319 * @exception UnknownEntityException if the user's record does not
320 * exist in the database.
321 * @exception DataBackendException if there is a problem accessing the
322 * storage.
323 */
324 @Override
325 public void forcePassword(User user, String password)
326 throws UnknownEntityException, DataBackendException
327 {
328 umDelegate.forcePassword(user, password);
329 }
330
331 /**
332 * Constructs an User object to represent an anonymous user of the
333 * application.
334 *
335 * @return An anonymous Turbine User.
336 * @throws UnknownEntityException
337 * if the anonymous User object couldn't be constructed.
338 */
339 @Override
340 public <T extends User> T getAnonymousUser() throws UnknownEntityException
341 {
342 TurbineUser u = umDelegate.getAnonymousUser();
343 return wrap(u);
344 }
345
346 /**
347 * Checks whether a passed user object matches the anonymous user pattern
348 * according to the configured user manager
349 *
350 * @param u a user object
351 *
352 * @return True if this is an anonymous user
353 *
354 */
355 @Override
356 public boolean isAnonymousUser(User u)
357 {
358 return umDelegate.isAnonymousUser(u);
359 }
360
361 /**
362 * Construct a blank User object.
363 *
364 * This method calls getUserClass, and then creates a new object using the
365 * default constructor.
366 *
367 * @return an object implementing User interface.
368 * @throws DataBackendException
369 * if the object could not be instantiated.
370 */
371 @Override
372 public <T extends User> T getUserInstance() throws DataBackendException
373 {
374 TurbineUser u = umDelegate.getUserInstance();
375 return wrap(u);
376 }
377
378 /**
379 * Construct a blank User object.
380 *
381 * This method calls getUserClass, and then creates a new object using the
382 * default constructor.
383 *
384 * @param userName
385 * The name of the user.
386 *
387 * @return an object implementing User interface.
388 * @throws DataBackendException
389 * if the object could not be instantiated.
390 */
391 @Override
392 public <T extends User> T getUserInstance(String userName) throws DataBackendException
393 {
394 TurbineUser u = umDelegate.getUserInstance(userName);
395 return wrap(u);
396 }
397
398 /**
399 * Return a Class object representing the system's chosen implementation of
400 * of ACL interface.
401 *
402 * @return systems's chosen implementation of ACL interface.
403 * @throws UnknownEntityException
404 * if the implementation of ACL interface could not be
405 * determined, or does not exist.
406 */
407 @Override
408 public <T extends AccessControlList> T getACL(User user) throws UnknownEntityException
409 {
410 return umDelegate.getACL(user);
411 }
412 }