From: Giovanni Meo Date: Tue, 28 May 2013 18:18:24 +0000 (+0000) Subject: Merge "Fix for bug 24." X-Git-Tag: releasepom-0.1.0~419 X-Git-Url: https://git.opendaylight.org/gerrit/gitweb?p=controller.git;a=commitdiff_plain;h=d0f1a6162437a9e003e87c7a8b36ea875f8de984;hp=261f59df395a0b8e2ebb1259837526f60f64baa4 Merge "Fix for bug 24." --- diff --git a/opendaylight/sal/yang-prototype/code-generator/binding-generator-impl/src/main/java/org/opendaylight/controller/sal/binding/yang/types/BaseYangTypes.java b/opendaylight/sal/yang-prototype/code-generator/binding-generator-impl/src/main/java/org/opendaylight/controller/sal/binding/yang/types/BaseYangTypes.java index 4cf4fadef6..374ad8bf92 100644 --- a/opendaylight/sal/yang-prototype/code-generator/binding-generator-impl/src/main/java/org/opendaylight/controller/sal/binding/yang/types/BaseYangTypes.java +++ b/opendaylight/sal/yang-prototype/code-generator/binding-generator-impl/src/main/java/org/opendaylight/controller/sal/binding/yang/types/BaseYangTypes.java @@ -21,6 +21,7 @@ public class BaseYangTypes { private static Map typeMap = new HashMap(); public static final Type BOOLEAN_TYPE = Types.typeForClass(Boolean.class); + public static final Type EMPTY_TYPE = Types.typeForClass(Boolean.class); public static final Type INT8_TYPE = Types.typeForClass(Byte.class); public static final Type INT16_TYPE = Types.typeForClass(Short.class); public static final Type INT32_TYPE = Types.typeForClass(Integer.class); @@ -34,6 +35,7 @@ public class BaseYangTypes { static { typeMap.put("boolean", BOOLEAN_TYPE); + typeMap.put("empty", EMPTY_TYPE); typeMap.put("int8", INT8_TYPE); typeMap.put("int16", INT16_TYPE); typeMap.put("int32", INT32_TYPE); diff --git a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/ClassCodeGenerator.java b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/ClassCodeGenerator.java index 6c8f9de0d4..942174fdce 100644 --- a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/ClassCodeGenerator.java +++ b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/ClassCodeGenerator.java @@ -7,14 +7,14 @@ */ package org.opendaylight.controller.sal.java.api.generator; -import static org.opendaylight.controller.sal.java.api.generator.Constants.NL; -import static org.opendaylight.controller.sal.java.api.generator.Constants.RCB; -import static org.opendaylight.controller.sal.java.api.generator.Constants.TAB; +import static org.opendaylight.controller.sal.java.api.generator.Constants.*; import java.io.IOException; import java.io.StringWriter; import java.io.Writer; +import java.util.LinkedHashMap; import java.util.List; +import java.util.Map; import org.opendaylight.controller.sal.binding.model.api.CodeGenerator; import org.opendaylight.controller.sal.binding.model.api.GeneratedProperty; @@ -23,52 +23,70 @@ import org.opendaylight.controller.sal.binding.model.api.Type; public class ClassCodeGenerator implements CodeGenerator { + private Map> imports; + @Override public Writer generate(Type type) throws IOException { final Writer writer = new StringWriter(); if (type instanceof GeneratedTransferObject) { GeneratedTransferObject genTO = (GeneratedTransferObject) type; + imports = GeneratorUtil.createImports(genTO); + + final String currentPkg = genTO.getPackageName(); final List fields = genTO.getProperties(); - writer.write(GeneratorUtil.createClassDeclarationWithPkgName(genTO, - "")); + writer.write(GeneratorUtil.createPackageDeclaration(currentPkg)); + writer.write(NL); + + List importLines = GeneratorUtil.createImportLines(imports); + for (String line : importLines) { + writer.write(line + NL); + } + writer.write(NL); + + writer.write(GeneratorUtil.createClassDeclaration(genTO, "", + imports)); writer.write(NL); writer.write(NL); if (fields != null) { for (GeneratedProperty field : fields) { - writer.write(GeneratorUtil.createField(field, TAB) + NL); + writer.write(GeneratorUtil.createField(field, TAB, imports, + currentPkg) + NL); } writer.write(NL); - writer.write(GeneratorUtil.createConstructor(genTO, TAB) + NL); + writer.write(GeneratorUtil.createConstructor(genTO, TAB, + imports) + NL); writer.write(NL); for (GeneratedProperty field : fields) { - writer.write(GeneratorUtil.createGetter(field, TAB) + NL); + writer.write(GeneratorUtil.createGetter(field, TAB, + imports, currentPkg) + NL); if (!field.isReadOnly()) { - writer.write(GeneratorUtil.createSetter(field, TAB) + NL); + writer.write(GeneratorUtil.createSetter(field, TAB, + imports, currentPkg) + NL); } } writer.write(NL); - + if (!genTO.getHashCodeIdentifiers().isEmpty()) { writer.write(GeneratorUtil.createHashCode( genTO.getHashCodeIdentifiers(), TAB) + NL); } - + if (!genTO.getEqualsIdentifiers().isEmpty()) { writer.write(GeneratorUtil.createEquals(genTO, genTO.getEqualsIdentifiers(), TAB) + NL); } - + if (!genTO.getToStringIdentifiers().isEmpty()) { writer.write(GeneratorUtil.createToString(genTO, genTO.getToStringIdentifiers(), TAB) + NL); } - + writer.write(RCB); } } diff --git a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/GeneratorUtil.java b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/GeneratorUtil.java index 9e9a3e5df1..b85e2b0ed7 100644 --- a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/GeneratorUtil.java +++ b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/GeneratorUtil.java @@ -7,28 +7,13 @@ */ package org.opendaylight.controller.sal.java.api.generator; -import static org.opendaylight.controller.sal.java.api.generator.Constants.CLASS; -import static org.opendaylight.controller.sal.java.api.generator.Constants.COMMA; -import static org.opendaylight.controller.sal.java.api.generator.Constants.ENUM; -import static org.opendaylight.controller.sal.java.api.generator.Constants.FINAL; -import static org.opendaylight.controller.sal.java.api.generator.Constants.GAP; -import static org.opendaylight.controller.sal.java.api.generator.Constants.IFC; -import static org.opendaylight.controller.sal.java.api.generator.Constants.LB; -import static org.opendaylight.controller.sal.java.api.generator.Constants.LCB; -import static org.opendaylight.controller.sal.java.api.generator.Constants.NL; -import static org.opendaylight.controller.sal.java.api.generator.Constants.PKG; -import static org.opendaylight.controller.sal.java.api.generator.Constants.PRIVATE; -import static org.opendaylight.controller.sal.java.api.generator.Constants.PUBLIC; -import static org.opendaylight.controller.sal.java.api.generator.Constants.RB; -import static org.opendaylight.controller.sal.java.api.generator.Constants.RCB; -import static org.opendaylight.controller.sal.java.api.generator.Constants.SC; -import static org.opendaylight.controller.sal.java.api.generator.Constants.STATIC; -import static org.opendaylight.controller.sal.java.api.generator.Constants.TAB; -import static org.opendaylight.controller.sal.java.api.generator.Constants.EXTENDS; -import static org.opendaylight.controller.sal.java.api.generator.Constants.IMPLEMENTS; +import static org.opendaylight.controller.sal.java.api.generator.Constants.*; import java.util.ArrayList; +import java.util.HashMap; +import java.util.LinkedHashMap; import java.util.List; +import java.util.Map; import org.opendaylight.controller.sal.binding.model.api.AnnotationType; import org.opendaylight.controller.sal.binding.model.api.Constant; @@ -47,23 +32,30 @@ public class GeneratorUtil { private GeneratorUtil() { } - public static String createIfcDeclarationWithPkgName( - final GeneratedType genType, final String indent) { - return createFileDeclarationWithPkgName(IFC, genType, indent); + public static String createIfcDeclaration(final GeneratedType genType, + final String indent, + final Map> availableImports) { + return createFileDeclaration(IFC, genType, indent, availableImports); } - public static String createClassDeclarationWithPkgName( - final GeneratedTransferObject genTransferObject, final String indent) { - return createFileDeclarationWithPkgName(CLASS, genTransferObject, - indent); + public static String createClassDeclaration( + final GeneratedTransferObject genTransferObject, + final String indent, + final Map> availableImports) { + return createFileDeclaration(CLASS, genTransferObject, indent, + availableImports); } - private static String createFileDeclarationWithPkgName(final String type, - final GeneratedType genType, final String indent) { + public static String createPackageDeclaration(final String packageName) { + return PKG + GAP + packageName + SC; + } + + private static String createFileDeclaration(final String type, + final GeneratedType genType, final String indent, + final Map> availableImports) { final StringBuilder builder = new StringBuilder(); - builder.append(PKG + GAP + genType.getPackageName() + SC); - builder.append(NL); - builder.append(NL); + final String currentPkg = genType.getPackageName(); + createComment(builder, genType.getComment(), indent); if (!genType.getAnnotations().isEmpty()) { @@ -73,7 +65,6 @@ public class GeneratorUtil { } builder.append(PUBLIC + GAP + type + GAP + genType.getName() + GAP); - final List genImplements = genType.getImplements(); if (genType instanceof GeneratedTransferObject) { GeneratedTransferObject genTO = (GeneratedTransferObject) genType; @@ -82,16 +73,21 @@ public class GeneratorUtil { builder.append(genTO.getExtends() + GAP); } } + + final List genImplements = genType.getImplements(); if (!genImplements.isEmpty()) { if (genType instanceof GeneratedTransferObject) { builder.append(IMPLEMENTS + GAP); } else { builder.append(EXTENDS + GAP); } - builder.append(getExplicitType(genImplements.get(0))); + builder.append(getExplicitType(genImplements.get(0), + availableImports, currentPkg)); + for (int i = 1; i < genImplements.size(); ++i) { builder.append(", "); - builder.append(getExplicitType(genImplements.get(i))); + builder.append(getExplicitType(genImplements.get(i), + availableImports, currentPkg)); } } @@ -155,18 +151,22 @@ public class GeneratorUtil { } public static String createConstant(final Constant constant, - final String indent) { + final String indent, + final Map> availableImports, + final String currentPkg) { final StringBuilder builder = new StringBuilder(); builder.append(indent + PUBLIC + GAP + STATIC + GAP + FINAL + GAP); - builder.append(getExplicitType(constant.getType()) + GAP - + constant.getName()); + builder.append(getExplicitType(constant.getType(), availableImports, + currentPkg) + GAP + constant.getName()); builder.append(GAP + "=" + GAP); builder.append(constant.getValue() + SC); return builder.toString(); } public static String createField(final GeneratedProperty property, - final String indent) { + final String indent, + Map> availableImports, + final String currentPkg) { final StringBuilder builder = new StringBuilder(); builder.append(indent); if (!property.getAnnotations().isEmpty()) { @@ -175,23 +175,28 @@ public class GeneratorUtil { builder.append(NL); } builder.append(indent + PRIVATE + GAP); - builder.append(getExplicitType(property.getReturnType()) + GAP - + property.getName()); + builder.append(getExplicitType(property.getReturnType(), + availableImports, currentPkg) + GAP + property.getName()); builder.append(SC); return builder.toString(); } /** * Create method declaration in interface. - * + * * @param method * @param indent * @return */ public static String createMethodDeclaration(final MethodSignature method, - final String indent) { + final String indent, + Map> availableImports, + final String currentPkg) { + final StringBuilder builder = new StringBuilder(); + if (method == null) { - throw new IllegalArgumentException("Method Signature parameter MUST be specified and cannot be NULL!"); + throw new IllegalArgumentException( + "Method Signature parameter MUST be specified and cannot be NULL!"); } final String comment = method.getComment(); @@ -202,12 +207,12 @@ public class GeneratorUtil { final Type type = method.getReturnType(); if (type == null) { - throw new IllegalStateException("Method Return type cannot be NULL!"); + throw new IllegalStateException( + "Method Return type cannot be NULL!"); } final List parameters = method.getParameters(); - final StringBuilder builder = new StringBuilder(); createComment(builder, comment, indent); builder.append(NL); builder.append(indent); @@ -218,7 +223,9 @@ public class GeneratorUtil { builder.append(NL); } - builder.append(indent + getExplicitType(type) + GAP + name); + builder.append(indent + + getExplicitType(type, availableImports, currentPkg) + GAP + + name); builder.append(LB); for (int i = 0; i < parameters.size(); i++) { Parameter p = parameters.get(i); @@ -226,8 +233,8 @@ public class GeneratorUtil { if (i + 1 == parameters.size()) { separator = ""; } - builder.append(getExplicitType(p.getType()) + GAP + p.getName() - + separator); + builder.append(getExplicitType(p.getType(), availableImports, + currentPkg) + GAP + p.getName() + separator); } builder.append(RB); builder.append(SC); @@ -236,9 +243,11 @@ public class GeneratorUtil { } public static String createConstructor( - GeneratedTransferObject genTransferObject, final String indent) { + GeneratedTransferObject genTransferObject, final String indent, + Map> availableImports) { final StringBuilder builder = new StringBuilder(); + final String currentPkg = genTransferObject.getPackageName(); final List properties = genTransferObject .getProperties(); final List ctorParams = new ArrayList(); @@ -247,21 +256,23 @@ public class GeneratorUtil { ctorParams.add(property); } } - + builder.append(indent); builder.append(PUBLIC); builder.append(GAP); builder.append(genTransferObject.getName()); builder.append(LB); - + if (!ctorParams.isEmpty()) { - builder.append(getExplicitType(ctorParams.get(0).getReturnType())); + builder.append(getExplicitType(ctorParams.get(0).getReturnType(), + availableImports, currentPkg)); builder.append(" "); builder.append(ctorParams.get(0).getName()); for (int i = 1; i < ctorParams.size(); ++i) { final GeneratedProperty param = ctorParams.get(i); builder.append(", "); - builder.append(getExplicitType(param.getReturnType())); + builder.append(getExplicitType(param.getReturnType(), + availableImports, currentPkg)); builder.append(GAP); builder.append(param.getName()); } @@ -285,7 +296,9 @@ public class GeneratorUtil { } public static String createGetter(final GeneratedProperty property, - final String indent) { + final String indent, + Map> availableImports, + final String currentPkg) { final StringBuilder builder = new StringBuilder(); final Type type = property.getReturnType(); @@ -293,7 +306,8 @@ public class GeneratorUtil { final char first = Character.toUpperCase(varName.charAt(0)); final String methodName = "get" + first + varName.substring(1); - builder.append(indent + PUBLIC + GAP + getExplicitType(type) + GAP + builder.append(indent + PUBLIC + GAP + + getExplicitType(type, availableImports, currentPkg) + GAP + methodName); builder.append(LB + RB + LCB + NL); @@ -304,9 +318,11 @@ public class GeneratorUtil { builder.append(indent + RCB); return builder.toString(); } - + public static String createSetter(final GeneratedProperty property, - final String indent) { + final String indent, + Map> availableImports, + String currentPkg) { final StringBuilder builder = new StringBuilder(); final Type type = property.getReturnType(); @@ -314,11 +330,12 @@ public class GeneratorUtil { final char first = Character.toUpperCase(varName.charAt(0)); final String methodName = "set" + first + varName.substring(1); - builder.append(indent + PUBLIC + GAP + "void" + GAP - + methodName); - builder.append(LB + getExplicitType(type) + GAP + varName + RB + LCB + NL); + builder.append(indent + PUBLIC + GAP + "void" + GAP + methodName); + builder.append(LB + getExplicitType(type, availableImports, currentPkg) + + GAP + varName + RB + LCB + NL); String currentIndent = indent + TAB; - builder.append(currentIndent + "this." + varName + " = " + varName + SC + NL); + builder.append(currentIndent + "this." + varName + " = " + varName + SC + + NL); builder.append(indent + RCB); return builder.toString(); } @@ -329,7 +346,7 @@ public class GeneratorUtil { builder.append(indent + "public int hashCode() {" + NL); builder.append(indent + TAB + "final int prime = 31;" + NL); builder.append(indent + TAB + "int result = 1;" + NL); - + for (GeneratedProperty property : properties) { String fieldName = property.getName(); builder.append(indent + TAB + "result = prime * result + ((" @@ -346,8 +363,8 @@ public class GeneratorUtil { final List properties, final String indent) { StringBuilder builder = new StringBuilder(); final String indent1 = indent + TAB; - final String indent2 = indent + TAB + TAB; - final String indent3 = indent + TAB + TAB + TAB; + final String indent2 = indent1 + TAB; + final String indent3 = indent2 + TAB; builder.append(indent + "public boolean equals(Object obj) {" + NL); builder.append(indent1 + "if (this == obj) {" + NL); @@ -360,7 +377,7 @@ public class GeneratorUtil { builder.append(indent2 + "return false;" + NL); builder.append(indent1 + "}" + NL); - String typeStr = type.getPackageName() + "." + type.getName(); + String typeStr = type.getName(); builder.append(indent1 + typeStr + " other = (" + typeStr + ") obj;" + NL); @@ -461,31 +478,59 @@ public class GeneratorUtil { return builder.toString(); } - private static String getExplicitType(final Type type) { + private static String getExplicitType(final Type type, + Map> availableImports, + final String currentPkg) { if (type == null) { - throw new IllegalArgumentException("Type parameter MUST be specified and cannot be NULL!"); + throw new IllegalArgumentException( + "Type parameter MUST be specified and cannot be NULL!"); } String packageName = type.getPackageName(); - if (packageName.endsWith(".")) { - packageName = packageName.substring(0, packageName.length() - 1); - } - final StringBuilder builder = new StringBuilder(packageName + "." - + type.getName()); - if (type instanceof ParameterizedType) { - final ParameterizedType pType = (ParameterizedType) type; - Type[] pTypes = pType.getActualTypeArguments(); - builder.append("<"); - builder.append(getParameters(pTypes)); - builder.append(">"); - } - if (builder.toString().equals("java.lang.Void")) { - return "void"; + LinkedHashMap imports = availableImports.get(type + .getName()); + + if ((imports != null && packageName + .equals(findMaxValue(imports).get(0))) + || packageName.equals(currentPkg)) { + final StringBuilder builder = new StringBuilder(type.getName()); + if (type instanceof ParameterizedType) { + ParameterizedType pType = (ParameterizedType) type; + Type[] pTypes = pType.getActualTypeArguments(); + builder.append("<"); + builder.append(getParameters(pTypes, availableImports, + currentPkg)); + builder.append(">"); + } + if (builder.toString().equals("Void")) { + return "void"; + } + return builder.toString(); + } else { + final StringBuilder builder = new StringBuilder(); + if (packageName.startsWith("java.lang")) { + builder.append(type.getName()); + } else { + builder.append(packageName + "." + type.getName()); + } + if (type instanceof ParameterizedType) { + ParameterizedType pType = (ParameterizedType) type; + Type[] pTypes = pType.getActualTypeArguments(); + builder.append("<"); + builder.append(getParameters(pTypes, availableImports, + currentPkg)); + builder.append(">"); + } + if (builder.toString().equals("Void")) { + return "void"; + } + return builder.toString(); } - return builder.toString(); } - private static String getParameters(final Type[] pTypes) { + private static String getParameters(final Type[] pTypes, + Map> availableImports, + String currentPkg) { final StringBuilder builder = new StringBuilder(); for (int i = 0; i < pTypes.length; i++) { Type t = pTypes[i]; @@ -494,11 +539,30 @@ public class GeneratorUtil { if (i + 1 == pTypes.length) { separator = ""; } - builder.append(getExplicitType(t) + separator); + builder.append(getExplicitType(t, availableImports, currentPkg) + + separator); } return builder.toString(); } + private static List findMaxValue( + LinkedHashMap imports) { + final List result = new ArrayList(); + + int maxValue = 0; + int currentValue = 0; + for (Map.Entry entry : imports.entrySet()) { + currentValue = entry.getValue(); + if (currentValue > maxValue) { + result.clear(); + result.add(entry.getKey()); + } else if (currentValue == maxValue) { + result.add(entry.getKey()); + } + } + return result; + } + private static void createComment(final StringBuilder builder, final String comment, final String indent) { if (comment != null && comment.length() > 0) { @@ -508,4 +572,101 @@ public class GeneratorUtil { } } + public static Map> createImports( + GeneratedType genType) { + final Map> imports = new HashMap>(); + final String genTypePkg = genType.getPackageName(); + + final List constants = genType.getConstantDefinitions(); + final List methods = genType.getMethodDefinitions(); + List impl = genType.getImplements(); + + // IMPLEMENTATIONS + if (impl != null) { + for (Type t : impl) { + addTypeToImports(t, imports, genTypePkg); + } + } + + // CONSTANTS + if (constants != null) { + for (Constant c : constants) { + Type ct = c.getType(); + addTypeToImports(ct, imports, genTypePkg); + } + } + + // METHODS + if (methods != null) { + for (MethodSignature m : methods) { + Type ct = m.getReturnType(); + addTypeToImports(ct, imports, genTypePkg); + for (MethodSignature.Parameter p : m.getParameters()) { + addTypeToImports(p.getType(), imports, genTypePkg); + } + } + } + + // PROPERTIES + if (genType instanceof GeneratedTransferObject) { + GeneratedTransferObject genTO = (GeneratedTransferObject) genType; + + List props = genTO.getProperties(); + if (props != null) { + for (GeneratedProperty prop : props) { + Type pt = prop.getReturnType(); + addTypeToImports(pt, imports, genTypePkg); + } + } + } + + return imports; + } + + private static void addTypeToImports(Type type, + Map> importedTypes, + String genTypePkg) { + String typeName = type.getName(); + String typePkg = type.getPackageName(); + if (typePkg.startsWith("java.lang") || typePkg.equals(genTypePkg)) { + return; + } + LinkedHashMap packages = importedTypes.get(typeName); + if (packages == null) { + packages = new LinkedHashMap(); + packages.put(typePkg, 1); + importedTypes.put(typeName, packages); + } else { + Integer occurrence = packages.get(typePkg); + if (occurrence == null) { + packages.put(typePkg, 1); + } else { + occurrence++; + packages.put(typePkg, occurrence); + } + } + + if (type instanceof ParameterizedType) { + ParameterizedType pt = (ParameterizedType) type; + Type[] params = pt.getActualTypeArguments(); + for (Type param : params) { + addTypeToImports(param, importedTypes, genTypePkg); + } + } + } + + public static List createImportLines( + Map> imports) { + List importLines = new ArrayList(); + + for (Map.Entry> entry : imports + .entrySet()) { + String typeName = entry.getKey(); + LinkedHashMap typePkgMap = entry.getValue(); + String typePkg = typePkgMap.keySet().iterator().next(); + importLines.add("import " + typePkg + "." + typeName + SC); + } + return importLines; + } + } diff --git a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/InterfaceGenerator.java b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/InterfaceGenerator.java index 51ce324eb4..abaf4fad21 100644 --- a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/InterfaceGenerator.java +++ b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/main/java/org/opendaylight/controller/sal/java/api/generator/InterfaceGenerator.java @@ -7,14 +7,14 @@ */ package org.opendaylight.controller.sal.java.api.generator; -import static org.opendaylight.controller.sal.java.api.generator.Constants.NL; -import static org.opendaylight.controller.sal.java.api.generator.Constants.RCB; -import static org.opendaylight.controller.sal.java.api.generator.Constants.TAB; +import static org.opendaylight.controller.sal.java.api.generator.Constants.*; import java.io.IOException; import java.io.StringWriter; import java.io.Writer; +import java.util.LinkedHashMap; import java.util.List; +import java.util.Map; import org.opendaylight.controller.sal.binding.model.api.CodeGenerator; import org.opendaylight.controller.sal.binding.model.api.Constant; @@ -26,31 +26,47 @@ import org.opendaylight.controller.sal.binding.model.api.Type; public class InterfaceGenerator implements CodeGenerator { + private Map> imports; + public Writer generate(Type type) throws IOException { Writer writer = new StringWriter(); - if (type instanceof GeneratedType && !(type instanceof GeneratedTransferObject)) { + if (type instanceof GeneratedType + && !(type instanceof GeneratedTransferObject)) { GeneratedType genType = (GeneratedType) type; + imports = GeneratorUtil.createImports(genType); + final String currentPkg = genType.getPackageName(); final List constants = genType.getConstantDefinitions(); final List methods = genType .getMethodDefinitions(); final List enums = genType.getEnumDefintions(); - writer.write(GeneratorUtil.createIfcDeclarationWithPkgName(genType, - "")); + writer.write(GeneratorUtil.createPackageDeclaration(genType + .getPackageName())); + writer.write(NL); + + List importLines = GeneratorUtil.createImportLines(imports); + for (String line : importLines) { + writer.write(line + NL); + } + writer.write(NL); + + writer.write(GeneratorUtil.createIfcDeclaration(genType, "", + imports)); writer.write(NL); if (constants != null) { for (Constant c : constants) { - writer.write(GeneratorUtil.createConstant(c, TAB) + NL); + writer.write(GeneratorUtil.createConstant(c, TAB, imports, + currentPkg) + NL); } writer.write(NL); } if (methods != null) { for (MethodSignature m : methods) { - writer.write(GeneratorUtil.createMethodDeclaration(m, TAB) - + NL); + writer.write(GeneratorUtil.createMethodDeclaration(m, TAB, + imports, currentPkg) + NL); } writer.write(NL); } diff --git a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/test/java/org/opendaylight/controller/sal/java/api/generator/test/ClassCodeGeneratorTest.java b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/test/java/org/opendaylight/controller/sal/java/api/generator/test/ClassCodeGeneratorTest.java index ea505cce97..3295becba6 100644 --- a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/test/java/org/opendaylight/controller/sal/java/api/generator/test/ClassCodeGeneratorTest.java +++ b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/test/java/org/opendaylight/controller/sal/java/api/generator/test/ClassCodeGeneratorTest.java @@ -1,8 +1,6 @@ package org.opendaylight.controller.sal.java.api.generator.test; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertNotNull; -import static org.junit.Assert.assertTrue; +import static org.junit.Assert.*; import java.io.File; import java.io.IOException; @@ -73,7 +71,7 @@ public class ClassCodeGeneratorTest { propertyCount++; } } - + final ClassCodeGenerator clsGen = new ClassCodeGenerator(); try { final Writer writer = clsGen.generate(genTO); @@ -81,16 +79,16 @@ public class ClassCodeGeneratorTest { final String outputStr = writer.toString(); writer.close(); - + assertNotNull(outputStr); assertTrue(outputStr - .contains("public CompositeKeyListKey(java.lang.String Key2, " + - "java.lang.Byte Key1)")); + .contains("public CompositeKeyListKey(String Key2, " + + "Byte Key1)")); } catch (IOException e) { e.printStackTrace(); } - + assertEquals(2, propertyCount); genTOsCount++; } else if (genTO.getName().equals("InnerListKey")) { @@ -108,18 +106,19 @@ public class ClassCodeGeneratorTest { @Test public void defaultConstructorTest() { - final GeneratedTOBuilder toBuilder = new GeneratedTOBuilderImpl("simple.pack", "DefCtor"); - + final GeneratedTOBuilder toBuilder = new GeneratedTOBuilderImpl( + "simple.pack", "DefCtor"); + GeneratedPropertyBuilder propBuilder = toBuilder.addProperty("foo"); propBuilder.addReturnType(Types.typeForClass(String.class)); propBuilder.setReadOnly(false); - + propBuilder = toBuilder.addProperty("bar"); propBuilder.addReturnType(Types.typeForClass(Integer.class)); propBuilder.setReadOnly(false); - + final GeneratedTransferObject genTO = toBuilder.toInstance(); - + final ClassCodeGenerator clsGen = new ClassCodeGenerator(); try { final Writer writer = clsGen.generate(genTO); @@ -127,10 +126,9 @@ public class ClassCodeGeneratorTest { final String outputStr = writer.toString(); writer.close(); - + assertNotNull(outputStr); - assertTrue(outputStr - .contains("public DefCtor()")); + assertTrue(outputStr.contains("public DefCtor()")); } catch (IOException e) { e.printStackTrace(); diff --git a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/test/java/org/opendaylight/controller/sal/java/api/generator/test/GeneratorJavaFileTest.java b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/test/java/org/opendaylight/controller/sal/java/api/generator/test/GeneratorJavaFileTest.java index 6c40c40cb1..076e2482ba 100644 --- a/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/test/java/org/opendaylight/controller/sal/java/api/generator/test/GeneratorJavaFileTest.java +++ b/opendaylight/sal/yang-prototype/code-generator/binding-java-api-generator/src/test/java/org/opendaylight/controller/sal/java/api/generator/test/GeneratorJavaFileTest.java @@ -7,9 +7,23 @@ */ package org.opendaylight.controller.sal.java.api.generator.test; +import static org.junit.Assert.*; + +import java.io.File; +import java.io.IOException; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.HashSet; +import java.util.List; +import java.util.Set; + +import javax.tools.JavaCompiler; +import javax.tools.JavaFileObject; +import javax.tools.StandardJavaFileManager; +import javax.tools.ToolProvider; + import org.junit.After; import org.junit.Before; -import org.junit.Ignore; import org.junit.Test; import org.opendaylight.controller.binding.generator.util.generated.type.builder.GeneratedTypeBuilderImpl; import org.opendaylight.controller.sal.binding.generator.api.BindingGenerator; @@ -24,39 +38,34 @@ import org.opendaylight.controller.yang.model.api.Module; import org.opendaylight.controller.yang.model.api.SchemaContext; import org.opendaylight.controller.yang.parser.impl.YangParserImpl; -import javax.tools.JavaCompiler; -import javax.tools.JavaFileObject; -import javax.tools.StandardJavaFileManager; -import javax.tools.ToolProvider; -import java.io.File; -import java.io.IOException; -import java.util.*; - -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertTrue; - public class GeneratorJavaFileTest { private static final String FS = File.separator; - private static final String PATH = "test-dir"; + private static final String PATH = "target/test/test-dir"; private final File testDir = new File(PATH); - private static final String GENERATOR_OUTPUT_PATH = "src/test/resources/src"; + private static final String GENERATOR_OUTPUT_PATH = "target/test/src"; private static final File GENERATOR_OUTPUT = new File(GENERATOR_OUTPUT_PATH); - private static final String COMPILER_OUTPUT_PATH = "src/test/resources/bin"; + private static final String COMPILER_OUTPUT_PATH = "target/test/bin"; private static final File COMPILER_OUTPUT = new File(COMPILER_OUTPUT_PATH); @Before public void init() { - assertTrue(testDir.mkdir()); + assertTrue(testDir.mkdirs()); assertTrue(COMPILER_OUTPUT.mkdirs()); assertTrue(GENERATOR_OUTPUT.mkdirs()); } @After public void cleanUp() { - deleteTestDir(testDir); - deleteTestDir(COMPILER_OUTPUT); - deleteTestDir(GENERATOR_OUTPUT); + if(testDir.exists()) { + deleteTestDir(testDir); + } + if(COMPILER_OUTPUT.exists()) { + deleteTestDir(COMPILER_OUTPUT); + } + if(GENERATOR_OUTPUT.exists()) { + deleteTestDir(GENERATOR_OUTPUT); + } } @Test @@ -85,7 +94,6 @@ public class GeneratorJavaFileTest { assertTrue(filesList.contains("Type3.java")); } - @Ignore @Test public void compilationTest() throws Exception { final YangParserImpl parser = new YangParserImpl(); diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/antlr/YangParser.g4 b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/antlr/YangParser.g4 index eea482a095..36aff55124 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/antlr/YangParser.g4 +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/antlr/YangParser.g4 @@ -53,8 +53,9 @@ container_stmt : CONTAINER_KEYWORD string (SEMICOLON | (LEFT_BRACE (identifier_ grouping_stmt : GROUPING_KEYWORD string (SEMICOLON | (LEFT_BRACE (identifier_stmt |status_stmt | description_stmt | reference_stmt | typedef_stmt | grouping_stmt | data_def_stmt )* RIGHT_BRACE)); value_stmt : VALUE_KEYWORD string stmtend; max_value_arg : /*UNBOUNDED_KEYWORD |*/ string; +min_value_arg : /*UNBOUNDED_KEYWORD |*/ string; max_elements_stmt : MAX_ELEMENTS_KEYWORD max_value_arg stmtend; -min_elements_stmt : MIN_ELEMENTS_KEYWORD string stmtend; +min_elements_stmt : MIN_ELEMENTS_KEYWORD min_value_arg stmtend; error_app_tag_stmt : ERROR_APP_TAG_KEYWORD string stmtend; error_message_stmt : ERROR_MESSAGE_KEYWORD string stmtend; must_stmt : MUST_KEYWORD string (SEMICOLON | (LEFT_BRACE (identifier_stmt |error_message_stmt | error_app_tag_stmt | description_stmt | reference_stmt )* RIGHT_BRACE)); diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/api/UsesNodeBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/api/UsesNodeBuilder.java index b3e8ad226e..7ac4ec01be 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/api/UsesNodeBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/api/UsesNodeBuilder.java @@ -19,11 +19,17 @@ import org.opendaylight.controller.yang.parser.util.RefineHolder; public interface UsesNodeBuilder extends Builder { SchemaPath getGroupingPath(); + void addAugment(AugmentationSchemaBuilder builder); + void setAugmenting(boolean augmenting); + List getRefines(); + void addRefine(RefineHolder refine); + void addRefineNode(SchemaNodeBuilder refineNode); + UsesNode build(); } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/AnyXmlBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/AnyXmlBuilder.java index 4b95ab9dcb..7d9e3ea8b7 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/AnyXmlBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/AnyXmlBuilder.java @@ -18,8 +18,10 @@ import org.opendaylight.controller.yang.model.api.SchemaPath; import org.opendaylight.controller.yang.model.api.Status; import org.opendaylight.controller.yang.model.api.UnknownSchemaNode; import org.opendaylight.controller.yang.parser.builder.api.DataSchemaNodeBuilder; +import org.opendaylight.controller.yang.parser.util.YangParseException; public class AnyXmlBuilder implements DataSchemaNodeBuilder { + private boolean built; private final int line; private final QName qname; private SchemaPath path; @@ -41,20 +43,23 @@ public class AnyXmlBuilder implements DataSchemaNodeBuilder { @Override public AnyXmlSchemaNode build() { - instance.setPath(path); - instance.setConstraints(constraints.build()); - instance.setDescription(description); - instance.setReference(reference); - instance.setStatus(status); - - // UNKNOWN NODES - final List unknownNodes = new ArrayList(); - for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { - unknownNodes.add(b.build()); - } - instance.setUnknownSchemaNodes(unknownNodes); + if (!built) { + instance.setPath(path); + instance.setConstraints(constraints.build()); + instance.setDescription(description); + instance.setReference(reference); + instance.setStatus(status); + instance.setConfiguration(configuration); + + // UNKNOWN NODES + final List unknownNodes = new ArrayList(); + for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { + unknownNodes.add(b.build()); + } + instance.setUnknownSchemaNodes(unknownNodes); - instance.setConfiguration(configuration); + built = true; + } return instance; } @@ -122,7 +127,7 @@ public class AnyXmlBuilder implements DataSchemaNodeBuilder { @Override public void setAugmenting(final boolean augmenting) { - throw new UnsupportedOperationException( + throw new YangParseException(line, "An anyxml node cannot be augmented."); } @@ -135,7 +140,7 @@ public class AnyXmlBuilder implements DataSchemaNodeBuilder { instance.setConfiguration(configuration); } - private class AnyXmlSchemaNodeImpl implements AnyXmlSchemaNode { + private final class AnyXmlSchemaNodeImpl implements AnyXmlSchemaNode { private final QName qname; private SchemaPath path; private String description; diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/AugmentationSchemaBuilderImpl.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/AugmentationSchemaBuilderImpl.java index 70079b39aa..a5db03b2e7 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/AugmentationSchemaBuilderImpl.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/AugmentationSchemaBuilderImpl.java @@ -29,8 +29,10 @@ import org.opendaylight.controller.yang.parser.builder.api.GroupingBuilder; import org.opendaylight.controller.yang.parser.builder.api.TypeDefinitionBuilder; import org.opendaylight.controller.yang.parser.builder.api.UsesNodeBuilder; import org.opendaylight.controller.yang.parser.util.YangModelBuilderUtil; +import org.opendaylight.controller.yang.parser.util.YangParseException; public class AugmentationSchemaBuilderImpl implements AugmentationSchemaBuilder { + private boolean built; private final AugmentationSchemaImpl instance; private final int line; private final String augmentTargetStr; @@ -94,37 +96,40 @@ public class AugmentationSchemaBuilderImpl implements AugmentationSchemaBuilder @Override public AugmentationSchema build() { - instance.setTargetPath(finalAugmentTarget); + if (!built) { + instance.setTargetPath(finalAugmentTarget); - RevisionAwareXPath whenStmt; - if (whenCondition == null) { - whenStmt = null; - } else { - whenStmt = new RevisionAwareXPathImpl(whenCondition, false); - } - instance.setWhenCondition(whenStmt); + RevisionAwareXPath whenStmt; + if (whenCondition == null) { + whenStmt = null; + } else { + whenStmt = new RevisionAwareXPathImpl(whenCondition, false); + } + instance.setWhenCondition(whenStmt); - // CHILD NODES - final Map childs = new HashMap(); - for (DataSchemaNodeBuilder node : childNodes) { - childs.put(node.getQName(), node.build()); - } - instance.setChildNodes(childs); + // CHILD NODES + final Map childs = new HashMap(); + for (DataSchemaNodeBuilder node : childNodes) { + childs.put(node.getQName(), node.build()); + } + instance.setChildNodes(childs); - // GROUPINGS - final Set groupingDefinitions = new HashSet(); - for (GroupingBuilder builder : groupings) { - groupingDefinitions.add(builder.build()); - } - instance.setGroupings(groupingDefinitions); + // GROUPINGS + final Set groupingDefinitions = new HashSet(); + for (GroupingBuilder builder : groupings) { + groupingDefinitions.add(builder.build()); + } + instance.setGroupings(groupingDefinitions); - // USES - final Set usesNodeDefinitions = new HashSet(); - for (UsesNodeBuilder builder : usesNodes) { - usesNodeDefinitions.add(builder.build()); - } - instance.setUses(usesNodeDefinitions); + // USES + final Set usesNodeDefinitions = new HashSet(); + for (UsesNodeBuilder builder : usesNodes) { + usesNodeDefinitions.add(builder.build()); + } + instance.setUses(usesNodeDefinitions); + built = true; + } return instance; } @@ -148,7 +153,7 @@ public class AugmentationSchemaBuilderImpl implements AugmentationSchemaBuilder @Override public void addTypedef(TypeDefinitionBuilder type) { - throw new UnsupportedOperationException( + throw new YangParseException(line, "Augmentation can not contains type definitions"); } @@ -186,7 +191,8 @@ public class AugmentationSchemaBuilderImpl implements AugmentationSchemaBuilder public int hashCode() { final int prime = 17; int result = 1; - result = prime * result + result = prime + * result + ((augmentTargetStr == null) ? 0 : augmentTargetStr.hashCode()); result = prime * result + ((whenCondition == null) ? 0 : whenCondition.hashCode()); @@ -231,8 +237,7 @@ public class AugmentationSchemaBuilderImpl implements AugmentationSchemaBuilder return true; } - - private static class AugmentationSchemaImpl implements AugmentationSchema { + private final class AugmentationSchemaImpl implements AugmentationSchema { private SchemaPath targetPath; private RevisionAwareXPath whenCondition; private Map childNodes = Collections.emptyMap(); diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ChoiceBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ChoiceBuilder.java index 7f3680ee53..04e7d33478 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ChoiceBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ChoiceBuilder.java @@ -28,9 +28,11 @@ import org.opendaylight.controller.yang.parser.builder.api.DataSchemaNodeBuilder import org.opendaylight.controller.yang.parser.builder.api.GroupingBuilder; import org.opendaylight.controller.yang.parser.builder.api.TypeDefinitionBuilder; import org.opendaylight.controller.yang.parser.builder.api.UsesNodeBuilder; +import org.opendaylight.controller.yang.parser.util.YangParseException; public class ChoiceBuilder implements DataSchemaNodeBuilder, ChildNodeBuilder, AugmentationTargetBuilder { + private boolean built; private final ChoiceNodeImpl instance; private final int line; // SchemaNode args @@ -62,36 +64,39 @@ public class ChoiceBuilder implements DataSchemaNodeBuilder, ChildNodeBuilder, @Override public ChoiceNode build() { - instance.setPath(schemaPath); - instance.setDescription(description); - instance.setReference(reference); - instance.setStatus(status); - instance.setAugmenting(augmenting); - instance.setConfiguration(configuration); - instance.setConstraints(constraints.build()); - instance.setDefaultCase(defaultCase); - - // CASES - final Set choiceCases = new HashSet(); - for (ChoiceCaseBuilder caseBuilder : cases) { - choiceCases.add(caseBuilder.build()); - } - instance.setCases(choiceCases); + if (!built) { + instance.setPath(schemaPath); + instance.setDescription(description); + instance.setReference(reference); + instance.setStatus(status); + instance.setAugmenting(augmenting); + instance.setConfiguration(configuration); + instance.setConstraints(constraints.build()); + instance.setDefaultCase(defaultCase); + + // CASES + final Set choiceCases = new HashSet(); + for (ChoiceCaseBuilder caseBuilder : cases) { + choiceCases.add(caseBuilder.build()); + } + instance.setCases(choiceCases); - // AUGMENTATIONS - final Set augmentations = new HashSet(); - for (AugmentationSchemaBuilder builder : addedAugmentations) { - augmentations.add(builder.build()); - } - instance.setAvailableAugmentations(augmentations); + // AUGMENTATIONS + final Set augmentations = new HashSet(); + for (AugmentationSchemaBuilder builder : addedAugmentations) { + augmentations.add(builder.build()); + } + instance.setAvailableAugmentations(augmentations); - // UNKNOWN NODES - final List unknownNodes = new ArrayList(); - for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { - unknownNodes.add(b.build()); - } - instance.setUnknownSchemaNodes(unknownNodes); + // UNKNOWN NODES + final List unknownNodes = new ArrayList(); + for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { + unknownNodes.add(b.build()); + } + instance.setUnknownSchemaNodes(unknownNodes); + built = true; + } return instance; } @@ -125,7 +130,7 @@ public class ChoiceBuilder implements DataSchemaNodeBuilder, ChildNodeBuilder, * Choice can not contains grouping statements, so this method always * returns an empty set. * - * @return + * @return empty set */ public Set getGroupings() { return Collections.emptySet(); @@ -133,7 +138,7 @@ public class ChoiceBuilder implements DataSchemaNodeBuilder, ChildNodeBuilder, @Override public void addGrouping(GroupingBuilder groupingBuilder) { - throw new IllegalStateException( + throw new YangParseException(line, "Can not add grouping to 'choice' node."); } @@ -247,7 +252,7 @@ public class ChoiceBuilder implements DataSchemaNodeBuilder, ChildNodeBuilder, return new HashSet(cases); } - private static class ChoiceNodeImpl implements ChoiceNode { + private class ChoiceNodeImpl implements ChoiceNode { private final QName qname; private SchemaPath path; private String description; diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ChoiceCaseBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ChoiceCaseBuilder.java index d86db6d920..a3b21b4abf 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ChoiceCaseBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ChoiceCaseBuilder.java @@ -23,6 +23,7 @@ import org.opendaylight.controller.yang.parser.builder.api.AbstractChildNodeBuil import org.opendaylight.controller.yang.parser.builder.api.DataSchemaNodeBuilder; import org.opendaylight.controller.yang.parser.builder.api.TypeDefinitionBuilder; import org.opendaylight.controller.yang.parser.builder.api.UsesNodeBuilder; +import org.opendaylight.controller.yang.parser.util.YangParseException; public final class ChoiceCaseBuilder extends AbstractChildNodeBuilder implements DataSchemaNodeBuilder { @@ -151,13 +152,13 @@ public final class ChoiceCaseBuilder extends AbstractChildNodeBuilder implements @Override public void addTypedef(TypeDefinitionBuilder typedefBuilder) { - throw new UnsupportedOperationException( + throw new YangParseException(line, "Can not add type definition to choice case."); } @Override public void setConfiguration(boolean configuration) { - throw new UnsupportedOperationException( + throw new YangParseException(line, "Can not add config definition to choice case."); } @@ -372,7 +373,6 @@ public final class ChoiceCaseBuilder extends AbstractChildNodeBuilder implements sb.append("]"); return sb.toString(); } - } } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ContainerSchemaNodeBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ContainerSchemaNodeBuilder.java index 81a701c66a..e12a3a9f4d 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ContainerSchemaNodeBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ContainerSchemaNodeBuilder.java @@ -38,6 +38,7 @@ import org.opendaylight.controller.yang.parser.builder.api.UsesNodeBuilder; public class ContainerSchemaNodeBuilder extends AbstractChildNodeBuilder implements TypeDefinitionAwareBuilder, AugmentationTargetBuilder, DataSchemaNodeBuilder { + private boolean built; private final ContainerSchemaNodeImpl instance; private final int line; private final ConstraintsBuilder constraints; @@ -63,59 +64,62 @@ public class ContainerSchemaNodeBuilder extends AbstractChildNodeBuilder @Override public ContainerSchemaNode build() { - instance.setPath(schemaPath); - instance.setDescription(description); - instance.setReference(reference); - instance.setStatus(status); - instance.setPresenceContainer(presence); - instance.setAugmenting(augmenting); - instance.setConfiguration(configuration); - - // CHILD NODES - final Map childs = new HashMap(); - for (DataSchemaNodeBuilder node : childNodes) { - childs.put(node.getQName(), node.build()); - } - instance.setChildNodes(childs); + if(!built) { + instance.setPath(schemaPath); + instance.setDescription(description); + instance.setReference(reference); + instance.setStatus(status); + instance.setPresenceContainer(presence); + instance.setAugmenting(augmenting); + instance.setConfiguration(configuration); + + // CHILD NODES + final Map childs = new HashMap(); + for (DataSchemaNodeBuilder node : childNodes) { + childs.put(node.getQName(), node.build()); + } + instance.setChildNodes(childs); - // GROUPINGS - final Set groupingDefs = new HashSet(); - for (GroupingBuilder builder : groupings) { - groupingDefs.add(builder.build()); - } - instance.setGroupings(groupingDefs); + // GROUPINGS + final Set groupingDefs = new HashSet(); + for (GroupingBuilder builder : groupings) { + groupingDefs.add(builder.build()); + } + instance.setGroupings(groupingDefs); - // TYPEDEFS - final Set> typedefs = new HashSet>(); - for (TypeDefinitionBuilder entry : addedTypedefs) { - typedefs.add(entry.build()); - } - instance.setTypeDefinitions(typedefs); + // TYPEDEFS + final Set> typedefs = new HashSet>(); + for (TypeDefinitionBuilder entry : addedTypedefs) { + typedefs.add(entry.build()); + } + instance.setTypeDefinitions(typedefs); - // USES - final Set uses = new HashSet(); - for (UsesNodeBuilder builder : addedUsesNodes) { - uses.add(builder.build()); - } - instance.setUses(uses); + // USES + final Set uses = new HashSet(); + for (UsesNodeBuilder builder : addedUsesNodes) { + uses.add(builder.build()); + } + instance.setUses(uses); - // AUGMENTATIONS - final Set augmentations = new HashSet(); - for(AugmentationSchemaBuilder builder : addedAugmentations) { - augmentations.add(builder.build()); - } - instance.setAvailableAugmentations(augmentations); + // AUGMENTATIONS + final Set augmentations = new HashSet(); + for(AugmentationSchemaBuilder builder : addedAugmentations) { + augmentations.add(builder.build()); + } + instance.setAvailableAugmentations(augmentations); - // UNKNOWN NODES - final List unknownNodes = new ArrayList(); - for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { - unknownNodes.add(b.build()); - } - instance.setUnknownSchemaNodes(unknownNodes); + // UNKNOWN NODES + final List unknownNodes = new ArrayList(); + for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { + unknownNodes.add(b.build()); + } + instance.setUnknownSchemaNodes(unknownNodes); - instance.setConstraints(constraints.build()); - instance.setAvailableAugmentations(augmentations); + instance.setConstraints(constraints.build()); + instance.setAvailableAugmentations(augmentations); + built = true; + } return instance; } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/IdentitySchemaNodeBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/IdentitySchemaNodeBuilder.java index 68fffd26b9..96c4121653 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/IdentitySchemaNodeBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/IdentitySchemaNodeBuilder.java @@ -89,6 +89,8 @@ public final class IdentitySchemaNodeBuilder implements SchemaNodeBuilder { @Override public void addUnknownSchemaNode(final UnknownSchemaNodeBuilder unknownNode) { + + addedUnknownNodes.add(unknownNode); } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/LeafListSchemaNodeBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/LeafListSchemaNodeBuilder.java index 60d8fb4fa7..28f250f121 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/LeafListSchemaNodeBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/LeafListSchemaNodeBuilder.java @@ -24,6 +24,7 @@ import org.opendaylight.controller.yang.parser.builder.api.SchemaNodeBuilder; public class LeafListSchemaNodeBuilder extends AbstractTypeAwareBuilder implements SchemaNodeBuilder, DataSchemaNodeBuilder { + private boolean built; private final LeafListSchemaNodeImpl instance; private final int line; // SchemaNode args @@ -49,28 +50,31 @@ public class LeafListSchemaNodeBuilder extends AbstractTypeAwareBuilder @Override public LeafListSchemaNode build() { - instance.setConstraints(constraints.build()); - instance.setPath(schemaPath); - instance.setDescription(description); - instance.setReference(reference); - instance.setStatus(status); - instance.setAugmenting(augmenting); - instance.setConfiguration(configuration); - instance.setUserOrdered(userOrdered); - - if (type == null) { - instance.setType(typedef.build()); - } else { - instance.setType(type); - } + if (!built) { + instance.setConstraints(constraints.build()); + instance.setPath(schemaPath); + instance.setDescription(description); + instance.setReference(reference); + instance.setStatus(status); + instance.setAugmenting(augmenting); + instance.setConfiguration(configuration); + instance.setUserOrdered(userOrdered); + + if (type == null) { + instance.setType(typedef.build()); + } else { + instance.setType(type); + } - // UNKNOWN NODES - final List unknownNodes = new ArrayList(); - for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { - unknownNodes.add(b.build()); - } - instance.setUnknownSchemaNodes(unknownNodes); + // UNKNOWN NODES + final List unknownNodes = new ArrayList(); + for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { + unknownNodes.add(b.build()); + } + instance.setUnknownSchemaNodes(unknownNodes); + built = true; + } return instance; } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/LeafSchemaNodeBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/LeafSchemaNodeBuilder.java index be58c7ecf5..ee7b3b1c81 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/LeafSchemaNodeBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/LeafSchemaNodeBuilder.java @@ -24,6 +24,7 @@ import org.opendaylight.controller.yang.parser.builder.api.SchemaNodeBuilder; public class LeafSchemaNodeBuilder extends AbstractTypeAwareBuilder implements DataSchemaNodeBuilder, SchemaNodeBuilder { + private boolean built; private final LeafSchemaNodeImpl instance; private final int line; // SchemaNode args @@ -50,30 +51,33 @@ public class LeafSchemaNodeBuilder extends AbstractTypeAwareBuilder implements @Override public LeafSchemaNode build() { - instance.setPath(path); - instance.setConstraints(constraints.build()); - instance.setDescription(description); - instance.setReference(reference); - instance.setStatus(status); - - // TYPE - if (type == null) { - instance.setType(typedef.build()); - } else { - instance.setType(type); - } + if(!built) { + instance.setPath(path); + instance.setConstraints(constraints.build()); + instance.setDescription(description); + instance.setReference(reference); + instance.setStatus(status); + instance.setAugmenting(augmenting); + instance.setConfiguration(configuration); + instance.setDefault(defaultStr); + instance.setUnits(unitsStr); + + // TYPE + if (type == null) { + instance.setType(typedef.build()); + } else { + instance.setType(type); + } - // UNKNOWN NODES - final List unknownNodes = new ArrayList(); - for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { - unknownNodes.add(b.build()); - } - instance.setUnknownSchemaNodes(unknownNodes); + // UNKNOWN NODES + final List unknownNodes = new ArrayList(); + for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { + unknownNodes.add(b.build()); + } + instance.setUnknownSchemaNodes(unknownNodes); - instance.setAugmenting(augmenting); - instance.setConfiguration(configuration); - instance.setDefault(defaultStr); - instance.setUnits(unitsStr); + built = true; + } return instance; } @@ -148,6 +152,8 @@ public class LeafSchemaNodeBuilder extends AbstractTypeAwareBuilder implements this.augmenting = augmenting; } + + public boolean isConfiguration() { return configuration; } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ListSchemaNodeBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ListSchemaNodeBuilder.java index b97399b00b..c9b1e7369b 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ListSchemaNodeBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ListSchemaNodeBuilder.java @@ -38,6 +38,7 @@ import org.opendaylight.controller.yang.parser.builder.api.UsesNodeBuilder; public class ListSchemaNodeBuilder extends AbstractChildNodeBuilder implements DataSchemaNodeBuilder, AugmentationTargetBuilder, TypeDefinitionAwareBuilder { + private boolean built; private final ListSchemaNodeImpl instance; private final int line; // SchemaNode args @@ -68,60 +69,63 @@ public class ListSchemaNodeBuilder extends AbstractChildNodeBuilder implements @Override public ListSchemaNode build() { - instance.setKeyDefinition(keyDefinition); - instance.setPath(schemaPath); - instance.setDescription(description); - instance.setReference(reference); - instance.setStatus(status); - instance.setAugmenting(augmenting); - instance.setConfiguration(configuration); - instance.setUserOrdered(userOrdered); - - // CHILD NODES - final Map childs = new HashMap(); - for (DataSchemaNodeBuilder node : childNodes) { - childs.put(node.getQName(), node.build()); - } - instance.setChildNodes(childs); + if(!built) { + instance.setKeyDefinition(keyDefinition); + instance.setPath(schemaPath); + instance.setDescription(description); + instance.setReference(reference); + instance.setStatus(status); + instance.setAugmenting(augmenting); + instance.setConfiguration(configuration); + instance.setUserOrdered(userOrdered); + + // CHILD NODES + final Map childs = new HashMap(); + for (DataSchemaNodeBuilder node : childNodes) { + childs.put(node.getQName(), node.build()); + } + instance.setChildNodes(childs); - // TYPEDEFS - final Set> typedefs = new HashSet>(); - for (TypeDefinitionBuilder entry : addedTypedefs) { - typedefs.add(entry.build()); - } - instance.setTypeDefinitions(typedefs); + // TYPEDEFS + final Set> typedefs = new HashSet>(); + for (TypeDefinitionBuilder entry : addedTypedefs) { + typedefs.add(entry.build()); + } + instance.setTypeDefinitions(typedefs); - // USES - final Set usesNodeDefs = new HashSet(); - for (UsesNodeBuilder builder : addedUsesNodes) { - usesNodeDefs.add(builder.build()); - } - instance.setUses(usesNodeDefs); + // USES + final Set usesNodeDefs = new HashSet(); + for (UsesNodeBuilder builder : addedUsesNodes) { + usesNodeDefs.add(builder.build()); + } + instance.setUses(usesNodeDefs); - // GROUPINGS - final Set groupingDefs = new HashSet(); - for (GroupingBuilder builder : groupings) { - groupingDefs.add(builder.build()); - } - instance.setGroupings(groupingDefs); + // GROUPINGS + final Set groupingDefs = new HashSet(); + for (GroupingBuilder builder : groupings) { + groupingDefs.add(builder.build()); + } + instance.setGroupings(groupingDefs); - // AUGMENTATIONS - final Set augmentations = new HashSet(); - for (AugmentationSchemaBuilder builder : addedAugmentations) { - augmentations.add(builder.build()); - } - instance.setAvailableAugmentations(augmentations); + // AUGMENTATIONS + final Set augmentations = new HashSet(); + for (AugmentationSchemaBuilder builder : addedAugmentations) { + augmentations.add(builder.build()); + } + instance.setAvailableAugmentations(augmentations); - // UNKNOWN NODES - final List unknownNodes = new ArrayList(); - for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { - unknownNodes.add(b.build()); - } - instance.setUnknownSchemaNodes(unknownNodes); + // UNKNOWN NODES + final List unknownNodes = new ArrayList(); + for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { + unknownNodes.add(b.build()); + } + instance.setUnknownSchemaNodes(unknownNodes); - instance.setConstraints(constraints.build()); - instance.setAvailableAugmentations(augmentations); + instance.setConstraints(constraints.build()); + instance.setAvailableAugmentations(augmentations); + built = true; + } return instance; } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ModuleBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ModuleBuilder.java index f88e8d1495..740f399168 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ModuleBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/ModuleBuilder.java @@ -555,7 +555,7 @@ public class ModuleBuilder implements Builder { .get(pathToAnyXml); if (parent != null) { if (parent instanceof AugmentationSchemaBuilder) { - throw new UnsupportedOperationException( + throw new YangParseException( "An anyxml node cannot be augmented."); } parent.addChildNode(builder); @@ -646,9 +646,11 @@ public class ModuleBuilder implements Builder { Builder builder = moduleNodes.get(parentPath); // current api did not support adding config to deviate if (!(builder instanceof DeviationBuilder)) { - DataSchemaNodeBuilder configBuilder = (DataSchemaNodeBuilder) moduleNodes - .get(parentPath); - configBuilder.setConfiguration(configuration); + if(builder instanceof RefineHolder) { + ((RefineHolder)builder).setConfig(configuration); + } else { + ((DataSchemaNodeBuilder)builder).setConfiguration(configuration); + } } } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/NotificationBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/NotificationBuilder.java index fda7dc7a09..3e9b9307bc 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/NotificationBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/NotificationBuilder.java @@ -35,6 +35,7 @@ import org.opendaylight.controller.yang.parser.builder.api.UsesNodeBuilder; public class NotificationBuilder extends AbstractChildNodeBuilder implements TypeDefinitionAwareBuilder, SchemaNodeBuilder { + private boolean built; private final NotificationDefinitionImpl instance; private final int line; private SchemaPath schemaPath; @@ -50,42 +51,46 @@ public class NotificationBuilder extends AbstractChildNodeBuilder implements @Override public SchemaNode build() { - instance.setPath(schemaPath); + if(!built) { + instance.setPath(schemaPath); - // CHILD NODES - final Map childs = new HashMap(); - for (DataSchemaNodeBuilder node : childNodes) { - childs.put(node.getQName(), node.build()); - } - instance.setChildNodes(childs); + // CHILD NODES + final Map childs = new HashMap(); + for (DataSchemaNodeBuilder node : childNodes) { + childs.put(node.getQName(), node.build()); + } + instance.setChildNodes(childs); - // GROUPINGS - final Set groupingDefs = new HashSet(); - for (GroupingBuilder builder : groupings) { - groupingDefs.add(builder.build()); - } - instance.setGroupings(groupingDefs); + // GROUPINGS + final Set groupingDefs = new HashSet(); + for (GroupingBuilder builder : groupings) { + groupingDefs.add(builder.build()); + } + instance.setGroupings(groupingDefs); - // TYPEDEFS - final Set> typedefs = new HashSet>(); - for (TypeDefinitionBuilder entry : addedTypedefs) { - typedefs.add(entry.build()); - } - instance.setTypeDefinitions(typedefs); + // TYPEDEFS + final Set> typedefs = new HashSet>(); + for (TypeDefinitionBuilder entry : addedTypedefs) { + typedefs.add(entry.build()); + } + instance.setTypeDefinitions(typedefs); - // USES - final Set uses = new HashSet(); - for (UsesNodeBuilder builder : addedUsesNodes) { - uses.add(builder.build()); - } - instance.setUses(uses); + // USES + final Set uses = new HashSet(); + for (UsesNodeBuilder builder : addedUsesNodes) { + uses.add(builder.build()); + } + instance.setUses(uses); + + // UNKNOWN NODES + final List unknownNodes = new ArrayList(); + for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { + unknownNodes.add(b.build()); + } + instance.setUnknownSchemaNodes(unknownNodes); - // UNKNOWN NODES - final List unknownNodes = new ArrayList(); - for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { - unknownNodes.add(b.build()); + built = true; } - instance.setUnknownSchemaNodes(unknownNodes); return instance; } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/RpcDefinitionBuilder.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/RpcDefinitionBuilder.java index ac25f9bbff..003ccced4a 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/RpcDefinitionBuilder.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/RpcDefinitionBuilder.java @@ -28,6 +28,7 @@ import org.opendaylight.controller.yang.parser.builder.api.TypeDefinitionBuilder public class RpcDefinitionBuilder implements SchemaNodeBuilder, TypeDefinitionAwareBuilder { + private boolean built; private final RpcDefinitionImpl instance; private final int line; private final QName qname; @@ -46,34 +47,37 @@ public class RpcDefinitionBuilder implements SchemaNodeBuilder, @Override public RpcDefinition build() { - final ContainerSchemaNode input = inputBuilder.build(); - final ContainerSchemaNode output = outputBuilder.build(); - instance.setInput(input); - instance.setOutput(output); - - instance.setPath(schemaPath); + if(!built) { + final ContainerSchemaNode input = inputBuilder.build(); + final ContainerSchemaNode output = outputBuilder.build(); + instance.setInput(input); + instance.setOutput(output); + + instance.setPath(schemaPath); + + // TYPEDEFS + final Set> typedefs = new HashSet>(); + for (TypeDefinitionBuilder entry : addedTypedefs) { + typedefs.add(entry.build()); + } + instance.setTypeDefinitions(typedefs); - // TYPEDEFS - final Set> typedefs = new HashSet>(); - for (TypeDefinitionBuilder entry : addedTypedefs) { - typedefs.add(entry.build()); - } - instance.setTypeDefinitions(typedefs); + // GROUPINGS + final Set groupings = new HashSet(); + for (GroupingBuilder entry : addedGroupings) { + groupings.add(entry.build()); + } + instance.setGroupings(groupings); - // GROUPINGS - final Set groupings = new HashSet(); - for (GroupingBuilder entry : addedGroupings) { - groupings.add(entry.build()); - } - instance.setGroupings(groupings); + // UNKNOWN NODES + final List unknownNodes = new ArrayList(); + for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { + unknownNodes.add(b.build()); + } + instance.setUnknownSchemaNodes(unknownNodes); - // UNKNOWN NODES - final List unknownNodes = new ArrayList(); - for (UnknownSchemaNodeBuilder b : addedUnknownNodes) { - unknownNodes.add(b.build()); + built = true; } - instance.setUnknownSchemaNodes(unknownNodes); - return instance; } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/UsesNodeBuilderImpl.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/UsesNodeBuilderImpl.java index c54a0dc036..0534f9def0 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/UsesNodeBuilderImpl.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/builder/impl/UsesNodeBuilderImpl.java @@ -26,6 +26,7 @@ import org.opendaylight.controller.yang.parser.builder.api.UsesNodeBuilder; import org.opendaylight.controller.yang.parser.util.RefineHolder; final class UsesNodeBuilderImpl implements UsesNodeBuilder { + private boolean built; private final UsesNodeImpl instance; private final int line; private final SchemaPath groupingPath; @@ -41,21 +42,24 @@ final class UsesNodeBuilderImpl implements UsesNodeBuilder { @Override public UsesNode build() { - // AUGMENTATIONS - final Set augments = new HashSet(); - for (AugmentationSchemaBuilder builder : addedAugments) { - augments.add(builder.build()); - } - instance.setAugmentations(augments); + if(!built) { + // AUGMENTATIONS + final Set augments = new HashSet(); + for (AugmentationSchemaBuilder builder : addedAugments) { + augments.add(builder.build()); + } + instance.setAugmentations(augments); - // REFINES - final Map refineNodes = new HashMap(); - for (SchemaNodeBuilder refineBuilder : refineBuilders) { - SchemaNode refineNode = refineBuilder.build(); - refineNodes.put(refineNode.getPath(), refineNode); - } - instance.setRefines(refineNodes); + // REFINES + final Map refineNodes = new HashMap(); + for (SchemaNodeBuilder refineBuilder : refineBuilders) { + SchemaNode refineNode = refineBuilder.build(); + refineNodes.put(refineNode.getPath(), refineNode); + } + instance.setRefines(refineNodes); + built = true; + } return instance; } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/SchemaContextImpl.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/SchemaContextImpl.java new file mode 100644 index 0000000000..1a71abf70c --- /dev/null +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/SchemaContextImpl.java @@ -0,0 +1,99 @@ +/* + * Copyright (c) 2013 Cisco Systems, Inc. and others. All rights reserved. + * + * This program and the accompanying materials are made available under the + * terms of the Eclipse Public License v1.0 which accompanies this distribution, + * and is available at http://www.eclipse.org/legal/epl-v10.html + */ +package org.opendaylight.controller.yang.parser.impl; + +import java.net.URI; +import java.util.Date; +import java.util.HashSet; +import java.util.Set; + +import org.opendaylight.controller.yang.model.api.DataSchemaNode; +import org.opendaylight.controller.yang.model.api.ExtensionDefinition; +import org.opendaylight.controller.yang.model.api.Module; +import org.opendaylight.controller.yang.model.api.NotificationDefinition; +import org.opendaylight.controller.yang.model.api.RpcDefinition; +import org.opendaylight.controller.yang.model.api.SchemaContext; + +final class SchemaContextImpl implements SchemaContext { + private final Set modules; + + SchemaContextImpl(final Set modules) { + this.modules = modules; + } + + @Override + public Set getDataDefinitions() { + final Set dataDefs = new HashSet(); + for (Module m : modules) { + dataDefs.addAll(m.getChildNodes()); + } + return dataDefs; + } + + @Override + public Set getModules() { + return modules; + } + + @Override + public Set getNotifications() { + final Set notifications = new HashSet(); + for (Module m : modules) { + notifications.addAll(m.getNotifications()); + } + return notifications; + } + + @Override + public Set getOperations() { + final Set rpcs = new HashSet(); + for (Module m : modules) { + rpcs.addAll(m.getRpcs()); + } + return rpcs; + } + + @Override + public Set getExtensions() { + final Set extensions = new HashSet(); + for (Module m : modules) { + extensions.addAll(m.getExtensionSchemaNodes()); + } + return extensions; + } + + @Override + public Module findModuleByName(final String name, final Date revision) { + if (name != null) { + for (final Module module : modules) { + if (revision == null) { + if (module.getName().equals(name)) { + return module; + } + } else if (module.getName().equals(name) + && module.getRevision().equals(revision)) { + return module; + } + } + } + return null; + } + + @Override + public Module findModuleByNamespace(final URI namespace) { + if (namespace != null) { + for (final Module module : modules) { + if (module.getNamespace().equals(namespace)) { + return module; + } + } + } + return null; + } + +} diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/YangParserImpl.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/YangParserImpl.java index 41392b0f49..85ca36791d 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/YangParserImpl.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/YangParserImpl.java @@ -12,7 +12,6 @@ import java.io.FileInputStream; import java.io.FileNotFoundException; import java.io.IOException; import java.io.InputStream; -import java.net.URI; import java.util.ArrayList; import java.util.Collections; import java.util.Date; @@ -34,13 +33,8 @@ import org.antlr.v4.runtime.tree.ParseTreeWalker; import org.opendaylight.controller.antlrv4.code.gen.YangLexer; import org.opendaylight.controller.antlrv4.code.gen.YangParser; import org.opendaylight.controller.yang.common.QName; -import org.opendaylight.controller.yang.model.api.DataSchemaNode; -import org.opendaylight.controller.yang.model.api.ExtensionDefinition; import org.opendaylight.controller.yang.model.api.Module; import org.opendaylight.controller.yang.model.api.ModuleImport; -import org.opendaylight.controller.yang.model.api.MustDefinition; -import org.opendaylight.controller.yang.model.api.NotificationDefinition; -import org.opendaylight.controller.yang.model.api.RpcDefinition; import org.opendaylight.controller.yang.model.api.SchemaContext; import org.opendaylight.controller.yang.model.api.SchemaPath; import org.opendaylight.controller.yang.model.api.TypeDefinition; @@ -123,7 +117,8 @@ public class YangParserImpl implements YangModelParser { private Map> resolveModuleBuilders( final List yangFileStreams) { - //Linked Hash Map MUST be used because Linked Hash Map preserves ORDER of items stored in map. + // Linked Hash Map MUST be used because Linked Hash Map preserves ORDER + // of items stored in map. final Map> modules = new LinkedHashMap>(); final ParseTreeWalker walker = new ParseTreeWalker(); final List trees = parseStreams(yangFileStreams); @@ -141,7 +136,7 @@ public class YangParserImpl implements YangModelParser { // module dependency graph sorted List sorted = ModuleDependencySort.sort(builders); - + for (ModuleBuilder builder : sorted) { final String builderName = builder.getName(); Date builderRevision = builder.getRevision(); @@ -195,7 +190,8 @@ public class YangParserImpl implements YangModelParser { resolveAugments(modules); // build - // Linked Hash Set MUST be used otherwise the Set will not maintain order! + // Linked Hash Set MUST be used otherwise the Set will not maintain + // order! // http://docs.oracle.com/javase/6/docs/api/java/util/LinkedHashSet.html final Set result = new LinkedHashSet(); for (Map.Entry> entry : modules @@ -224,7 +220,7 @@ public class YangParserImpl implements YangModelParser { /** * Search for dirty nodes (node which contains UnknownType) and resolve * unknown types. - * + * * @param modules * all available modules * @param module @@ -544,38 +540,36 @@ public class YangParserImpl implements YangModelParser { } /** - * Go through all typedef statements from given module and search for one - * with given name - * - * @param typedefs - * typedef statements to search + * Search for type definition builder by name. + * + * @param dependentModule + * module to search * @param name - * name of searched typedef - * @return typedef with name equals to given name + * name of type definition + * @param currentModuleName + * current module name + * @param line + * current line in yang model + * @return */ private TypeDefinitionBuilder findTypedefBuilderByName( final ModuleBuilder dependentModule, final String name, final String currentModuleName, final int line) { - TypeDefinitionBuilder result = null; final Set typedefs = dependentModule .getModuleTypedefs(); for (TypeDefinitionBuilder td : typedefs) { if (td.getQName().getLocalName().equals(name)) { - result = td; - break; + return td; } } - if (result == null) { - throw new YangParseException(currentModuleName, line, - "Target module '" + dependentModule.getName() - + "' does not contain typedef '" + name + "'."); - } - return result; + throw new YangParseException(currentModuleName, line, "Target module '" + + dependentModule.getName() + "' does not contain typedef '" + + name + "'."); } /** * Pull restriction from referenced type and add them to given constraints - * + * * @param referencedType * @param constraints */ @@ -603,9 +597,9 @@ public class YangParserImpl implements YangModelParser { } /** - * Go through all augmentation definitions and resolve them. This method - * also finds referenced node and add child nodes to it. - * + * Go through all augment definitions and resolve them. This method also + * finds augment target node and add child nodes to it. + * * @param modules * all available modules */ @@ -648,7 +642,7 @@ public class YangParserImpl implements YangModelParser { } /** - * + * * @param modules * all available modules * @param module @@ -666,8 +660,7 @@ public class YangParserImpl implements YangModelParser { .getTargetPath(); final List path = augmentTargetSchemaPath.getPath(); - int i = 0; - final QName qname = path.get(i); + final QName qname = path.get(0); String prefix = qname.getPrefix(); if (prefix == null) { prefix = module.getPrefix(); @@ -682,12 +675,11 @@ public class YangParserImpl implements YangModelParser { if (childQName.getLocalName().equals( qname.getLocalName())) { currentParent = child; - i++; break; } } - for (; i < path.size(); i++) { + for (int i = 1; i < path.size(); i++) { final QName currentQName = path.get(i); DataSchemaNodeBuilder newParent = null; for (DataSchemaNodeBuilder child : ((ChildNodeBuilder) currentParent) @@ -730,7 +722,7 @@ public class YangParserImpl implements YangModelParser { /** * Go through identity statements defined in current module and resolve * their 'base' statement if present. - * + * * @param modules * all modules * @param module @@ -772,7 +764,7 @@ public class YangParserImpl implements YangModelParser { /** * Go through uses statements defined in current module and resolve their * refine statements. - * + * * @param modules * all modules * @param module @@ -787,120 +779,52 @@ public class YangParserImpl implements YangModelParser { .entrySet()) { final List key = entry.getKey(); final UsesNodeBuilder usesNode = entry.getValue(); + final int line = usesNode.getLine(); final String groupingName = key.get(key.size() - 1); for (RefineHolder refine : usesNode.getRefines()) { - // refine statements - final String defaultStr = refine.getDefaultStr(); - final Boolean mandatory = refine.isMandatory(); - final MustDefinition must = refine.getMust(); - final Boolean presence = refine.isPresence(); - final Integer min = refine.getMinElements(); - final Integer max = refine.getMaxElements(); - final List unknownNodes = refine - .getUnknownNodes(); - - Builder refineTarget = getRefineTargetBuilder(groupingName, + Builder refineTarget = getRefineNodeBuilderCopy(groupingName, refine, modules, module); + ParserUtils.refineDefault(refineTarget, refine, line); if (refineTarget instanceof LeafSchemaNodeBuilder) { final LeafSchemaNodeBuilder leaf = (LeafSchemaNodeBuilder) refineTarget; - if (defaultStr != null && !("".equals(defaultStr))) { - leaf.setDefaultStr(defaultStr); - } - if (mandatory != null) { - leaf.getConstraints().setMandatory(mandatory); - } - if (must != null) { - leaf.getConstraints().addMustDefinition(must); - } - if (unknownNodes != null) { - for (UnknownSchemaNodeBuilder unknown : unknownNodes) { - leaf.addUnknownSchemaNode(unknown); - } - } + ParserUtils.refineLeaf(leaf, refine, line); usesNode.addRefineNode(leaf); } else if (refineTarget instanceof ContainerSchemaNodeBuilder) { final ContainerSchemaNodeBuilder container = (ContainerSchemaNodeBuilder) refineTarget; - if (presence != null) { - container.setPresence(presence); - } - if (must != null) { - container.getConstraints().addMustDefinition(must); - } - if (unknownNodes != null) { - for (UnknownSchemaNodeBuilder unknown : unknownNodes) { - container.addUnknownSchemaNode(unknown); - } - } + ParserUtils.refineContainer(container, refine, line); usesNode.addRefineNode(container); } else if (refineTarget instanceof ListSchemaNodeBuilder) { final ListSchemaNodeBuilder list = (ListSchemaNodeBuilder) refineTarget; - if (must != null) { - list.getConstraints().addMustDefinition(must); - } - if (min != null) { - list.getConstraints().setMinElements(min); - } - if (max != null) { - list.getConstraints().setMaxElements(max); - } - if (unknownNodes != null) { - for (UnknownSchemaNodeBuilder unknown : unknownNodes) { - list.addUnknownSchemaNode(unknown); - } - } + ParserUtils.refineList(list, refine, line); + usesNode.addRefineNode(list); } else if (refineTarget instanceof LeafListSchemaNodeBuilder) { - final LeafListSchemaNodeBuilder leafList = (LeafListSchemaNodeBuilder) getRefineTargetBuilder( + final LeafListSchemaNodeBuilder leafList = (LeafListSchemaNodeBuilder) getRefineNodeBuilderCopy( groupingName, refine, modules, module); - if (must != null) { - leafList.getConstraints().addMustDefinition(must); - } - if (min != null) { - leafList.getConstraints().setMinElements(min); - } - if (max != null) { - leafList.getConstraints().setMaxElements(max); - } - if (unknownNodes != null) { - for (UnknownSchemaNodeBuilder unknown : unknownNodes) { - leafList.addUnknownSchemaNode(unknown); - } - } + ParserUtils.refineLeafList(leafList, refine, line); + usesNode.addRefineNode(leafList); } else if (refineTarget instanceof ChoiceBuilder) { final ChoiceBuilder choice = (ChoiceBuilder) refineTarget; - if (defaultStr != null) { - choice.setDefaultCase(defaultStr); - } - if (mandatory != null) { - choice.getConstraints().setMandatory(mandatory); - } - if (unknownNodes != null) { - for (UnknownSchemaNodeBuilder unknown : unknownNodes) { - choice.addUnknownSchemaNode(unknown); - } - } + ParserUtils.refineChoice(choice, refine, line); + usesNode.addRefineNode(choice); } else if (refineTarget instanceof AnyXmlBuilder) { final AnyXmlBuilder anyXml = (AnyXmlBuilder) refineTarget; - if (mandatory != null) { - anyXml.getConstraints().setMandatory(mandatory); - } - if (must != null) { - anyXml.getConstraints().addMustDefinition(must); - } - if (unknownNodes != null) { - for (UnknownSchemaNodeBuilder unknown : unknownNodes) { - anyXml.addUnknownSchemaNode(unknown); - } - } + ParserUtils.refineAnyxml(anyXml, refine, line); + usesNode.addRefineNode(anyXml); } } } } /** - * Find original builder of refine node and return copy of this builder. - * + * Find original builder of node to refine and return copy of this builder. + *

