1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30 package org.apache.commons.httpclient.cookie;
31
32 import java.util.Collections;
33 import java.util.HashMap;
34 import java.util.Map;
35
36 import org.apache.commons.logging.Log;
37 import org.apache.commons.logging.LogFactory;
38
39 /***
40 * Cookie management policy class. The cookie policy provides corresponding
41 * cookie management interfrace for a given type or version of cookie.
42 * <p>RFC 2109 specification is used per default. Other supported specification
43 * can be chosen when appropriate or set default when desired
44 * <p>The following specifications are provided:
45 * <ul>
46 * <li><tt>BROWSER_COMPATIBILITY</tt>: compatible with the common cookie
47 * management practices (even if they are not 100% standards compliant)
48 * <li><tt>NETSCAPE</tt>: Netscape cookie draft compliant
49 * <li><tt>RFC_2109</tt>: RFC2109 compliant (default)
50 * </ul>
51 *
52 * @author <a href="mailto:oleg@ural.ru">Oleg Kalnichevski</a>
53 * @author <a href="mailto:mbowler@GargoyleSoftware.com">Mike Bowler</a>
54 *
55 * @since 2.0
56 */
57 public abstract class CookiePolicy {
58
59 private static Map SPECS = Collections.synchronizedMap(new HashMap());
60
61 /***
62 * The policy that provides high degree of compatibilty
63 * with common cookie management of popular HTTP agents.
64 *
65 * @since 3.0
66 */
67 public static final String BROWSER_COMPATIBILITY = "compatibility";
68
69 /***
70 * The Netscape cookie draft compliant policy.
71 *
72 * @since 3.0
73 */
74 public static final String NETSCAPE = "netscape";
75
76 /***
77 * The RFC 2109 compliant policy.
78 *
79 * @since 3.0
80 */
81 public static final String RFC_2109 = "rfc2109";
82
83 /***
84 * The policy that ignores cookies.
85 *
86 * @since 3.0
87 */
88 public static final String IGNORE_COOKIES = "ignoreCookies";
89
90 /***
91 * The default cookie policy.
92 *
93 * @since 3.0
94 */
95 public static final String DEFAULT = "default";
96
97 static {
98 CookiePolicy.registerCookieSpec(DEFAULT, RFC2109Spec.class);
99 CookiePolicy.registerCookieSpec(RFC_2109, RFC2109Spec.class);
100 CookiePolicy.registerCookieSpec(BROWSER_COMPATIBILITY, CookieSpecBase.class);
101 CookiePolicy.registerCookieSpec(NETSCAPE, NetscapeDraftSpec.class);
102 CookiePolicy.registerCookieSpec(IGNORE_COOKIES, IgnoreCookiesSpec.class);
103 }
104
105 /***
106 * The <tt>COMPATIBILITY</tt> policy provides high compatibilty
107 * with common cookie management of popular HTTP agents.
108 *
109 * @deprecated Use {@link #BROWSER_COMPATIBILITY}
110 */
111 public static final int COMPATIBILITY = 0;
112
113 /***
114 * The <tt>NETSCAPE_DRAFT</tt> Netscape draft compliant policy.
115 *
116 * @deprecated Use {@link #NETSCAPE}
117 */
118 public static final int NETSCAPE_DRAFT = 1;
119
120 /***
121 * The <tt>RFC2109</tt> RFC 2109 compliant policy.
122 *
123 * @deprecated Use {@link #RFC_2109}
124 */
125 public static final int RFC2109 = 2;
126
127 /***
128 * The default cookie policy.
129 *
130 * @deprecated Use {@link #DEFAULT}
131 */
132 private static int defaultPolicy = RFC2109;
133
134 /*** Log object. */
135 protected static final Log LOG = LogFactory.getLog(CookiePolicy.class);
136
137 /***
138 * Registers a new {@link CookieSpec cookie specification} with the given identifier.
139 * If a specification with the given ID already exists it will be overridden.
140 * This ID is the same one used to retrieve the {@link CookieSpec cookie specification}
141 * from {@link #getCookieSpec(String)}.
142 *
143 * @param id the identifier for this specification
144 * @param clazz the {@link CookieSpec cookie specification} class to register
145 *
146 * @see #getCookieSpec(String)
147 *
148 * @since 3.0
149 */
150 public static void registerCookieSpec(final String id, final Class clazz) {
151 if (id == null) {
152 throw new IllegalArgumentException("Id may not be null");
153 }
154 if (clazz == null) {
155 throw new IllegalArgumentException("Cookie spec class may not be null");
156 }
157 SPECS.put(id.toLowerCase(), clazz);
158 }
159
160 /***
161 * Unregisters the {@link CookieSpec cookie specification} with the given ID.
162 *
163 * @param id the ID of the {@link CookieSpec cookie specification} to unregister
164 *
165 * @since 3.0
166 */
167 public static void unregisterCookieSpec(final String id) {
168 if (id == null) {
169 throw new IllegalArgumentException("Id may not be null");
170 }
171 SPECS.remove(id.toLowerCase());
172 }
173
174 /***
175 * Gets the {@link CookieSpec cookie specification} with the given ID.
176 *
177 * @param id the {@link CookieSpec cookie specification} ID
178 *
179 * @return {@link CookieSpec cookie specification}
180 *
181 * @throws IllegalStateException if a policy with the ID cannot be found
182 *
183 * @since 3.0
184 */
185 public static CookieSpec getCookieSpec(final String id)
186 throws IllegalStateException {
187
188 if (id == null) {
189 throw new IllegalArgumentException("Id may not be null");
190 }
191 Class clazz = (Class)SPECS.get(id.toLowerCase());
192
193 if (clazz != null) {
194 try {
195 return (CookieSpec)clazz.newInstance();
196 } catch (Exception e) {
197 LOG.error("Error initializing cookie spec: " + id, e);
198 throw new IllegalStateException(id +
199 " cookie spec implemented by " +
200 clazz.getName() + " could not be initialized");
201 }
202 } else {
203 throw new IllegalStateException("Unsupported cookie spec " + id);
204 }
205 }
206
207 /***
208 * @return default cookie policy
209 * <tt>(COMPATIBILITY | NETSCAPE_DRAFT | RFC2109)</tt>
210 *
211 * @deprecated Use {@link CookiePolicy#getCookieSpec(String)}
212 * @see #DEFAULT
213 */
214 public static int getDefaultPolicy() {
215 return defaultPolicy;
216 }
217
218
219 /***
220 * @param policy new default cookie policy
221 * <tt>(COMPATIBILITY | NETSCAPE_DRAFT | RFC2109)</tt>
222 *
223 * @deprecated Use {@link CookiePolicy#registerCookieSpec(String, Class)}
224 * @see #DEFAULT
225 */
226 public static void setDefaultPolicy(int policy) {
227 defaultPolicy = policy;
228 }
229
230 /***
231 * @param policy cookie policy to get the CookieSpec for
232 * @return cookie specification interface for the given policy
233 * <tt>(COMPATIBILITY | NETSCAPE_DRAFT | RFC2109)</tt>
234 *
235 * @deprecated Use {@link CookiePolicy#getCookieSpec(String)}
236 */
237 public static CookieSpec getSpecByPolicy(int policy) {
238 switch(policy) {
239 case COMPATIBILITY:
240 return new CookieSpecBase();
241 case NETSCAPE_DRAFT:
242 return new NetscapeDraftSpec();
243 case RFC2109:
244 return new RFC2109Spec();
245 default:
246 return getDefaultSpec();
247 }
248 }
249
250
251 /***
252 * Returns {@link CookieSpec cookie specification} registered as {@link #DEFAULT}.
253 * If no default {@link CookieSpec cookie specification} has been registered,
254 * {@link RFC2109Spec RFC2109 specification} is returned.
255 *
256 * @return default {@link CookieSpec cookie specification}
257 *
258 * @see #DEFAULT
259 */
260 public static CookieSpec getDefaultSpec() {
261 try {
262 return getCookieSpec(DEFAULT);
263 } catch (IllegalStateException e) {
264 LOG.warn("Default cookie policy is not registered");
265 return new RFC2109Spec();
266 }
267 }
268
269
270 /***
271 * Gets the CookieSpec for a particular cookie version.
272 *
273 * <p>Supported versions:
274 * <ul>
275 * <li><tt>version 0</tt> corresponds to the Netscape draft
276 * <li><tt>version 1</tt> corresponds to the RFC 2109
277 * <li>Any other cookie value coresponds to the default spec
278 * <ul>
279 *
280 * @param ver the cookie version to get the spec for
281 * @return cookie specification interface intended for processing
282 * cookies with the given version
283 *
284 * @deprecated Use {@link CookiePolicy#getCookieSpec(String)}
285 */
286 public static CookieSpec getSpecByVersion(int ver) {
287 switch(ver) {
288 case 0:
289 return new NetscapeDraftSpec();
290 case 1:
291 return new RFC2109Spec();
292 default:
293 return getDefaultSpec();
294 }
295 }
296
297 /***
298 * @return cookie specification interface that provides high compatibilty
299 * with common cookie management of popular HTTP agents
300 *
301 * @deprecated Use {@link CookiePolicy#getCookieSpec(String)}
302 */
303 public static CookieSpec getCompatibilitySpec() {
304 return getSpecByPolicy(COMPATIBILITY);
305 }
306 }