Upgrade ietf-{inet,yang}-types to 2013-07-15
[bgpcep.git] / bgp / flowspec / src / test / java / org / opendaylight / protocol / bgp / flowspec / SimpleFlowspecIpv6NlriParserTest.java
1 /*
2  * Copyright (c) 2015 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.protocol.bgp.flowspec;
9
10 import static org.junit.Assert.assertArrayEquals;
11 import static org.junit.Assert.assertEquals;
12 import static org.opendaylight.protocol.bgp.flowspec.SimpleFlowspecIpv4NlriParserTest.PATH_ID;
13
14 import com.google.common.collect.Lists;
15 import com.google.common.collect.Sets;
16 import io.netty.buffer.ByteBuf;
17 import io.netty.buffer.Unpooled;
18 import java.util.ArrayList;
19 import java.util.List;
20 import java.util.Optional;
21 import org.junit.Before;
22 import org.junit.Test;
23 import org.mockito.Mock;
24 import org.mockito.Mockito;
25 import org.mockito.MockitoAnnotations;
26 import org.opendaylight.protocol.bgp.flowspec.handlers.AbstractNumericOperandParser;
27 import org.opendaylight.protocol.bgp.flowspec.handlers.AbstractOperandParser;
28 import org.opendaylight.protocol.bgp.flowspec.handlers.BitmaskOperandParser;
29 import org.opendaylight.protocol.bgp.parser.BGPParsingException;
30 import org.opendaylight.protocol.bgp.parser.spi.MultiPathSupport;
31 import org.opendaylight.protocol.bgp.parser.spi.PeerSpecificParserConstraint;
32 import org.opendaylight.protocol.util.ByteArray;
33 import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.inet.types.rev130715.Ipv6Prefix;
34 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.BitmaskOperand;
35 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.FlowspecSubsequentAddressFamily;
36 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.Fragment;
37 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.NumericOperand;
38 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.Flowspec;
39 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.FlowspecBuilder;
40 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.flowspec.FlowspecType;
41 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.flowspec.flowspec.type.FragmentCase;
42 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.flowspec.flowspec.type.FragmentCaseBuilder;
43 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.flowspec.flowspec.type.fragment._case.Fragments;
44 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.flowspec.flowspec.type.fragment._case.FragmentsBuilder;
45 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.DestinationIpv6PrefixCase;
46 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.DestinationIpv6PrefixCaseBuilder;
47 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.FlowLabelCaseBuilder;
48 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.NextHeaderCase;
49 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.NextHeaderCaseBuilder;
50 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.SourceIpv6PrefixCase;
51 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.SourceIpv6PrefixCaseBuilder;
52 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.flow.label._case.FlowLabel;
53 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.flow.label._case.FlowLabelBuilder;
54 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.next.header._case.NextHeaders;
55 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.group.ipv6.flowspec.flowspec.type.next.header._case.NextHeadersBuilder;
56 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.destination.ipv6.DestinationFlowspecBuilder;
57 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.flowspec.ipv6.route.FlowspecRoute;
58 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.message.rev130919.path.attributes.AttributesBuilder;
59 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.multiprotocol.rev130919.Attributes1;
60 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.multiprotocol.rev130919.Attributes1Builder;
61 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.multiprotocol.rev130919.Attributes2;
62 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.multiprotocol.rev130919.Attributes2Builder;
63 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.multiprotocol.rev130919.update.attributes.MpReachNlriBuilder;
64 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.multiprotocol.rev130919.update.attributes.MpUnreachNlriBuilder;
65 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.multiprotocol.rev130919.update.attributes.mp.reach.nlri.AdvertizedRoutesBuilder;
66 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.multiprotocol.rev130919.update.attributes.mp.unreach.nlri.WithdrawnRoutesBuilder;
67 import org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.types.rev130919.Ipv6AddressFamily;
68 import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier.NodeIdentifier;
69 import org.opendaylight.yangtools.yang.data.api.YangInstanceIdentifier.NodeIdentifierWithPredicates;
70 import org.opendaylight.yangtools.yang.data.api.schema.MapEntryNode;
71 import org.opendaylight.yangtools.yang.data.impl.schema.Builders;
72 import org.opendaylight.yangtools.yang.data.impl.schema.builder.api.DataContainerNodeAttrBuilder;
73
74 public class SimpleFlowspecIpv6NlriParserTest {
75     private static final NodeIdentifier NEXT_HEADER_NID = new NodeIdentifier(NextHeaders.QNAME);
76     private static final NodeIdentifier FLOW_LABEL_NID = new NodeIdentifier(FlowLabel.QNAME);
77
78     @Mock
79     private PeerSpecificParserConstraint constraint;
80     @Mock
81     private MultiPathSupport muliPathSupport;
82     private final SimpleFlowspecExtensionProviderContext flowspecContext = new SimpleFlowspecExtensionProviderContext();
83     private final FlowspecActivator fsa = new FlowspecActivator(flowspecContext);
84     private final SimpleFlowspecIpv6NlriParser FS_PARSER = new SimpleFlowspecIpv6NlriParser(flowspecContext.getFlowspecTypeRegistry(SimpleFlowspecExtensionProviderContext.AFI.IPV6, SimpleFlowspecExtensionProviderContext.SAFI.FLOWSPEC));
85
86     private static final byte[] REACHED_NLRI = new byte[] {
87         0x13,
88         1, 0x28, 0, 1, 2, 3, 4, 5,
89         2, 0x28, 0, 1, 2, 3, 4, 6,
90         03, (byte) 0x81, 06};
91
92     private static final byte[] REACHED_NLRI_ADD_PATH = new byte[] {
93         0x0, 0x0, 0x0, 0x1,
94         0x13,
95         1, 0x28, 0, 1, 2, 3, 4, 5,
96         2, 0x28, 0, 1, 2, 3, 4, 6,
97         03, (byte) 0x81, 06};
98
99     private static final byte[] UNREACHED_NLRI = new byte[] {
100         0x0c,
101         0x0c, (byte) 0x81, 0x0e,
102         0x0d, (byte) 0x21, 1, 0, 0, 6, (byte) 0x91, 1, 2
103     };
104
105     private static final byte[] UNREACHED_NLRI_ADD_PATH = new byte[] {
106         0x0, 0x0, 0x0, 0x1,
107         0x0c,
108         0x0c, (byte) 0x81, 0x0e,
109         0x0d, (byte) 0x21, 1, 0, 0, 6, (byte) 0x91, 1, 2
110     };
111
112     @Before
113     public void setUp() {
114         MockitoAnnotations.initMocks(this);
115         Mockito.doReturn(Optional.of(this.muliPathSupport)).when(constraint).getPeerConstraint(Mockito.any());
116         Mockito.doReturn(true).when(this.muliPathSupport).isTableTypeSupported(Mockito.any());
117     }
118
119     @Test
120     public void testParseMpReachNlri() throws BGPParsingException {
121         final List<Flowspec> fs = new ArrayList<>();
122         final MpReachNlriBuilder mp = new MpReachNlriBuilder();
123
124         final FlowspecBuilder builder = new FlowspecBuilder();
125         final DestinationIpv6PrefixCase destinationPrefix = new DestinationIpv6PrefixCaseBuilder().setDestinationPrefix(new Ipv6Prefix("102:304:500::/40")).build();
126         builder.setFlowspecType(destinationPrefix);
127         fs.add(builder.build());
128
129         final SourceIpv6PrefixCase sourcePrefix = new SourceIpv6PrefixCaseBuilder().setSourcePrefix(new Ipv6Prefix("102:304:600::/40")).build();
130         builder.setFlowspecType(sourcePrefix);
131         fs.add(builder.build());
132
133         final List<NextHeaders> nextheaders = Lists.newArrayList(new NextHeadersBuilder().setOp(new NumericOperand(false, true, true, false, false)).setValue((short) 6).build());
134         final NextHeaderCase headersCase = new NextHeaderCaseBuilder().setNextHeaders(nextheaders).build();
135         builder.setFlowspecType(headersCase);
136         fs.add(builder.build());
137
138
139         mp.setAdvertizedRoutes(new AdvertizedRoutesBuilder().setDestinationType(
140             new org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.update.attributes.mp.reach.nlri.advertized.routes.destination.type.DestinationFlowspecIpv6CaseBuilder()
141                 .setDestinationFlowspec(
142                     new DestinationFlowspecBuilder()
143                         .setFlowspec(fs)
144                         .build()
145                 )
146                 .build()
147             ).build()
148         );
149
150         final MpReachNlriBuilder result = new MpReachNlriBuilder();
151         result.setAfi(Ipv6AddressFamily.class);
152         result.setSafi(FlowspecSubsequentAddressFamily.class);
153         FS_PARSER.parseNlri(Unpooled.wrappedBuffer(REACHED_NLRI), result);
154
155         final List<Flowspec> flows = ((org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.update.attributes.mp.reach.nlri.advertized.routes.destination.type.DestinationFlowspecIpv6Case) (result.getAdvertizedRoutes().getDestinationType()))
156             .getDestinationFlowspec().getFlowspec();
157         assertEquals(3, flows.size());
158         assertEquals(destinationPrefix, flows.get(0).getFlowspecType());
159         assertEquals(sourcePrefix, flows.get(1).getFlowspecType());
160         assertEquals(headersCase, flows.get(2).getFlowspecType());
161
162         final ByteBuf buffer = Unpooled.buffer();
163         FS_PARSER.serializeAttribute(new AttributesBuilder().addAugmentation(Attributes1.class, new Attributes1Builder().setMpReachNlri(mp.setAfi(Ipv6AddressFamily.class).build()).build()).build(), buffer);
164         assertArrayEquals(REACHED_NLRI, ByteArray.readAllBytes(buffer));
165
166         assertEquals("all packets to 102:304:500::/40 AND from 102:304:600::/40 AND where next header equals to 6 ", FS_PARSER.stringNlri(flows));
167     }
168
169     @Test
170     public void testParseMpReachNlriConstraint() throws BGPParsingException {
171         final List<Flowspec> fs = new ArrayList<>();
172         final MpReachNlriBuilder mp = new MpReachNlriBuilder();
173
174         final FlowspecBuilder builder = new FlowspecBuilder();
175         final DestinationIpv6PrefixCase destinationPrefix = new DestinationIpv6PrefixCaseBuilder().setDestinationPrefix(new Ipv6Prefix("102:304:500::/40")).build();
176         builder.setFlowspecType(destinationPrefix);
177         fs.add(builder.build());
178
179         final SourceIpv6PrefixCase sourcePrefix = new SourceIpv6PrefixCaseBuilder().setSourcePrefix(new Ipv6Prefix("102:304:600::/40")).build();
180         builder.setFlowspecType(sourcePrefix);
181         fs.add(builder.build());
182
183         final List<NextHeaders> nextheaders = Lists.newArrayList(new NextHeadersBuilder().setOp(new NumericOperand(false, true, true, false, false)).setValue((short) 6).build());
184         final NextHeaderCase headersCase = new NextHeaderCaseBuilder().setNextHeaders(nextheaders).build();
185         builder.setFlowspecType(headersCase);
186         fs.add(builder.build());
187
188
189         mp.setAdvertizedRoutes(new AdvertizedRoutesBuilder().setDestinationType(
190             new org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.update.attributes.mp.reach.nlri.advertized.routes.destination.type.DestinationFlowspecIpv6CaseBuilder()
191                 .setDestinationFlowspec(
192                     new DestinationFlowspecBuilder()
193                         .setPathId(PATH_ID)
194                         .setFlowspec(fs)
195                         .build()
196                 ).build()
197             ).build()
198         );
199
200         final MpReachNlriBuilder result = new MpReachNlriBuilder();
201         result.setAfi(Ipv6AddressFamily.class);
202         result.setSafi(FlowspecSubsequentAddressFamily.class);
203         FS_PARSER.parseNlri(Unpooled.wrappedBuffer(REACHED_NLRI_ADD_PATH), result, this.constraint);
204
205         final List<Flowspec> flows = ((org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.update.attributes.mp.reach.nlri.advertized.routes.destination.type.DestinationFlowspecIpv6Case) (result.getAdvertizedRoutes().getDestinationType()))
206             .getDestinationFlowspec().getFlowspec();
207         assertEquals(3, flows.size());
208         assertEquals(destinationPrefix, flows.get(0).getFlowspecType());
209         assertEquals(sourcePrefix, flows.get(1).getFlowspecType());
210         assertEquals(headersCase, flows.get(2).getFlowspecType());
211
212         final ByteBuf buffer = Unpooled.buffer();
213         FS_PARSER.serializeAttribute(new AttributesBuilder().addAugmentation(Attributes1.class, new Attributes1Builder().setMpReachNlri(mp.setAfi(Ipv6AddressFamily.class).build()).build()).build(), buffer);
214         assertArrayEquals(REACHED_NLRI_ADD_PATH, ByteArray.readAllBytes(buffer));
215
216         assertEquals("all packets to 102:304:500::/40 AND from 102:304:600::/40 AND where next header equals to 6 ", FS_PARSER.stringNlri(flows));
217     }
218
219     @Test
220     public void testParseMpUnreachNlri() throws BGPParsingException {
221         final List<Flowspec> fs = new ArrayList<>();
222         final MpUnreachNlriBuilder mp = new MpUnreachNlriBuilder();
223
224         final FlowspecBuilder builder = new FlowspecBuilder();
225
226         final FragmentCase fragment = createFragment();
227         builder.setFlowspecType(fragment);
228         fs.add(builder.build());
229
230         final FlowspecType label = createLabel();
231         builder.setFlowspecType(label);
232         fs.add(builder.build());
233
234         mp.setAfi(Ipv6AddressFamily.class).setWithdrawnRoutes(new WithdrawnRoutesBuilder().setDestinationType(
235             new org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.update.attributes.mp.unreach.nlri.withdrawn.routes.destination.type.DestinationFlowspecIpv6CaseBuilder()
236                 .setDestinationFlowspec(
237                     new DestinationFlowspecBuilder()
238                         .setFlowspec(fs)
239                         .build()
240                 ).build()
241             ).build()
242         );
243
244         final MpUnreachNlriBuilder result = new MpUnreachNlriBuilder();
245         result.setAfi(Ipv6AddressFamily.class);
246         result.setSafi(FlowspecSubsequentAddressFamily.class);
247         FS_PARSER.parseNlri(Unpooled.wrappedBuffer(UNREACHED_NLRI), result);
248
249         final List<Flowspec> flows = ((org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.update.attributes.mp.unreach.nlri.withdrawn.routes.destination.type.DestinationFlowspecIpv6Case) (result.getWithdrawnRoutes().getDestinationType()))
250             .getDestinationFlowspec().getFlowspec();
251         assertEquals(2, flows.size());
252         assertEquals(fragment, flows.get(0).getFlowspecType());
253         assertEquals(label, flows.get(1).getFlowspecType());
254
255         final ByteBuf buffer = Unpooled.buffer();
256         FS_PARSER.serializeAttribute(new AttributesBuilder().addAugmentation(Attributes2.class, new Attributes2Builder().setMpUnreachNlri(mp.build()).build()).build(), buffer);
257
258         assertArrayEquals(UNREACHED_NLRI, ByteArray.readAllBytes(buffer));
259
260         assertEquals("all packets where fragment does match 'IS FIRST' 'IS LAST' 'IS A' AND where flow label equals to 16777222 or equals to 258 ", FS_PARSER.stringNlri(flows));
261     }
262
263     private FragmentCase createFragment() {
264         final List<Fragments> fragments = Lists.newArrayList(new FragmentsBuilder().setOp(new BitmaskOperand(false, true, true, false)).setValue(new Fragment(false, true, true, true)).build());
265         return new FragmentCaseBuilder().setFragments(fragments).build();
266     }
267
268     private FlowspecType createLabel() {
269         final List<FlowLabel> labels = Lists.newArrayList();
270         labels.add(new FlowLabelBuilder().setOp(new NumericOperand(false, false, true, false, false)).setValue(new Long(16777222L)).build());
271         labels.add(new FlowLabelBuilder().setOp(new NumericOperand(false, true, true, false, false)).setValue(new Long(258L)).build());
272         return new FlowLabelCaseBuilder().setFlowLabel(labels).build();
273     }
274
275     @Test
276     public void testParseMpUnreachNlriConstraint() throws BGPParsingException {
277         final List<Flowspec> fs = new ArrayList<>();
278         final MpUnreachNlriBuilder mp = new MpUnreachNlriBuilder();
279
280         final FlowspecBuilder builder = new FlowspecBuilder();
281         final FragmentCase fragment = createFragment();
282
283         builder.setFlowspecType(fragment);
284         fs.add(builder.build());
285
286         final FlowspecType label = createLabel();
287         builder.setFlowspecType(label);
288         fs.add(builder.build());
289
290         mp.setAfi(Ipv6AddressFamily.class).setWithdrawnRoutes(new WithdrawnRoutesBuilder().setDestinationType(
291             new org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.update.attributes.mp.unreach.nlri.withdrawn.routes.destination.type.DestinationFlowspecIpv6CaseBuilder()
292                 .setDestinationFlowspec(
293                     new DestinationFlowspecBuilder()
294                         .setPathId(PATH_ID)
295                         .setFlowspec(fs)
296                         .build()
297                 ).build()
298             ).build()
299         );
300
301         final MpUnreachNlriBuilder result = new MpUnreachNlriBuilder();
302         result.setAfi(Ipv6AddressFamily.class);
303         result.setSafi(FlowspecSubsequentAddressFamily.class);
304         FS_PARSER.parseNlri(Unpooled.wrappedBuffer(UNREACHED_NLRI_ADD_PATH), result, this.constraint);
305
306         final List<Flowspec> flows = ((org.opendaylight.yang.gen.v1.urn.opendaylight.params.xml.ns.yang.bgp.flowspec.rev150807.update.attributes.mp.unreach.nlri.withdrawn.routes.destination.type.DestinationFlowspecIpv6Case) (result.getWithdrawnRoutes().getDestinationType()))
307             .getDestinationFlowspec().getFlowspec();
308         assertEquals(2, flows.size());
309         assertEquals(fragment, flows.get(0).getFlowspecType());
310         assertEquals(label, flows.get(1).getFlowspecType());
311
312         final ByteBuf buffer = Unpooled.buffer();
313         FS_PARSER.serializeAttribute(new AttributesBuilder().addAugmentation(Attributes2.class, new Attributes2Builder().setMpUnreachNlri(mp.build()).build()).build(), buffer);
314
315         assertArrayEquals(UNREACHED_NLRI_ADD_PATH, ByteArray.readAllBytes(buffer));
316
317         assertEquals("all packets where fragment does match 'IS FIRST' 'IS LAST' 'IS A' AND where flow label equals to 16777222 or equals to 258 ", FS_PARSER.stringNlri(flows));
318     }
319
320     @Test
321     public void testExtractFlowspecFragments() {
322         final DataContainerNodeAttrBuilder<NodeIdentifierWithPredicates, MapEntryNode> entry = Builders.mapEntryBuilder();
323         entry.withNodeIdentifier(new NodeIdentifierWithPredicates(FlowspecRoute.QNAME, FlowspecRoute.QNAME, entry));
324         entry.withChild(Builders.unkeyedListBuilder()
325             .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
326             .withChild(Builders.unkeyedListEntryBuilder()
327                 .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
328                 .withChild(Builders.choiceBuilder()
329                     .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_TYPE_NID)
330                     .withChild(Builders.unkeyedListBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.FRAGMENT_NID)
331                         .withChild(Builders.unkeyedListEntryBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.OP_NID)
332                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.OP_NID).withValue(Sets.<String>newHashSet(AbstractOperandParser.AND_BIT_VALUE, AbstractOperandParser.END_OF_LIST_VALUE, BitmaskOperandParser.MATCH_VALUE, BitmaskOperandParser.NOT_VALUE)).build())
333                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.VALUE_NID).withValue(Sets.newHashSet(AbstractFlowspecNlriParser.DO_NOT_VALUE, AbstractFlowspecNlriParser.FIRST_VALUE, AbstractFlowspecNlriParser.IS_A_VALUE, AbstractFlowspecNlriParser.LAST_VALUE)).build()).build())
334                         .build()).build()).build()).build());
335         final FlowspecBuilder expectedFS = new FlowspecBuilder();
336         expectedFS.setFlowspecType(new FragmentCaseBuilder().setFragments(Lists.<Fragments>newArrayList(new FragmentsBuilder().setValue(new Fragment(true, true, true, true)).setOp(new BitmaskOperand(true, true, true, true)).build())).build());
337         final List<Flowspec> expectedValue = new ArrayList<>();
338         expectedValue.add(expectedFS.build());
339         assertEquals(expectedValue, FS_PARSER.extractFlowspec(entry.build()));
340     }
341
342     @Test
343     public void testExtractFlowspecNextHeaders() {
344         final DataContainerNodeAttrBuilder<NodeIdentifierWithPredicates, MapEntryNode> entry = Builders.mapEntryBuilder();
345         entry.withNodeIdentifier(new NodeIdentifierWithPredicates(FlowspecRoute.QNAME, FlowspecRoute.QNAME, entry));
346         entry.withChild(Builders.unkeyedListBuilder()
347             .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
348             .withChild(Builders.unkeyedListEntryBuilder()
349                 .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
350                 .withChild(Builders.choiceBuilder()
351                     .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_TYPE_NID)
352                     .withChild(Builders.unkeyedListBuilder().withNodeIdentifier(NEXT_HEADER_NID)
353                         .withChild(Builders.unkeyedListEntryBuilder().withNodeIdentifier(NEXT_HEADER_NID)
354                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.OP_NID).withValue(Sets.<String>newHashSet(AbstractOperandParser.END_OF_LIST_VALUE, AbstractOperandParser.AND_BIT_VALUE)).build())
355                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.VALUE_NID).withValue((short) 100).build()).build())
356                         .withChild(Builders.unkeyedListEntryBuilder().withNodeIdentifier(NEXT_HEADER_NID)
357                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.OP_NID).withValue(Sets.<String>newHashSet(AbstractOperandParser.AND_BIT_VALUE)).build())
358                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.VALUE_NID).withValue((short) 200).build()).build())
359                         .withChild(Builders.unkeyedListEntryBuilder().withNodeIdentifier(NEXT_HEADER_NID)
360                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.OP_NID).withValue(Sets.<String>newHashSet(AbstractOperandParser.END_OF_LIST_VALUE, AbstractOperandParser.AND_BIT_VALUE, AbstractNumericOperandParser.EQUALS_VALUE)).build())
361                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.VALUE_NID).withValue((short) 210).build()).build())
362                         .build()).build()).build()).build());
363
364         final FlowspecBuilder expectedFS = new FlowspecBuilder();
365         expectedFS.setFlowspecType(new NextHeaderCaseBuilder().setNextHeaders(Lists.<NextHeaders>newArrayList(
366             new NextHeadersBuilder().setValue((short) 100).setOp(new NumericOperand(true, true, false, false, false)).build(),
367             new NextHeadersBuilder().setValue((short) 200).setOp(new NumericOperand(true, false, false, false, false)).build(),
368             new NextHeadersBuilder().setValue((short) 210).setOp(new NumericOperand(true, true, true, false, false)).build())).build());
369         final List<Flowspec> expectedValue = new ArrayList<>();
370         expectedValue.add(expectedFS.build());
371         assertEquals(expectedValue, FS_PARSER.extractFlowspec(entry.build()));
372     }
373
374     @Test
375     public void testExtractFlowspecFlowLabels() {
376         final DataContainerNodeAttrBuilder<NodeIdentifierWithPredicates, MapEntryNode> entry = Builders.mapEntryBuilder();
377         entry.withNodeIdentifier(new NodeIdentifierWithPredicates(FlowspecRoute.QNAME, FlowspecRoute.QNAME, entry));
378         entry.withChild(Builders.unkeyedListBuilder()
379             .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
380             .withChild(Builders.unkeyedListEntryBuilder()
381                 .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
382                 .withChild(Builders.choiceBuilder()
383                     .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_TYPE_NID)
384                     .withChild(Builders.unkeyedListBuilder().withNodeIdentifier(FLOW_LABEL_NID)
385                         .withChild(Builders.unkeyedListEntryBuilder().withNodeIdentifier(FLOW_LABEL_NID)
386                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.OP_NID).withValue(Sets.<String>newHashSet(AbstractOperandParser.END_OF_LIST_VALUE, AbstractOperandParser.AND_BIT_VALUE)).build())
387                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.VALUE_NID).withValue(100L).build()).build())
388                         .withChild(Builders.unkeyedListEntryBuilder().withNodeIdentifier(FLOW_LABEL_NID)
389                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.OP_NID).withValue(Sets.<String>newHashSet(AbstractOperandParser.AND_BIT_VALUE)).build())
390                             .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.VALUE_NID).withValue(200L).build()).build())
391                         .build()).build()).build()).build());
392
393         final FlowspecBuilder expectedFS = new FlowspecBuilder();
394         expectedFS.setFlowspecType(new FlowLabelCaseBuilder().setFlowLabel(Lists.<FlowLabel>newArrayList(
395             new FlowLabelBuilder().setValue(100L).setOp(new NumericOperand(true, true, false, false, false)).build(),
396             new FlowLabelBuilder().setValue(200L).setOp(new NumericOperand(true, false, false, false, false)).build())).build());
397         final List<Flowspec> expectedValue = new ArrayList<>();
398         expectedValue.add(expectedFS.build());
399         assertEquals(expectedValue, FS_PARSER.extractFlowspec(entry.build()));
400     }
401
402     @Test
403     public void testExtractFlowspecDestPrefix() {
404         final DataContainerNodeAttrBuilder<NodeIdentifierWithPredicates, MapEntryNode> entry = Builders.mapEntryBuilder();
405         entry.withNodeIdentifier(new NodeIdentifierWithPredicates(FlowspecRoute.QNAME, FlowspecRoute.QNAME, entry));
406         entry.withChild(Builders.unkeyedListBuilder()
407             .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
408             .withChild(Builders.unkeyedListEntryBuilder()
409                 .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
410                 .withChild(Builders.choiceBuilder()
411                     .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_TYPE_NID)
412                     .withChild(Builders.leafBuilder().withNodeIdentifier(AbstractFlowspecNlriParser.DEST_PREFIX_NID).withValue("102:304:500::/40").build()).build()).build()).build());
413         final FlowspecBuilder expectedFS = new FlowspecBuilder();
414         expectedFS.setFlowspecType(new DestinationIpv6PrefixCaseBuilder().setDestinationPrefix(new Ipv6Prefix("102:304:500::/40")).build());
415         final List<Flowspec> expectedValue = new ArrayList<>();
416         expectedValue.add(expectedFS.build());
417         assertEquals(expectedValue, FS_PARSER.extractFlowspec(entry.build()));
418     }
419
420     @Test
421     public void testExtractFlowspecSourcePrefix() {
422         final DataContainerNodeAttrBuilder<NodeIdentifierWithPredicates, MapEntryNode> entry = Builders.mapEntryBuilder();
423         entry.withNodeIdentifier(new NodeIdentifierWithPredicates(FlowspecRoute.QNAME, FlowspecRoute.QNAME, entry));
424         entry.withChild(Builders.unkeyedListBuilder()
425             .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
426             .withChild(Builders.unkeyedListEntryBuilder()
427                 .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_NID)
428                 .withChild(Builders.choiceBuilder()
429                     .withNodeIdentifier(AbstractFlowspecNlriParser.FLOWSPEC_TYPE_NID)
430                     .withChild(Builders.leafBuilder().withNodeIdentifier(SimpleFlowspecIpv4NlriParser.SOURCE_PREFIX_NID).withValue("102:304:600::/40").build()).build()).build()).build());
431         final FlowspecBuilder expectedFS = new FlowspecBuilder();
432         expectedFS.setFlowspecType(new SourceIpv6PrefixCaseBuilder().setSourcePrefix(new Ipv6Prefix("102:304:600::/40")).build());
433         final List<Flowspec> expectedValue = new ArrayList<>();
434         expectedValue.add(expectedFS.build());
435         assertEquals(expectedValue, FS_PARSER.extractFlowspec(entry.build()));
436     }
437 }
438