+ * We must make a copy of builder to preserve original builder, because this + * object will be refined (modified) and later added to + * {@link UsesNodeBuilder}. + *

+ * * @param groupingPath * path to grouping which contains node to refine * @param refine @@ -909,10 +833,10 @@ public class YangParserImpl implements YangModelParser { * all loaded modules * @param module * current module - * @return copy of Builder object of node to be refined if it is present in - * grouping, null otherwise + * @return copy of node to be refined if it is present in grouping, null + * otherwise */ - private Builder getRefineTargetBuilder(final String groupingPath, + private Builder getRefineNodeBuilderCopy(final String groupingPath, final RefineHolder refine, final Map> modules, final ModuleBuilder module) { @@ -946,7 +870,7 @@ public class YangParserImpl implements YangModelParser { /** * Find builder of refine node. - * + * * @param groupingPath * path to grouping which contains node to refine * @param refineNodeName @@ -1033,7 +957,7 @@ public class YangParserImpl implements YangModelParser { /** * Find dependent module based on given prefix - * + * * @param modules * all available modules * @param module @@ -1086,82 +1010,4 @@ public class YangParserImpl implements YangModelParser { return dependentModule; } - private static class SchemaContextImpl implements SchemaContext { - private final Set modules; - - private SchemaContextImpl(final Set modules) { - this.modules = modules; - } - - @Override - public Set getDataDefinitions() { - final Set dataDefs = new HashSet(); - for (Module m : modules) { - dataDefs.addAll(m.getChildNodes()); - } - return dataDefs; - } - - @Override - public Set getModules() { - return modules; - } - - @Override - public Set getNotifications() { - final Set notifications = new HashSet(); - for (Module m : modules) { - notifications.addAll(m.getNotifications()); - } - return notifications; - } - - @Override - public Set getOperations() { - final Set rpcs = new HashSet(); - for (Module m : modules) { - rpcs.addAll(m.getRpcs()); - } - return rpcs; - } - - @Override - public Set getExtensions() { - final Set extensions = new HashSet(); - for (Module m : modules) { - extensions.addAll(m.getExtensionSchemaNodes()); - } - return extensions; - } - - @Override - public Module findModuleByName(final String name, final Date revision) { - if (name != null) { - for (final Module module : modules) { - if (revision == null) { - if (module.getName().equals(name)) { - return module; - } - } else if (module.getName().equals(name) - && module.getRevision().equals(revision)) { - return module; - } - } - } - return null; - } - - @Override - public Module findModuleByNamespace(final URI namespace) { - if (namespace != null) { - for (final Module module : modules) { - if (module.getNamespace().equals(namespace)) { - return module; - } - } - } - return null; - } - } - } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/YangParserListenerImpl.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/YangParserListenerImpl.java index fcc4cd0452..46265529da 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/YangParserListenerImpl.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/impl/YangParserListenerImpl.java @@ -409,8 +409,7 @@ public final class YangParserListenerImpl extends YangParserBaseListener { QName containerQName = new QName(namespace, revision, yangModelPrefix, containerName); ContainerSchemaNodeBuilder containerBuilder = moduleBuilder - .addContainerNode(containerQName, actualPath, ctx.getStart() - .getLine()); + .addContainerNode(containerQName, actualPath, ctx.getStart().getLine()); updatePath(containerName); containerBuilder.setPath(createActualSchemaPath(actualPath, namespace, diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/BitImpl.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/BitImpl.java index c744f1b881..c6bbc6557e 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/BitImpl.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/BitImpl.java @@ -17,7 +17,7 @@ import org.opendaylight.controller.yang.model.api.UnknownSchemaNode; import org.opendaylight.controller.yang.model.api.type.BitsTypeDefinition; import org.opendaylight.controller.yang.model.api.type.BitsTypeDefinition.Bit; -public final class BitImpl implements BitsTypeDefinition.Bit { +final class BitImpl implements BitsTypeDefinition.Bit { private final Long position; private final QName qname; private final SchemaPath schemaPath; diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/MustDefinitionImpl.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/MustDefinitionImpl.java index 31f39e325a..977b3fffcd 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/MustDefinitionImpl.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/MustDefinitionImpl.java @@ -10,15 +10,15 @@ package org.opendaylight.controller.yang.parser.util; import org.opendaylight.controller.yang.model.api.MustDefinition; import org.opendaylight.controller.yang.model.api.RevisionAwareXPath; -public final class MustDefinitionImpl implements MustDefinition { +final class MustDefinitionImpl implements MustDefinition { private final String mustStr; private final String description; private final String reference; private final String errorAppTag; private final String errorMessage; - public MustDefinitionImpl(String mustStr, String description, - String reference, String errorAppTag, String errorMessage) { + MustDefinitionImpl(String mustStr, String description, String reference, + String errorAppTag, String errorMessage) { this.mustStr = mustStr; this.description = description; this.reference = reference; diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/ParserUtils.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/ParserUtils.java index 757c02c8a0..84e0b041e6 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/ParserUtils.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/ParserUtils.java @@ -7,6 +7,7 @@ */ package org.opendaylight.controller.yang.parser.util; +import java.lang.reflect.Method; import java.util.ArrayList; import java.util.List; @@ -16,6 +17,7 @@ import org.opendaylight.controller.yang.model.api.MustDefinition; import org.opendaylight.controller.yang.model.api.SchemaPath; import org.opendaylight.controller.yang.model.api.TypeDefinition; import org.opendaylight.controller.yang.parser.builder.api.AugmentationSchemaBuilder; +import org.opendaylight.controller.yang.parser.builder.api.Builder; import org.opendaylight.controller.yang.parser.builder.api.ChildNodeBuilder; import org.opendaylight.controller.yang.parser.builder.api.DataSchemaNodeBuilder; import org.opendaylight.controller.yang.parser.builder.api.GroupingBuilder; @@ -103,21 +105,206 @@ public final class ParserUtils { private static void correctPath(final ChildNodeBuilder node, final SchemaPath parentSchemaPath) { - for(DataSchemaNodeBuilder builder : node.getChildNodes()) { + for (DataSchemaNodeBuilder builder : node.getChildNodes()) { // add correct path SchemaPath targetNodeSchemaPath = parentSchemaPath; - List targetNodePath = new ArrayList(targetNodeSchemaPath.getPath()); + List targetNodePath = new ArrayList( + targetNodeSchemaPath.getPath()); targetNodePath.add(builder.getQName()); builder.setPath(new SchemaPath(targetNodePath, true)); - if(builder instanceof ChildNodeBuilder) { - ChildNodeBuilder cnb = (ChildNodeBuilder)builder; + if (builder instanceof ChildNodeBuilder) { + ChildNodeBuilder cnb = (ChildNodeBuilder) builder; correctPath(cnb, builder.getPath()); } } } + public static void refineLeaf(LeafSchemaNodeBuilder leaf, + RefineHolder refine, int line) { + String defaultStr = refine.getDefaultStr(); + Boolean mandatory = refine.isMandatory(); + MustDefinition must = refine.getMust(); + List unknownNodes = refine.getUnknownNodes(); + + if (defaultStr != null && !("".equals(defaultStr))) { + leaf.setDefaultStr(defaultStr); + } + if (mandatory != null) { + leaf.getConstraints().setMandatory(mandatory); + } + if (must != null) { + leaf.getConstraints().addMustDefinition(must); + } + if (unknownNodes != null) { + for (UnknownSchemaNodeBuilder unknown : unknownNodes) { + leaf.addUnknownSchemaNode(unknown); + } + } + } + + public static void refineContainer(ContainerSchemaNodeBuilder container, + RefineHolder refine, int line) { + Boolean presence = refine.isPresence(); + MustDefinition must = refine.getMust(); + List unknownNodes = refine.getUnknownNodes(); + + if (presence != null) { + container.setPresence(presence); + } + if (must != null) { + container.getConstraints().addMustDefinition(must); + } + if (unknownNodes != null) { + for (UnknownSchemaNodeBuilder unknown : unknownNodes) { + container.addUnknownSchemaNode(unknown); + } + } + } + + public static void refineList(ListSchemaNodeBuilder list, + RefineHolder refine, int line) { + MustDefinition must = refine.getMust(); + Integer min = refine.getMinElements(); + Integer max = refine.getMaxElements(); + List unknownNodes = refine.getUnknownNodes(); + + if (must != null) { + list.getConstraints().addMustDefinition(must); + } + if (min != null) { + list.getConstraints().setMinElements(min); + } + if (max != null) { + list.getConstraints().setMaxElements(max); + } + if (unknownNodes != null) { + for (UnknownSchemaNodeBuilder unknown : unknownNodes) { + list.addUnknownSchemaNode(unknown); + } + } + } + + public static void refineLeafList(LeafListSchemaNodeBuilder leafList, + RefineHolder refine, int line) { + MustDefinition must = refine.getMust(); + Integer min = refine.getMinElements(); + Integer max = refine.getMaxElements(); + List unknownNodes = refine.getUnknownNodes(); + + if (must != null) { + leafList.getConstraints().addMustDefinition(must); + } + if (min != null) { + leafList.getConstraints().setMinElements(min); + } + if (max != null) { + leafList.getConstraints().setMaxElements(max); + } + if (unknownNodes != null) { + for (UnknownSchemaNodeBuilder unknown : unknownNodes) { + leafList.addUnknownSchemaNode(unknown); + } + } + } + + public static void refineChoice(ChoiceBuilder choice, RefineHolder refine, + int line) { + String defaultStr = refine.getDefaultStr(); + Boolean mandatory = refine.isMandatory(); + List unknownNodes = refine.getUnknownNodes(); + + if (defaultStr != null) { + choice.setDefaultCase(defaultStr); + } + if (mandatory != null) { + choice.getConstraints().setMandatory(mandatory); + } + if (unknownNodes != null) { + for (UnknownSchemaNodeBuilder unknown : unknownNodes) { + choice.addUnknownSchemaNode(unknown); + } + } + } + + public static void refineAnyxml(AnyXmlBuilder anyXml, RefineHolder refine, + int line) { + Boolean mandatory = refine.isMandatory(); + MustDefinition must = refine.getMust(); + List unknownNodes = refine.getUnknownNodes(); + + if (mandatory != null) { + anyXml.getConstraints().setMandatory(mandatory); + } + if (must != null) { + anyXml.getConstraints().addMustDefinition(must); + } + if (unknownNodes != null) { + for (UnknownSchemaNodeBuilder unknown : unknownNodes) { + anyXml.addUnknownSchemaNode(unknown); + } + } + } + + /** + * Perform refine operation of following parameters: + *
    + *
  • description
  • + *
  • reference
  • + *
  • config
  • + *
+ * + * These parameters may be refined for any node. + * + * @param node + * node to refine + * @param refine + * refine holder containing values to refine + * @param line + * current line in yang model + */ + public static void refineDefault(Builder node, RefineHolder refine, + int line) { + Class cls = node.getClass(); + + String description = refine.getDescription(); + if (description != null) { + try { + Method method = cls.getDeclaredMethod("setDescription", + String.class); + method.invoke(node, description); + } catch (Exception e) { + throw new YangParseException(line, + "Cannot refine description in " + cls.getName(), e); + } + } + + String reference = refine.getReference(); + if (reference != null) { + try { + Method method = cls.getDeclaredMethod("setReference", + String.class); + method.invoke(node, reference); + } catch (Exception e) { + throw new YangParseException(line, + "Cannot refine reference in " + cls.getName(), e); + } + } + + Boolean config = refine.isConfig(); + if (config != null) { + try { + Method method = cls.getDeclaredMethod("setConfiguration", + Boolean.TYPE); + method.invoke(node, config); + } catch (Exception e) { + throw new YangParseException(line, "Cannot refine config in " + + cls.getName(), e); + } + } + } + public static LeafSchemaNodeBuilder copyLeafBuilder( final LeafSchemaNodeBuilder old) { final LeafSchemaNodeBuilder copy = new LeafSchemaNodeBuilder( @@ -244,7 +431,8 @@ public final class ParserUtils { } public static ChoiceBuilder copyChoiceBuilder(final ChoiceBuilder old) { - final ChoiceBuilder copy = new ChoiceBuilder(old.getQName(), old.getLine()); + final ChoiceBuilder copy = new ChoiceBuilder(old.getQName(), + old.getLine()); copy.setPath(old.getPath()); copyConstraints(old, copy); for (ChoiceCaseBuilder caseBuilder : old.getCases()) { @@ -272,7 +460,8 @@ public final class ParserUtils { } public static AnyXmlBuilder copyAnyXmlBuilder(final AnyXmlBuilder old) { - final AnyXmlBuilder copy = new AnyXmlBuilder(old.getQName(), old.getLine()); + final AnyXmlBuilder copy = new AnyXmlBuilder(old.getQName(), + old.getLine()); copy.setPath(old.getPath()); copyConstraints(old, copy); for (UnknownSchemaNodeBuilder unknown : old.getUnknownNodes()) { diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/UnknownBoundaryNumber.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/UnknownBoundaryNumber.java index ac3263ac59..7f74333ea7 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/UnknownBoundaryNumber.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/UnknownBoundaryNumber.java @@ -10,7 +10,7 @@ package org.opendaylight.controller.yang.parser.util; /** * Marker object representing special 'min' or 'max' values in YANG. */ -public final class UnknownBoundaryNumber extends Number { +final class UnknownBoundaryNumber extends Number { private static final long serialVersionUID = 1464861684686434869L; private final String value; diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/YangModelBuilderUtil.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/YangModelBuilderUtil.java index 0df5d2cbdf..873e3842db 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/YangModelBuilderUtil.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/main/java/org/opendaylight/controller/yang/parser/util/YangModelBuilderUtil.java @@ -36,7 +36,9 @@ import org.opendaylight.controller.antlrv4.code.gen.YangParser.Length_stmtContex import org.opendaylight.controller.antlrv4.code.gen.YangParser.Mandatory_argContext; import org.opendaylight.controller.antlrv4.code.gen.YangParser.Mandatory_stmtContext; import org.opendaylight.controller.antlrv4.code.gen.YangParser.Max_elements_stmtContext; +import org.opendaylight.controller.antlrv4.code.gen.YangParser.Max_value_argContext; import org.opendaylight.controller.antlrv4.code.gen.YangParser.Min_elements_stmtContext; +import org.opendaylight.controller.antlrv4.code.gen.YangParser.Min_value_argContext; import org.opendaylight.controller.antlrv4.code.gen.YangParser.Must_stmtContext; import org.opendaylight.controller.antlrv4.code.gen.YangParser.Numerical_restrictionsContext; import org.opendaylight.controller.antlrv4.code.gen.YangParser.Ordered_by_argContext; @@ -372,6 +374,7 @@ public final class YangModelBuilderUtil { } if (value < -2147483648 || value > 2147483647) { throw new YangParseException( + ctx.getStart().getLine(), "Error on enum '" + name + "': the enum value MUST be in the range from -2147483648 to 2147483647, but was: " @@ -671,8 +674,8 @@ public final class YangModelBuilderUtil { try { result = Long.valueOf(value); } catch (NumberFormatException e) { - throw new YangParseException("Error on line " + line - + ": Unable to parse range value '" + value + "'.", e); + throw new YangParseException(line, + "Unable to parse range value '" + value + "'.", e); } } return result; @@ -790,7 +793,7 @@ public final class YangModelBuilderUtil { try { result = Integer.valueOf(value); } catch (NumberFormatException e) { - throw new YangParseException( + throw new YangParseException(ctx.getStart().getLine(), "Unable to parse fraction digits value '" + value + "'.", e); } @@ -888,6 +891,7 @@ public final class YangModelBuilderUtil { } if (position < 0 || position > 4294967295L) { throw new YangParseException( + ctx.getStart().getLine(), "Error on bit '" + name + "': the position value MUST be in the range 0 to 4294967295"); @@ -1193,10 +1197,10 @@ public final class YangModelBuilderUtil { for (int i = 0; i < ctx.getChildCount(); ++i) { final ParseTree childNode = ctx.getChild(i); if (childNode instanceof Max_elements_stmtContext) { - Integer max = Integer.valueOf(stringFromNode(childNode)); - constraints.setMinElements(max); + Integer max = parseMaxElements((Max_elements_stmtContext) childNode); + constraints.setMaxElements(max); } else if (childNode instanceof Min_elements_stmtContext) { - Integer min = Integer.valueOf(stringFromNode(childNode)); + Integer min = parseMinElements((Min_elements_stmtContext) childNode); constraints.setMinElements(min); } else if (childNode instanceof Must_stmtContext) { MustDefinition must = parseMust((Must_stmtContext) childNode); @@ -1216,6 +1220,44 @@ public final class YangModelBuilderUtil { } } + private static Integer parseMinElements(Min_elements_stmtContext ctx) { + Integer result = null; + try { + for (int j = 0; j < ctx.getChildCount(); j++) { + ParseTree minArg = ctx.getChild(j); + if (minArg instanceof Min_value_argContext) { + result = Integer.valueOf(stringFromNode(minArg)); + } + } + if (result == null) { + throw new IllegalArgumentException(); + } + return result; + } catch (Exception e) { + throw new YangParseException(ctx.getStart().getLine(), + "Failed to parse min-elements.", e); + } + } + + private static Integer parseMaxElements(Max_elements_stmtContext ctx) { + Integer result = null; + try { + for (int j = 0; j < ctx.getChildCount(); j++) { + ParseTree maxArg = ctx.getChild(j); + if (maxArg instanceof Max_value_argContext) { + result = Integer.valueOf(stringFromNode(maxArg)); + } + } + if (result == null) { + throw new IllegalArgumentException(); + } + return result; + } catch (Exception e) { + throw new YangParseException(ctx.getStart().getLine(), + "Failed to parse max-elements.", e); + } + } + /** * Parse given context and return yin value. * @@ -1278,8 +1320,12 @@ public final class YangModelBuilderUtil { /** * Parse refine statement. - * @param refineCtx refine statement - * @return + * + * @param refineCtx + * refine statement + * @param line + * current line in yang model + * @return RefineHolder object representing this refine statement */ public static RefineHolder parseRefine(Refine_stmtContext refineCtx) { final String refineTarget = stringFromNode(refineCtx); @@ -1290,6 +1336,8 @@ public final class YangModelBuilderUtil { if (refinePom instanceof Refine_pomContext) { for (int k = 0; k < refinePom.getChildCount(); k++) { ParseTree refineStmt = refinePom.getChild(k); + parseRefineDefault(refine, refineStmt); + if (refineStmt instanceof Refine_leaf_stmtsContext) { parseRefine(refine, (Refine_leaf_stmtsContext) refineStmt); @@ -1315,6 +1363,23 @@ public final class YangModelBuilderUtil { return refine; } + private static void parseRefineDefault(RefineHolder refine, + ParseTree refineStmt) { + for (int i = 0; i < refineStmt.getChildCount(); i++) { + ParseTree refineArg = refineStmt.getChild(i); + if (refineArg instanceof Description_stmtContext) { + String description = stringFromNode(refineArg); + refine.setDescription(description); + } else if (refineArg instanceof Reference_stmtContext) { + String reference = stringFromNode(refineArg); + refine.setReference(reference); + } else if (refineArg instanceof Config_stmtContext) { + boolean config = parseConfig((Config_stmtContext) refineArg); + refine.setConfig(config); + } + } + } + private static RefineHolder parseRefine(RefineHolder refine, Refine_leaf_stmtsContext refineStmt) { for (int i = 0; i < refineStmt.getChildCount(); i++) { @@ -1362,10 +1427,10 @@ public final class YangModelBuilderUtil { MustDefinition must = parseMust((Must_stmtContext) refineArg); refine.setMust(must); } else if (refineArg instanceof Max_elements_stmtContext) { - Integer max = Integer.valueOf(stringFromNode(refineArg)); - refine.setMinElements(max); + Integer max = parseMaxElements((Max_elements_stmtContext) refineArg); + refine.setMaxElements(max); } else if (refineArg instanceof Min_elements_stmtContext) { - Integer min = Integer.valueOf(stringFromNode(refineArg)); + Integer min = parseMinElements((Min_elements_stmtContext) refineArg); refine.setMinElements(min); } } @@ -1380,10 +1445,10 @@ public final class YangModelBuilderUtil { MustDefinition must = parseMust((Must_stmtContext) refineArg); refine.setMust(must); } else if (refineArg instanceof Max_elements_stmtContext) { - Integer max = Integer.valueOf(stringFromNode(refineArg)); - refine.setMinElements(max); + Integer max = parseMaxElements((Max_elements_stmtContext) refineArg); + refine.setMaxElements(max); } else if (refineArg instanceof Min_elements_stmtContext) { - Integer min = Integer.valueOf(stringFromNode(refineArg)); + Integer min = parseMinElements((Min_elements_stmtContext) refineArg); refine.setMinElements(min); } } diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/test/java/org/opendaylight/controller/yang/parser/impl/YangParserTest.java b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/test/java/org/opendaylight/controller/yang/parser/impl/YangParserTest.java index 9cbf5b9719..fe358995fa 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/test/java/org/opendaylight/controller/yang/parser/impl/YangParserTest.java +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/test/java/org/opendaylight/controller/yang/parser/impl/YangParserTest.java @@ -165,8 +165,8 @@ public class YangParserTest { assertNull(constraints.getWhenCondition()); assertEquals(0, constraints.getMustConstraints().size()); assertFalse(constraints.isMandatory()); - assertNull(constraints.getMinElements()); - assertNull(constraints.getMaxElements()); + assertEquals(1, (int)constraints.getMinElements()); + assertEquals(11, (int)constraints.getMaxElements()); // test AugmentationTarget args Set availableAugmentations = ifEntry .getAvailableAugmentations(); @@ -551,25 +551,62 @@ public class YangParserTest { assertEquals(1, usesNodes.size()); UsesNode usesNode = usesNodes.iterator().next(); Map refines = usesNode.getRefines(); - assertEquals(2, refines.size()); + assertEquals(3, refines.size()); + LeafSchemaNode refineLeaf = null; + ContainerSchemaNode refineContainer = null; + ListSchemaNode refineList = null; for (Map.Entry entry : refines.entrySet()) { SchemaNode value = entry.getValue(); - if (value instanceof LeafSchemaNode) { - LeafSchemaNode refineLeaf = (LeafSchemaNode) value; - assertNotNull(refineLeaf); - } else { - ContainerSchemaNode refineContainer = (ContainerSchemaNode) value; - Set mustConstraints = refineContainer - .getConstraints().getMustConstraints(); - assertEquals(1, mustConstraints.size()); - MustDefinition must = mustConstraints.iterator().next(); - assertEquals("must-condition", must.toString()); - assertEquals("An error message test", must.getErrorMessage()); - assertEquals(("An error app tag test"), must.getErrorAppTag()); + refineLeaf = (LeafSchemaNode) value; + } else if(value instanceof ContainerSchemaNode) { + refineContainer = (ContainerSchemaNode) value; + } else if(value instanceof ListSchemaNode) { + refineList = (ListSchemaNode)value; } } + + // leaf address + assertNotNull(refineLeaf); + assertEquals("address", refineLeaf.getQName().getLocalName()); + assertEquals("description of address defined by refine", + refineLeaf.getDescription()); + assertEquals("address reference added by refine", + refineLeaf.getReference()); + assertFalse(refineLeaf.isConfiguration()); + assertTrue(refineLeaf.getConstraints().isMandatory()); + Set leafMustConstraints = refineLeaf.getConstraints() + .getMustConstraints(); + assertEquals(1, leafMustConstraints.size()); + MustDefinition leafMust = leafMustConstraints.iterator().next(); + assertEquals( + "\"ifType != 'ethernet' or (ifType = 'ethernet' and ifMTU = 1500)\"", + leafMust.toString()); + + // container port + assertNotNull(refineContainer); + Set mustConstraints = refineContainer.getConstraints() + .getMustConstraints(); + assertEquals(1, mustConstraints.size()); + MustDefinition must = mustConstraints.iterator().next(); + assertEquals("must-condition", must.toString()); + assertEquals("An error message test", must.getErrorMessage()); + assertEquals(("An error app tag test"), must.getErrorAppTag()); + assertEquals("description of port defined by refine", + refineContainer.getDescription()); + assertEquals("port reference added by refine", + refineContainer.getReference()); + assertFalse(refineContainer.isConfiguration()); + assertTrue(refineContainer.isPresenceContainer()); + + // list addresses + assertNotNull(refineList); + assertEquals("description of addresses defined by refine", refineList.getDescription()); + assertEquals("addresses reference added by refine", refineList.getReference()); + assertFalse(refineList.isConfiguration()); + assertEquals(2, (int)refineList.getConstraints().getMinElements()); + assertEquals(12, (int)refineList.getConstraints().getMaxElements()); } @Test diff --git a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/test/resources/model/testfile2.yang b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/test/resources/model/testfile2.yang index 783c89b617..a4e5868c4f 100644 --- a/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/test/resources/model/testfile2.yang +++ b/opendaylight/sal/yang-prototype/code-generator/yang-model-parser-impl/src/test/resources/model/testfile2.yang @@ -143,6 +143,13 @@ module types2 { container port { description "Target port container"; } + + list addresses { + key "id"; + leaf id { + type int8; + } + } } container peer { @@ -150,12 +157,31 @@ module types2 { uses target { refine address { default "1.2.3.4"; + description "description of address defined by refine"; + reference "address reference added by refine"; + config false; + mandatory true; + must "ifType != 'ethernet' or " + + "(ifType = 'ethernet' and ifMTU = 1500)" { + error-message "An ethernet MTU must be 1500"; + } } refine port { must "must-condition" { error-message "An error message test"; error-app-tag "An error app tag test"; } + description "description of port defined by refine"; + reference "port reference added by refine"; + config false; + presence "presence is required"; + } + refine addresses { + description "description of addresses defined by refine"; + reference "addresses reference added by refine"; + config false; + min-elements 2; + max-elements 12; } } } @@ -173,6 +199,9 @@ module types2 { leaf ifMtu { type int32; } + + min-elements 1; + max-elements 11; } }