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