Added Maven plugin for generation SAL APIs from YANG
[controller.git] / opendaylight / sal / yang-prototype / code-generator / binding-java-api-generator / src / main / java / org / opendaylight / controller / sal / java / api / generator / GeneratorUtil.java
1 /*
2  * Copyright (c) 2013 Cisco Systems, Inc. and others.  All rights reserved.
3  *
4  * This program and the accompanying materials are made available under the
5  * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6  * and is available at http://www.eclipse.org/legal/epl-v10.html
7  */
8 package org.opendaylight.controller.sal.java.api.generator;
9
10 import static org.opendaylight.controller.sal.java.api.generator.Constants.CLASS;
11 import static org.opendaylight.controller.sal.java.api.generator.Constants.COMMA;
12 import static org.opendaylight.controller.sal.java.api.generator.Constants.ENUM;
13 import static org.opendaylight.controller.sal.java.api.generator.Constants.FINAL;
14 import static org.opendaylight.controller.sal.java.api.generator.Constants.GAP;
15 import static org.opendaylight.controller.sal.java.api.generator.Constants.IFC;
16 import static org.opendaylight.controller.sal.java.api.generator.Constants.LB;
17 import static org.opendaylight.controller.sal.java.api.generator.Constants.LCB;
18 import static org.opendaylight.controller.sal.java.api.generator.Constants.NL;
19 import static org.opendaylight.controller.sal.java.api.generator.Constants.PKG;
20 import static org.opendaylight.controller.sal.java.api.generator.Constants.PRIVATE;
21 import static org.opendaylight.controller.sal.java.api.generator.Constants.PUBLIC;
22 import static org.opendaylight.controller.sal.java.api.generator.Constants.RB;
23 import static org.opendaylight.controller.sal.java.api.generator.Constants.RCB;
24 import static org.opendaylight.controller.sal.java.api.generator.Constants.SC;
25 import static org.opendaylight.controller.sal.java.api.generator.Constants.STATIC;
26 import static org.opendaylight.controller.sal.java.api.generator.Constants.TAB;
27
28 import java.util.List;
29
30 import org.opendaylight.controller.sal.binding.model.api.AnnotationType;
31 import org.opendaylight.controller.sal.binding.model.api.Constant;
32 import org.opendaylight.controller.sal.binding.model.api.Enumeration;
33 import org.opendaylight.controller.sal.binding.model.api.Enumeration.Pair;
34 import org.opendaylight.controller.sal.binding.model.api.GeneratedProperty;
35 import org.opendaylight.controller.sal.binding.model.api.GeneratedTransferObject;
36 import org.opendaylight.controller.sal.binding.model.api.GeneratedType;
37 import org.opendaylight.controller.sal.binding.model.api.MethodSignature;
38 import org.opendaylight.controller.sal.binding.model.api.MethodSignature.Parameter;
39 import org.opendaylight.controller.sal.binding.model.api.ParameterizedType;
40 import org.opendaylight.controller.sal.binding.model.api.Type;
41
42 public class GeneratorUtil {
43
44     private GeneratorUtil() {
45     }
46
47     public static String createIfcDeclarationWithPkgName(
48             final GeneratedType genType, final String indent) {
49         return createFileDeclarationWithPkgName(IFC, genType, indent);
50     }
51
52     public static String createClassDeclarationWithPkgName(
53             final GeneratedTransferObject genTransferObject, final String indent) {
54         return createFileDeclarationWithPkgName(CLASS, genTransferObject,
55                 indent);
56     }
57
58     private static String createFileDeclarationWithPkgName(final String type,
59             final GeneratedType genType, final String indent) {
60         final StringBuilder builder = new StringBuilder();
61         builder.append(PKG + GAP + genType.getPackageName() + SC);
62         builder.append(NL);
63         builder.append(NL);
64         createComment(builder, genType.getComment(), indent);
65         
66         if (!genType.getAnnotations().isEmpty()) {
67             final List<AnnotationType> annotations = genType.getAnnotations();
68             appendAnnotations(builder, annotations);
69             builder.append(NL);
70         }
71         builder.append(PUBLIC + GAP + type + GAP + genType.getName() + GAP
72                 + LCB);
73         return builder.toString();
74     }
75
76     private static StringBuilder appendAnnotations(final StringBuilder builder, final List<AnnotationType> annotations) {
77         if ((builder != null) && (annotations != null)) {
78             for (final AnnotationType annotation : annotations) {
79                 builder.append("@");
80                 builder.append(annotation.getPackageName());
81                 builder.append(".");
82                 builder.append(annotation.getName());
83
84                 if (annotation.containsParameters()) {
85                     builder.append("(");
86                     final List<AnnotationType.Parameter> parameters = annotation
87                             .getParameters();
88                     appendAnnotationParams(builder, parameters);
89                     builder.append(")");
90                 }
91             }
92         }
93         return builder;
94     }
95
96     private static StringBuilder appendAnnotationParams(
97             final StringBuilder builder,
98             final List<AnnotationType.Parameter> parameters) {
99         if (parameters != null) {
100             int i = 0;
101             for (final AnnotationType.Parameter param : parameters) {
102                 if (param == null) {
103                     continue;
104                 }
105                 if (i > 0) {
106                     builder.append(", ");
107                 }
108                 final String paramName = param.getName();
109                 if (param.getValue() != null) {
110                     builder.append(paramName);
111                     builder.append(" = ");
112                     builder.append(param.getValue());
113                 } else {
114                     builder.append(paramName);
115                     builder.append(" = {");
116                     final List<String> values = param.getValues();
117                     builder.append(values.get(0));
118                     for (int j = 1; j < values.size(); ++j) {
119                         builder.append(", ");
120                         builder.append(values.get(j));
121                     }
122                     builder.append("}");
123                 }
124                 i++;
125             }
126         }
127         return builder;
128     }
129
130     public static String createConstant(final Constant constant,
131             final String indent) {
132         final StringBuilder builder = new StringBuilder();
133         builder.append(indent + PUBLIC + GAP + STATIC + GAP + FINAL + GAP);
134         builder.append(getExplicitType(constant.getType()) + GAP
135                 + constant.getName());
136         builder.append(GAP + "=" + GAP);
137         builder.append(constant.getValue() + SC);
138         return builder.toString();
139     }
140
141     public static String createField(final GeneratedProperty property,
142             final String indent) {
143         final StringBuilder builder = new StringBuilder();
144         builder.append(indent);
145         if (!property.getAnnotations().isEmpty()) {
146             final List<AnnotationType> annotations = property.getAnnotations();
147             appendAnnotations(builder, annotations);
148             builder.append(NL);
149         }
150         builder.append(indent + PRIVATE + GAP);
151         builder.append(getExplicitType(property.getReturnType()) + GAP
152                 + property.getName());
153         builder.append(SC);
154         return builder.toString();
155     }
156
157     /**
158      * Create method declaration in interface.
159      * 
160      * @param method
161      * @param indent
162      * @return
163      */
164     public static String createMethodDeclaration(final MethodSignature method,
165             final String indent) {
166         final String comment = method.getComment();
167         final Type type = method.getReturnType();
168         final String name = method.getName();
169         final List<Parameter> parameters = method.getParameters();
170
171         final StringBuilder builder = new StringBuilder();
172         createComment(builder, comment, indent);
173         builder.append(NL);
174         builder.append(indent);
175         
176         if (!method.getAnnotations().isEmpty()) {
177             final List<AnnotationType> annotations = method.getAnnotations();
178             appendAnnotations(builder, annotations);
179             builder.append(NL);
180         }
181         
182         builder.append(indent + getExplicitType(type) + GAP + name);
183         builder.append(LB);
184         for (int i = 0; i < parameters.size(); i++) {
185             Parameter p = parameters.get(i);
186             String separator = COMMA;
187             if (i + 1 == parameters.size()) {
188                 separator = "";
189             }
190             builder.append(getExplicitType(p.getType()) + GAP + p.getName()
191                     + separator);
192         }
193         builder.append(RB);
194         builder.append(SC);
195
196         return builder.toString();
197     }
198
199     public static String createConstructor(
200             GeneratedTransferObject genTransferObject, final String indent) {
201         final StringBuilder builder = new StringBuilder();
202
203         final List<GeneratedProperty> properties = genTransferObject
204                 .getProperties();
205         builder.append(indent);
206         builder.append(PUBLIC);
207         builder.append(GAP);
208         builder.append(genTransferObject.getName());
209         builder.append(LB);
210
211         boolean first = true;
212         if (properties != null) {
213             for (final GeneratedProperty property : properties) {
214                 if (first) {
215                     builder.append(getExplicitType(property.getReturnType()));
216                     builder.append(" ");
217                     builder.append(property.getName());
218                     first = false;
219                 } else {
220                     builder.append(", ");
221                     builder.append(getExplicitType(property.getReturnType()));
222                     builder.append(builder.append(" "));
223                     builder.append(property.getName());
224                 }
225             }
226         }
227
228         builder.append(RB);
229         builder.append(GAP);
230         builder.append(LCB);
231         builder.append(NL);
232         builder.append(indent);
233         builder.append(TAB);
234         builder.append("super();");
235         builder.append(NL);
236
237         if (properties != null) {
238             for (final GeneratedProperty property : properties) {
239                 builder.append(indent);
240                 builder.append(TAB);
241                 builder.append("this.");
242                 builder.append(property.getName());
243                 builder.append(" = ");
244                 builder.append(property.getName());
245                 builder.append(SC);
246                 builder.append(NL);
247             }
248         }
249
250         builder.append(indent);
251         builder.append(RCB);
252
253         return builder.toString();
254     }
255
256     public static String createGetter(final GeneratedProperty property,
257             final String indent) {
258         final StringBuilder builder = new StringBuilder();
259
260         final Type type = property.getReturnType();
261         final String varName = property.getName();
262         final char first = Character.toUpperCase(varName.charAt(0));
263         final String methodName = "get" + first + varName.substring(1);
264
265         builder.append(indent + PUBLIC + GAP + getExplicitType(type) + GAP
266                 + methodName);
267         builder.append(LB + RB + LCB + NL);
268
269         String currentIndent = indent + TAB;
270
271         builder.append(currentIndent + "return " + varName + SC + NL);
272
273         builder.append(indent + RCB);
274         return builder.toString();
275     }
276
277     public static String createHashCode(
278             final List<GeneratedProperty> properties, final String indent) {
279         StringBuilder builder = new StringBuilder();
280         builder.append(indent + "public int hashCode() {" + NL);
281         builder.append(indent + TAB + "final int prime = 31;" + NL);
282         builder.append(indent + TAB + "int result = 1;" + NL);
283
284         for (GeneratedProperty property : properties) {
285             String fieldName = property.getName();
286             builder.append(indent + TAB + "result = prime * result + (("
287                     + fieldName + " == null) ? 0 : " + fieldName
288                     + ".hashCode());" + NL);
289         }
290
291         builder.append(indent + TAB + "return result;" + NL);
292         builder.append(indent + RCB + NL);
293         return builder.toString();
294     }
295
296     public static String createEquals(final GeneratedTransferObject type,
297             final List<GeneratedProperty> properties, final String indent) {
298         StringBuilder builder = new StringBuilder();
299         final String indent1 = indent + TAB;
300         final String indent2 = indent + TAB + TAB;
301         final String indent3 = indent + TAB + TAB + TAB;
302
303         builder.append(indent + "public boolean equals(Object obj) {" + NL);
304         builder.append(indent1 + "if (this == obj) {" + NL);
305         builder.append(indent2 + "return true;" + NL);
306         builder.append(indent1 + "}" + NL);
307         builder.append(indent1 + "if (obj == null) {" + NL);
308         builder.append(indent2 + "return false;" + NL);
309         builder.append(indent1 + "}" + NL);
310         builder.append(indent1 + "if (getClass() != obj.getClass()) {" + NL);
311         builder.append(indent2 + "return false;" + NL);
312         builder.append(indent1 + "}" + NL);
313
314         String typeStr = type.getPackageName() + "." + type.getName();
315         builder.append(indent1 + typeStr + " other = (" + typeStr + ") obj;"
316                 + NL);
317
318         for (GeneratedProperty property : properties) {
319             String fieldName = property.getName();
320             builder.append(indent1 + "if (" + fieldName + " == null) {" + NL);
321             builder.append(indent2 + "if (other." + fieldName + " != null) {"
322                     + NL);
323             builder.append(indent3 + "return false;" + NL);
324             builder.append(indent2 + "}" + NL);
325             builder.append(indent1 + "} else if (!" + fieldName
326                     + ".equals(other." + fieldName + ")) {" + NL);
327             builder.append(indent2 + "return false;" + NL);
328             builder.append(indent1 + "}" + NL);
329         }
330
331         builder.append(indent1 + "return true;" + NL);
332
333         builder.append(indent + RCB + NL);
334         return builder.toString();
335     }
336
337     public static String createToString(final GeneratedTransferObject type,
338             final List<GeneratedProperty> properties, final String indent) {
339         StringBuilder builder = new StringBuilder();
340         builder.append(indent);
341         builder.append("public String toString() {");
342         builder.append(NL);
343         builder.append(indent);
344         builder.append(TAB);
345         builder.append("StringBuilder builder = new StringBuilder();");
346         builder.append(NL);
347         builder.append(indent);
348         builder.append(TAB);
349         builder.append("builder.append(\"");
350         builder.append(type.getName());
351         builder.append(" [");
352
353         boolean first = true;
354         for (GeneratedProperty property : properties) {
355             if (first) {
356                 builder.append(property.getName());
357                 builder.append("=\");");
358                 builder.append(NL);
359                 builder.append(indent);
360                 builder.append(TAB);
361                 builder.append("builder.append(");
362                 builder.append(property.getName());
363                 builder.append(");");
364                 first = false;
365             } else {
366                 builder.append(NL);
367                 builder.append(indent);
368                 builder.append(TAB);
369                 builder.append("builder.append(\", ");
370                 builder.append(property.getName());
371                 builder.append("=\");");
372                 builder.append(NL);
373                 builder.append(indent);
374                 builder.append(TAB);
375                 builder.append("builder.append(\", ");
376                 builder.append(property.getName());
377                 builder.append(");");
378             }
379         }
380         builder.append(NL);
381         builder.append(indent);
382         builder.append(TAB);
383         builder.append("builder.append(\"]\");");
384         builder.append(NL);
385         builder.append(indent);
386         builder.append(TAB);
387         builder.append("return builder.toString();");
388
389         builder.append(NL);
390         builder.append(indent);
391         builder.append(RCB);
392         builder.append(NL);
393         return builder.toString();
394     }
395
396     public static String createEnum(final Enumeration enumeration,
397             final String indent) {
398         final StringBuilder builder = new StringBuilder(indent + ENUM + GAP
399                 + enumeration.getName() + GAP + LCB + NL);
400
401         String separator = COMMA;
402         final List<Pair> values = enumeration.getValues();
403         builder.append(indent + TAB);
404         for (int i = 0; i < values.size(); i++) {
405             if (i + 1 == values.size()) {
406                 separator = SC;
407             }
408             builder.append(values.get(i).getName() + separator);
409         }
410         builder.append(NL);
411         builder.append(indent + RCB);
412         return builder.toString();
413     }
414
415     private static String getExplicitType(final Type type) {
416         String packageName = type.getPackageName();
417         if (packageName.endsWith(".")) {
418             packageName = packageName.substring(0, packageName.length() - 1);
419         }
420         final StringBuilder builder = new StringBuilder(packageName + "."
421                 + type.getName());
422         if (type instanceof ParameterizedType) {
423             ParameterizedType pType = (ParameterizedType) type;
424             Type[] pTypes = pType.getActualTypeArguments();
425             builder.append("<");
426             builder.append(getParameters(pTypes));
427             builder.append(">");
428         }
429         if (builder.toString().equals("java.lang.Void")) {
430             return "void";
431         }
432         return builder.toString();
433     }
434
435     private static String getParameters(final Type[] pTypes) {
436         final StringBuilder builder = new StringBuilder();
437         for (int i = 0; i < pTypes.length; i++) {
438             Type t = pTypes[i];
439
440             String separator = COMMA;
441             if (i + 1 == pTypes.length) {
442                 separator = "";
443             }
444             builder.append(getExplicitType(t) + separator);
445         }
446         return builder.toString();
447     }
448
449     private static void createComment(final StringBuilder builder,
450             final String comment, final String indent) {
451         if (comment != null && comment.length() > 0) {
452             builder.append(indent + "/*" + NL);
453             builder.append(indent + comment + NL);
454             builder.append(indent + "*/" + NL);
455         }
456     }
457
458 }