View Javadoc

1   /*
2    * Created on May 17, 2005
3    *
4    */
5   package org.dbe.sdl.util;
6   
7   import java.io.File;
8   import java.io.FileInputStream;
9   import java.io.FileNotFoundException;
10  import java.io.IOException;
11  import java.util.ArrayList;
12  import java.util.HashMap;
13  import java.util.Iterator;
14  import java.util.List;
15  import java.util.Map;
16  import java.util.Map.Entry;
17  
18  import javax.xml.parsers.DocumentBuilder;
19  import javax.xml.parsers.DocumentBuilderFactory;
20  import javax.xml.parsers.ParserConfigurationException;
21  
22  import org.w3c.dom.Document;
23  import org.w3c.dom.Element;
24  import org.w3c.dom.Node;
25  import org.w3c.dom.NodeList;
26  import org.xml.sax.SAXException;
27  
28  /***
29   * Simple SDL parser
30   * 
31   * @author bob
32   */
33  public class SDLParamParser {
34  
35      /*** operations */
36      private Map operations = new HashMap();
37      private Element rootElement;
38      /***
39       * @throws ParserConfigurationException
40       * @throws IOException
41       * @throws SAXException
42       * @throws FileNotFoundException
43       *  
44       */
45      public SDLParamParser(File f) {
46  
47          try {
48              DocumentBuilderFactory builderFactory = DocumentBuilderFactory
49                      .newInstance();
50              DocumentBuilder builder = builderFactory.newDocumentBuilder();
51  
52              Document document = builder.parse(new FileInputStream(f));
53  
54              document.getDocumentElement().normalize();
55  
56              parse(document);
57  
58          } catch (ParserConfigurationException e) {
59              e.printStackTrace();
60          } catch (FileNotFoundException e) {
61              e.printStackTrace();
62          } catch (SAXException e) {
63              e.printStackTrace();
64          } catch (IOException e) {
65              e.printStackTrace();
66          }
67  
68      }
69  
70      /***
71       * Return the operations for the passed method. The method is not case
72       * sensitive because the SDL doesn't is
73       * 
74       * @param method
75       *            name of the method (not case sensitive)
76       * @return String array with the name of parameters
77       */
78      public String[] getParameters(String method) {
79          return (String[]) operations.get(method.toUpperCase());
80      }
81  
82      /***
83       * @param document
84       */
85      private void parse(Document document) {
86          this.rootElement = document.getDocumentElement();
87  
88          // Read all Methods and store them
89          readMethods(rootElement);
90  
91          // Find each method
92          for (Iterator it = operations.entrySet().iterator(); it.hasNext();) {
93              Map.Entry entry = (Entry) it.next();
94  
95              // Find index Parameters for each Index
96              List newParams = parseMethodParams((List) entry.getValue(),
97                      rootElement);
98  
99              entry.setValue(newParams.toArray(new String[0]));
100         }
101     }
102 
103     /***
104      * Read all methods
105      * 
106      * @param element
107      */
108     private void readMethods(Element element) {
109         // Find operations NodeList
110         NodeList list = element
111                 .getElementsByTagName("sdl:Interface.cmpOperation");
112         Node node = list.item(0);
113         list = node.getChildNodes();
114 
115         // Find each Operation
116         for (int i = 0; i < list.getLength(); i++) {
117             Node mynode = list.item(i);
118 
119             // new operation Found
120             if ("sdl:Operation".equals(mynode.getNodeName())) {
121                 // Get name
122                 Node operation = mynode.getAttributes().getNamedItem("ElName");
123 
124                 // Get parameters
125                 List parameters = readParameters(mynode.getChildNodes());
126 
127                 // add operation
128                 // XXX: Look, we are NOT case sensitive
129                 operations.put(operation.getNodeValue().toUpperCase(),
130                         parameters);
131             }
132         }
133     }
134 
135     /***
136      * Read Parameters names
137      * 
138      * @param paramList
139      * @param element
140      * @return
141      */
142     private List parseMethodParams(List paramList, Element element) {
143         List newParamList = new ArrayList();
144 
145         // Find each Parameters
146         for (int i = 0; i < paramList.size(); i++) {
147 
148             // Find operations NodeList
149             NodeList list = element
150                     .getElementsByTagName("sdl:Definitions.cmpMessage");
151             Node node = list.item(0);
152             list = node.getChildNodes();
153 
154             // FIXME: I suposse SDL will be wellformed some day
155             // At the moment we use index, because we cannot assure they
156             // are doing this in the proper way. Some ids are repeated
157             // and some others have some parts within the same id ¿What
158             // is correct? I dont know
159             // So we use an index to sort results (ok, i think it will
160             // work)
161             int index = 0;
162 
163             // Find each Operation
164             for (int j = 0; j < list.getLength(); j++) {
165                 Node mynode = list.item(j);
166 
167                 // new operation Found
168                 if (("sdl:SimpleMessage".equals(mynode.getNodeName()))
169                         && (mynode.getAttributes().getNamedItem("xmi.id")
170                                 .getNodeValue().equals((String) paramList
171                                 .get(i)))) {
172 
173                     Element el = (Element) mynode;
174                     NodeList pList = el.getElementsByTagName(
175                             "sdl:SimpleMessage.cmpPart").item(0)
176                             .getChildNodes();
177 
178                     // Find each Operation
179                     for (int k = 0; k < pList.getLength(); k++) {
180                         Node pNode = pList.item(k);
181                         if (pNode.getNodeName().equals("sdl:Part")) {
182                             String finalName = pNode.getAttributes()
183                                     .getNamedItem("ElName").getNodeValue();
184                             // Add name
185                             newParamList.add(index++, finalName);
186                         }
187                     }
188 
189                 }
190             }
191         }
192 
193         return newParamList;
194     }
195 
196     /***
197      * 
198      * @param parameterList
199      * @return
200      */
201     private List readParameters(NodeList parameterList) {
202 
203         List parameters = new ArrayList();
204 
205         // Find each Parameters
206         for (int i = 0; i < parameterList.getLength(); i++) {
207 
208             Node node = parameterList.item(i);
209 
210             // If it's parameter (input or output)
211             if (("sdl:Operation.refOutputMessage".equals(node.getNodeName()))
212                     || ("sdl:Operation.refInputMessage".equals(node
213                             .getNodeName()))) {
214 
215                 Node node2 = node.getLastChild().getPreviousSibling();
216 
217                 String paramName = node2.getAttributes().getNamedItem(
218                         "xmi.idref").getNodeValue();
219                 parameters.add(paramName);
220 
221             }
222             // Add parameter. Parameters are in INVERSE order
223         }
224 
225         return parameters;
226     }
227 
228     /***
229      *  
230      */
231     public String toString() {
232         StringBuffer sb = new StringBuffer();
233 
234         for (Iterator it = operations.entrySet().iterator(); it.hasNext();) {
235             Map.Entry entry = (Map.Entry) it.next();
236 
237             sb.append(entry.getKey());
238             sb.append("( ");
239 
240             String[] s = (String[]) entry.getValue();
241             for (int i = 0; i < s.length; i++) {
242 
243                 if (i > 0) {
244                     sb.append(", ");
245                 }
246 
247                 sb.append(s[i]);
248             }
249 
250             sb.append(");\n");
251         }
252 
253         return sb.toString();
254     }
255 
256     public List getOperationNames() {
257         NodeList list = rootElement.getElementsByTagName("sdl:Operation");
258         List operations = new ArrayList();
259         
260         for (int i=0; i < list.getLength(); i++) {
261             Node node = list.item(i);
262             operations.add(node.getAttributes().getNamedItem("ElName").getNodeValue());
263         }
264         
265         return operations;
266     }
267     
268     public String getInterfaceName() {
269         NodeList list = rootElement.getElementsByTagName("sdl:Interface");
270         Node node = list.item(0);
271         return node.getAttributes().getNamedItem("ElName").getNodeValue();
272     }
273 }