View Javadoc

1   package org.apache.torque.generator.control.action;
2   
3   /*
4    * Licensed to the Apache Software Foundation (ASF) under one
5    * or more contributor license agreements.  See the NOTICE file
6    * distributed with this work for additional information
7    * regarding copyright ownership.  The ASF licenses this file
8    * to you under the Apache License, Version 2.0 (the
9    * "License"); you may not use this file except in compliance
10   * with the License.  You may obtain a copy of the License at
11   *
12   *   http://www.apache.org/licenses/LICENSE-2.0
13   *
14   * Unless required by applicable law or agreed to in writing,
15   * software distributed under the License is distributed on an
16   * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
17   * KIND, either express or implied.  See the License for the
18   * specific language governing permissions and limitations
19   * under the License.
20   */
21  
22  import java.util.ArrayList;
23  import java.util.List;
24  
25  import org.apache.torque.generator.GeneratorException;
26  import org.apache.torque.generator.configuration.outlet.OutletConfiguration;
27  import org.apache.torque.generator.control.ControllerState;
28  import org.apache.torque.generator.control.TokenReplacer;
29  import org.apache.torque.generator.outlet.Outlet;
30  import org.apache.torque.generator.outlet.OutletResult;
31  import org.apache.torque.generator.qname.Namespace;
32  import org.apache.torque.generator.qname.QualifiedName;
33  import org.apache.torque.generator.source.SourceElement;
34  import org.apache.torque.generator.source.SourcePath;
35  
36  /**
37   * Traverses all matching elements, and applies a outlet to each matching
38   * element. The output of each outlet is appended to the output.
39   */
40  public class TraverseAllAction implements MergepointAction
41  {
42      /**
43       * The filter for the elements to traverse, not null.
44       */
45      private final String elementsToTraverseName;
46  
47      /**
48       * The name of the outlet to be invoked for each element, not null.
49       */
50      private final String outletName;
51  
52      /**
53       * Whether it is correct to have no element to traverse.
54       */
55      private boolean acceptEmpty = true;
56  
57      /**
58       * Constructor.
59       *
60       * @param elementsToTraverseName the elements to traverse, not null.
61       * @param outletName the name of the outlet to be invoked for each
62       *        element, not null.
63       * @param acceptEmpty true if it is correct if no matching elements are
64       *        found, false to throw an error if no matching elements are found,
65       *        null means true.
66       */
67      public TraverseAllAction(
68              String elementsToTraverseName,
69              String outletName,
70              Boolean acceptEmpty)
71      {
72          if (elementsToTraverseName == null)
73          {
74              throw new IllegalArgumentException(
75                      "TraverseAllAction: "
76                      + "elementsToTraverseName must not be null");
77          }
78          this.elementsToTraverseName = elementsToTraverseName;
79  
80          if (outletName == null)
81          {
82              throw new IllegalArgumentException(
83                      "TraverseAllAction: outletName must not be null");
84          }
85          this.outletName = outletName;
86          if (acceptEmpty != null)
87          {
88              this.acceptEmpty = acceptEmpty.booleanValue();
89          }
90      }
91  
92      /**
93       * Traverses all matching elements, and applies an outlet to each matching
94       * element. The output of each outlet is appended to the output.
95       * ${...} Tokens are replaced within outletName and
96       * elementsToTraverseName.
97       */
98      public OutletResult execute(ControllerState controllerState)
99          throws GeneratorException
100     {
101         TokenReplacer tokenReplacer = new TokenReplacer(controllerState);
102 
103         Outlet outlet;
104         {
105             OutletConfiguration outletConfiguration
106                     = controllerState.getUnitConfiguration()
107                         .getOutletConfiguration();
108             String detokenizedOutletName
109                     = tokenReplacer.process(outletName);
110             QualifiedName outletQName = new QualifiedName(
111                     detokenizedOutletName,
112                     Namespace.ROOT_NAMESPACE);
113 
114             outlet = outletConfiguration.getOutlet(outletQName);
115             if (outlet == null)
116             {
117                 throw new GeneratorException("TraverseAllAction : The outlet "
118                         + outletName
119                         + " does not exist");
120             }
121         }
122 
123         SourceElement currentElement = controllerState.getSourceElement();
124         String detokenizedElementToTraverseName
125                 = tokenReplacer.process(elementsToTraverseName);
126 
127         List<SourceElement> selectedElements
128                 = SourcePath.getElements(
129                         currentElement,
130                         detokenizedElementToTraverseName);
131         if (!acceptEmpty && selectedElements.isEmpty())
132         {
133             throw new GeneratorException(
134                     "TraverseAllAction : selected element "
135                         + elementsToTraverseName
136                         + " does not exist and acceptEmpty was set to false");
137         }
138 
139         List<OutletResult> resultList
140                 = new ArrayList<OutletResult>(selectedElements.size());
141         for (SourceElement sourceElement : selectedElements)
142         {
143             controllerState.setSourceElement(sourceElement);
144             outlet.beforeExecute(controllerState);
145             resultList.add(outlet.execute(controllerState));
146             outlet.afterExecute(controllerState);
147         }
148         controllerState.setSourceElement(currentElement);
149         if (resultList.isEmpty())
150         {
151             return new OutletResult("");
152         }
153         return OutletResult.concatenate(resultList);
154     }
155 
156     @Override
157     public String toString()
158     {
159         return "(TraverseAllAction: element = "
160                 + elementsToTraverseName
161                 + ", outlet = "
162                 + outletName
163                 + ", acceptEmpty = "
164                 + acceptEmpty
165                 + ")";
166     }
167 
168     @Override
169     public int hashCode()
170     {
171         final int prime = 31;
172         final int secondPrime = 1231;
173         final int thirdPrime = 1237;
174         int result = 1;
175         result = prime * result + (acceptEmpty ? secondPrime : thirdPrime);
176         result = prime * result + elementsToTraverseName.hashCode();
177         result = prime * result + outletName.hashCode();
178         return result;
179     }
180 
181     @Override
182     public boolean equals(Object obj)
183     {
184         if (this == obj)
185         {
186             return true;
187         }
188         if (obj == null)
189         {
190             return false;
191         }
192         if (getClass() != obj.getClass())
193         {
194             return false;
195         }
196 
197         final TraverseAllAction other = (TraverseAllAction) obj;
198         if (acceptEmpty != other.acceptEmpty)
199         {
200             return false;
201         }
202         if (!elementsToTraverseName.equals(other.elementsToTraverseName))
203         {
204             return false;
205         }
206         if (!outletName.equals(other.outletName))
207         {
208             return false;
209         }
210         return true;
211     }
212 }