|
29 | 29 | import java.nio.charset.Charset;
|
30 | 30 | import java.nio.charset.StandardCharsets;
|
31 | 31 | import java.security.Principal;
|
| 32 | +import java.util.AbstractCollection; |
| 33 | +import java.util.AbstractMap; |
| 34 | +import java.util.AbstractSet; |
32 | 35 | import java.util.Arrays;
|
| 36 | +import java.util.Collection; |
33 | 37 | import java.util.Enumeration;
|
34 | 38 | import java.util.Iterator;
|
35 | 39 | import java.util.List;
|
36 | 40 | import java.util.Map;
|
| 41 | +import java.util.Set; |
37 | 42 |
|
38 | 43 | import jakarta.servlet.http.HttpServletRequest;
|
39 | 44 |
|
@@ -67,6 +72,10 @@ public class ServletServerHttpRequest implements ServerHttpRequest {
|
67 | 72 | @Nullable
|
68 | 73 | private HttpHeaders headers;
|
69 | 74 |
|
| 75 | + @Nullable |
| 76 | + private Map<String, Object> attributes; |
| 77 | + |
| 78 | + |
70 | 79 | @Nullable
|
71 | 80 | private ServerHttpAsyncRequestControl asyncRequestControl;
|
72 | 81 |
|
@@ -207,6 +216,16 @@ public InetSocketAddress getRemoteAddress() {
|
207 | 216 | return new InetSocketAddress(this.servletRequest.getRemoteHost(), this.servletRequest.getRemotePort());
|
208 | 217 | }
|
209 | 218 |
|
| 219 | + @Override |
| 220 | + public Map<String, Object> getAttributes() { |
| 221 | + Map<String, Object> attributes = this.attributes; |
| 222 | + if (attributes == null) { |
| 223 | + attributes = new AttributesMap(); |
| 224 | + this.attributes = attributes; |
| 225 | + } |
| 226 | + return attributes; |
| 227 | + } |
| 228 | + |
210 | 229 | @Override
|
211 | 230 | public InputStream getBody() throws IOException {
|
212 | 231 | if (isFormPost(this.servletRequest) && this.servletRequest.getQueryString() == null) {
|
@@ -276,4 +295,151 @@ private InputStream getBodyFromServletRequestParameters(HttpServletRequest reque
|
276 | 295 | return new ByteArrayInputStream(bytes);
|
277 | 296 | }
|
278 | 297 |
|
| 298 | + |
| 299 | + private final class AttributesMap extends AbstractMap<String, Object> { |
| 300 | + |
| 301 | + @Nullable |
| 302 | + private transient Set<String> keySet; |
| 303 | + |
| 304 | + @Nullable |
| 305 | + private transient Collection<Object> values; |
| 306 | + |
| 307 | + @Nullable |
| 308 | + private transient Set<Entry<String, Object>> entrySet; |
| 309 | + |
| 310 | + |
| 311 | + @Override |
| 312 | + public int size() { |
| 313 | + int size = 0; |
| 314 | + for (Enumeration<?> names = servletRequest.getAttributeNames(); names.hasMoreElements(); names.nextElement()) { |
| 315 | + size++; |
| 316 | + } |
| 317 | + return size; |
| 318 | + } |
| 319 | + |
| 320 | + @Override |
| 321 | + @Nullable |
| 322 | + public Object get(Object key) { |
| 323 | + if (key instanceof String name) { |
| 324 | + return servletRequest.getAttribute(name); |
| 325 | + } |
| 326 | + else { |
| 327 | + return null; |
| 328 | + } |
| 329 | + } |
| 330 | + |
| 331 | + @Override |
| 332 | + @Nullable |
| 333 | + public Object put(String key, Object value) { |
| 334 | + Object old = get(key); |
| 335 | + servletRequest.setAttribute(key, value); |
| 336 | + return old; |
| 337 | + } |
| 338 | + |
| 339 | + @Override |
| 340 | + @Nullable |
| 341 | + public Object remove(Object key) { |
| 342 | + if (key instanceof String name) { |
| 343 | + Object old = get(key); |
| 344 | + servletRequest.removeAttribute(name); |
| 345 | + return old; |
| 346 | + } |
| 347 | + else { |
| 348 | + return null; |
| 349 | + } |
| 350 | + } |
| 351 | + |
| 352 | + @Override |
| 353 | + public void clear() { |
| 354 | + for (Enumeration<String> names = servletRequest.getAttributeNames(); names.hasMoreElements(); ) { |
| 355 | + String name = names.nextElement(); |
| 356 | + servletRequest.removeAttribute(name); |
| 357 | + } |
| 358 | + } |
| 359 | + |
| 360 | + @Override |
| 361 | + public Set<String> keySet() { |
| 362 | + Set<String> keySet = this.keySet; |
| 363 | + if (keySet == null) { |
| 364 | + keySet = new AbstractSet<>() { |
| 365 | + @Override |
| 366 | + public Iterator<String> iterator() { |
| 367 | + return servletRequest.getAttributeNames().asIterator(); |
| 368 | + } |
| 369 | + |
| 370 | + @Override |
| 371 | + public int size() { |
| 372 | + return AttributesMap.this.size(); |
| 373 | + } |
| 374 | + }; |
| 375 | + this.keySet = keySet; |
| 376 | + } |
| 377 | + return keySet; |
| 378 | + } |
| 379 | + |
| 380 | + @Override |
| 381 | + public Collection<Object> values() { |
| 382 | + Collection<Object> values = this.values; |
| 383 | + if (values == null) { |
| 384 | + values = new AbstractCollection<>() { |
| 385 | + @Override |
| 386 | + public Iterator<Object> iterator() { |
| 387 | + Enumeration<String> e = servletRequest.getAttributeNames(); |
| 388 | + return new Iterator<>() { |
| 389 | + @Override |
| 390 | + public boolean hasNext() { |
| 391 | + return e.hasMoreElements(); |
| 392 | + } |
| 393 | + |
| 394 | + @Override |
| 395 | + public Object next() { |
| 396 | + String name = e.nextElement(); |
| 397 | + return servletRequest.getAttribute(name); |
| 398 | + } |
| 399 | + }; |
| 400 | + } |
| 401 | + |
| 402 | + @Override |
| 403 | + public int size() { |
| 404 | + return AttributesMap.this.size(); |
| 405 | + } |
| 406 | + }; |
| 407 | + this.values = values; |
| 408 | + } |
| 409 | + return values; |
| 410 | + } |
| 411 | + |
| 412 | + @Override |
| 413 | + public Set<Entry<String, Object>> entrySet() { |
| 414 | + Set<Entry<String, Object>> entrySet = this.entrySet; |
| 415 | + if (entrySet == null) { |
| 416 | + entrySet = new AbstractSet<>() { |
| 417 | + @Override |
| 418 | + public Iterator<Entry<String, Object>> iterator() { |
| 419 | + Enumeration<String> e = servletRequest.getAttributeNames(); |
| 420 | + return new Iterator<>() { |
| 421 | + @Override |
| 422 | + public boolean hasNext() { |
| 423 | + return e.hasMoreElements(); |
| 424 | + } |
| 425 | + |
| 426 | + @Override |
| 427 | + public Entry<String, Object> next() { |
| 428 | + String name = e.nextElement(); |
| 429 | + Object value = servletRequest.getAttribute(name); |
| 430 | + return new SimpleImmutableEntry<>(name, value); |
| 431 | + } |
| 432 | + }; |
| 433 | + } |
| 434 | + |
| 435 | + @Override |
| 436 | + public int size() { |
| 437 | + return AttributesMap.this.size(); |
| 438 | + } |
| 439 | + }; |
| 440 | + this.entrySet = entrySet; |
| 441 | + } |
| 442 | + return entrySet; |
| 443 | + } |
| 444 | + } |
279 | 445 | }
|
0 commit comments