KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > meshcms > core > UserInfo


1 /*
2  * MeshCMS - A simple CMS based on SiteMesh
3  * Copyright (C) 2004-2007 Luciano Vernaschi
4  *
5  * This program is free software; you can redistribute it and/or
6  * modify it under the terms of the GNU General Public License
7  * as published by the Free Software Foundation; either version 2
8  * of the License, or (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18  *
19  * You can contact the author at http://www.cromoteca.com
20  * and at info@cromoteca.com
21  */

22
23 package org.meshcms.core;
24
25 import java.io.*;
26 import java.util.*;
27 import org.meshcms.util.*;
28
29 /**
30  * Profile of a user. Modifications made by calling the set methods are not
31  * stored until you use {@link #store}.
32  */

33 public class UserInfo implements Serializable {
34   /**
35    * Permission to add other users.
36    */

37   public static final int CAN_ADD_USERS = 1;
38
39   /**
40    * Permission to edit pages (in the home path of the user profile).
41    */

42   public static final int CAN_EDIT_PAGES = 2;
43
44   /**
45    * Permission to manage files.
46    */

47   public static final int CAN_MANAGE_FILES = 4;
48
49   /**
50    * Permission to view other user profiles.
51    */

52   public static final int CAN_VIEW_OTHER_USERINFO = 8;
53
54   /**
55    * Permission to do maintainance operations.
56    */

57   public static final int CAN_DO_ADMINTASKS = 16;
58
59   /**
60    * Permission to browse files.
61    */

62   public static final int CAN_BROWSE_FILES = 32;
63
64   /**
65    * Permissions for guest user (non-logged in).
66    */

67   public static final int GUEST = 0;
68
69   /**
70    * Permissions for a member (can't edit files).
71    */

72   public static final int MEMBER = CAN_BROWSE_FILES |
73                                    CAN_VIEW_OTHER_USERINFO;
74
75   /**
76    * Permissions for an editor (can edit files, but is not an administrator).
77    */

78   public static final int EDITOR = CAN_EDIT_PAGES |
79                                    CAN_MANAGE_FILES |
80                                    CAN_VIEW_OTHER_USERINFO |
81                                    CAN_BROWSE_FILES;
82   /**
83    * Permissions for an administrator (full permissions).
84    */

85   public static final int ADMIN = 0x00FFFFFF;
86
87   protected static final String JavaDoc USERNAME = "P_USN";
88   protected static final String JavaDoc PASSWORD = "P_PWS";
89   protected static final String JavaDoc HOME_PATH = "P_HPT";
90   protected static final String JavaDoc PERMISSIONS = "P_PRM";
91   protected static final String JavaDoc E_MAIL = "P_EML";
92   protected static final String JavaDoc LANGUAGE = "P_LNG";
93
94   /**
95    * Names for user detail fields.
96    */

97   public static final String JavaDoc[] DETAILS = {
98     "salutation",
99     "name",
100     "surname",
101     "company",
102     "address",
103     "zip",
104     "city",
105     "state",
106     "country",
107     "phone_number",
108     "fax_number",
109     "mobile_phone_number"
110   };
111
112   /**
113    * Characters allowed in a username.
114    */

115   protected static final String JavaDoc VALID_USERNAME_CHARS =
116     "abcdefghijklmnopqrstuvwxyz._0123456789";
117   protected static final String JavaDoc SALT = "LV";
118
119   protected Properties info;
120   protected boolean global;
121
122   /**
123    * Creates a new empty instance. Use {@link #load} to load a defined user.
124    */

125   public UserInfo() {
126     loadGuest();
127   }
128
129   /**
130    * Sets the username for this user.
131    */

132   public void setUsername(String JavaDoc username) {
133     if (username != null) {
134       info.setProperty(USERNAME, username);
135     }
136   }
137
138   /**
139    * @return the user's username.
140    */

141   public String JavaDoc getUsername() {
142     return getValue(USERNAME);
143   }
144
145   /**
146    * Sets the password for this user. The password will be encrypted.
147    */

148   public void setPassword(String JavaDoc password) {
149     info.setProperty(PASSWORD, cryptPassword(password));
150   }
151
152   /**
153    * Sets the password for this user after verification of the old password.
154    * The password will be encrypted.
155    *
156    * @return the result of the operation
157    */

158   public boolean updatePassword(String JavaDoc oldPassword, String JavaDoc newPassword) {
159     if (verifyPassword(oldPassword)) {
160       setPassword(newPassword);
161       return true;
162     }
163
164     return false;
165   }
166
167   /**
168    * @return the user's (encrypted) password.
169    */

170   public String JavaDoc getPassword() {
171     return getValue(PASSWORD);
172   }
173
174   /**
175    * Sets the e-mail address of this user.
176    * {@link org.meshcms.util.Utils#checkAddress} is used to verify the new
177    * address.
178    *
179    * @return the result of the operation
180    */

181   public boolean setEmail(String JavaDoc email) {
182     if (Utils.checkAddress(email)) {
183       info.setProperty(E_MAIL, email);
184       return true;
185     }
186
187     return false;
188   }
189
190   /**
191    * @return the user's e-mail address.
192    */

193   public String JavaDoc getEmail() {
194     return getValue(E_MAIL);
195   }
196
197   /**
198    * Sets the home path for the user. A user can't edit files outside his own
199    * home path.
200    */

201   public void setHomePath(Path homePath) {
202     if (homePath != null) {
203       info.setProperty(HOME_PATH, homePath.toString());
204     }
205   }
206
207   /**
208    * @return the user's home path.
209    */

210   public Path getHomePath() {
211     return new Path(getValue(HOME_PATH));
212   }
213
214   /**
215    * Sets permissions for the user. This method should be called when creating
216    * the user.
217    */

218   public void setPermissions(int permissions) {
219     info.setProperty(PERMISSIONS, Integer.toHexString(permissions));
220   }
221
222   /**
223    * @return the user's permissions.
224    */

225   public int getPermissions() {
226     try {
227       return Integer.parseInt(getValue(PERMISSIONS), 16);
228     } catch (Exception JavaDoc ex) {}
229
230     return GUEST;
231   }
232
233   /**
234    * @return the preferred locale for the user, in a form like
235    * <code>en_US</code>, <code>it</code> or similar.
236    */

237   public String JavaDoc getPreferredLocaleCode() {
238     return getValue(LANGUAGE);
239   }
240
241   /**
242    * Sets the preferred locale for the user.
243    */

244   public void setPreferredLocaleCode(String JavaDoc localeCode) {
245     if (localeCode == null || localeCode.length() < 2) {
246       localeCode = "en_US";
247     }
248
249     info.setProperty(LANGUAGE, localeCode);
250   }
251
252   /**
253    * Loads the guest user.
254    */

255   public void loadGuest() {
256     info = new Properties();
257     global = false;
258   }
259
260   /**
261    * Loads a specific user.
262    */

263   public boolean load(WebSite webSite, String JavaDoc username, String JavaDoc password) {
264     if (Utils.isNullOrEmpty(username)) {
265       return false;
266     }
267
268     boolean global = false;
269     Path userPath = getUserPath(webSite, username);
270
271     if (!webSite.getFile(userPath).exists() &&
272         webSite instanceof VirtualWebSite) {
273       webSite = ((VirtualWebSite) webSite).getMainWebSite();
274       userPath = getUserPath(webSite, username);
275       global = true;
276     }
277
278     if (webSite.getFile(userPath).exists()) {
279       Properties p = (Properties) webSite.loadFromXML(userPath);
280
281       if (p != null && p.getProperty(PASSWORD).equals(cryptPassword(password))) {
282         Properties bak = info;
283         info = p;
284
285         if (global) {
286           if (canDo(CAN_DO_ADMINTASKS) && getHomePath().isRoot()) {
287             this.global = true;
288           } else {
289             info = bak;
290             return false;
291           }
292         }
293
294         return true;
295       }
296     } else if (username.equals("admin") && password.equals("admin")) {
297       info = new Properties();
298       info.setProperty(USERNAME, "admin");
299       info.setProperty(PASSWORD, cryptPassword("admin"));
300       info.setProperty(HOME_PATH, "");
301       info.setProperty(PERMISSIONS, Integer.toHexString(ADMIN));
302       info.setProperty(LANGUAGE, "en_US");
303       store(webSite);
304       return true;
305     }
306
307     return false;
308   }
309
310   /**
311    * Stores the user's profile in a file.
312    */

313   public boolean store(WebSite webSite) {
314     return webSite.storeToXML(info, getUserPath(webSite, getUsername()));
315   }
316
317   /**
318    * Crypts the password if it has not been encrypted yet.
319    */

320   private String JavaDoc cryptPassword(String JavaDoc password) {
321     if (Utils.isNullOrEmpty(password)) {
322       return "";
323     }
324
325     /* if (password.startsWith(SALT)) {
326       return password;
327     } */

328
329     return com.kingwoodcable.locutus.jfd.JCrypt.crypt(SALT, password);
330   }
331
332   /**
333    * Checks if the username is valid (i.e. contains characters in
334    * {@link #VALID_USERNAME_CHARS} only).
335    */

336   public static boolean verifyUsername(String JavaDoc username) {
337     if (Utils.isNullOrEmpty(username)) {
338       return false;
339     }
340
341     for (int i = 0; i < username.length(); i++) {
342       if (VALID_USERNAME_CHARS.indexOf(username.charAt(i)) == -1) {
343         return false;
344       }
345     }
346
347     return true;
348   }
349
350   /**
351    * Verifies the given password agains the one in the current profile.
352    */

353   public boolean verifyPassword(String JavaDoc password) {
354     return getPassword().equals(cryptPassword(password));
355   }
356
357   private File getUserFile(WebSite webSite, String JavaDoc username) {
358     return webSite.getFile(getUserPath(webSite, username));
359   }
360
361   private Path getUserPath(WebSite webSite, String JavaDoc username) {
362     return webSite.getUsersPath().add(username + ".xml");
363   }
364
365   /**
366    * Verifies the permissions to do a certain thing. Example:
367    * <code>user.canDo(UserInfo.CAN_EDIT_PAGES)</code>
368    */

369   public boolean canDo(int what) {
370     return (getPermissions() & what) != 0;
371   }
372
373   /**
374    * Verifies all permissions to write the file at a certain path in the web
375    * application.
376    */

377   public boolean canWrite(WebSite webSite, Path filePath) {
378     if (filePath == null || !canDo(CAN_EDIT_PAGES) ||
379         filePath.isContainedIn(webSite.getAdminPath())) {
380       return false;
381     }
382
383     return filePath.isContainedIn(getHomePath());
384   }
385
386   /**
387    * Sets a user's detail. Available details are specified in
388    * {@link #DETAILS}. Other details can be set, but they will not be stored
389    * when {@link #store} is called.
390    *
391    * @see #getValue
392    */

393   public boolean setDetail(String JavaDoc name, String JavaDoc value) {
394     if (Utils.searchString(DETAILS, name, false) != -1) {
395       info.setProperty(name, value);
396       return true;
397     }
398
399     return false;
400   }
401
402   /**
403    * @return the value of a specific property. It is used internally, but can
404    * be use to retrieve the value of user's details.
405    *
406    * @see #setDetail
407    */

408   public String JavaDoc getValue(String JavaDoc name) {
409     return Utils.noNull(info.getProperty(name));
410   }
411
412   /**
413    * @return the value of the given user detail.
414    */

415   public String JavaDoc getDetailValue(String JavaDoc name) {
416     if (name != null) {
417       name = name.toLowerCase();
418
419       if (Utils.searchString(DETAILS, name, false) != -1) {
420         return getValue(name);
421       }
422     }
423
424     return null;
425   }
426
427   /**
428    * @return the name of the user detail at the given index.
429    */

430   public String JavaDoc getDetailName(int index) {
431     return DETAILS[index];
432   }
433
434   /**
435    * @return a string suitable to describe the user. It can be his full name,
436    * partial name or username, according to the available data.
437    */

438   public String JavaDoc getDisplayName() {
439     String JavaDoc name = getValue(DETAILS[1]);
440     String JavaDoc surname = getValue(DETAILS[2]);
441
442     if (name.equals("") && surname.equals("")) {
443       return isGuest() ? "guest" : getUsername();
444     }
445
446     if (name.equals("")) {
447       return surname;
448     }
449
450     if (surname.equals("")) {
451       return name;
452     }
453
454     return name + " " + surname;
455   }
456
457   /**
458    * Checks if the user is a guest.
459    */

460   public boolean isGuest() {
461     return getPermissions() == GUEST;
462   }
463
464   /**
465    * Checks if the user exists. A user exists when the corresponding file
466    * exists.
467    */

468   public boolean exists(WebSite webSite, String JavaDoc username) {
469     return getUserFile(webSite, username).exists();
470   }
471
472   public boolean isGlobal() {
473     return global;
474   }
475 }
476
Popular Tags