1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package javax.faces.component.behavior;
20
21 import javax.el.ValueExpression;
22 import javax.faces.component.StateHelper;
23 import javax.faces.component.StateHolder;
24 import javax.faces.component.UIComponentBase;
25 import javax.faces.context.FacesContext;
26 import java.io.Serializable;
27 import java.util.ArrayList;
28 import java.util.Collection;
29 import java.util.HashMap;
30 import java.util.Iterator;
31 import java.util.List;
32 import java.util.Map;
33
34
35
36
37
38
39
40
41
42
43 class _AjaxBehaviorDeltaStateHelper<A extends AjaxBehavior> implements StateHelper
44 {
45
46
47
48
49
50
51 private A _target;
52
53
54
55
56 private Map<Serializable, Object> _fullState;
57
58
59
60
61 private Map<Serializable, Object> _deltas;
62
63
64
65
66
67
68
69 private boolean _transient = false;
70
71 public _AjaxBehaviorDeltaStateHelper(A component)
72 {
73 super();
74 this._target = component;
75 _fullState = new HashMap<Serializable, Object>();
76 _deltas = null;
77
78 }
79
80
81
82
83
84
85 private boolean _createDeltas()
86 {
87 if (isInitialStateMarked())
88 {
89 if (_deltas == null)
90 {
91 _deltas = new HashMap<Serializable, Object>(2);
92 }
93 return true;
94 }
95
96 return false;
97 }
98
99 protected boolean isInitialStateMarked()
100 {
101 return _target.initialStateMarked();
102 }
103
104 public void add(Serializable key, Object value)
105 {
106 if (_createDeltas())
107 {
108
109 Map<Object, Boolean> deltaListMapValues = (Map<Object, Boolean>) _deltas
110 .get(key);
111 if (deltaListMapValues == null)
112 {
113 deltaListMapValues = new InternalDeltaListMap<Object, Boolean>(
114 3);
115 _deltas.put(key, deltaListMapValues);
116 }
117 deltaListMapValues.put(value, Boolean.TRUE);
118 }
119
120
121 List<Object> fullListValues = (List<Object>) _fullState.get(key);
122 if (fullListValues == null)
123 {
124 fullListValues = new InternalList<Object>(3);
125 _fullState.put(key, fullListValues);
126 }
127 fullListValues.add(value);
128 }
129
130 public Object eval(Serializable key)
131 {
132 Object returnValue = _fullState.get(key);
133 if (returnValue != null)
134 {
135 return returnValue;
136 }
137 ValueExpression expression = _target.getValueExpression(key
138 .toString());
139 if (expression != null)
140 {
141 return expression.getValue(FacesContext.getCurrentInstance()
142 .getELContext());
143 }
144 return null;
145 }
146
147 public Object eval(Serializable key, Object defaultValue)
148 {
149 Object returnValue = _fullState.get(key);
150 if (returnValue != null)
151 {
152 return returnValue;
153 }
154 ValueExpression expression = _target.getValueExpression(key
155 .toString());
156 if (expression != null)
157 {
158 return expression.getValue(FacesContext.getCurrentInstance()
159 .getELContext());
160 }
161 return defaultValue;
162 }
163
164 public Object get(Serializable key)
165 {
166 return _fullState.get(key);
167 }
168
169 public Object put(Serializable key, Object value)
170 {
171 Object returnValue = null;
172 if (_createDeltas())
173 {
174 if (_deltas.containsKey(key))
175 {
176 returnValue = _deltas.put(key, value);
177 _fullState.put(key, value);
178 }
179 else
180 {
181 _deltas.put(key, value);
182 returnValue = _fullState.put(key, value);
183 }
184 }
185 else
186 {
187
188
189
190
191
192
193 returnValue = _fullState.put(key, value);
194 }
195 return returnValue;
196 }
197
198 public Object put(Serializable key, String mapKey, Object value)
199 {
200 boolean returnSet = false;
201 Object returnValue = null;
202 if (_createDeltas())
203 {
204
205 Map<String, Object> mapValues = (Map<String, Object>) _deltas
206 .get(key);
207 if (mapValues == null)
208 {
209 mapValues = new InternalMap<String, Object>();
210 _deltas.put(key, mapValues);
211 }
212 if (mapValues.containsKey(mapKey))
213 {
214 returnValue = mapValues.put(mapKey, value);
215 returnSet = true;
216 }
217 else
218 {
219 mapValues.put(mapKey, value);
220 }
221 }
222
223
224 Map<String, Object> mapValues = (Map<String, Object>) _fullState
225 .get(key);
226 if (mapValues == null)
227 {
228 mapValues = new InternalMap<String, Object>();
229 _fullState.put(key, mapValues);
230 }
231 if (returnSet)
232 {
233 mapValues.put(mapKey, value);
234 }
235 else
236 {
237 returnValue = mapValues.put(mapKey, value);
238 }
239 return returnValue;
240 }
241
242 public Object remove(Serializable key)
243 {
244 Object returnValue = null;
245 if (_createDeltas())
246 {
247 if (_deltas.containsKey(key))
248 {
249
250 returnValue = _deltas.put(key, null);
251 _fullState.remove(key);
252 }
253 else
254 {
255
256 _deltas.put(key, null);
257 returnValue = _fullState.remove(key);
258 }
259 }
260 else
261 {
262 returnValue = _fullState.remove(key);
263 }
264 return returnValue;
265 }
266
267 public Object remove(Serializable key, Object valueOrKey)
268 {
269
270
271
272
273
274
275 Object collectionOrMap = _fullState.get(key);
276 Object returnValue = null;
277 if (collectionOrMap instanceof InternalMap)
278 {
279 if (_createDeltas())
280 {
281 returnValue = _removeValueOrKeyFromMap(_deltas, key,
282 valueOrKey, true);
283 _removeValueOrKeyFromMap(_fullState, key, valueOrKey, false);
284 }
285 else
286 {
287 returnValue = _removeValueOrKeyFromMap(_fullState, key,
288 valueOrKey, false);
289 }
290 }
291 else if (collectionOrMap instanceof InternalList)
292 {
293 if (_createDeltas())
294 {
295 returnValue = _removeValueOrKeyFromCollectionDelta(_deltas,
296 key, valueOrKey);
297 _removeValueOrKeyFromCollection(_fullState, key, valueOrKey);
298 }
299 else
300 {
301 returnValue = _removeValueOrKeyFromCollection(_fullState, key,
302 valueOrKey);
303 }
304 }
305 return returnValue;
306 }
307
308 private static Object _removeValueOrKeyFromCollectionDelta(
309 Map<Serializable, Object> stateMap, Serializable key,
310 Object valueOrKey)
311 {
312 Object returnValue = null;
313 Map<Object, Boolean> c = (Map<Object, Boolean>) stateMap.get(key);
314 if (c != null)
315 {
316 if (c.containsKey(valueOrKey))
317 {
318 returnValue = valueOrKey;
319 }
320 c.put(valueOrKey, Boolean.FALSE);
321 }
322 return returnValue;
323 }
324
325 private static Object _removeValueOrKeyFromCollection(
326 Map<Serializable, Object> stateMap, Serializable key,
327 Object valueOrKey)
328 {
329 Object returnValue = null;
330 Collection c = (Collection) stateMap.get(key);
331 if (c != null)
332 {
333 if (c.remove(valueOrKey))
334 {
335 returnValue = valueOrKey;
336 }
337 if (c.isEmpty())
338 {
339 stateMap.remove(key);
340 }
341 }
342 return returnValue;
343 }
344
345 private static Object _removeValueOrKeyFromMap(
346 Map<Serializable, Object> stateMap, Serializable key,
347 Object valueOrKey, boolean delta)
348 {
349 if (valueOrKey == null)
350 {
351 return null;
352 }
353
354 Object returnValue = null;
355 Map<String, Object> map = (Map<String, Object>) stateMap.get(key);
356 if (map != null)
357 {
358 if (delta)
359 {
360
361 returnValue = map.put((String) valueOrKey, null);
362 }
363 else
364 {
365 returnValue = map.remove(valueOrKey);
366 }
367
368 if (map.isEmpty())
369 {
370
371 stateMap.put(key, null);
372 }
373 }
374 return returnValue;
375 }
376
377 public boolean isTransient()
378 {
379 return _transient;
380 }
381
382
383
384
385
386
387
388
389
390
391
392
393 public Object saveState(FacesContext context)
394 {
395 Map serializableMap = (isInitialStateMarked()) ? _deltas : _fullState;
396
397 if (serializableMap == null || serializableMap.isEmpty())
398 {
399 return null;
400 }
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416 Map.Entry<Serializable, Object> entry;
417
418 Object[] retArr = new Object[serializableMap.entrySet().size() * 2];
419
420
421 Iterator<Map.Entry<Serializable, Object>> it = serializableMap.entrySet().iterator();
422 int cnt = 0;
423 while (it.hasNext())
424 {
425 entry = it.next();
426 retArr[cnt] = entry.getKey();
427
428 Object value = entry.getValue();
429
430
431
432
433 if (value instanceof StateHolder ||
434 value instanceof List ||
435 !(value instanceof Serializable))
436 {
437 Object savedValue = UIComponentBase.saveAttachedState(context,
438 value);
439 retArr[cnt + 1] = savedValue;
440 }
441 else
442 {
443 retArr[cnt + 1] = value;
444 }
445 cnt += 2;
446 }
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481 return retArr;
482 }
483
484
485 public void restoreState(FacesContext context, Object state)
486 {
487 if (state == null)
488 {
489 return;
490 }
491
492 Object[] serializedState = (Object[]) state;
493
494 for (int cnt = 0; cnt < serializedState.length; cnt += 2)
495 {
496 Serializable key = (Serializable) serializedState[cnt];
497
498 Object savedValue = UIComponentBase.restoreAttachedState(context,
499 serializedState[cnt + 1]);
500
501 if (isInitialStateMarked())
502 {
503 if (savedValue instanceof InternalDeltaListMap)
504 {
505 for (Map.Entry<Object, Boolean> mapEntry : ((Map<Object, Boolean>) savedValue)
506 .entrySet())
507 {
508 boolean addOrRemove = mapEntry.getValue();
509 if (addOrRemove)
510 {
511
512 this.add(key, mapEntry.getKey());
513 }
514 else
515 {
516
517 this.remove(key, mapEntry.getKey());
518 }
519 }
520 }
521 else if (savedValue instanceof InternalMap)
522 {
523 for (Map.Entry<String, Object> mapEntry : ((Map<String, Object>) savedValue)
524 .entrySet())
525 {
526 this.put(key, mapEntry.getKey(), mapEntry.getValue());
527 }
528 }
529
530
531
532
533
534
535
536
537
538
539 else
540 {
541 put(key, savedValue);
542 }
543 }
544 else
545 {
546 put(key, savedValue);
547 }
548 }
549 }
550
551 public void setTransient(boolean transientValue)
552 {
553 _transient = transientValue;
554 }
555
556
557
558 static class InternalMap<K, V> extends HashMap<K, V> implements StateHolder
559 {
560 public InternalMap()
561 {
562 super();
563 }
564
565 public InternalMap(int initialCapacity, float loadFactor)
566 {
567 super(initialCapacity, loadFactor);
568 }
569
570 public InternalMap(Map<? extends K, ? extends V> m)
571 {
572 super(m);
573 }
574
575 public InternalMap(int initialSize)
576 {
577 super(initialSize);
578 }
579
580 public boolean isTransient()
581 {
582 return false;
583 }
584
585 public void setTransient(boolean newTransientValue)
586 {
587
588 }
589
590 public void restoreState(FacesContext context, Object state)
591 {
592 Object[] listAsMap = (Object[]) state;
593 for (int cnt = 0; cnt < listAsMap.length; cnt += 2)
594 {
595 this.put((K) listAsMap[cnt], (V) UIComponentBase
596 .restoreAttachedState(context, listAsMap[cnt + 1]));
597 }
598 }
599
600 public Object saveState(FacesContext context)
601 {
602 int cnt = 0;
603 Object[] mapArr = new Object[this.size() * 2];
604 for (Map.Entry<K, V> entry : this.entrySet())
605 {
606 mapArr[cnt] = entry.getKey();
607 Object value = entry.getValue();
608
609 if (value instanceof StateHolder ||
610 value instanceof List ||
611 !(value instanceof Serializable))
612 {
613 mapArr[cnt + 1] = UIComponentBase.saveAttachedState(context, value);
614 }
615 else
616 {
617 mapArr[cnt + 1] = value;
618 }
619 cnt += 2;
620 }
621 return mapArr;
622 }
623 }
624
625
626
627
628 static class InternalDeltaListMap<K, V> extends InternalMap<K, V>
629 {
630
631 public InternalDeltaListMap()
632 {
633 super();
634 }
635
636 public InternalDeltaListMap(int initialCapacity, float loadFactor)
637 {
638 super(initialCapacity, loadFactor);
639 }
640
641 public InternalDeltaListMap(int initialSize)
642 {
643 super(initialSize);
644 }
645
646 public InternalDeltaListMap(Map<? extends K, ? extends V> m)
647 {
648 super(m);
649 }
650 }
651
652 static class InternalList<T> extends ArrayList<T> implements StateHolder
653 {
654 public InternalList()
655 {
656 super();
657 }
658
659 public InternalList(Collection<? extends T> c)
660 {
661 super(c);
662 }
663
664 public InternalList(int initialSize)
665 {
666 super(initialSize);
667 }
668
669 public boolean isTransient()
670 {
671 return false;
672 }
673
674 public void setTransient(boolean newTransientValue)
675 {
676 }
677
678 public void restoreState(FacesContext context, Object state)
679 {
680 Object[] listAsArr = (Object[]) state;
681
682
683 for (Object elem : listAsArr)
684 {
685 add((T) UIComponentBase.restoreAttachedState(context, elem));
686 }
687 }
688
689 public Object saveState(FacesContext context)
690 {
691 Object[] values = new Object[size()];
692 for (int i = 0; i < size(); i++)
693 {
694 Object value = get(i);
695
696 if (value instanceof StateHolder ||
697 value instanceof List ||
698 !(value instanceof Serializable))
699 {
700 values[i] = UIComponentBase.saveAttachedState(context, value);
701 }
702 else
703 {
704 values[i] = value;
705 }
706 }
707 return values;
708 }
709 }
710 }