View Javadoc

1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one
3    * or more contributor license agreements.  See the NOTICE file
4    * distributed with this work for additional information
5    * regarding copyright ownership.  The ASF licenses this file
6    * to you under the Apache License, Version 2.0 (the
7    * "License"); you may not use this file except in compliance
8    * with the License.  You may obtain a copy of the License at
9    *
10   *   http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing,
13   * software distributed under the License is distributed on an
14   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15   * KIND, either express or implied.  See the License for the
16   * specific language governing permissions and limitations
17   * under the License.
18   */
19  package org.apache.myfaces.extensions.validator.core.metadata.transformer;
20  
21  import org.apache.myfaces.extensions.validator.core.mapper.NameMapper;
22  import org.apache.myfaces.extensions.validator.core.mapper.SubMapperAwareNameMapper;
23  import org.apache.myfaces.extensions.validator.core.Nested;
24  import org.apache.myfaces.extensions.validator.internal.UsageCategory;
25  import org.apache.myfaces.extensions.validator.internal.UsageInformation;
26  
27  import java.util.List;
28  import java.util.ArrayList;
29  import java.util.Collections;
30  import java.util.Collection;
31  import java.util.Comparator;
32  import java.util.Iterator;
33  import java.util.ListIterator;
34  import java.util.concurrent.CopyOnWriteArrayList;
35  
36  
37  /**
38   * @since x.x.3
39   */
40  @UsageInformation({UsageCategory.INTERNAL})
41  class SortedNameMapperList<T extends NameMapper> extends CopyOnWriteArrayList<T>
42  {
43      private static final long serialVersionUID = 1502156999599962365L;
44  
45      private List<T> wrapped;
46      private List<T> globalSubNameMapperList;
47  
48      SortedNameMapperList(List<T> wrapped, List<T> subNameMapperList)
49      {
50          this.wrapped = wrapped;
51          this.globalSubNameMapperList = subNameMapperList;
52      }
53  
54      public boolean add(T t)
55      {
56          if (t != null && t.getClass().isAnnotationPresent(Nested.class))
57          {
58              return addSubNameMapper(t);
59          }
60          else
61          {
62              boolean result = wrapped.add(t);
63  
64              sortWrappedList();
65              return result;
66          }
67      }
68  
69      private void sortWrappedList()
70      {
71          List<T> sortableList = new ArrayList<T>(wrapped);
72          Collections.sort(sortableList, new Comparator<T>()
73          {
74              public int compare(T nm1, T nm2)
75              {
76                  if (nm1 instanceof SubMapperAwareNameMapper && nm2 instanceof SubMapperAwareNameMapper)
77                  {
78                      return 0;
79                  }
80                  return nm1 instanceof SubMapperAwareNameMapper ? 1 : -1;
81              }
82          });
83          wrapped.clear();
84          wrapped.addAll(sortableList);
85      }
86  
87      @SuppressWarnings({"unchecked"})
88      private boolean addSubNameMapper(T subNameMapper)
89      {
90          boolean result = false;
91          for (NameMapper nameMapper : this.wrapped)
92          {
93              if (nameMapper instanceof SubMapperAwareNameMapper)
94              {
95                  ((SubMapperAwareNameMapper) nameMapper).addNameMapper(subNameMapper);
96                  result = true;
97              }
98          }
99  
100         tryToAddMapperAsGlobalSubNameMapper(subNameMapper);
101         return result;
102     }
103 
104     private void tryToAddMapperAsGlobalSubNameMapper(T subNameMapper)
105     {
106         if(!this.globalSubNameMapperList.contains(subNameMapper))
107         {
108             this.globalSubNameMapperList.add(subNameMapper);
109         }
110     }
111 
112     /*
113      * generated
114      */
115     public int size()
116     {
117         return wrapped.size();
118     }
119 
120     public boolean isEmpty()
121     {
122         return wrapped.isEmpty();
123     }
124 
125     public boolean contains(Object o)
126     {
127         return wrapped.contains(o);
128     }
129 
130     public Iterator<T> iterator()
131     {
132         return wrapped.iterator();
133     }
134 
135     public Object[] toArray()
136     {
137         return wrapped.toArray();
138     }
139 
140     @SuppressWarnings({"SuspiciousToArrayCall"})
141     public <T> T[] toArray(T[] a)
142     {
143         return wrapped.toArray(a);
144     }
145 
146     public boolean remove(Object o)
147     {
148         return wrapped.remove(o);
149     }
150 
151     public boolean containsAll(Collection<?> c)
152     {
153         return wrapped.containsAll(c);
154     }
155 
156     public boolean addAll(Collection<? extends T> c)
157     {
158         return wrapped.addAll(c);
159     }
160 
161     public boolean addAll(int index, Collection<? extends T> c)
162     {
163         return wrapped.addAll(index, c);
164     }
165 
166     public boolean removeAll(Collection<?> c)
167     {
168         return wrapped.removeAll(c);
169     }
170 
171     public boolean retainAll(Collection<?> c)
172     {
173         return wrapped.retainAll(c);
174     }
175 
176     public void clear()
177     {
178         wrapped.clear();
179     }
180 
181     public T get(int index)
182     {
183         return wrapped.get(index);
184     }
185 
186     public T set(int index, T element)
187     {
188         return wrapped.set(index, element);
189     }
190 
191     public void add(int index, T element)
192     {
193         wrapped.add(index, element);
194     }
195 
196     public T remove(int index)
197     {
198         return wrapped.remove(index);
199     }
200 
201     public int indexOf(Object o)
202     {
203         return wrapped.indexOf(o);
204     }
205 
206     public int lastIndexOf(Object o)
207     {
208         return wrapped.lastIndexOf(o);
209     }
210 
211     public ListIterator<T> listIterator()
212     {
213         return wrapped.listIterator();
214     }
215 
216     public ListIterator<T> listIterator(int index)
217     {
218         return wrapped.listIterator(index);
219     }
220 
221     public List<T> subList(int fromIndex, int toIndex)
222     {
223         return wrapped.subList(fromIndex, toIndex);
224     }
225 }