Add seed code for sdnr app based on ONF Centennial
[ccsdk/apps.git] / sdnr / wireless-transport / code-Carbon-SR1 / apps / route / impl / src / main / java / com / highstreet / technologies / odl / app / impl / tools / NeExecutor.java
1 /*
2  * Copyright © 2015 ZTE 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 com.highstreet.technologies.odl.app.impl.tools;
9
10 import com.google.common.base.Optional;
11 import com.highstreet.technologies.odl.app.impl.delegates.LtpInOdlCreator;
12 import com.highstreet.technologies.odl.app.impl.listener.ACMListener;
13 import org.opendaylight.controller.md.sal.binding.api.*;
14 import org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType;
15 import org.opendaylight.controller.md.sal.common.api.data.ReadFailedException;
16 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.*;
17 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.local._class.g.LocalId;
18 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.local._class.g.LocalIdBuilder;
19 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.logical.termination.point.g.Lp;
20 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.logical.termination.point.g.LpBuilder;
21 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.logical.termination.point.g.LpKey;
22 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.name.g.Name;
23 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.name.g.NameBuilder;
24 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.network.element.FdBuilder;
25 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.network.element.Ltp;
26 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.network.element.LtpBuilder;
27 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.core.model.rev170320.network.element.LtpKey;
28 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.ltp.path.rev170526.ltp.path.ltp.path.list.LogicalTerminationPointList;
29 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.microwave.model.rev170324.MwAirInterfacePac;
30 import org.opendaylight.yang.gen.v1.urn.onf.params.xml.ns.yang.microwave.model.rev170324.MwAirInterfacePacKey;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.route.rev150105.RestoreFollowTopoInputBuilder;
32 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.route.rev150105.SwitchFollowTopoInputBuilder;
33 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.route.rev150105.fc_desc.Fc;
34 import org.opendaylight.yangtools.yang.binding.ChildOf;
35 import org.opendaylight.yangtools.yang.binding.InstanceIdentifier;
36 import org.slf4j.Logger;
37 import org.slf4j.LoggerFactory;
38
39 import java.util.*;
40 import java.util.concurrent.ExecutionException;
41
42 import static com.highstreet.technologies.odl.app.impl.tools.MountPointServiceHolder.getMountPoint;
43 import static com.highstreet.technologies.odl.app.impl.tools.RPCHolder.rpc;
44 import static org.opendaylight.controller.md.sal.common.api.data.LogicalDatastoreType.CONFIGURATION;
45
46 /**
47  * Created by odl on 17-6-3.
48  */
49 public class NeExecutor
50 {
51     private boolean isBroken = false;
52
53     public NeExecutor(Fc fc, Integer vlanid, LtpInOdlCreator ltpCreator)
54     {
55         this(getMountPoint(fc.getNodeName()));
56         this.vlanId = vlanid;
57         process(fc, vlanid, ltpCreator);
58     }
59
60     public NeExecutor(MountPoint mountPoint)
61     {
62         if (mountPoint != null)
63         {
64             this.dataBroker = mountPoint.getService(DataBroker.class).get();
65             mountPoint.getService(NotificationService.class).get().registerNotificationListener(new ACMListener(this));
66         } else
67         {
68             this.isBroken = true;
69             LOG.warn("mount point is null");
70         }
71     }
72
73     private List<LogicalTerminationPointList> process(Fc fc, Integer vlanId, LtpInOdlCreator ltpInOdlCreator)
74     {
75         try
76         {
77             if (isBroken)
78                 return new ArrayList<>();
79             getNe();
80
81             // start the creation of fc
82             // add client ltps
83             ltp.add(addClientLtpTo(neBuilder, vlanId, fc.getAEnd(), ltpInOdlCreator));
84             ltp.add(addClientLtpTo(neBuilder, vlanId, fc.getZEnd(), ltpInOdlCreator));
85
86             // add fc into fd
87             FdBuilder fdBuilder = new FdBuilder(neBuilder.getFd().remove(0));
88             if (fdBuilder.getFc() == null)
89                 fdBuilder.setFc(new ArrayList<>());
90
91             fdBuilder.getFc().add(new UniversalId(buildFcName(ltp)));
92
93             neBuilder.getFd().add(fdBuilder.build());
94         } catch (Throwable e)
95         {
96             LOG.warn(e.getMessage(), e);
97         }
98
99         return ltp;
100     }
101
102     private void getNe() throws ReadFailedException
103     {
104         InstanceIdentifier<NetworkElement> path = InstanceIdentifier.create(NetworkElement.class);
105         ReadOnlyTransaction networkElementTransaction = dataBroker.newReadOnlyTransaction();
106         try
107         {
108             Optional<NetworkElement> networkElementOpt = networkElementTransaction.read(
109                     CONFIGURATION, path).checkedGet();
110             if (networkElementOpt.isPresent())
111             {
112                 this.neBuilder = new NetworkElementBuilder(oldNe = networkElementOpt.get());
113             }
114         } finally
115         {
116             networkElementTransaction.close();
117         }
118     }
119
120     private LogicalTerminationPointList addClientLtpTo(
121             NetworkElementBuilder ne, int vlanid, String ltpName,
122             LtpInOdlCreator ltpInOdlCreator)
123     {
124         String clientLtpName = nameFrom(ltpName, LAYER_PROTOCOL_NAME.getValue(), vlanid);
125         String lpName = nameFrom(clientLtpName, "LP", 1);
126
127         // add client ltp to ltp
128         Ltp serverLTP = null;
129         Iterator<Ltp> iterator = ne.getLtp().iterator();
130         while (iterator.hasNext())
131         {
132             Ltp temp = iterator.next();
133             if (temp.getUuid().getValue().equalsIgnoreCase(ltpName))
134             {
135                 iterator.remove();
136                 serverLTP = temp;
137                 break;
138             }
139         }
140         if (serverLTP == null)
141         {
142             StringBuffer serverNames = new StringBuffer();
143             ne.getLtp().forEach(sltp -> serverNames.append(sltp.getKey().getUuid().getValue()).append(" | "));
144             throw new IllegalArgumentException(
145                     "no proper server ltp found, input name is: " + ltpName + " and ltps from NE are: " + serverNames);
146         }
147
148         LtpBuilder serverBuilder = new LtpBuilder(serverLTP);
149
150         if (serverBuilder.getClientLtp() == null)
151             serverBuilder.setClientLtp(new ArrayList<>());
152         serverBuilder.getClientLtp().add(new UniversalId(clientLtpName));
153
154         // add client ltp to ltps
155         LtpBuilder clientLtpBuilder = new LtpBuilder();
156         clientLtpBuilder.setKey(new LtpKey(new UniversalId(clientLtpName)));
157         clientLtpBuilder.setName(new ArrayList<>());
158         clientLtpBuilder.getName().add(toName(clientLtpName));
159         clientLtpBuilder.setServerLtp(Arrays.asList(new UniversalId(serverLTP.getKey().getUuid())));
160         // add lp to client ltp
161         LpBuilder lpBuilder = new LpBuilder();
162         lpBuilder.setKey(new LpKey(new UniversalId(lpName)));
163         lpBuilder.setLayerProtocolName(LAYER_PROTOCOL_NAME);
164         lpBuilder.setName(new ArrayList<>());
165         lpBuilder.getName().add(toName(lpName));
166
167         lpBuilder.setLocalId(new ArrayList<>());
168         lpBuilder.getLocalId().add(toLocalId(lpName));
169         lpBuilder.setTerminationState(TerminationState.LpCanNeverTerminate);
170         clientLtpBuilder.setLp(Arrays.asList(lpBuilder.build()));
171
172         ne.getLtp().add(clientLtpBuilder.build());
173         ne.getLtp().add(serverBuilder.build());
174
175         return ltpInOdlCreator.create(ne.getName().get(0).getValue(), clientLtpName, serverLTP);
176     }
177
178     private String buildFcName(ArrayList<LogicalTerminationPointList> clientLtpsInFC)
179     {
180 //        String fcName = "LTP-ETY-1.1.1-ETH-23,LTP-ETC-1.3.1-ETH-23"
181         StringBuilder fcName = new StringBuilder("");
182         for (LogicalTerminationPointList ltp : clientLtpsInFC)
183         {
184             fcName.append(ltp.getLtpReference().getValue()).append(",");
185         }
186         return fcName.deleteCharAt(fcName.length() - 1).toString();
187     }
188
189     private String nameFrom(String ltpName, String mediator, int vlanId)
190     {
191         return String.format(ltpName + "-%1$s-%2$d", mediator, vlanId);
192     }
193
194     private Name toName(String name)
195     {
196         NameBuilder nameBuilder = new NameBuilder();
197         nameBuilder.setValue(name);
198         nameBuilder.setValueName("vName");
199         return nameBuilder.build();
200     }
201
202     private LocalId toLocalId(String name)
203     {
204         LocalIdBuilder builder = new LocalIdBuilder();
205         builder.setValue(name);
206         builder.setValueName("vLocalId");
207         return builder.build();
208     }
209
210     private static final Logger LOG = LoggerFactory.getLogger(NeExecutor.class);
211     private static final LayerProtocolName LAYER_PROTOCOL_NAME = new LayerProtocolName("ETH");
212     private static boolean IS_MAIN = true;
213     private DataBroker dataBroker;
214     private Integer vlanId;
215     private ArrayList<LogicalTerminationPointList> ltp = new ArrayList<>();
216     private NetworkElementBuilder neBuilder;
217     private NetworkElement oldNe;
218
219     public List<LogicalTerminationPointList> getLtp()
220     {
221         return ltp;
222     }
223
224     public void clear(int vlanId)
225     {
226         try
227         {
228             this.neBuilder = new NetworkElementBuilder(oldNe);
229
230             // remove fc in fd
231             FdBuilder fdBuilder = new FdBuilder(neBuilder.getFd().get(0));
232             fdBuilder.getFc().removeIf(fcName -> fcName.getValue().contains(LAYER_PROTOCOL_NAME.getValue() + "-" + vlanId));
233             neBuilder.setFd(Collections.singletonList(fdBuilder.build()));
234
235             // remove ltp created by vlan
236             neBuilder.getLtp().removeIf(
237                     ltp1 -> ltp1.getUuid().getValue().endsWith(LAYER_PROTOCOL_NAME.getValue() + "-" + vlanId));
238
239             // remove all client ltp
240             ArrayList<Ltp> ltpList = new ArrayList<>();
241             for (Ltp ltp : neBuilder.getLtp())
242             {
243                 LtpBuilder ltpBuilder = new LtpBuilder(ltp);
244                 if (ltpBuilder.getClientLtp() != null)
245                 {
246                     ltpBuilder.getClientLtp().removeIf(
247                             uuid -> uuid.getValue().endsWith(LAYER_PROTOCOL_NAME.getValue() + "-" + vlanId));
248                     ltpBuilder.getLp().removeIf(
249                             lp -> lp.getKey().getUuid().getValue().contains(LAYER_PROTOCOL_NAME.getValue() + "-" + vlanId));
250                 }
251                 ltpList.add(ltpBuilder.build());
252             }
253
254             neBuilder.setLtp(ltpList);
255
256             commit();
257         } catch (Exception e)
258         {
259             LOG.warn("", e);
260         }
261     }
262
263     public void commit()
264     {
265         // submit to network element
266         try
267         {
268             ReadWriteTransaction neCommitTrans = dataBroker.newReadWriteTransaction();
269             neCommitTrans.put(CONFIGURATION, InstanceIdentifier.create(NetworkElement.class), neBuilder.build());
270
271             neCommitTrans.submit();
272         } catch (Exception e)
273         {
274             LOG.warn("caught exception when commit to ne, skip it", e);
275         }
276     }
277
278     public <T extends ChildOf<MwAirInterfacePac>> T getUnderAirPac(
279             String lpId_airInterface, Class<T> tClass,
280             LogicalDatastoreType type) throws ReadFailedException, ExecutionException, InterruptedException
281     {
282         try (ReadOnlyTransaction readOnlyTrans = dataBroker.newReadOnlyTransaction())
283         {
284             InstanceIdentifier<T> mwAirInterfaceConfigurationIID = InstanceIdentifier
285                     .builder(MwAirInterfacePac.class, new MwAirInterfacePacKey(new UniversalId(lpId_airInterface)))
286                     .child(tClass)
287                     .build();
288
289             Optional<T> op = readOnlyTrans.read(type, mwAirInterfaceConfigurationIID).get();
290             return op.isPresent() ? op.get() : null;
291         }
292     }
293
294     public boolean isLtpOfThisOnPath(String lpName)
295     {
296         for (LogicalTerminationPointList logicalTerminationPointList : ltp)
297         {
298             String ethLtpName = logicalTerminationPointList.getLtpReference().getValue();
299             Ltp airInterface = getLtpNameByLp(lpName);
300             if (belongTo(airInterface, ethLtpName))
301             {
302                 return true;
303             }
304         }
305         return false;
306     }
307
308     private boolean belongTo(Ltp airInterface, String ethLtpName)
309     {
310         if (airInterface == null || airInterface.getClientLtp() == null)
311         {
312             return false;
313         }
314         for (UniversalId clientID : airInterface.getClientLtp())
315         {
316             if (clientID.getValue().equalsIgnoreCase(ethLtpName))
317                 return true;
318             if (belongTo(getLtpByName(clientID), ethLtpName))
319             {
320                 return true;
321             }
322         }
323         return false;
324     }
325
326     private Ltp getLtpByName(UniversalId clientID)
327     {
328         for (Ltp ltp1 : neBuilder.getLtp())
329         {
330             if (ltp1.getKey().getUuid().equals(clientID))
331             {
332                 return ltp1;
333             }
334         }
335         return null;
336     }
337
338     private Ltp getLtpNameByLp(String lpId_airInterface)
339     {
340         for (Ltp ltp1 : neBuilder.getLtp())
341         {
342             for (Lp lp : ltp1.getLp())
343             {
344                 if (lp.getKey().getUuid().getValue().equalsIgnoreCase(lpId_airInterface))
345                 {
346                     return ltp1;
347                 }
348             }
349         }
350         return null;
351     }
352
353     public void reportSwitch()
354     {
355
356         if (IS_MAIN)
357         {
358             SwitchFollowTopoInputBuilder builder = new SwitchFollowTopoInputBuilder();
359             builder.setVlanid(vlanId);
360             rpc.switchFollowTopo(builder.build());
361         } else
362         {
363             RestoreFollowTopoInputBuilder builder = new RestoreFollowTopoInputBuilder();
364             builder.setVlanid(vlanId);
365             rpc.restoreFollowTopo(builder.build());
366         }
367
368         IS_MAIN = !IS_MAIN;
369     }
370 }