2 * Copyright (c) 2017 Pantheon Technologies s.r.o. and others. All rights reserved.
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
8 package org.opendaylight.openflowplugin.extension.onf.converter;
10 import java.util.Collection;
11 import java.util.List;
12 import java.util.Optional;
13 import org.opendaylight.openflowplugin.extension.api.ConverterMessageToOFJava;
14 import org.opendaylight.openflowplugin.extension.api.ConvertorMessageFromOFJava;
15 import org.opendaylight.openflowplugin.extension.api.ExtensionConvertorData;
16 import org.opendaylight.openflowplugin.extension.api.exception.ConversionException;
17 import org.opendaylight.openflowplugin.extension.api.path.MessagePath;
18 import org.opendaylight.openflowplugin.extension.onf.OnfConstants;
19 import org.opendaylight.openflowplugin.openflow.md.core.sal.convertor.ConvertorExecutor;
20 import org.opendaylight.openflowplugin.openflow.md.core.sal.convertor.ConvertorManagerFactory;
21 import org.opendaylight.openflowplugin.openflow.md.core.sal.convertor.data.XidConvertorData;
22 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.AddFlowInputBuilder;
23 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.RemoveFlowInputBuilder;
24 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.service.rev130819.flow.update.UpdatedFlowBuilder;
25 import org.opendaylight.yang.gen.v1.urn.opendaylight.flow.types.port.rev130925.port.mod.port.Port;
26 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.AddGroupInputBuilder;
27 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.RemoveGroupInputBuilder;
28 import org.opendaylight.yang.gen.v1.urn.opendaylight.group.service.rev130918.group.update.UpdatedGroupBuilder;
29 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.common.types.rev130731.ExperimenterId;
30 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.FlowModInputBuilder;
31 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.GroupModInputBuilder;
32 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflow.protocol.rev130731.PortModInput;
33 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.bundle.inner.message.grouping.BundleInnerMessage;
34 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.bundle.inner.message.grouping.bundle.inner.message.BundleAddFlowCase;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.bundle.inner.message.grouping.bundle.inner.message.BundleAddGroupCase;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.bundle.inner.message.grouping.bundle.inner.message.BundleRemoveFlowCase;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.bundle.inner.message.grouping.bundle.inner.message.BundleRemoveGroupCase;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.bundle.inner.message.grouping.bundle.inner.message.BundleUpdateFlowCase;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.bundle.inner.message.grouping.bundle.inner.message.BundleUpdateGroupCase;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.bundle.inner.message.grouping.bundle.inner.message.BundleUpdatePortCase;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.send.experimenter.input.experimenter.message.of.choice.BundleAddMessageSal;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.send.experimenter.input.experimenter.message.of.choice.BundleAddMessageSalBuilder;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.bundle.service.rev170124.send.experimenter.input.experimenter.message.of.choice.bundle.add.message.sal.SalAddMessageDataBuilder;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.bundle.add.message.grouping.bundle.inner.message.BundleFlowModCase;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.bundle.add.message.grouping.bundle.inner.message.BundleFlowModCaseBuilder;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.bundle.add.message.grouping.bundle.inner.message.BundleGroupModCase;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.bundle.add.message.grouping.bundle.inner.message.BundleGroupModCaseBuilder;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.bundle.add.message.grouping.bundle.inner.message.BundlePortModCase;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.bundle.add.message.grouping.bundle.inner.message.BundlePortModCaseBuilder;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.bundle.add.message.grouping.bundle.inner.message.bundle.flow.mod._case.FlowModCaseDataBuilder;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.bundle.add.message.grouping.bundle.inner.message.bundle.group.mod._case.GroupModCaseDataBuilder;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.bundle.add.message.grouping.bundle.inner.message.bundle.port.mod._case.PortModCaseDataBuilder;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.experimenter.input.experimenter.data.of.choice.BundleAddMessageOnf;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.experimenter.input.experimenter.data.of.choice.BundleAddMessageOnfBuilder;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.openflowplugin.extension.onf.rev170124.experimenter.input.experimenter.data.of.choice.bundle.add.message.onf.OnfAddMessageGroupingDataBuilder;
56 import org.opendaylight.yangtools.yang.common.Uint32;
57 import org.slf4j.Logger;
58 import org.slf4j.LoggerFactory;
61 * Converter for BundleAddMessage messages (ONF approved extension #230).
63 public class BundleAddMessageConverter implements
64 ConverterMessageToOFJava<BundleAddMessageSal, BundleAddMessageOnf, ExtensionConvertorData>,
65 ConvertorMessageFromOFJava<BundleAddMessageOnf, MessagePath> {
67 private static final Logger LOG = LoggerFactory.getLogger(BundleAddMessageConverter.class);
68 private static final ConvertorExecutor CONVERTER_EXECUTOR = ConvertorManagerFactory.createDefaultManager();
71 public BundleAddMessageOnf convert(final BundleAddMessageSal experimenterMessageCase,
72 final ExtensionConvertorData extensionData) throws ConversionException {
73 final OnfAddMessageGroupingDataBuilder dataBuilder = new OnfAddMessageGroupingDataBuilder();
74 dataBuilder.setBundleId(experimenterMessageCase.getSalAddMessageData().getBundleId());
75 dataBuilder.setFlags(experimenterMessageCase.getSalAddMessageData().getFlags());
76 dataBuilder.setBundleProperty(experimenterMessageCase.getSalAddMessageData().getBundleProperty());
77 final BundleInnerMessage innerMessage = experimenterMessageCase.getSalAddMessageData().getBundleInnerMessage();
78 final XidConvertorData data = new XidConvertorData(extensionData.getVersion());
79 data.setDatapathId(extensionData.getDatapathId());
80 data.setXid(extensionData.getXid());
81 LOG.trace("Flow or group pushed to the node: {} with transaction id : {} is {}",
82 data.getDatapathId(), data.getXid(),
83 experimenterMessageCase.getSalAddMessageData().getBundleInnerMessage());
84 if (innerMessage.implementedInterface().equals(BundleAddFlowCase.class)
85 || innerMessage.implementedInterface().equals(BundleUpdateFlowCase.class)
86 || innerMessage.implementedInterface().equals(BundleRemoveFlowCase.class)) {
87 dataBuilder.setBundleInnerMessage(convertBundleFlowCase(innerMessage, data));
88 } else if (innerMessage.implementedInterface().equals(BundleAddGroupCase.class)
89 || innerMessage.implementedInterface().equals(BundleUpdateGroupCase.class)
90 || innerMessage.implementedInterface().equals(BundleRemoveGroupCase.class)) {
91 dataBuilder.setBundleInnerMessage(convertBundleGroupCase(innerMessage, data));
92 } else if (innerMessage.implementedInterface().equals(BundleUpdatePortCase.class)) {
93 dataBuilder.setBundleInnerMessage(convertBundlePortCase(innerMessage, data));
95 throw new ConversionException("Unsupported inner message");
98 return new BundleAddMessageOnfBuilder().setOnfAddMessageGroupingData(dataBuilder.build()).build();
102 public BundleAddMessageSal convert(final BundleAddMessageOnf input, final MessagePath path) {
103 return new BundleAddMessageSalBuilder()
104 .setSalAddMessageData(new SalAddMessageDataBuilder(input.getOnfAddMessageGroupingData())
109 private static BundleFlowModCase convertBundleFlowCase(final BundleInnerMessage messageCase,
110 final XidConvertorData data) throws ConversionException {
111 final Optional<List<FlowModInputBuilder>> flowModInputs;
112 final Class<?> clazz = messageCase.implementedInterface();
113 if (clazz.equals(BundleAddFlowCase.class)) {
114 flowModInputs = CONVERTER_EXECUTOR.convert(
115 new AddFlowInputBuilder(((BundleAddFlowCase) messageCase).getAddFlowCaseData()).build(), data);
116 } else if (clazz.equals(BundleUpdateFlowCase.class)) {
117 flowModInputs = CONVERTER_EXECUTOR.convert(
118 new UpdatedFlowBuilder(((BundleUpdateFlowCase) messageCase).getUpdateFlowCaseData()).build(), data);
119 } else if (clazz.equals(BundleRemoveFlowCase.class)) {
120 flowModInputs = CONVERTER_EXECUTOR.convert(
121 new RemoveFlowInputBuilder(((BundleRemoveFlowCase) messageCase).getRemoveFlowCaseData()).build(),
124 flowModInputs = Optional.empty();
127 if (flowModInputs.isEmpty()) {
128 throw new ConversionException("BundleFlowCase conversion unsuccessful.");
130 final List<FlowModInputBuilder> inputs = flowModInputs.orElseThrow();
131 if (inputs.size() != 1) {
132 throw new ConversionException(
133 "BundleFlowCase conversion unsuccessful - not able to convert to multiple flows.");
136 return new BundleFlowModCaseBuilder()
137 .setFlowModCaseData(new FlowModCaseDataBuilder(inputs.get(0).setXid(data.getXid()).build()).build())
141 private static BundleGroupModCase convertBundleGroupCase(final BundleInnerMessage messageCase,
142 final XidConvertorData data) throws ConversionException {
143 final Optional<GroupModInputBuilder> groupModInput;
144 final Class<?> clazz = messageCase.implementedInterface();
145 if (clazz.equals(BundleAddGroupCase.class)) {
146 groupModInput = CONVERTER_EXECUTOR.convert(
147 new AddGroupInputBuilder(((BundleAddGroupCase) messageCase).getAddGroupCaseData()).build(), data);
148 } else if (clazz.equals(BundleUpdateGroupCase.class)) {
149 groupModInput = CONVERTER_EXECUTOR.convert(
150 new UpdatedGroupBuilder(((BundleUpdateGroupCase) messageCase).getUpdateGroupCaseData()).build(),
152 } else if (clazz.equals(BundleRemoveGroupCase.class)) {
153 groupModInput = CONVERTER_EXECUTOR.convert(
154 new RemoveGroupInputBuilder(((BundleRemoveGroupCase) messageCase).getRemoveGroupCaseData()).build(),
157 groupModInput = Optional.empty();
160 if (groupModInput.isEmpty()) {
161 throw new ConversionException("BundleGroupCase conversion unsuccessful.");
164 return new BundleGroupModCaseBuilder()
165 .setGroupModCaseData(new GroupModCaseDataBuilder(groupModInput.orElseThrow().setXid(data.getXid()).build())
170 private static BundlePortModCase convertBundlePortCase(final BundleInnerMessage messageCase,
171 final XidConvertorData data) throws ConversionException {
172 final Optional<PortModInput> portModInput;
173 final Class<?> clazz = messageCase.implementedInterface();
174 if (clazz.equals(BundleUpdatePortCase.class)) {
175 Collection<Port> ports
176 = ((BundleUpdatePortCase) messageCase).getUpdatePortCaseData().getPort().nonnullPort().values();
177 Port port = ports.iterator().next();
178 portModInput = CONVERTER_EXECUTOR.convert(port, data);
180 portModInput = Optional.empty();
183 if (portModInput.isEmpty()) {
184 throw new ConversionException("BundlePortCase conversion unsuccessful.");
186 return new BundlePortModCaseBuilder()
187 .setPortModCaseData(new PortModCaseDataBuilder(portModInput.orElseThrow()).setXid(data.getXid()).build())
192 public ExperimenterId getExperimenterId() {
193 return OnfConstants.ONF_EXPERIMENTER_ID;
197 public Uint32 getType() {
198 return OnfConstants.ONF_ET_BUNDLE_ADD_MESSAGE;