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