1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.acegisecurity.providers.encoding;
17
18 /***
19 * <p>
20 * Convenience base for all password encoders.
21 * </p>
22 *
23 * @author Ben Alex
24 * @version $Id: BasePasswordEncoder.java,v 1.2 2005/11/17 00:55:49 benalex Exp $
25 */
26 public abstract class BasePasswordEncoder implements PasswordEncoder {
27
28
29 /***
30 * Used by subclasses to extract the password and salt from a merged
31 * <code>String</code> created using {@link
32 * #mergePasswordAndSalt(String,Object,boolean)}.
33 *
34 * <P>
35 * The first element in the returned array is the password. The second
36 * element is the salt. The salt array element will always be present,
37 * even if no salt was found in the <code>mergedPasswordSalt</code>
38 * argument.
39 * </p>
40 *
41 * @param mergedPasswordSalt as generated by
42 * <code>mergePasswordAndSalt</code>
43 *
44 * @return an array, in which the first element is the password and the
45 * second the salt
46 *
47 * @throws IllegalArgumentException DOCUMENT ME!
48 */
49 protected String[] demergePasswordAndSalt(String mergedPasswordSalt) {
50 if ((mergedPasswordSalt == null) || "".equals(mergedPasswordSalt)) {
51 throw new IllegalArgumentException(
52 "Cannot pass a null or empty String");
53 }
54
55 String password = mergedPasswordSalt;
56 String salt = "";
57
58 int saltBegins = mergedPasswordSalt.lastIndexOf("{");
59
60 if ((saltBegins != -1)
61 && ((saltBegins + 1) < mergedPasswordSalt.length())) {
62 salt = mergedPasswordSalt.substring(saltBegins + 1,
63 mergedPasswordSalt.length() - 1);
64 password = mergedPasswordSalt.substring(0, saltBegins);
65 }
66
67 return new String[] {password, salt};
68 }
69
70 /***
71 * Used by subclasses to generate a merged password and salt
72 * <code>String</code>.
73 *
74 * <P>
75 * The generated password will be in the form of
76 * <code>password{salt}</code>.
77 * </p>
78 *
79 * <P>
80 * A <code>null</code> can be passed to either method, and will be handled
81 * correctly. If the <code>salt</code> is <code>null</code> or empty, the
82 * resulting generated password will simply be the passed
83 * <code>password</code>. The <code>toString</code> method of the
84 * <code>salt</code> will be used to represent the salt.
85 * </p>
86 *
87 * @param password the password to be used (can be <code>null</code>)
88 * @param salt the salt to be used (can be <code>null</code>)
89 * @param strict ensures salt doesn't contain the delimiters
90 *
91 * @return a merged password and salt <code>String</code>
92 *
93 * @throws IllegalArgumentException DOCUMENT ME!
94 */
95 protected String mergePasswordAndSalt(String password, Object salt,
96 boolean strict) {
97 if (password == null) {
98 password = "";
99 }
100
101 if (strict && (salt != null)) {
102 if ((salt.toString().lastIndexOf("{") != -1)
103 || (salt.toString().lastIndexOf("}") != -1)) {
104 throw new IllegalArgumentException(
105 "Cannot use { or } in salt.toString()");
106 }
107 }
108
109 if ((salt == null) || "".equals(salt)) {
110 return password;
111 } else {
112 return password + "{" + salt.toString() + "}";
113 }
114 }
115 }