1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16 package org.jboss.netty.handler.codec.http;
17
18 import java.util.Collections;
19 import java.util.Set;
20 import java.util.TreeSet;
21
22
23
24
25
26
27 public class DefaultCookie implements Cookie {
28
29 private final String name;
30 private String value;
31 private String domain;
32 private String path;
33 private String comment;
34 private String commentUrl;
35 private boolean discard;
36 private Set<Integer> ports = Collections.emptySet();
37 private Set<Integer> unmodifiablePorts = ports;
38 private int maxAge = Integer.MIN_VALUE;
39 private int version;
40 private boolean secure;
41 private boolean httpOnly;
42
43
44
45
46 public DefaultCookie(String name, String value) {
47 if (name == null) {
48 throw new NullPointerException("name");
49 }
50 name = name.trim();
51 if (name.length() == 0) {
52 throw new IllegalArgumentException("empty name");
53 }
54
55 for (int i = 0; i < name.length(); i ++) {
56 char c = name.charAt(i);
57 if (c > 127) {
58 throw new IllegalArgumentException(
59 "name contains non-ascii character: " + name);
60 }
61
62
63 switch (c) {
64 case '\t': case '\n': case 0x0b: case '\f': case '\r':
65 case ' ': case ',': case ';': case '=':
66 throw new IllegalArgumentException(
67 "name contains one of the following prohibited characters: " +
68 "=,; \\t\\r\\n\\v\\f: " + name);
69 }
70 }
71
72 if (name.charAt(0) == '$') {
73 throw new IllegalArgumentException("name starting with '$' not allowed: " + name);
74 }
75
76 this.name = name;
77 setValue(value);
78 }
79
80 public String getName() {
81 return name;
82 }
83
84 public String getValue() {
85 return value;
86 }
87
88 public void setValue(String value) {
89 if (value == null) {
90 throw new NullPointerException("value");
91 }
92 this.value = value;
93 }
94
95 public String getDomain() {
96 return domain;
97 }
98
99 public void setDomain(String domain) {
100 this.domain = validateValue("domain", domain);
101 }
102
103 public String getPath() {
104 return path;
105 }
106
107 public void setPath(String path) {
108 this.path = validateValue("path", path);
109 }
110
111 public String getComment() {
112 return comment;
113 }
114
115 public void setComment(String comment) {
116 this.comment = validateValue("comment", comment);
117 }
118
119 public String getCommentUrl() {
120 return commentUrl;
121 }
122
123 public void setCommentUrl(String commentUrl) {
124 this.commentUrl = validateValue("commentUrl", commentUrl);
125 }
126
127 public boolean isDiscard() {
128 return discard;
129 }
130
131 public void setDiscard(boolean discard) {
132 this.discard = discard;
133 }
134
135 public Set<Integer> getPorts() {
136 if (unmodifiablePorts == null) {
137 unmodifiablePorts = Collections.unmodifiableSet(ports);
138 }
139 return unmodifiablePorts;
140 }
141
142 public void setPorts(int... ports) {
143 if (ports == null) {
144 throw new NullPointerException("ports");
145 }
146
147 int[] portsCopy = ports.clone();
148 if (portsCopy.length == 0) {
149 unmodifiablePorts = this.ports = Collections.emptySet();
150 } else {
151 Set<Integer> newPorts = new TreeSet<Integer>();
152 for (int p: portsCopy) {
153 if (p <= 0 || p > 65535) {
154 throw new IllegalArgumentException("port out of range: " + p);
155 }
156 newPorts.add(p);
157 }
158 this.ports = newPorts;
159 unmodifiablePorts = null;
160 }
161 }
162
163 public void setPorts(Iterable<Integer> ports) {
164 Set<Integer> newPorts = new TreeSet<Integer>();
165 for (int p: ports) {
166 if (p <= 0 || p > 65535) {
167 throw new IllegalArgumentException("port out of range: " + p);
168 }
169 newPorts.add(p);
170 }
171 if (newPorts.isEmpty()) {
172 unmodifiablePorts = this.ports = Collections.emptySet();
173 } else {
174 this.ports = newPorts;
175 unmodifiablePorts = null;
176 }
177 }
178
179 public int getMaxAge() {
180 return maxAge;
181 }
182
183 public void setMaxAge(int maxAge) {
184 this.maxAge = maxAge;
185 }
186
187 public int getVersion() {
188 return version;
189 }
190
191 public void setVersion(int version) {
192 this.version = version;
193 }
194
195 public boolean isSecure() {
196 return secure;
197 }
198
199 public void setSecure(boolean secure) {
200 this.secure = secure;
201 }
202
203 public boolean isHttpOnly() {
204 return httpOnly;
205 }
206
207 public void setHttpOnly(boolean httpOnly) {
208 this.httpOnly = httpOnly;
209 }
210
211 @Override
212 public int hashCode() {
213 return getName().hashCode();
214 }
215
216 @Override
217 public boolean equals(Object o) {
218 if (!(o instanceof Cookie)) {
219 return false;
220 }
221
222 Cookie that = (Cookie) o;
223 if (!getName().equalsIgnoreCase(that.getName())) {
224 return false;
225 }
226
227 if (getPath() == null) {
228 if (that.getPath() != null) {
229 return false;
230 }
231 } else if (that.getPath() == null) {
232 return false;
233 } else if (!getPath().equals(that.getPath())) {
234 return false;
235 }
236
237 if (getDomain() == null) {
238 if (that.getDomain() != null) {
239 return false;
240 }
241 } else if (that.getDomain() == null) {
242 return false;
243 } else {
244 return getDomain().equalsIgnoreCase(that.getDomain());
245 }
246
247 return true;
248 }
249
250 public int compareTo(Cookie c) {
251 int v;
252 v = getName().compareToIgnoreCase(c.getName());
253 if (v != 0) {
254 return v;
255 }
256
257 if (getPath() == null) {
258 if (c.getPath() != null) {
259 return -1;
260 }
261 } else if (c.getPath() == null) {
262 return 1;
263 } else {
264 v = getPath().compareTo(c.getPath());
265 if (v != 0) {
266 return v;
267 }
268 }
269
270 if (getDomain() == null) {
271 if (c.getDomain() != null) {
272 return -1;
273 }
274 } else if (c.getDomain() == null) {
275 return 1;
276 } else {
277 v = getDomain().compareToIgnoreCase(c.getDomain());
278 return v;
279 }
280
281 return 0;
282 }
283
284 @Override
285 public String toString() {
286 StringBuilder buf = new StringBuilder();
287 buf.append(getName());
288 buf.append('=');
289 buf.append(getValue());
290 if (getDomain() != null) {
291 buf.append(", domain=");
292 buf.append(getDomain());
293 }
294 if (getPath() != null) {
295 buf.append(", path=");
296 buf.append(getPath());
297 }
298 if (getComment() != null) {
299 buf.append(", comment=");
300 buf.append(getComment());
301 }
302 if (getMaxAge() >= 0) {
303 buf.append(", maxAge=");
304 buf.append(getMaxAge());
305 buf.append('s');
306 }
307 if (isSecure()) {
308 buf.append(", secure");
309 }
310 if (isHttpOnly()) {
311 buf.append(", HTTPOnly");
312 }
313 return buf.toString();
314 }
315
316 private static String validateValue(String name, String value) {
317 if (value == null) {
318 return null;
319 }
320 value = value.trim();
321 if (value.length() == 0) {
322 return null;
323 }
324 for (int i = 0; i < value.length(); i ++) {
325 char c = value.charAt(i);
326 switch (c) {
327 case '\r': case '\n': case '\f': case 0x0b: case ';':
328 throw new IllegalArgumentException(
329 name + " contains one of the following prohibited characters: " +
330 ";\\r\\n\\f\\v (" + value + ')');
331 }
332 }
333 return value;
334 }
335 }
336