Service-notification handling for Renderer
[transportpce.git] / servicehandler / src / main / java / org / opendaylight / transportpce / servicehandler / stub / StubrendererImpl.java
1 /*
2  * Copyright © 2017 Orange, 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
9
10 package org.opendaylight.transportpce.servicehandler.stub;
11
12 import com.google.common.base.Optional;
13 import com.google.common.util.concurrent.ListenableFuture;
14
15 import java.util.concurrent.ExecutionException;
16 import java.util.concurrent.TimeUnit;
17 import java.util.concurrent.TimeoutException;
18
19 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
20 import org.opendaylight.controller.md.sal.binding.api.NotificationPublishService;
21 import org.opendaylight.controller.md.sal.binding.api.ReadOnlyTransaction;
22 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
23 import org.opendaylight.transportpce.common.ResponseCodes;
24 import org.opendaylight.transportpce.common.Timeouts;
25 import org.opendaylight.transportpce.renderer.NetworkModelWavelengthService;
26 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.ServiceDeleteInput;
27 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.ServiceDeleteOutput;
28 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.ServiceDeleteOutputBuilder;
29 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.ServiceImplementationRequestInput;
30 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.ServiceImplementationRequestOutput;
31 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.ServiceImplementationRequestOutputBuilder;
32 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.ServiceRpcResultSp;
33 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.ServiceRpcResultSpBuilder;
34 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.service.rpc.result.sp.PathTopology;
35 import org.opendaylight.yang.gen.v1.http.org.opendaylight.transportpce.renderer.rev171017.service.rpc.result.sp.PathTopologyBuilder;
36 import org.opendaylight.yang.gen.v1.http.org.openroadm.common.service.types.rev161014.configuration.response.common.ConfigurationResponseCommonBuilder;
37 import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev171016.RpcStatusEx;
38 import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev171016.ServicePathNotificationTypes;
39 import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.service.types.rev171016.service.path.PathDescription;
40 import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.servicepath.rev171017.ServicePathList;
41 import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.servicepath.rev171017.service.path.list.ServicePaths;
42 import org.opendaylight.yang.gen.v1.http.org.transportpce.b.c._interface.servicepath.rev171017.service.path.list.ServicePathsKey;
43 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
44 import org.opendaylight.yangtools.yang.binding.Notification;
45 import org.opendaylight.yangtools.yang.common.RpcResult;
46 import org.opendaylight.yangtools.yang.common.RpcResultBuilder;
47 import org.slf4j.Logger;
48 import org.slf4j.LoggerFactory;
49
50
51
52 /**
53  * Class to implement StubrendererService.
54  * @author Martial Coulibaly ( martial.coulibaly@gfi.com ) on behalf of Orange
55  *
56  */
57 public class StubrendererImpl {
58     /** Logging. */
59     private static final Logger LOG = LoggerFactory.getLogger(StubrendererImpl.class);
60     /** check service sdnc-request-header compliancy. */
61     private final NotificationPublishService notificationPublishService;
62     private final NetworkModelWavelengthService networkModelWavelengthService;
63     private final DataBroker dataBroker;
64     private ServiceRpcResultSp notification = null;
65
66     public StubrendererImpl(NetworkModelWavelengthService networkModelWavelengthService, DataBroker dataBroker,
67             NotificationPublishService notificationPublishService) {
68         this.notificationPublishService = notificationPublishService;
69         this.networkModelWavelengthService = networkModelWavelengthService;
70         this.dataBroker = dataBroker;
71     }
72
73     private void sendNotifications(Notification notif) {
74         try {
75             notificationPublishService.putNotification(notif);
76         } catch (InterruptedException e) {
77             LOG.info("notification offer rejected : ", e.getMessage());
78         }
79     }
80
81     public ListenableFuture<RpcResult<ServiceDeleteOutput>> serviceDelete(ServiceDeleteInput input) {
82         LOG.info("ServiceDelete request ...");
83         String serviceName = input.getServiceName();
84         String message = "";
85         String responseCode = null;
86         notification = new ServiceRpcResultSpBuilder().setNotificationType(ServicePathNotificationTypes.ServiceDelete)
87                 .setServiceName(serviceName).setStatus(RpcStatusEx.Pending)
88                 .setStatusMessage("Service compliant, submitting serviceDelete Request ...").build();
89         sendNotifications(notification);
90         try {
91             LOG.info("Wait for 10s til beginning the Renderer serviceDelete request");
92             Thread.sleep(10000); // sleep for 1s
93         } catch (InterruptedException e) {
94             message = "deleting service failed !";
95             LOG.error("deleting service failed !", e);
96             responseCode = ResponseCodes.RESPONSE_FAILED;
97         }
98         // Obtain path description
99         Optional<PathDescription> pathDescriptionOpt = getPathDescriptionFromDatastore(serviceName);
100         PathDescription pathDescription;
101         if (pathDescriptionOpt.isPresent()) {
102             pathDescription = pathDescriptionOpt.get();
103             this.networkModelWavelengthService.freeWavelengths(pathDescription);
104             responseCode = ResponseCodes.RESPONSE_OK;
105             message = "service deleted !";
106         } else {
107             LOG.error("failed to get pathDescription for service : {}", serviceName);
108             responseCode = ResponseCodes.RESPONSE_FAILED;
109             message = "failed to get pathDescription for service : " + serviceName;
110         }
111         notification = new ServiceRpcResultSpBuilder().setNotificationType(ServicePathNotificationTypes.ServiceDelete)
112                 .setServiceName(input.getServiceName()).setStatus(RpcStatusEx.Successful)
113                 .setStatusMessage("Service deleted").build();
114         sendNotifications(notification);
115         responseCode = ResponseCodes.RESPONSE_OK;
116         ConfigurationResponseCommonBuilder configurationResponseCommon = new ConfigurationResponseCommonBuilder()
117                 .setAckFinalIndicator(ResponseCodes.FINAL_ACK_YES)
118                 .setRequestId(input.getServiceHandlerHeader().getRequestId())
119                 .setResponseCode(responseCode)
120                 .setResponseMessage(message);
121         ServiceDeleteOutput output =  new ServiceDeleteOutputBuilder()
122                 .setConfigurationResponseCommon(configurationResponseCommon.build())
123                 .build();
124         return RpcResultBuilder.success(output).buildFuture();
125     }
126
127     public ListenableFuture<RpcResult<ServiceImplementationRequestOutput>>
128         serviceImplementation(ServiceImplementationRequestInput input) {
129         LOG.info("serviceImplementation request ...");
130         String message = "";
131         String responseCode = null;
132         notification = new ServiceRpcResultSpBuilder()
133                 .setNotificationType(ServicePathNotificationTypes.ServiceImplementationRequest)
134                 .setServiceName(input.getServiceName()).setStatus(RpcStatusEx.Pending)
135                 .setStatusMessage("Service compliant, submitting serviceImplementation Request ...").build();
136         sendNotifications(notification);
137         try {
138             LOG.info("Wait for 10s til beginning the Renderer serviceImplementation request");
139             Thread.sleep(10000); // sleep for 1s
140         } catch (InterruptedException e) {
141             message = "implementing service failed !";
142             LOG.error(message);
143             responseCode = ResponseCodes.RESPONSE_FAILED;
144         }
145         this.networkModelWavelengthService.useWavelengths(input.getPathDescription());
146         message = "service implemented !";
147         PathTopology pathTopology = new PathTopologyBuilder().build();
148         notification = new ServiceRpcResultSpBuilder()
149                 .setNotificationType(ServicePathNotificationTypes.ServiceImplementationRequest)
150                 .setServiceName(input.getServiceName()).setStatus(RpcStatusEx.Successful)
151                 .setStatusMessage("Service implemented").setPathTopology(pathTopology).build();
152         sendNotifications(notification);
153         responseCode = ResponseCodes.RESPONSE_OK;
154         ConfigurationResponseCommonBuilder configurationResponseCommon = new ConfigurationResponseCommonBuilder()
155                 .setAckFinalIndicator(ResponseCodes.FINAL_ACK_YES)
156                 .setRequestId(input.getServiceHandlerHeader().getRequestId())
157                 .setResponseCode(responseCode)
158                 .setResponseMessage(message);
159         ServiceImplementationRequestOutput output =  new ServiceImplementationRequestOutputBuilder()
160                 .setConfigurationResponseCommon(configurationResponseCommon.build())
161                 .build();
162         return RpcResultBuilder.success(output).buildFuture();
163     }
164
165     private Optional<PathDescription> getPathDescriptionFromDatastore(String serviceName) {
166         InstanceIdentifier<PathDescription> pathDescriptionIID = InstanceIdentifier.create(ServicePathList.class)
167                 .child(ServicePaths.class, new ServicePathsKey(serviceName)).child(PathDescription.class);
168         ReadOnlyTransaction pathDescReadTx = this.dataBroker.newReadOnlyTransaction();
169         try {
170             LOG.debug("Getting path description for service {}", serviceName);
171             return pathDescReadTx.read(LogicalDatastoreType.OPERATIONAL, pathDescriptionIID)
172                     .get(Timeouts.DATASTORE_READ, TimeUnit.MILLISECONDS);
173         } catch (InterruptedException | ExecutionException | TimeoutException e) {
174             LOG.warn("Exception while getting path description from datastore {} for service {}!", pathDescriptionIID,
175                     serviceName, e);
176             return Optional.absent();
177         }
178     }
179 }