0b89ce10fbfc8d511102f43abbad007c6142a914
[aai/aai-common.git] / aai-core / src / main / java / org / onap / aai / util / genxsd / NodesYAMLfromOXM.java
1 /**
2  * ============LICENSE_START=======================================================
3  * org.onap.aai
4  * ================================================================================
5  * Copyright © 2017-2018 AT&T Intellectual Property. All rights reserved.
6  * ================================================================================
7  * Licensed under the Apache License, Version 2.0 (the "License");
8  * you may not use this file except in compliance with the License.
9  * You may obtain a copy of the License at
10  *
11  *    http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing, software
14  * distributed under the License is distributed on an "AS IS" BASIS,
15  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16  * See the License for the specific language governing permissions and
17  * limitations under the License.
18  * ============LICENSE_END=========================================================
19  */
20 package org.onap.aai.util.genxsd;
21
22 import java.io.BufferedWriter;
23 import java.io.File;
24 import java.io.FileNotFoundException;
25 import java.io.IOException;
26 import java.nio.charset.Charset;
27 import java.nio.file.Files;
28 import java.nio.file.Path;
29 import java.nio.file.Paths;
30 import java.util.HashMap;
31 import java.util.LinkedHashSet;
32 import java.util.Map;
33 import java.util.Set;
34 import java.util.SortedSet;
35 import java.util.StringTokenizer;
36 import java.util.TreeMap;
37 import java.util.TreeSet;
38 import java.util.Vector;
39
40 import javax.xml.parsers.ParserConfigurationException;
41
42 import org.apache.commons.lang3.StringUtils;
43 import org.onap.aai.edges.EdgeIngestor;
44 import org.onap.aai.edges.EdgeRule;
45 import org.onap.aai.edges.EdgeRuleQuery;
46 import org.onap.aai.edges.exceptions.EdgeRuleNotFoundException;
47 import org.onap.aai.exceptions.AAIException;
48 import org.onap.aai.setup.SchemaVersion;
49 import org.onap.aai.setup.SchemaVersions;
50 import org.onap.aai.nodes.NodeIngestor;
51 import org.slf4j.Logger;
52 import org.slf4j.LoggerFactory;
53 import org.w3c.dom.Element;
54 import org.w3c.dom.NodeList;
55 import org.xml.sax.SAXException;
56
57 import com.google.common.collect.Multimap;
58
59 public class NodesYAMLfromOXM extends OxmFileProcessor {
60         private static final Logger logger = LoggerFactory.getLogger("GenerateXsd.class");
61         private static final String root = "../aai-schema/src/main/resources";
62         private static final String autoGenRoot = "aai-schema/src/main/resources";
63         private static final String generateTypeYAML = "yaml";
64         private static final String normalStartDir = "aai-core";
65         private static final String yaml_dir = (((System.getProperty("user.dir") != null) && (!System.getProperty("user.dir").contains(normalStartDir))) ? autoGenRoot : root) + "/aai_swagger_yaml";
66         private StringBuilder inventoryDefSb = null;    
67         private Map<String,String> operationDefinitions = new HashMap<>();
68
69         private String basePath;
70
71         public NodesYAMLfromOXM(String basePath, SchemaVersions schemaVersions, NodeIngestor ni, EdgeIngestor ei){
72                 super(schemaVersions, ni,ei);
73                 this.basePath = basePath;
74         }
75         public void setOxmVersion(File oxmFile, SchemaVersion v) {
76                 super.setOxmVersion(oxmFile, v);
77         }
78         public void setXmlVersion(String xml, SchemaVersion v){
79                 super.setXmlVersion(xml, v);
80         }
81         
82         public void setVersion(SchemaVersion v) {
83                 super.setVersion(v);
84         }
85
86         @Override
87         public String getDocumentHeader() {
88                 StringBuffer sb = new StringBuffer();
89                 sb.append("swagger: \"2.0\"\ninfo:\n  ");
90                 sb.append("description: |");
91         if ( versionSupportsSwaggerDiff(v.toString())) {
92             sb.append("\n\n    [Differences versus the previous schema version]("+"apidocs/aai_swagger_" + v.toString() + ".diff)");
93         }
94                 sb.append("\n\n    Copyright &copy; 2017-18 AT&amp;T Intellectual Property. All rights reserved.\n\n    Licensed under the Creative Commons License, Attribution 4.0 Intl. (the &quot;License&quot;); you may not use this documentation except in compliance with the License.\n\n    You may obtain a copy of the License at\n\n    (https://creativecommons.org/licenses/by/4.0/)\n\n    Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an &quot;AS IS&quot; BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License.\n\n    This document is best viewed with Firefox or Chrome. Nodes can be found by appending /#/definitions/node-type-to-find to the path to this document. Edge definitions can be found with the node definitions.\n  version: \"" + v.toString() +"\"\n");
95                 sb.append("  title: Active and Available Inventory REST API\n");
96                 sb.append("  license:\n    name: Apache 2.0\n    url: http://www.apache.org/licenses/LICENSE-2.0.html\n");
97                 sb.append("  contact:\n    name:\n    url:\n    email:\n");
98                 sb.append("host:\nbasePath: " + basePath + "/" + v.toString() + "\n");
99                 sb.append("schemes:\n  - https\npaths:\n");
100                 return sb.toString();
101         }
102         
103         protected void init() throws ParserConfigurationException, SAXException, IOException, AAIException, FileNotFoundException, EdgeRuleNotFoundException {
104                 super.init();
105         }
106
107         @Override
108         public String process() throws ParserConfigurationException, SAXException, IOException, AAIException, FileNotFoundException, EdgeRuleNotFoundException {
109                 StringBuffer sb = new StringBuffer();
110                 StringBuffer pathSb = new StringBuffer();
111                 NodeGetOperation.resetContainers();
112                 try {
113                         init();
114                 } catch(Exception e) {
115                         logger.error( "Error initializing " + this.getClass());
116                         throw e;
117                 }
118                 pathSb.append(getDocumentHeader());
119                 StringBuffer definitionsSb = new StringBuffer();
120                 Element elem;
121                 String javaTypeName;
122                 for ( int i = 0; i < javaTypeNodes.getLength(); ++ i ) {
123                         elem = (Element)javaTypeNodes.item(i);
124                         javaTypeName = elem.getAttribute("name");
125                         if ( !"Inventory".equals(javaTypeName ) ) {
126                                 if ( generatedJavaType.containsKey(javaTypeName) ) {
127                                         continue;
128                                 }
129                                 // will combine all matching java-types
130                                 elem = getJavaTypeElementSwagger(javaTypeName );
131                         }                       
132                         
133                         XSDElement javaTypeElement = new XSDElement(elem);
134                         
135                         
136                         logger.debug("External: "+javaTypeElement.getAttribute("name")+"/"+getXmlRootElementName(javaTypeName));
137                         if ( javaTypeName == null ) {
138                                 String msg = "Invalid OXM file: <java-type> has no name attribute in " + oxmFile; 
139                                 logger.error(msg);
140                                 throw new AAIException(msg);
141                         }
142                         namespaceFilter.add(getXmlRootElementName(javaTypeName));
143
144                         processJavaTypeElementSwagger( javaTypeName, javaTypeElement, pathSb,
145                                 definitionsSb, null, null, null, null, null, null);
146                 }
147                 sb.append(pathSb);
148 //              sb.append(getDocumentHeader());
149 //              sb.append(totalPathSbAccumulator);
150                 sb.append(appendOperations());
151                 sb.append(appendDefinitions());
152                 PutRelationPathSet prp = new PutRelationPathSet(v);
153                 prp.generateRelations(ei);
154                 return sb.toString();
155         }
156         
157         public String appendDefinitions() {
158                 return appendDefinitions(null);
159         }
160         
161         public String appendDefinitions(Set<String> namespaceFilter) {
162                 if ( inventoryDefSb != null ) {
163                         javaTypeDefinitions.put("inventory", inventoryDefSb.toString());
164                 }                       
165                 StringBuffer sb = new StringBuffer("definitions:\n");
166                 Map<String, String> sortedJavaTypeDefinitions = new TreeMap<>(javaTypeDefinitions);
167
168                 for (Map.Entry<String, String> entry : sortedJavaTypeDefinitions.entrySet()) {
169                         if(namespaceFilter != null && (! namespaceFilter.contains(entry.getKey()))) {
170                                 continue;
171                         }
172                     sb.append(entry.getValue());
173                 }
174                 return sb.toString();
175         }
176         
177         private String processJavaTypeElementSwagger( String javaTypeName, Element javaTypeElement,
178                         StringBuffer pathSb, StringBuffer definitionsSb, String path, String tag, String opId,
179                         String getItemName, StringBuffer pathParams, String validEdges) {
180                 
181                 String xmlRootElementName = getXMLRootElementName(javaTypeElement);
182                 StringBuilder definitionsLocalSb = new StringBuilder(256);
183                 
184                 String useTag = null;
185                 String useOpId = null;
186                 logger.debug("tag="+tag);
187
188                 if(tag != null && (! validTag(tag))) {
189                         logger.debug("tag="+tag+"; javaTypeName="+javaTypeName);
190                         return null;
191                 }               
192                 if ( !javaTypeName.equals("Inventory") ) {
193                         if ( javaTypeName.equals("AaiInternal"))
194                                 return null;
195                         if ( opId == null )
196                                 useOpId = javaTypeName;
197                         else
198                                 useOpId = opId + javaTypeName;
199                         if ( tag == null )
200                                 useTag = javaTypeName;
201                 }
202
203                 path = xmlRootElementName.equals("inventory") ? "" : (path == null) ? "/" + xmlRootElementName : path + "/" + xmlRootElementName;
204                 XSDJavaType javaType = new XSDJavaType(javaTypeElement);
205                 if ( getItemName != null) {
206                 if ( getItemName.equals("array") )
207                         return javaType.getArrayType();
208                 else
209                         return javaType.getItemName();
210                 }
211                         
212                 NodeList parentNodes = javaTypeElement.getElementsByTagName("java-attributes");
213                 if ( parentNodes.getLength() == 0 ) {
214                         logger.debug( "no java-attributes for java-type " + javaTypeName);
215                         return "";
216                 }
217
218                 String pathDescriptionProperty = javaType.getPathDescriptionProperty();
219                 String container = javaType.getContainerProperty();
220                 Vector<String> indexedProps = javaType.getIndexedProps();
221                 Vector<String> containerProps = new Vector<String>();
222                 if(container != null) {
223                         logger.debug("javaTypeName " + javaTypeName + " container:" + container +" indexedProps:"+indexedProps);
224                 }
225                 
226                 Element parentElement = (Element)parentNodes.item(0);
227                 NodeList xmlElementNodes = parentElement.getElementsByTagName("xml-element");
228
229                 StringBuffer sbParameters = new StringBuffer();
230                 StringBuffer sbRequired = new StringBuffer();
231                 int requiredCnt = 0;
232                 int propertyCnt = 0;
233                 StringBuffer sbProperties = new StringBuffer();
234                 
235                 if ( appliedPaths.containsKey(path)) 
236                         return null;
237                 
238                 StringTokenizer st = new StringTokenizer(path, "/");
239                 logger.debug("path: " + path + " st? " + st.toString());
240                 if ( st.countTokens() > 1 && getItemName == null ) {
241                         logger.debug("appliedPaths: " + appliedPaths + " containsKey? " + appliedPaths.containsKey(path));
242                         appliedPaths.put(path, xmlRootElementName);
243                 }
244                 Vector<String> addTypeV = null;
245                 for ( int i = 0; i < xmlElementNodes.getLength(); ++i ) {
246                                 XSDElement xmlElementElement = new XSDElement((Element)xmlElementNodes.item(i));
247                                 if ( !xmlElementElement.getParentNode().isSameNode(parentElement))
248                                         continue;
249                                 String elementDescription=xmlElementElement.getPathDescriptionProperty();
250                                 if(getItemName == null) {
251                                         addTypeV = xmlElementElement.getAddTypes(v.toString());
252                                 }
253                     if ( "true".equals(xmlElementElement.getAttribute("xml-key"))) {
254                         path += "/{" + xmlElementElement.getAttribute("name") + "}";
255                     }
256                     logger.debug("path: " + path);
257                 logger.debug( "xmlElementElement.getAttribute(required):"+xmlElementElement.getAttribute("required") );
258                                 
259                                 if ( ("true").equals(xmlElementElement.getAttribute("required"))) {
260                                         if ( requiredCnt == 0 )
261                                                 sbRequired.append("    required:\n");
262                                         ++requiredCnt;
263                                         if ( addTypeV == null || addTypeV.isEmpty()) {
264                                                 sbRequired.append("    - " + xmlElementElement.getAttribute("name") + "\n");
265                                         } else { 
266                                                 for ( int k = 0; k < addTypeV.size(); ++k ) {
267                                                         sbRequired.append("    - " + getXmlRootElementName(addTypeV.elementAt(k)) + ":\n");
268                                                 }
269                                         }
270                                 }
271
272                                 if ( "true".equals(xmlElementElement.getAttribute("xml-key")) )  {
273                                         sbParameters.append(xmlElementElement.getPathParamYAML(elementDescription));
274                                 }
275                                 if (  indexedProps != null
276                                                 && indexedProps.contains(xmlElementElement.getAttribute("name") ) ) {
277                                         containerProps.add(xmlElementElement.getQueryParamYAML());
278                                         NodeGetOperation.addContainerProps(container, containerProps);
279                                 }
280                         if ( xmlElementElement.isStandardType()) {
281                                 sbProperties.append(xmlElementElement.getTypePropertyYAML());
282                                 ++propertyCnt;
283                         }
284                         
285 //                      StringBuffer newPathParams = new StringBuffer((pathParams == null ? "" : pathParams.toString())+sbParameters.toString()); //cp8128 don't append the pathParams to sbParameters so that child nodes don't contain the parameters from parent
286                         StringBuffer newPathParams = new StringBuffer(sbParameters.toString());
287                 for ( int k = 0; addTypeV != null && k < addTypeV.size(); ++k ) {
288                         String addType = addTypeV.elementAt(k);
289                                 namespaceFilter.add(getXmlRootElementName(addType));
290                         if ( opId == null || !opId.contains(addType)) {
291                                 processJavaTypeElementSwagger( addType, getJavaTypeElementSwagger(addType), 
292                                         pathSb, definitionsSb, path,  tag == null ? useTag : tag, useOpId, null,
293                                         newPathParams, validEdges);
294                         }
295                         // need item name of array
296                                 String itemName = processJavaTypeElementSwagger( addType, getJavaTypeElementSwagger(addType), 
297                                         pathSb, definitionsSb, path,  tag == null ? useTag : tag, useOpId, 
298                                                         "array", null, null);
299                                         
300                                 if ( itemName != null ) {
301                                         if ( addType.equals("AaiInternal") ) {
302                                                 logger.debug( "addType AaiInternal, skip properties");
303                                                         
304                                         } else if ( getItemName == null) {
305                                                 ++propertyCnt;
306                                                 sbProperties.append("      " + getXmlRootElementName(addType) + ":\n");
307                                                 sbProperties.append("        type: array\n        items:\n");
308                                                 sbProperties.append("          $ref: \"#/definitions/" + (itemName == "" ? "aai-internal" : itemName) + "\"\n");
309                                                 if ( StringUtils.isNotEmpty(elementDescription) )
310                                                         sbProperties.append("        description: " + elementDescription + "\n");
311                                         }
312                                 } else {
313                                         if ( ("java.util.ArrayList").equals(xmlElementElement.getAttribute("container-type"))) {
314                                                         // need properties for getXmlRootElementName(addType)
315                                                 namespaceFilter.add(getXmlRootElementName(addType));
316                                                 if(getXmlRootElementName(addType).equals("service-capabilities"))
317                                                 {
318                                                         logger.info("arrays: "+ getXmlRootElementName(addType));
319                                                 }                                               
320 //                                              newPathParams = new StringBuffer((pathParams == null ? "" : pathParams.toString())+sbParameters.toString()); //cp8128 - change this to not append pathParameters. Just use sbParameters
321                                                 newPathParams = new StringBuffer(sbParameters.toString());
322                                                 processJavaTypeElementSwagger( addType, getJavaTypeElementSwagger(addType), 
323                                                         pathSb, definitionsSb, path,  tag == null ? useTag : tag, useOpId, 
324                                                                         null, newPathParams, validEdges);
325                                                 sbProperties.append("      " + getXmlRootElementName(addType) + ":\n");
326                                                 sbProperties.append("        type: array\n        items:          \n");
327                                                 sbProperties.append("          $ref: \"#/definitions/" + getXmlRootElementName(addType) + "\"\n");
328                                                 if ( StringUtils.isNotEmpty(elementDescription) )
329                                                         sbProperties.append("        description: " + elementDescription + "\n");
330
331                                         } else {
332                                                 //Make sure certain types added to the filter don't appear
333                                                 if (nodeFilter.contains(getXmlRootElementName(addType))) {
334                                                         ;
335                                                 } else {
336                                                         sbProperties.append("      " + getXmlRootElementName(addType) + ":\n");
337                                                         sbProperties.append("        type: object\n");
338                                                         sbProperties.append("        $ref: \"#/definitions/" + getXmlRootElementName(addType) + "\"\n");
339                                                 }
340                                         }
341                                         if ( StringUtils.isNotEmpty(elementDescription) )
342                                                 sbProperties.append("        description: " + elementDescription + "\n");
343                                         ++propertyCnt;
344                                 }
345                 }
346                 }
347                 
348                 if ( sbParameters.toString().length() > 0 ) {
349                         if ( pathParams == null )
350                                 pathParams = new StringBuffer();
351                         pathParams.append(sbParameters);
352                 }
353                 if (indexedProps.isEmpty() && containerProps.isEmpty()){
354                         NodeGetOperation get = new NodeGetOperation(useOpId, xmlRootElementName, tag, path, null);
355                         String operation = get.toString();
356                         if(StringUtils.isNotEmpty(operation)) {
357                                 operationDefinitions.put(xmlRootElementName, operation);
358                         }                       
359                 } else {
360                         NodeGetOperation get = new NodeGetOperation(useOpId, xmlRootElementName, tag, path,  pathParams == null ? "" : pathParams.toString());
361                         String operation = get.toString();
362                         if(StringUtils.isNotEmpty(operation)) {
363                                 operationDefinitions.put(xmlRootElementName, operation);
364                         }                       
365                 }
366             logger.debug("opId vs useOpId:"+opId+" vs "+useOpId+" PathParams="+pathParams);
367                 // add PUT
368                 if ( generatedJavaType.containsKey(xmlRootElementName) ) {
369                         logger.debug("xmlRootElementName(1)="+xmlRootElementName);
370                         return null;
371                 }
372                 boolean processingInventoryDef = false;
373                 if ( xmlRootElementName.equals("inventory")) {
374                         // inventory properties for each oxm to be concatenated
375                         processingInventoryDef = true;
376                         if ( inventoryDefSb == null ) {
377                                 inventoryDefSb = new StringBuilder();
378                                 definitionsSb.append("  " + xmlRootElementName + ":\n");
379                                 definitionsLocalSb.append("  " + xmlRootElementName + ":\n");
380                                 definitionsLocalSb.append("    properties:\n");
381                         }
382
383                 } else {
384                         definitionsSb.append("  " + xmlRootElementName + ":\n");
385                         definitionsLocalSb.append("  " + xmlRootElementName + ":\n");
386                 }
387                 DeleteFootnoteSet footnotes = new DeleteFootnoteSet(xmlRootElementName);
388                 StringBuffer sbEdge = new StringBuffer();
389                 LinkedHashSet<String> preventDelete = new LinkedHashSet<String>();
390                 String prevent=null;
391                 String nodeCaption = new String("      ###### Related Nodes\n");
392                 try {
393                         EdgeRuleQuery q = new EdgeRuleQuery.Builder(xmlRootElementName).version(v).fromOnly().build();
394                         Multimap<String, EdgeRule> results = ei.getRules(q);
395                         SortedSet<String> ss=new TreeSet<>(results.keySet());
396                         sbEdge.append(nodeCaption);
397                         nodeCaption="";
398                         for(String key : ss) {
399                                 results.get(key).stream().filter((i) -> (i.getFrom().equals(xmlRootElementName) && (! i.isPrivateEdge()))).forEach((i) ->{ logger.info(new String(new StringBuffer("      - TO ").append(i.getTo()).append(i.getDirection().toString()).append(i.getContains())));} );
400                                 results.get(key).stream().filter((i) -> (i.getFrom().equals(xmlRootElementName) && (! i.isPrivateEdge()))).forEach((i) ->{ sbEdge.append("      - TO "+i.getTo()); EdgeDescription ed = new EdgeDescription(i);  String footnote = ed.getAlsoDeleteFootnote(xmlRootElementName); sbEdge.append(ed.getRelationshipDescription("TO", xmlRootElementName)+footnote+"\n"); if(StringUtils.isNotEmpty(footnote)) footnotes.add(footnote);} );
401                                 results.get(key).stream().filter((i) -> (i.getFrom().equals(xmlRootElementName) && (! i.isPrivateEdge() && i.getPreventDelete().equals("OUT")))).forEach((i) ->{ preventDelete.add(i.getTo().toUpperCase());} );
402                         }
403                 } catch(Exception e) {
404                         logger.debug("xmlRootElementName: "+xmlRootElementName+"\n"+e);
405                 }
406                 try {
407                         EdgeRuleQuery q1 = new EdgeRuleQuery.Builder(xmlRootElementName).version(v).toOnly().build();
408                         Multimap<String, EdgeRule> results = ei.getRules(q1);
409                         SortedSet<String> ss=new TreeSet<String>(results.keySet());
410                         sbEdge.append(nodeCaption);
411                         for(String key : ss) {
412                                 results.get(key).stream().filter((i) -> (i.getTo().equals(xmlRootElementName) && (! i.isPrivateEdge()))).forEach((i) ->{ sbEdge.append("      - FROM "+i.getFrom()); EdgeDescription ed = new EdgeDescription(i);  String footnote = ed.getAlsoDeleteFootnote(xmlRootElementName); sbEdge.append(ed.getRelationshipDescription("FROM", xmlRootElementName)+footnote+"\n"); if(StringUtils.isNotEmpty(footnote)) footnotes.add(footnote);} );
413                                 results.get(key).stream().filter((i) -> (i.getTo().equals(xmlRootElementName) && (! i.isPrivateEdge()))).forEach((i) ->{ logger.info(new String(new StringBuffer("      - FROM ").append(i.getFrom()).append(i.getDirection().toString()).append(i.getContains())));} );
414                                 results.get(key).stream().filter((i) -> (i.getTo().equals(xmlRootElementName) && (! i.isPrivateEdge() && i.getPreventDelete().equals("IN")))).forEach((i) ->{ preventDelete.add(i.getFrom().toUpperCase());} );
415                         }
416                 } catch(Exception e) {
417                         logger.debug("xmlRootElementName: "+xmlRootElementName+"\n"+e);
418                 }
419                 if(preventDelete.size() > 0) {
420                         prevent = xmlRootElementName.toUpperCase()+" cannot be deleted if related to "+String.join(",",preventDelete);
421                         logger.debug(prevent);
422                 }
423
424                 if(StringUtils.isNotEmpty(prevent)) {
425                         footnotes.add(prevent);
426                 }
427                 if(footnotes.footnotes.size() > 0) {
428                         sbEdge.append(footnotes.toString());
429                 }                       
430                 validEdges = sbEdge.toString();
431
432                 // Handle description property.  Might have a description OR valid edges OR both OR neither.
433                 // Only put a description: tag if there is at least one.
434                 if (StringUtils.isNotEmpty(pathDescriptionProperty) || StringUtils.isNotEmpty(validEdges) ) {
435                         definitionsSb.append("    description: |\n");
436                         definitionsLocalSb.append("    description: |\n");      
437
438                         if ( pathDescriptionProperty != null ) {
439                                 definitionsSb.append("      " + pathDescriptionProperty + "\n" );
440                                 definitionsLocalSb.append("      " + pathDescriptionProperty    + "\n" );
441                         }
442                         definitionsSb.append(validEdges);
443                         definitionsLocalSb.append(validEdges);
444                 }
445                 
446                 if ( requiredCnt > 0 ) {
447                         definitionsSb.append(sbRequired);
448                         definitionsLocalSb.append(sbRequired);
449                 }
450                         
451                 if ( propertyCnt > 0 ) {
452                         definitionsSb.append("    properties:\n");
453                         definitionsSb.append(sbProperties);
454                         if  ( !processingInventoryDef) {
455                                 definitionsLocalSb.append("    properties:\n");
456                         }
457                         definitionsLocalSb.append(sbProperties);
458                 }
459                 try {
460                         namespaceFilter.add(xmlRootElementName);
461                         if ( xmlRootElementName.equals("inventory") ) {
462                                 //will add to javaTypeDefinitions at end 
463                                 inventoryDefSb.append(definitionsLocalSb.toString());
464                         } else {
465                                 javaTypeDefinitions.put(xmlRootElementName, definitionsLocalSb.toString());
466                         }
467                 } catch (Exception e) {
468                         e.printStackTrace();
469                 }
470                 if ( xmlRootElementName.equals("inventory") ) {
471                         logger.trace("skip xmlRootElementName(2)="+xmlRootElementName);
472                         return null;
473                 }
474                 generatedJavaType.put(xmlRootElementName, null);
475                 //Write operations by Namespace(tagName)
476 /*
477                 if( validTag(javaTypeName) && javaTypeName == useTag && tag == null) {
478                         writeYAMLfile("nodes_"+javaTypeName, getDocumentHeader()+pathSb.toString()+appendDefinitions(namespaceFilter));
479                         totalPathSbAccumulator.append(pathSb);
480                         pathSb.delete(0, pathSb.length());
481                         namespaceFilter.clear();
482                 }
483 */
484                 logger.debug("xmlRootElementName(2)="+xmlRootElementName);
485                 return null;
486         }
487         
488         private void writeYAMLfile(String outfileName, String fileContent) {
489                 outfileName = (StringUtils.isEmpty(outfileName)) ? "aai_swagger" : outfileName;
490                 outfileName = (outfileName.lastIndexOf(File.separator) == -1) ? yaml_dir + File.separator +outfileName+"_" + v.toString() + "." + generateTypeYAML : outfileName;
491                 File outfile = new File(outfileName);
492                 File parentDir = outfile.getParentFile();
493                 if(parentDir != null && ! parentDir.exists()) 
494                         parentDir.mkdirs();
495                 try {
496                         outfile.createNewFile();
497                 } catch (IOException e) {
498                         logger.error( "Exception creating output file " + outfileName);
499                         e.printStackTrace();
500                 }
501                 Path path = Paths.get(outfileName);
502                 Charset charset = Charset.forName("UTF-8");
503                 try {
504                         BufferedWriter bw = Files.newBufferedWriter(path, charset);
505                         bw.write(fileContent);
506                         if ( bw != null ) {
507                                 bw.close();
508                         }
509                 } catch ( IOException e) {
510                         logger.error( "Exception writing output file " + outfileName);
511                         e.printStackTrace();
512                 } 
513         }
514         
515         public boolean validTag(String tag) {
516                 if(tag != null) {
517                         switch ( tag ) {
518                         case "Network":
519                         case "Search":
520                         case "Actions":
521                         case "ServiceDesignAndCreation":
522                         case "Business":
523                         case "LicenseManagement":
524                         case "CloudInfrastructure":
525                                 return true;
526                         }
527                 }
528                 return false;
529         }
530         
531         public String appendOperations() {
532                 //append definitions
533                 StringBuffer sb = new StringBuffer();
534                 Map<String, String> sortedOperationDefinitions = new TreeMap<String, String>(operationDefinitions);
535                 for (Map.Entry<String, String> entry : sortedOperationDefinitions.entrySet()) {
536                     sb.append(entry.getValue());
537                 }
538                 return sb.toString();
539         }
540 }
541