Remove yang-test
[controller.git] / opendaylight / config / yang-jmx-generator / src / main / java / org / opendaylight / controller / config / yangjmxgenerator / attribute / TOAttribute.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.config.yangjmxgenerator.attribute;
9
10 import com.google.common.base.Function;
11 import com.google.common.collect.Collections2;
12 import com.google.common.collect.Maps;
13 import com.google.common.collect.Sets;
14 import java.util.ArrayList;
15 import java.util.HashMap;
16 import java.util.List;
17 import java.util.Map;
18 import java.util.Map.Entry;
19 import java.util.Set;
20 import javax.management.openmbean.CompositeType;
21 import javax.management.openmbean.OpenDataException;
22 import javax.management.openmbean.OpenType;
23 import org.opendaylight.controller.config.yangjmxgenerator.TypeProviderWrapper;
24 import org.opendaylight.mdsal.binding.model.api.JavaTypeName;
25 import org.opendaylight.mdsal.binding.model.api.Type;
26 import org.opendaylight.mdsal.binding.model.util.ReferencedTypeImpl;
27 import org.opendaylight.yangtools.yang.model.api.AugmentationTarget;
28 import org.opendaylight.yangtools.yang.model.api.ContainerSchemaNode;
29 import org.opendaylight.yangtools.yang.model.api.DataNodeContainer;
30 import org.opendaylight.yangtools.yang.model.api.DataSchemaNode;
31 import org.opendaylight.yangtools.yang.model.api.LeafListSchemaNode;
32 import org.opendaylight.yangtools.yang.model.api.LeafSchemaNode;
33 import org.opendaylight.yangtools.yang.model.api.ListSchemaNode;
34
35 public class TOAttribute extends AbstractAttribute implements TypedAttribute {
36
37     private final String nullableDescription, nullableDefault;
38     private final Map<String, AttributeIfc> yangNameToAttributeMap;
39     private final Map<String, String> attributeNameMap;
40     private final String packageName;
41
42     private static final Set<Class<? extends DataSchemaNode>> ALLOWED_CHILDREN = Sets
43             .newHashSet();
44     static {
45         ALLOWED_CHILDREN.add(LeafListSchemaNode.class);
46         ALLOWED_CHILDREN.add(ListSchemaNode.class);
47         ALLOWED_CHILDREN.add(LeafSchemaNode.class);
48         ALLOWED_CHILDREN.add(ContainerSchemaNode.class);
49     }
50
51     public static <T extends DataNodeContainer & AugmentationTarget & DataSchemaNode> TOAttribute create(
52             final T containerSchemaNode, final TypeProviderWrapper typeProviderWrapper, final String packageName) {
53         // Transfer Object: get the leaves
54         final Map<String, AttributeIfc> map = new HashMap<>();
55         final Map<String, String> attributeNameMap = new HashMap<>();
56         for (final DataSchemaNode dataSchemaNode : containerSchemaNode.getChildNodes()) {
57             try {
58                 final String yangName = dataSchemaNode.getQName().getLocalName();
59                 map.put(yangName, createInnerAttribute(dataSchemaNode, typeProviderWrapper, packageName));
60             } catch (final IllegalArgumentException e) {
61                 throw new IllegalStateException("Unable to create TO", e);
62             }
63         }
64         return new TOAttribute(containerSchemaNode, map, attributeNameMap,
65                 containerSchemaNode.getDescription().orElse(null), packageName);
66     }
67
68     private static AttributeIfc createInnerAttribute(
69             final DataSchemaNode dataSchemaNode,
70             final TypeProviderWrapper typeProviderWrapper, final String packageName) {
71         final Class<? extends DataSchemaNode> type = isAllowedType(dataSchemaNode);
72
73         if (type.equals(LeafSchemaNode.class)) {
74             return new JavaAttribute((LeafSchemaNode) dataSchemaNode, typeProviderWrapper);
75         } else if (type.equals(ListSchemaNode.class)) {
76             return ListAttribute.create((ListSchemaNode) dataSchemaNode, typeProviderWrapper, packageName);
77         } else if (type.equals(LeafListSchemaNode.class)) {
78             return ListAttribute.create((LeafListSchemaNode) dataSchemaNode, typeProviderWrapper);
79         } else if (type.equals(ContainerSchemaNode.class)) {
80             return TOAttribute.create((ContainerSchemaNode) dataSchemaNode, typeProviderWrapper, packageName);
81         }
82
83         throw new IllegalStateException("This should never happen");
84     }
85
86     private static Class<? extends DataSchemaNode> isAllowedType(
87             final DataSchemaNode dataSchemaNode) {
88         for (final Class<? extends DataSchemaNode> allowedType : ALLOWED_CHILDREN) {
89             if (allowedType.isAssignableFrom(dataSchemaNode.getClass())) {
90                 return allowedType;
91             }
92         }
93         throw new IllegalArgumentException("Illegal child node for TO: "
94                 + dataSchemaNode.getClass() + " allowed node types: "
95                 + ALLOWED_CHILDREN);
96     }
97
98     private TOAttribute(final DataSchemaNode attrNode,
99             final Map<String, AttributeIfc> transferObject,
100             final Map<String, String> attributeNameMap, final String nullableDescription, final String packageName) {
101         super(attrNode);
102         this.yangNameToAttributeMap = transferObject;
103         this.attributeNameMap = attributeNameMap;
104         this.nullableDescription = nullableDescription;
105         this.nullableDefault = null;
106         this.packageName = packageName;
107     }
108
109     public Map<String, String> getAttributeNameMap() {
110         return this.attributeNameMap;
111     }
112
113     public Map<String, AttributeIfc> getCapitalizedPropertiesToTypesMap() {
114         final Map<String, AttributeIfc> capitalizedPropertiesToTypesMap = Maps
115                 .newHashMap();
116         for (final Entry<String, AttributeIfc> entry : this.yangNameToAttributeMap
117                 .entrySet()) {
118
119             capitalizedPropertiesToTypesMap.put(
120                     TypeProviderWrapper.convertToJavaName(entry.getKey(), true),
121                     entry.getValue());
122         }
123         return capitalizedPropertiesToTypesMap;
124     }
125
126     public Map<String, AttributeIfc> getJmxPropertiesToTypesMap() {
127         final Map<String, AttributeIfc> jmxPropertiesToTypesMap = Maps.newHashMap();
128         for (final Entry<String, AttributeIfc> entry : this.yangNameToAttributeMap
129                 .entrySet()) {
130
131             jmxPropertiesToTypesMap.put(
132                     TypeProviderWrapper.convertToJavaName(entry.getKey(), false),
133                     entry.getValue());
134         }
135         return jmxPropertiesToTypesMap;
136     }
137
138     public Map<String, AttributeIfc> getYangPropertiesToTypesMap() {
139         return this.yangNameToAttributeMap;
140     }
141
142     @Override
143     public String getNullableDescription() {
144         return this.nullableDescription;
145     }
146
147     @Override
148     public String getNullableDefault() {
149         return this.nullableDefault;
150     }
151
152     @Override
153     public boolean equals(final Object o) {
154         if (this == o) {
155             return true;
156         }
157         if (o == null || getClass() != o.getClass()) {
158             return false;
159         }
160         if (!super.equals(o)) {
161             return false;
162         }
163
164         final TOAttribute that = (TOAttribute) o;
165
166         if (this.nullableDefault != null ? !this.nullableDefault
167                 .equals(that.nullableDefault) : that.nullableDefault != null) {
168             return false;
169         }
170         if (this.nullableDescription != null ? !this.nullableDescription
171                 .equals(that.nullableDescription)
172                 : that.nullableDescription != null) {
173             return false;
174         }
175         if (this.yangNameToAttributeMap != null ? !this.yangNameToAttributeMap
176                 .equals(that.yangNameToAttributeMap)
177                 : that.yangNameToAttributeMap != null) {
178             return false;
179         }
180
181         return true;
182     }
183
184     @Override
185     public int hashCode() {
186         int result = super.hashCode();
187         result = 31
188                 * result
189                 + (this.nullableDescription != null ? this.nullableDescription.hashCode()
190                         : 0);
191         result = 31 * result
192                 + (this.nullableDefault != null ? this.nullableDefault.hashCode() : 0);
193         result = 31
194                 * result
195                 + (this.yangNameToAttributeMap != null ? this.yangNameToAttributeMap
196                         .hashCode() : 0);
197         return result;
198     }
199
200     @Override
201     public String toString() {
202         return "TOAttribute{" + getAttributeYangName() + "," + "to="
203                 + this.yangNameToAttributeMap + '}';
204     }
205
206     @Override
207     public Type getType() {
208         // TODO: ReferencedTypeImpl from Types
209         return new ReferencedTypeImpl(JavaTypeName.create(this.packageName, getUpperCaseCammelCase()));
210     }
211
212     @Override
213     public CompositeType getOpenType() {
214         final String description = getNullableDescription() == null ? getAttributeYangName() : getNullableDescription();
215
216         final FunctionImpl functionImpl = new FunctionImpl();
217         final Map<String, AttributeIfc> jmxPropertiesToTypesMap = getJmxPropertiesToTypesMap();
218         final OpenType<?>[] itemTypes = Collections2.transform(
219                 jmxPropertiesToTypesMap.entrySet(), functionImpl).toArray(
220                 new OpenType<?>[] {});
221         final String[] itemNames = functionImpl.getItemNames();
222         try {
223             // TODO add package name to create fully qualified name for this
224             // type
225             final CompositeType compositeType = new CompositeType(
226                     getUpperCaseCammelCase(), description, itemNames,
227                     itemNames, itemTypes);
228             return compositeType;
229         } catch (final OpenDataException e) {
230             throw new RuntimeException("Unable to create CompositeType for "
231                     + this, e);
232         }
233     }
234
235     public String getPackageName() {
236         return this.packageName;
237     }
238
239 }
240
241 class FunctionImpl implements
242         Function<Entry<String, AttributeIfc>, OpenType<?>> {
243     private final List<String> itemNames = new ArrayList<>();
244
245     @Override
246     public OpenType<?> apply(final Entry<String, AttributeIfc> input) {
247         final AttributeIfc innerType = input.getValue();
248         this.itemNames.add(input.getKey());
249         return innerType.getOpenType();
250     }
251
252     public String[] getItemNames(){
253         return this.itemNames.toArray(new String[this.itemNames.size()]);
254     }
255 }