Provide the SPCE module
[alto.git] / alto-services / provider / simple-alto / src / main / java / org / opendaylight / alto / services / provider / simple / SimpleAltoService.java
1 /*
2  * Copyright (c) 2015 Yale University 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
9 package org.opendaylight.alto.services.provider.simple;
10
11 import org.opendaylight.alto.commons.helper.NetworkMapIpPrefixHelper;
12 import org.opendaylight.alto.commons.types.converter.CostRequest2EndpointCostServiceInputConverter;
13 import org.opendaylight.alto.commons.types.converter.EndpointCostServiceOutput2CostResponseConverter;
14 import org.opendaylight.alto.commons.types.converter.YANGJSON2RFCCostMapConverter;
15 import org.opendaylight.alto.commons.types.converter.YANGJSON2RFCEndpointPropMapConverter;
16 import org.opendaylight.alto.commons.types.converter.YANGJSON2RFCIRDConverter;
17 import org.opendaylight.alto.commons.types.converter.YANGJSON2RFCNetworkMapConverter;
18 import org.opendaylight.alto.commons.types.rfc7285.RFC7285CostMap;
19 import org.opendaylight.alto.commons.types.rfc7285.RFC7285CostType;
20 import org.opendaylight.alto.commons.types.rfc7285.RFC7285Endpoint;
21 import org.opendaylight.alto.commons.types.rfc7285.RFC7285Endpoint.AddressGroup;
22 import org.opendaylight.alto.commons.types.rfc7285.RFC7285Endpoint.CostRequest;
23 import org.opendaylight.alto.commons.types.rfc7285.RFC7285Endpoint.CostResponse;
24 import org.opendaylight.alto.commons.types.rfc7285.RFC7285Endpoint.PropertyRequest;
25 import org.opendaylight.alto.commons.types.rfc7285.RFC7285Endpoint.PropertyResponse;
26 import org.opendaylight.alto.commons.types.rfc7285.RFC7285EndpointPropertyMap;
27 import org.opendaylight.alto.commons.types.rfc7285.RFC7285IRD;
28 import org.opendaylight.alto.commons.types.rfc7285.RFC7285JSONMapper;
29 import org.opendaylight.alto.commons.types.rfc7285.RFC7285NetworkMap;
30 import org.opendaylight.alto.commons.types.rfc7285.RFC7285VersionTag;
31 import org.opendaylight.alto.services.api.rfc7285.AltoService;
32 import org.opendaylight.alto.services.api.rfc7285.NetworkMapService;
33 import org.opendaylight.alto.services.api.rfc7285.CostMapService;
34 import org.opendaylight.alto.services.api.rfc7285.EndpointCostService;
35 import org.opendaylight.alto.services.api.rfc7285.EndpointPropertyService;
36 import org.opendaylight.alto.services.api.rfc7285.IRDService;
37 import org.opendaylight.alto.commons.helper.ServiceHelper;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.cost.map.map.DstCosts;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.AltoServiceService;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.EndpointCostServiceInput;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.EndpointCostServiceOutput;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.Resources;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.resources.CostMaps;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.resources.EndpointPropertyMap;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.resources.IRD;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.resources.NetworkMaps;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.resources.cost.maps.CostMap;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.resources.cost.maps.CostMapKey;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.resources.network.maps.NetworkMap;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.rev150404.resources.network.maps.NetworkMapKey;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.service.types.rev150404.PidName;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.service.types.rev150404.ResourceId;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.service.types.rev150404.TypedEndpointAddress;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.service.types.rev150404.TypedEndpointAddressBuilder;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.service.types.rev150404.ird.Meta;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.alto.service.types.rev150404.ird.meta.DefaultAltoNetworkMap;
57 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
58 import org.opendaylight.yangtools.yang.binding.Augmentation;
59 import org.opendaylight.yangtools.yang.binding.util.BindingReflections;
60 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
61 import org.opendaylight.controller.md.sal.binding.api.ReadOnlyTransaction;
62 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
63 import org.opendaylight.yangtools.yang.common.RpcResult;
64 import org.osgi.framework.ServiceRegistration;
65
66 import com.google.common.base.Optional;
67 import com.google.common.util.concurrent.ListenableFuture;
68
69 import java.util.Iterator;
70 import java.util.Map;
71 import java.util.LinkedHashMap;
72 import java.util.List;
73 import java.util.LinkedList;
74 import java.util.concurrent.ExecutionException;
75 import java.util.concurrent.Future;
76
77 import org.slf4j.Logger;
78 import org.slf4j.LoggerFactory;
79
80 import com.fasterxml.jackson.core.JsonGenerator;
81 import com.fasterxml.jackson.databind.ObjectMapper;
82 import com.fasterxml.jackson.databind.node.ObjectNode;
83 import com.fasterxml.jackson.databind.JsonSerializer;
84 import com.fasterxml.jackson.databind.SerializerProvider;
85 import com.fasterxml.jackson.databind.module.SimpleModule;
86
87 @SuppressWarnings("rawtypes")
88 public class SimpleAltoService implements AltoService, AutoCloseable {
89
90     private final Logger m_logger = LoggerFactory.getLogger(SimpleAltoService.class);
91     private DataBroker m_db = null;
92     private AltoServiceService m_service = null;
93
94     private ObjectMapper m_mapper = new ObjectMapper();
95     private RFC7285JSONMapper j_mapper = new RFC7285JSONMapper();
96     private List<ServiceRegistration> m_reg = new LinkedList<ServiceRegistration>();
97     private YANGJSON2RFCNetworkMapConverter m_nmconverter = null;
98     private YANGJSON2RFCCostMapConverter m_cmconverter = null;
99     private YANGJSON2RFCEndpointPropMapConverter m_epmconverter = null;
100     private YANGJSON2RFCIRDConverter m_irdconverter = null;
101     private EndpointCostServiceOutput2CostResponseConverter ecsOutputConverter = null;
102     private CostRequest2EndpointCostServiceInputConverter ecsInputConverter = null;
103     private NetworkMapIpPrefixHelper iHelper = new NetworkMapIpPrefixHelper();
104     private final String PRIV_NETWORK_MAP = "private-network-map";
105     private final String PRIV_ENDPOINT_PROPERTY_NAME = "priv:ietf-type";
106
107     protected class DstCostSerializer extends JsonSerializer<DstCosts> {
108         @Override
109         public void serialize(DstCosts value, JsonGenerator jgen, SerializerProvider provider) {
110             try {
111                 jgen.writeStartObject();
112
113                 jgen.writeObjectFieldStart("dst");
114                 jgen.writeStringField("value", value.getDst().getValue());
115                 jgen.writeEndObject();
116
117                 Map<Class<? extends Augmentation<?>>, Augmentation<?>> augmentations
118                         = BindingReflections.getAugmentations(value);
119                 String cost = null;
120                 for (Augmentation<?> aug : augmentations.values()) {
121                     try {
122                         ObjectNode node = m_mapper.valueToTree(aug);
123                         for (Iterator<String> itr = node.fieldNames(); itr.hasNext();) {
124                             String field = itr.next();
125                             if (field.toLowerCase().indexOf("cost") >= 0) {
126                                 cost = node.get(field).asText();
127                                 break;
128                             }
129                         }
130                     } catch (Exception e) {
131                         m_logger.warn("Failed to write data from {}", cost);
132                     }
133                 }
134                 if (cost != null) {
135                     jgen.writeStringField("cost", cost);
136                 }
137
138                 jgen.writeEndObject();
139             } catch (Exception e) {
140                 m_logger.info("Failed to parse DstCosts");
141             }
142         }
143     }
144
145     public SimpleAltoService(DataBroker db, AltoServiceService service) {
146         this.m_db = db;
147         this.m_service = service;
148         this.m_nmconverter = new YANGJSON2RFCNetworkMapConverter();
149         this.m_cmconverter = new YANGJSON2RFCCostMapConverter();
150         this.m_epmconverter = new YANGJSON2RFCEndpointPropMapConverter();
151         this.m_irdconverter = new YANGJSON2RFCIRDConverter();
152         this.ecsOutputConverter = new EndpointCostServiceOutput2CostResponseConverter();
153         this.ecsInputConverter = new CostRequest2EndpointCostServiceInputConverter();
154
155         this.register(IRDService.class);
156         this.register(NetworkMapService.class);
157         this.register(CostMapService.class);
158         this.register(EndpointPropertyService.class);
159         this.register(EndpointCostService.class);
160
161         try {
162             SimpleModule module = new SimpleModule();
163             module.addSerializer(DstCosts.class, new DstCostSerializer());
164             m_mapper.registerModule(module);
165         } catch (Exception e) {
166             m_logger.info("failed to load customized serializer");
167         }
168     }
169
170     protected <E> void register(Class<E> clazz) {
171         ServiceRegistration reg = ServiceHelper.registerGlobalServiceWReg(clazz, this, null);
172         if (reg != null)
173             this.m_reg.add(reg);
174
175         assert ServiceHelper.getGlobalInstance(clazz, this) != this;
176     }
177
178     @Override
179     public void close() {
180         for (ServiceRegistration reg : this.m_reg) {
181             reg.unregister();
182         }
183         this.m_reg.clear();
184     }
185
186     @Override
187     public RFC7285NetworkMap getDefaultNetworkMap() {
188         //TODO
189         return null;
190     }
191
192     @Override
193     public RFC7285NetworkMap getNetworkMap(String id) {
194         m_logger.info("Handling resource-id: {}", id);
195         InstanceIdentifier<NetworkMap> niid = getNetworkMapIID(id);
196         m_logger.info("IID: {}", niid);
197
198         try {
199             ReadOnlyTransaction tx = m_db.newReadOnlyTransaction();
200             ListenableFuture<Optional<NetworkMap>> result
201                         = tx.read(LogicalDatastoreType.CONFIGURATION, niid);
202             if (result.get().isPresent()) {
203                 NetworkMap nm = result.get().get();
204                 ObjectNode node = m_mapper.valueToTree(nm);
205                 m_logger.info(m_mapper.writeValueAsString(nm));
206
207                 RFC7285NetworkMap ret = m_nmconverter.convert(node);
208                 return ret;
209             } else {
210                 m_logger.info("Failed to read with niid: {}", niid);
211             }
212         } catch (Exception e) {
213             e.printStackTrace();
214         }
215         return null;
216     }
217
218     @Override
219     public RFC7285NetworkMap getNetworkMap(RFC7285VersionTag vtag) {
220         RFC7285NetworkMap nm = getNetworkMap(vtag.rid);
221
222         if ((nm != null) && (vtag.equals(nm.meta.vtag))) {
223             return nm;
224         }
225         return null;
226     }
227
228     @Override
229     public RFC7285NetworkMap getNetworkMap(String id, RFC7285NetworkMap.Filter filter) {
230         RFC7285NetworkMap nm = getNetworkMap(id);
231
232         if (nm == null)
233             return null;
234
235         LinkedHashMap<String, RFC7285Endpoint.AddressGroup> map = new LinkedHashMap<String, RFC7285Endpoint.AddressGroup>();
236         for (String pid : filter.pids) {
237             if (nm.map.get(pid) != null)
238                 map.put(pid, nm.map.get(pid));
239         }
240         if (filter.pids.isEmpty()) {
241             map = new LinkedHashMap<String, RFC7285Endpoint.AddressGroup>(nm.map);
242         }
243         LinkedHashMap<String, RFC7285Endpoint.AddressGroup> ret = new LinkedHashMap<String, RFC7285Endpoint.AddressGroup>();
244         for (Map.Entry<String, RFC7285Endpoint.AddressGroup> entry : map.entrySet()) {
245             String pid = entry.getKey();
246             if (filter.addressTypes != null && (!filter.addressTypes.isEmpty())) {
247                 AddressGroup ag = new AddressGroup();
248                 if (filter.addressTypes.contains("ipv4")) {
249                     ag.ipv4 = nm.map.get(pid).ipv4;
250                 }
251                 if (filter.addressTypes.contains("ipv6")) {
252                     ag.ipv6 = nm.map.get(pid).ipv6;
253                 }
254                 if (!ag.ipv4.isEmpty() || !ag.ipv6.isEmpty())
255                     ret.put(pid, ag);
256             } else {
257                 ret.put(pid, entry.getValue());
258             }
259         }
260         nm.map = ret;
261         return nm;
262     }
263
264     @Override
265     public RFC7285NetworkMap getNetworkMap(RFC7285VersionTag vtag, RFC7285NetworkMap.Filter filter) {
266         RFC7285NetworkMap nm = getNetworkMap(vtag.rid, filter);
267         if ((nm != null) && (vtag.equals(nm.meta.vtag))) {
268             return nm;
269         }
270         return null;
271     }
272
273     @Override
274     public Boolean validateNetworkMapFilter(String id, RFC7285NetworkMap.Filter filter) {
275         return (filter != null) && (filter.pids != null);
276     }
277
278     @Override
279     public Boolean validateNetworkMapFilter(RFC7285VersionTag vtag, RFC7285NetworkMap.Filter filter) {
280         return validateNetworkMapFilter(vtag.rid, filter);
281     }
282
283     @Override
284     public RFC7285CostMap getCostMap(String id) {
285         m_logger.info("Handling cost-map resource: {}", id);
286         InstanceIdentifier<CostMap> ciid = getCostMapIID(id);
287         m_logger.info("CostMap IID: {}", ciid);
288
289         try {
290             ReadOnlyTransaction tx = m_db.newReadOnlyTransaction();
291             ListenableFuture<Optional<CostMap>> result
292                         = tx.read(LogicalDatastoreType.CONFIGURATION, ciid);
293             if (result.get().isPresent()) {
294                 CostMap cm = result.get().get();
295                 m_logger.info(cm.toString());
296                 m_logger.info(m_mapper.writeValueAsString(cm));
297                 ObjectNode node = m_mapper.valueToTree(cm);
298
299                 RFC7285CostMap ret = m_cmconverter.convert(node);
300                 return ret;
301             } else {
302                 m_logger.info("Failed to read with ciid: {}", ciid);
303             }
304         } catch (Exception e) {
305             e.printStackTrace();
306         }
307         return null;
308     }
309
310     @Override
311     public RFC7285CostMap getCostMap(RFC7285VersionTag vtag) {
312         //TODO
313         return null;
314     }
315
316     @Override
317     public RFC7285CostMap getCostMap(String id, RFC7285CostType type) {
318         RFC7285CostMap cm = getCostMap(id);
319         if (cm == null)
320             return null;
321         if (!type.equals(cm.meta.costType))
322             return null;
323         return cm;
324     }
325
326     @Override
327     public RFC7285CostMap getCostMap(RFC7285VersionTag vtag, RFC7285CostType type) {
328         //TODO
329         return null;
330     }
331
332     @Override
333     public RFC7285CostMap getCostMap(String id, RFC7285CostMap.Filter filter) {
334         RFC7285CostMap cm = getCostMap(id + "-" + filter.costType.metric + "-" + filter.costType.mode);
335
336         if (cm == null)
337             return null;
338
339         if (filter.pids != null) {
340             if (filter.pids.src.isEmpty())
341                 filter.pids.src = new LinkedList<String>(cm.map.keySet());
342             if (filter.pids.dst.isEmpty())
343                 filter.pids.dst = new LinkedList<String>(cm.map.keySet());
344
345             Map<String, Map<String, Object>> data = new LinkedHashMap<String, Map<String, Object>>();
346             for (String src : filter.pids.src) {
347                 if (!cm.map.containsKey(src))
348                     continue;
349                 Map<String, Object> old_data = cm.map.get(src);
350                 if (old_data == null)
351                     continue;
352
353                 Map<String, Object> new_data = new LinkedHashMap<String, Object>();
354                 for (String dst : filter.pids.dst) {
355                     if (!old_data.containsKey(dst))
356                         continue;
357                     if (filter.constraints == null || filter.constraints.isEmpty()
358                             || meetConstraints(filter.constraints, old_data.get(dst)))
359                         new_data.put(dst, old_data.get(dst));
360                 }
361                 data.put(src, new_data);
362             }
363             cm.map = data;
364         }
365         return cm;
366     }
367
368     private boolean meetConstraints(List<String> constraints, Object object) {
369         // We'd better simplify the constraints before using it.
370         for (String constraint : constraints)
371             if (!meetConstraint(constraint, object))
372                 return false;
373         return true;
374     }
375
376     private boolean meetConstraint(String constraint, Object object) {
377         String operator = constraint.substring(0, 2);
378         double target = Double.parseDouble(object.toString());
379         double value = Double.parseDouble(constraint.substring(3));
380         switch (operator) {
381         case "gt":
382             return target > value;
383         case "lt":
384             return target < value;
385         case "ge":
386             return target >= value;
387         case "le":
388             return target <= value;
389         case "eq":
390             return target == value;
391         }
392         return false;
393     }
394
395     @Override
396     public RFC7285CostMap getCostMap(RFC7285VersionTag vtag, RFC7285CostMap.Filter filter) {
397         //TODO
398         return null;
399     }
400
401     @Override
402     public Boolean supportCostType(String id, RFC7285CostType type) {
403         //TODO
404         return true;
405     }
406
407     @Override
408     public Boolean supportCostType(RFC7285VersionTag vtag, RFC7285CostType type) {
409         //TODO
410         return true;
411     }
412
413     @Override
414     public Boolean validateCostMapFilter(String id, RFC7285CostMap.Filter filter) {
415         //TODO
416         return true;
417     }
418
419     @Override
420     public Boolean validateCostMapFilter(RFC7285VersionTag vtag, RFC7285CostMap.Filter filter) {
421         //TODO
422         return true;
423     }
424
425     protected InstanceIdentifier<DefaultAltoNetworkMap> getDefaultNetworkMapIID() {
426         InstanceIdentifier<DefaultAltoNetworkMap> iid = InstanceIdentifier.builder(Resources.class)
427                                                 .child(IRD.class)
428                                                 .child(Meta.class)
429                                                 .child(DefaultAltoNetworkMap.class).build();
430         return iid;
431     }
432
433     protected InstanceIdentifier<NetworkMap> getNetworkMapIID(String resource_id) {
434         NetworkMapKey key = new NetworkMapKey(ResourceId.getDefaultInstance(resource_id));
435         InstanceIdentifier<NetworkMap> iid = InstanceIdentifier.builder(Resources.class)
436                                                 .child(NetworkMaps.class)
437                                                 .child(NetworkMap.class, key)
438                                                 .build();
439         return iid;
440     }
441
442     protected InstanceIdentifier<CostMap> getCostMapIID(String resource_id) {
443         CostMapKey key = new CostMapKey(ResourceId.getDefaultInstance(resource_id));
444         InstanceIdentifier<CostMap> iid = InstanceIdentifier.builder(Resources.class)
445                                                 .child(CostMaps.class)
446                                                 .child(CostMap.class, key)
447                                                 .build();
448         return iid;
449     }
450
451     protected InstanceIdentifier<EndpointPropertyMap> getEndpointPropertyMapIID() {
452         InstanceIdentifier<EndpointPropertyMap> iid = InstanceIdentifier.builder(Resources.class)
453                 .child(EndpointPropertyMap.class).build();
454         return iid;
455     }
456
457     @Override
458     public PropertyResponse getEndpointProperty(PropertyRequest request) {
459         InstanceIdentifier<EndpointPropertyMap> eiid = getEndpointPropertyMapIID();
460         m_logger.info("EndpointPropertyMap IID: {}", eiid);
461         updatePrivateNetworkMap();
462
463         try {
464             ReadOnlyTransaction tx = m_db.newReadOnlyTransaction();
465             ListenableFuture<Optional<EndpointPropertyMap>> result = tx.read(LogicalDatastoreType.CONFIGURATION, eiid);
466             if (result.get().isPresent()) {
467                 EndpointPropertyMap epm = result.get().get();
468                 ObjectNode node = m_mapper.valueToTree(epm);
469                 m_logger.info(m_mapper.writeValueAsString(epm));
470
471                 RFC7285EndpointPropertyMap endpointPropMap = m_epmconverter.convert(node);
472                 RFC7285EndpointPropertyMap ret = new RFC7285EndpointPropertyMap();
473                 ret.meta = endpointPropMap.meta;
474                 ret.meta.netmap_tags = getDependentTags(endpointPropMap.meta, request.properties);
475                 for (String addr : request.endpoints) {
476                     Map<String, String> newProps = new LinkedHashMap<String, String>();
477                     if (endpointPropMap.map.containsKey(addr.toLowerCase())) {
478                         Map<String, String> props = endpointPropMap.map.get(addr);
479                         for (String type : request.properties) {
480                             if (props.containsKey(type)) {
481                                 newProps.put(type, props.get(type));
482                             }
483                         }
484                     } else if (request.properties.contains(PRIV_ENDPOINT_PROPERTY_NAME)) {
485                         newProps = getPrivateEndpointProperty(addr);
486                     }
487                     if (!newProps.isEmpty())
488                         ret.map.put(addr, newProps);
489                 }
490                 return j_mapper.asPropertyResponse(j_mapper.asJSON(ret));
491             } else {
492                 m_logger.info("Failed to read with eiid: {}", eiid);
493             }
494         } catch (Exception e) {
495             e.printStackTrace();
496         }
497         return null;
498     }
499
500     private void updatePrivateNetworkMap() {
501         InstanceIdentifier<NetworkMap> niid = getNetworkMapIID(PRIV_NETWORK_MAP);
502         try {
503             ReadOnlyTransaction tx = m_db.newReadOnlyTransaction();
504             ListenableFuture<Optional<NetworkMap>> result
505                         = tx.read(LogicalDatastoreType.CONFIGURATION, niid);
506             if (result.get().isPresent()) {
507                 NetworkMap privateNetworkMap = result.get().get();
508                 iHelper.update(privateNetworkMap);
509             } else {
510                 m_logger.info("Failed to read with niid: {}", niid);
511             }
512         } catch (Exception e) {
513             e.printStackTrace();
514         }
515     }
516
517     private List<RFC7285VersionTag> getDependentTags(RFC7285EndpointPropertyMap.Meta meta, List<String> properties) {
518         List<RFC7285VersionTag> dependentTags = new LinkedList<RFC7285VersionTag>();
519         for (RFC7285VersionTag vtag : meta.netmap_tags) {
520             if (properties.contains(vtag.rid + ".pid"))
521                 dependentTags.add(vtag);
522         }
523         return dependentTags;
524     }
525
526     private Map<String, String> getPrivateEndpointProperty(String addr) {
527         Map<String, String> property = new LinkedHashMap<String, String>();
528         try {
529             TypedEndpointAddress address = TypedEndpointAddressBuilder.getDefaultInstance(addr);
530             PidName pid = iHelper.getPIDByEndpointAddress(address);
531             if (pid != null)
532                 property.put(PRIV_ENDPOINT_PROPERTY_NAME, pid.getValue());
533         } catch (Exception e) {
534             e.printStackTrace();
535         }
536         return property;
537     }
538
539     @Override
540     public RFC7285IRD getDefaultIRD() {
541         InstanceIdentifier<IRD> iid = getIRDIID();
542
543         try {
544             ReadOnlyTransaction tx = m_db.newReadOnlyTransaction();
545             ListenableFuture<Optional<IRD>> result = tx.read(LogicalDatastoreType.CONFIGURATION, iid);
546             if (result.get().isPresent()) {
547                 IRD iIRD = result.get().get();
548                 m_logger.info(iIRD.toString());
549                 m_logger.info(m_mapper.writeValueAsString(iIRD));
550                 ObjectNode node = m_mapper.valueToTree(iIRD);
551
552                 RFC7285IRD ret = m_irdconverter.convert(node);
553                 m_logger.info("IRD convert compelete.");
554                 return ret;
555             } else {
556                 m_logger.info("Failed to read with ciid: {}", iid);
557             }
558         } catch (Exception e) {
559             e.printStackTrace();
560         }
561         return null;
562     }
563
564     @Override
565     public PropertyResponse getEndpointProperty(RFC7285VersionTag vtag, PropertyRequest request) {
566         return null;
567     }
568
569     @Override
570     public CostResponse getEndpointCost(CostRequest request) {
571         CostResponse response = null;
572         EndpointCostServiceInput input = this.ecsInputConverter.convert(request);
573         Future<RpcResult<EndpointCostServiceOutput>> result = this.m_service.endpointCostService(input);
574         try {
575             EndpointCostServiceOutput output = result.get().getResult();
576             response = this.ecsOutputConverter.convert(output);
577         } catch (InterruptedException | ExecutionException e) {
578             e.printStackTrace();
579         }
580         return response;
581     }
582
583     @Override
584     public CostResponse getEndpointCost(RFC7285VersionTag vtag, CostRequest request) {
585         return null;
586     }
587
588     public RFC7285IRD getIRD(String id) {
589         return this.getDefaultIRD();
590     }
591
592     protected InstanceIdentifier<IRD> getIRDIID() {
593         InstanceIdentifier<IRD> iid = InstanceIdentifier.builder(Resources.class).child(IRD.class).build();
594         return iid;
595     }
596 }