Committed by
Gerrit Code Review
Support [ONOS-4593] and implement [ONOS-4594]
Changes: - Adds extension to sp2mp intents; - Adds extension to linkcollection intents; - Adds extension to sp2mp compiler; - Adds extension to linkcollection compiler; - Adds re-ordering of the actions; - Adds unit tests for both sp2mp intents and linkcollection intents; Change-Id: Ib925e9066682e077a0bb4bbfd20a4382623b7541
Showing
8 changed files
with
517 additions
and
43 deletions
... | @@ -16,19 +16,20 @@ | ... | @@ -16,19 +16,20 @@ |
16 | 16 | ||
17 | package org.onosproject.net.intent; | 17 | package org.onosproject.net.intent; |
18 | 18 | ||
19 | +import java.util.List; | ||
20 | +import java.util.Map; | ||
21 | +import java.util.Set; | ||
22 | + | ||
19 | import com.google.common.annotations.Beta; | 23 | import com.google.common.annotations.Beta; |
20 | -import com.google.common.base.MoreObjects; | ||
21 | import com.google.common.collect.ImmutableMap; | 24 | import com.google.common.collect.ImmutableMap; |
22 | -import com.google.common.collect.ImmutableSet; | ||
23 | import org.onosproject.core.ApplicationId; | 25 | import org.onosproject.core.ApplicationId; |
24 | import org.onosproject.net.ConnectPoint; | 26 | import org.onosproject.net.ConnectPoint; |
25 | import org.onosproject.net.Link; | 27 | import org.onosproject.net.Link; |
26 | import org.onosproject.net.flow.TrafficSelector; | 28 | import org.onosproject.net.flow.TrafficSelector; |
27 | import org.onosproject.net.flow.TrafficTreatment; | 29 | import org.onosproject.net.flow.TrafficTreatment; |
28 | 30 | ||
29 | -import java.util.List; | 31 | +import com.google.common.base.MoreObjects; |
30 | -import java.util.Map; | 32 | +import com.google.common.collect.ImmutableSet; |
31 | -import java.util.Set; | ||
32 | 33 | ||
33 | /** | 34 | /** |
34 | * Abstraction of a connectivity intent that is implemented by a set of path | 35 | * Abstraction of a connectivity intent that is implemented by a set of path |
... | @@ -41,12 +42,15 @@ public final class LinkCollectionIntent extends ConnectivityIntent { | ... | @@ -41,12 +42,15 @@ public final class LinkCollectionIntent extends ConnectivityIntent { |
41 | 42 | ||
42 | private final Set<ConnectPoint> ingressPoints; | 43 | private final Set<ConnectPoint> ingressPoints; |
43 | private final Set<ConnectPoint> egressPoints; | 44 | private final Set<ConnectPoint> egressPoints; |
45 | + private final boolean egressTreatmentFlag; | ||
44 | /** | 46 | /** |
45 | * To manage multiple selectors use case. | 47 | * To manage multiple selectors use case. |
46 | */ | 48 | */ |
47 | private final Map<ConnectPoint, TrafficSelector> ingressSelectors; | 49 | private final Map<ConnectPoint, TrafficSelector> ingressSelectors; |
48 | - | 50 | + /** |
49 | - private final boolean egressTreatmentFlag; | 51 | + * To manage multiple treatments use case. |
52 | + */ | ||
53 | + private final Map<ConnectPoint, TrafficTreatment> egressTreatments; | ||
50 | 54 | ||
51 | /** | 55 | /** |
52 | * Creates a new actionable intent capable of funneling the selected | 56 | * Creates a new actionable intent capable of funneling the selected |
... | @@ -64,6 +68,7 @@ public final class LinkCollectionIntent extends ConnectivityIntent { | ... | @@ -64,6 +68,7 @@ public final class LinkCollectionIntent extends ConnectivityIntent { |
64 | * @param priority priority to use for the flows generated by this intent | 68 | * @param priority priority to use for the flows generated by this intent |
65 | * @param egressTreatment true if treatment should be applied by the egress device | 69 | * @param egressTreatment true if treatment should be applied by the egress device |
66 | * @param ingressSelectors map to store the association ingress to selector | 70 | * @param ingressSelectors map to store the association ingress to selector |
71 | + * @param egressTreatments map to store the association egress to treatment | ||
67 | * @throws NullPointerException {@code path} is null | 72 | * @throws NullPointerException {@code path} is null |
68 | */ | 73 | */ |
69 | private LinkCollectionIntent(ApplicationId appId, | 74 | private LinkCollectionIntent(ApplicationId appId, |
... | @@ -76,13 +81,15 @@ public final class LinkCollectionIntent extends ConnectivityIntent { | ... | @@ -76,13 +81,15 @@ public final class LinkCollectionIntent extends ConnectivityIntent { |
76 | List<Constraint> constraints, | 81 | List<Constraint> constraints, |
77 | int priority, | 82 | int priority, |
78 | boolean egressTreatment, | 83 | boolean egressTreatment, |
79 | - Map<ConnectPoint, TrafficSelector> ingressSelectors) { | 84 | + Map<ConnectPoint, TrafficSelector> ingressSelectors, |
85 | + Map<ConnectPoint, TrafficTreatment> egressTreatments) { | ||
80 | super(appId, key, resources(links), selector, treatment, constraints, priority); | 86 | super(appId, key, resources(links), selector, treatment, constraints, priority); |
81 | this.links = links; | 87 | this.links = links; |
82 | this.ingressPoints = ingressPoints; | 88 | this.ingressPoints = ingressPoints; |
83 | this.egressPoints = egressPoints; | 89 | this.egressPoints = egressPoints; |
84 | this.egressTreatmentFlag = egressTreatment; | 90 | this.egressTreatmentFlag = egressTreatment; |
85 | this.ingressSelectors = ingressSelectors; | 91 | this.ingressSelectors = ingressSelectors; |
92 | + this.egressTreatments = egressTreatments; | ||
86 | } | 93 | } |
87 | 94 | ||
88 | /** | 95 | /** |
... | @@ -95,6 +102,7 @@ public final class LinkCollectionIntent extends ConnectivityIntent { | ... | @@ -95,6 +102,7 @@ public final class LinkCollectionIntent extends ConnectivityIntent { |
95 | this.egressPoints = null; | 102 | this.egressPoints = null; |
96 | this.egressTreatmentFlag = false; | 103 | this.egressTreatmentFlag = false; |
97 | this.ingressSelectors = null; | 104 | this.ingressSelectors = null; |
105 | + this.egressTreatments = null; | ||
98 | } | 106 | } |
99 | 107 | ||
100 | /** | 108 | /** |
... | @@ -117,6 +125,7 @@ public final class LinkCollectionIntent extends ConnectivityIntent { | ... | @@ -117,6 +125,7 @@ public final class LinkCollectionIntent extends ConnectivityIntent { |
117 | Set<ConnectPoint> ingressPoints; | 125 | Set<ConnectPoint> ingressPoints; |
118 | Set<ConnectPoint> egressPoints; | 126 | Set<ConnectPoint> egressPoints; |
119 | Map<ConnectPoint, TrafficSelector> ingressSelectors = ImmutableMap.of(); | 127 | Map<ConnectPoint, TrafficSelector> ingressSelectors = ImmutableMap.of(); |
128 | + Map<ConnectPoint, TrafficTreatment> egressTreatments = ImmutableMap.of(); | ||
120 | boolean egressTreatmentFlag; | 129 | boolean egressTreatmentFlag; |
121 | 130 | ||
122 | private Builder() { | 131 | private Builder() { |
... | @@ -189,6 +198,17 @@ public final class LinkCollectionIntent extends ConnectivityIntent { | ... | @@ -189,6 +198,17 @@ public final class LinkCollectionIntent extends ConnectivityIntent { |
189 | } | 198 | } |
190 | 199 | ||
191 | /** | 200 | /** |
201 | + * Sets the map egress treatments to connection points of the intent. | ||
202 | + * | ||
203 | + * @param egressTreatments maps connection point to traffic treatment | ||
204 | + * @return this builder | ||
205 | + */ | ||
206 | + public Builder egressTreatments(Map<ConnectPoint, TrafficTreatment> egressTreatments) { | ||
207 | + this.egressTreatments = ImmutableMap.copyOf(egressTreatments); | ||
208 | + return this; | ||
209 | + } | ||
210 | + | ||
211 | + /** | ||
192 | * Sets the links of the link collection intent | 212 | * Sets the links of the link collection intent |
193 | * that will be built. | 213 | * that will be built. |
194 | * | 214 | * |
... | @@ -231,12 +251,12 @@ public final class LinkCollectionIntent extends ConnectivityIntent { | ... | @@ -231,12 +251,12 @@ public final class LinkCollectionIntent extends ConnectivityIntent { |
231 | constraints, | 251 | constraints, |
232 | priority, | 252 | priority, |
233 | egressTreatmentFlag, | 253 | egressTreatmentFlag, |
234 | - ingressSelectors | 254 | + ingressSelectors, |
255 | + egressTreatments | ||
235 | ); | 256 | ); |
236 | } | 257 | } |
237 | } | 258 | } |
238 | 259 | ||
239 | - | ||
240 | /** | 260 | /** |
241 | * Returns the set of links that represent the network connections needed | 261 | * Returns the set of links that represent the network connections needed |
242 | * by this intent. | 262 | * by this intent. |
... | @@ -274,6 +294,14 @@ public final class LinkCollectionIntent extends ConnectivityIntent { | ... | @@ -274,6 +294,14 @@ public final class LinkCollectionIntent extends ConnectivityIntent { |
274 | } | 294 | } |
275 | 295 | ||
276 | /** | 296 | /** |
297 | + * Returns the multiple treatments jointly with their connection points. | ||
298 | + * @return multiple treatments | ||
299 | + */ | ||
300 | + public Map<ConnectPoint, TrafficTreatment> egressTreatments() { | ||
301 | + return egressTreatments; | ||
302 | + } | ||
303 | + | ||
304 | + /** | ||
277 | * Returns whether treatment should be applied on egress. | 305 | * Returns whether treatment should be applied on egress. |
278 | * | 306 | * |
279 | * @return the egress treatment flag | 307 | * @return the egress treatment flag |
... | @@ -296,7 +324,8 @@ public final class LinkCollectionIntent extends ConnectivityIntent { | ... | @@ -296,7 +324,8 @@ public final class LinkCollectionIntent extends ConnectivityIntent { |
296 | .add("ingress", ingressPoints()) | 324 | .add("ingress", ingressPoints()) |
297 | .add("egress", egressPoints()) | 325 | .add("egress", egressPoints()) |
298 | .add("selectors", ingressSelectors()) | 326 | .add("selectors", ingressSelectors()) |
299 | - .add("treatmentOnEgress", applyTreatmentOnEgress()) | 327 | + .add("treatments", egressTreatments()) |
328 | + .add("treatementOnEgress", applyTreatmentOnEgress()) | ||
300 | .toString(); | 329 | .toString(); |
301 | } | 330 | } |
302 | } | 331 | } | ... | ... |
... | @@ -17,14 +17,18 @@ package org.onosproject.net.intent; | ... | @@ -17,14 +17,18 @@ package org.onosproject.net.intent; |
17 | 17 | ||
18 | import com.google.common.annotations.Beta; | 18 | import com.google.common.annotations.Beta; |
19 | import com.google.common.base.MoreObjects; | 19 | import com.google.common.base.MoreObjects; |
20 | +import com.google.common.collect.ImmutableList; | ||
21 | +import com.google.common.collect.ImmutableMap; | ||
20 | import com.google.common.collect.ImmutableSet; | 22 | import com.google.common.collect.ImmutableSet; |
21 | 23 | ||
24 | +import com.google.common.collect.Sets; | ||
22 | import org.onosproject.core.ApplicationId; | 25 | import org.onosproject.core.ApplicationId; |
23 | import org.onosproject.net.ConnectPoint; | 26 | import org.onosproject.net.ConnectPoint; |
27 | +import org.onosproject.net.flow.DefaultTrafficTreatment; | ||
24 | import org.onosproject.net.flow.TrafficSelector; | 28 | import org.onosproject.net.flow.TrafficSelector; |
25 | import org.onosproject.net.flow.TrafficTreatment; | 29 | import org.onosproject.net.flow.TrafficTreatment; |
26 | 30 | ||
27 | -import java.util.Collections; | 31 | +import java.util.Map; |
28 | import java.util.Set; | 32 | import java.util.Set; |
29 | import java.util.List; | 33 | import java.util.List; |
30 | 34 | ||
... | @@ -39,6 +43,10 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { | ... | @@ -39,6 +43,10 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { |
39 | 43 | ||
40 | private final ConnectPoint ingressPoint; | 44 | private final ConnectPoint ingressPoint; |
41 | private final Set<ConnectPoint> egressPoints; | 45 | private final Set<ConnectPoint> egressPoints; |
46 | + /** | ||
47 | + * To manage multiple treatments use case. | ||
48 | + */ | ||
49 | + private final Map<ConnectPoint, TrafficTreatment> egressTreatments; | ||
42 | 50 | ||
43 | /** | 51 | /** |
44 | * Creates a new single-to-multi point connectivity intent. | 52 | * Creates a new single-to-multi point connectivity intent. |
... | @@ -51,27 +59,32 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { | ... | @@ -51,27 +59,32 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { |
51 | * @param egressPoints set of ports on which traffic will egress | 59 | * @param egressPoints set of ports on which traffic will egress |
52 | * @param constraints constraints to apply to the intent | 60 | * @param constraints constraints to apply to the intent |
53 | * @param priority priority to use for flows generated by this intent | 61 | * @param priority priority to use for flows generated by this intent |
62 | + * @param egressTreatments map to store the association egress to treatment | ||
54 | * @throws NullPointerException if {@code ingressPoint} or | 63 | * @throws NullPointerException if {@code ingressPoint} or |
55 | * {@code egressPoints} is null | 64 | * {@code egressPoints} is null |
56 | * @throws IllegalArgumentException if the size of {@code egressPoints} is | 65 | * @throws IllegalArgumentException if the size of {@code egressPoints} is |
57 | * not more than 1 | 66 | * not more than 1 |
58 | */ | 67 | */ |
59 | private SinglePointToMultiPointIntent(ApplicationId appId, | 68 | private SinglePointToMultiPointIntent(ApplicationId appId, |
60 | - Key key, | 69 | + Key key, |
61 | - TrafficSelector selector, TrafficTreatment treatment, | 70 | + TrafficSelector selector, |
62 | - ConnectPoint ingressPoint, Set<ConnectPoint> egressPoints, | 71 | + TrafficTreatment treatment, |
63 | - List<Constraint> constraints, | 72 | + ConnectPoint ingressPoint, |
64 | - int priority) { | 73 | + Set<ConnectPoint> egressPoints, |
65 | - super(appId, key, Collections.emptyList(), selector, treatment, constraints, | 74 | + List<Constraint> constraints, |
66 | - priority); | 75 | + int priority, |
76 | + Map<ConnectPoint, TrafficTreatment> egressTreatments) { | ||
77 | + super(appId, key, ImmutableList.of(), selector, treatment, constraints, | ||
78 | + priority); | ||
67 | checkNotNull(egressPoints); | 79 | checkNotNull(egressPoints); |
68 | checkNotNull(ingressPoint); | 80 | checkNotNull(ingressPoint); |
69 | checkArgument(!egressPoints.isEmpty(), "Egress point set cannot be empty"); | 81 | checkArgument(!egressPoints.isEmpty(), "Egress point set cannot be empty"); |
70 | checkArgument(!egressPoints.contains(ingressPoint), | 82 | checkArgument(!egressPoints.contains(ingressPoint), |
71 | "Set of egresses should not contain ingress (ingress: %s)", ingressPoint); | 83 | "Set of egresses should not contain ingress (ingress: %s)", ingressPoint); |
72 | 84 | ||
73 | - this.ingressPoint = checkNotNull(ingressPoint); | 85 | + this.ingressPoint = ingressPoint; |
74 | - this.egressPoints = egressPoints; | 86 | + this.egressPoints = Sets.newHashSet(egressPoints); |
87 | + this.egressTreatments = egressTreatments; | ||
75 | } | 88 | } |
76 | 89 | ||
77 | /** | 90 | /** |
... | @@ -92,6 +105,7 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { | ... | @@ -92,6 +105,7 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { |
92 | public static final class Builder extends ConnectivityIntent.Builder { | 105 | public static final class Builder extends ConnectivityIntent.Builder { |
93 | ConnectPoint ingressPoint; | 106 | ConnectPoint ingressPoint; |
94 | Set<ConnectPoint> egressPoints; | 107 | Set<ConnectPoint> egressPoints; |
108 | + Map<ConnectPoint, TrafficTreatment> egressTreatments = ImmutableMap.of(); | ||
95 | 109 | ||
96 | private Builder() { | 110 | private Builder() { |
97 | // Hide constructor | 111 | // Hide constructor |
... | @@ -152,6 +166,18 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { | ... | @@ -152,6 +166,18 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { |
152 | } | 166 | } |
153 | 167 | ||
154 | /** | 168 | /** |
169 | + * Sets the treatments of the single point to multi point intent | ||
170 | + * that will be built. | ||
171 | + * | ||
172 | + * @param egressTreatments the multiple treatments | ||
173 | + * @return this builder | ||
174 | + */ | ||
175 | + public Builder treatments(Map<ConnectPoint, TrafficTreatment> egressTreatments) { | ||
176 | + this.egressTreatments = ImmutableMap.copyOf(egressTreatments); | ||
177 | + return this; | ||
178 | + } | ||
179 | + | ||
180 | + /** | ||
155 | * Builds a single point to multi point intent from the | 181 | * Builds a single point to multi point intent from the |
156 | * accumulated parameters. | 182 | * accumulated parameters. |
157 | * | 183 | * |
... | @@ -159,6 +185,12 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { | ... | @@ -159,6 +185,12 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { |
159 | */ | 185 | */ |
160 | public SinglePointToMultiPointIntent build() { | 186 | public SinglePointToMultiPointIntent build() { |
161 | 187 | ||
188 | + if (treatment != null && !treatment.allInstructions().isEmpty() && | ||
189 | + !treatment.equals(DefaultTrafficTreatment.emptyTreatment()) && | ||
190 | + egressTreatments != null && !egressTreatments.isEmpty()) { | ||
191 | + throw new IllegalArgumentException("Treatment and Multiple Treatments are both set"); | ||
192 | + } | ||
193 | + | ||
162 | return new SinglePointToMultiPointIntent( | 194 | return new SinglePointToMultiPointIntent( |
163 | appId, | 195 | appId, |
164 | key, | 196 | key, |
... | @@ -167,7 +199,8 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { | ... | @@ -167,7 +199,8 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { |
167 | ingressPoint, | 199 | ingressPoint, |
168 | egressPoints, | 200 | egressPoints, |
169 | constraints, | 201 | constraints, |
170 | - priority | 202 | + priority, |
203 | + egressTreatments | ||
171 | ); | 204 | ); |
172 | } | 205 | } |
173 | } | 206 | } |
... | @@ -179,6 +212,7 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { | ... | @@ -179,6 +212,7 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { |
179 | super(); | 212 | super(); |
180 | this.ingressPoint = null; | 213 | this.ingressPoint = null; |
181 | this.egressPoints = null; | 214 | this.egressPoints = null; |
215 | + this.egressTreatments = null; | ||
182 | } | 216 | } |
183 | 217 | ||
184 | /** | 218 | /** |
... | @@ -200,6 +234,14 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { | ... | @@ -200,6 +234,14 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { |
200 | return egressPoints; | 234 | return egressPoints; |
201 | } | 235 | } |
202 | 236 | ||
237 | + /** | ||
238 | + * Returns the multiple treatments jointly with their connection points. | ||
239 | + * @return multiple treatments | ||
240 | + */ | ||
241 | + public Map<ConnectPoint, TrafficTreatment> egressTreatments() { | ||
242 | + return egressTreatments; | ||
243 | + } | ||
244 | + | ||
203 | @Override | 245 | @Override |
204 | public String toString() { | 246 | public String toString() { |
205 | return MoreObjects.toStringHelper(getClass()) | 247 | return MoreObjects.toStringHelper(getClass()) |
... | @@ -212,6 +254,7 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { | ... | @@ -212,6 +254,7 @@ public final class SinglePointToMultiPointIntent extends ConnectivityIntent { |
212 | .add("treatment", treatment()) | 254 | .add("treatment", treatment()) |
213 | .add("ingress", ingressPoint) | 255 | .add("ingress", ingressPoint) |
214 | .add("egress", egressPoints) | 256 | .add("egress", egressPoints) |
257 | + .add("treatments", egressTreatments) | ||
215 | .add("constraints", constraints()) | 258 | .add("constraints", constraints()) |
216 | .toString(); | 259 | .toString(); |
217 | } | 260 | } | ... | ... |
... | @@ -43,6 +43,7 @@ public abstract class ConnectivityIntentTest extends IntentTest { | ... | @@ -43,6 +43,7 @@ public abstract class ConnectivityIntentTest extends IntentTest { |
43 | public static final TrafficSelector MATCH = DefaultTrafficSelector.emptySelector(); | 43 | public static final TrafficSelector MATCH = DefaultTrafficSelector.emptySelector(); |
44 | public static final TrafficTreatment NOP = DefaultTrafficTreatment.emptyTreatment(); | 44 | public static final TrafficTreatment NOP = DefaultTrafficTreatment.emptyTreatment(); |
45 | public static final Map<ConnectPoint, TrafficSelector> MATCHES = Collections.emptyMap(); | 45 | public static final Map<ConnectPoint, TrafficSelector> MATCHES = Collections.emptyMap(); |
46 | + public static final Map<ConnectPoint, TrafficTreatment> TREATMENTS = Collections.emptyMap(); | ||
46 | 47 | ||
47 | public static final ConnectPoint P1 = new ConnectPoint(DeviceId.deviceId("111"), PortNumber.portNumber(0x1)); | 48 | public static final ConnectPoint P1 = new ConnectPoint(DeviceId.deviceId("111"), PortNumber.portNumber(0x1)); |
48 | public static final ConnectPoint P2 = new ConnectPoint(DeviceId.deviceId("222"), PortNumber.portNumber(0x2)); | 49 | public static final ConnectPoint P2 = new ConnectPoint(DeviceId.deviceId("222"), PortNumber.portNumber(0x2)); |
... | @@ -64,4 +65,17 @@ public abstract class ConnectivityIntentTest extends IntentTest { | ... | @@ -64,4 +65,17 @@ public abstract class ConnectivityIntentTest extends IntentTest { |
64 | VLANMATCHES.put(P2, VLANMATCH2); | 65 | VLANMATCHES.put(P2, VLANMATCH2); |
65 | } | 66 | } |
66 | 67 | ||
68 | + public static final TrafficTreatment VLANACTION1 = DefaultTrafficTreatment.builder() | ||
69 | + .setVlanId(VlanId.vlanId("2")) | ||
70 | + .build(); | ||
71 | + public static final TrafficTreatment VLANACTION2 = DefaultTrafficTreatment.builder() | ||
72 | + .setVlanId(VlanId.vlanId("3")) | ||
73 | + .build(); | ||
74 | + | ||
75 | + public static final Map<ConnectPoint, TrafficTreatment> VLANACTIONS = Maps.newHashMap(); | ||
76 | + static { | ||
77 | + VLANACTIONS.put(P1, VLANACTION1); | ||
78 | + VLANACTIONS.put(P2, VLANACTION2); | ||
79 | + } | ||
80 | + | ||
67 | } | 81 | } | ... | ... |
... | @@ -15,7 +15,9 @@ | ... | @@ -15,7 +15,9 @@ |
15 | */ | 15 | */ |
16 | package org.onosproject.net.intent; | 16 | package org.onosproject.net.intent; |
17 | 17 | ||
18 | +import org.junit.Rule; | ||
18 | import org.junit.Test; | 19 | import org.junit.Test; |
20 | +import org.junit.rules.ExpectedException; | ||
19 | 21 | ||
20 | import static org.junit.Assert.assertEquals; | 22 | import static org.junit.Assert.assertEquals; |
21 | import static org.onlab.junit.ImmutableClassChecker.assertThatClassIsImmutable; | 23 | import static org.onlab.junit.ImmutableClassChecker.assertThatClassIsImmutable; |
... | @@ -42,6 +44,41 @@ public class SinglePointToMultiPointIntentTest extends ConnectivityIntentTest { | ... | @@ -42,6 +44,41 @@ public class SinglePointToMultiPointIntentTest extends ConnectivityIntentTest { |
42 | assertEquals("incorrect egress", PS2, intent.egressPoints()); | 44 | assertEquals("incorrect egress", PS2, intent.egressPoints()); |
43 | } | 45 | } |
44 | 46 | ||
47 | + @Rule | ||
48 | + public ExpectedException wrongMultiple = ExpectedException.none(); | ||
49 | + | ||
50 | + @Test | ||
51 | + public void multipleTreatments() { | ||
52 | + | ||
53 | + SinglePointToMultiPointIntent intent = createFirstMultiple(); | ||
54 | + assertEquals("incorrect id", APPID, intent.appId()); | ||
55 | + assertEquals("incorrect match", MATCH, intent.selector()); | ||
56 | + assertEquals("incorrect ingress", P1, intent.ingressPoint()); | ||
57 | + assertEquals("incorrect egress", PS2, intent.egressPoints()); | ||
58 | + assertEquals("incorrect treatment", NOP, intent.treatment()); | ||
59 | + assertEquals("incorrect treatments", TREATMENTS, intent.egressTreatments()); | ||
60 | + | ||
61 | + intent = createSecondMultiple(); | ||
62 | + assertEquals("incorrect id", APPID, intent.appId()); | ||
63 | + assertEquals("incorrect match", MATCH, intent.selector()); | ||
64 | + assertEquals("incorrect ingress", P1, intent.ingressPoint()); | ||
65 | + assertEquals("incorrect egress", PS2, intent.egressPoints()); | ||
66 | + assertEquals("incorrect treatment", VLANACTION1, intent.treatment()); | ||
67 | + assertEquals("incorrect selectors", TREATMENTS, intent.egressTreatments()); | ||
68 | + | ||
69 | + intent = createThirdMultiple(); | ||
70 | + assertEquals("incorrect id", APPID, intent.appId()); | ||
71 | + assertEquals("incorrect match", MATCH, intent.selector()); | ||
72 | + assertEquals("incorrect ingress", P1, intent.ingressPoint()); | ||
73 | + assertEquals("incorrect egress", PS2, intent.egressPoints()); | ||
74 | + assertEquals("incorrect treatment", NOP, intent.treatment()); | ||
75 | + assertEquals("incorrect selectors", VLANACTIONS, intent.egressTreatments()); | ||
76 | + | ||
77 | + wrongMultiple.expect(IllegalArgumentException.class); | ||
78 | + wrongMultiple.expectMessage("Treatment and Multiple Treatments are both set"); | ||
79 | + intent = createWrongMultiple(); | ||
80 | + } | ||
81 | + | ||
45 | @Override | 82 | @Override |
46 | protected SinglePointToMultiPointIntent createOne() { | 83 | protected SinglePointToMultiPointIntent createOne() { |
47 | return SinglePointToMultiPointIntent.builder() | 84 | return SinglePointToMultiPointIntent.builder() |
... | @@ -63,4 +100,50 @@ public class SinglePointToMultiPointIntentTest extends ConnectivityIntentTest { | ... | @@ -63,4 +100,50 @@ public class SinglePointToMultiPointIntentTest extends ConnectivityIntentTest { |
63 | .egressPoints(PS1) | 100 | .egressPoints(PS1) |
64 | .build(); | 101 | .build(); |
65 | } | 102 | } |
103 | + | ||
104 | + | ||
105 | + protected SinglePointToMultiPointIntent createFirstMultiple() { | ||
106 | + return SinglePointToMultiPointIntent.builder() | ||
107 | + .appId(APPID) | ||
108 | + .selector(MATCH) | ||
109 | + .treatment(NOP) | ||
110 | + .ingressPoint(P1) | ||
111 | + .egressPoints(PS2) | ||
112 | + .treatments(TREATMENTS) | ||
113 | + .build(); | ||
114 | + } | ||
115 | + | ||
116 | + protected SinglePointToMultiPointIntent createSecondMultiple() { | ||
117 | + return SinglePointToMultiPointIntent.builder() | ||
118 | + .appId(APPID) | ||
119 | + .selector(MATCH) | ||
120 | + .treatment(VLANACTION1) | ||
121 | + .ingressPoint(P1) | ||
122 | + .egressPoints(PS2) | ||
123 | + .treatments(TREATMENTS) | ||
124 | + .build(); | ||
125 | + } | ||
126 | + | ||
127 | + protected SinglePointToMultiPointIntent createThirdMultiple() { | ||
128 | + return SinglePointToMultiPointIntent.builder() | ||
129 | + .appId(APPID) | ||
130 | + .selector(MATCH) | ||
131 | + .treatment(NOP) | ||
132 | + .ingressPoint(P1) | ||
133 | + .egressPoints(PS2) | ||
134 | + .treatments(VLANACTIONS) | ||
135 | + .build(); | ||
136 | + } | ||
137 | + | ||
138 | + protected SinglePointToMultiPointIntent createWrongMultiple() { | ||
139 | + return SinglePointToMultiPointIntent.builder() | ||
140 | + .appId(APPID) | ||
141 | + .selector(MATCH) | ||
142 | + .treatment(VLANACTION1) | ||
143 | + .ingressPoint(P1) | ||
144 | + .egressPoints(PS2) | ||
145 | + .treatments(VLANACTIONS) | ||
146 | + .build(); | ||
147 | + } | ||
148 | + | ||
66 | } | 149 | } | ... | ... |
... | @@ -27,6 +27,7 @@ import org.onosproject.net.flow.DefaultTrafficSelector; | ... | @@ -27,6 +27,7 @@ import org.onosproject.net.flow.DefaultTrafficSelector; |
27 | import org.onosproject.net.flow.DefaultTrafficTreatment; | 27 | import org.onosproject.net.flow.DefaultTrafficTreatment; |
28 | import org.onosproject.net.flow.TrafficSelector; | 28 | import org.onosproject.net.flow.TrafficSelector; |
29 | import org.onosproject.net.flow.TrafficTreatment; | 29 | import org.onosproject.net.flow.TrafficTreatment; |
30 | +import org.onosproject.net.flow.instructions.Instruction; | ||
30 | import org.onosproject.net.flow.instructions.L0ModificationInstruction; | 31 | import org.onosproject.net.flow.instructions.L0ModificationInstruction; |
31 | import org.onosproject.net.flow.instructions.L1ModificationInstruction; | 32 | import org.onosproject.net.flow.instructions.L1ModificationInstruction; |
32 | import org.onosproject.net.flow.instructions.L2ModificationInstruction; | 33 | import org.onosproject.net.flow.instructions.L2ModificationInstruction; |
... | @@ -211,10 +212,29 @@ public class LinkCollectionCompiler<T> { | ... | @@ -211,10 +212,29 @@ public class LinkCollectionCompiler<T> { |
211 | } | 212 | } |
212 | } else { | 213 | } else { |
213 | if (outPorts.stream().allMatch(egressPorts::contains)) { | 214 | if (outPorts.stream().allMatch(egressPorts::contains)) { |
214 | - TrafficTreatment.Builder egressTreatmentBuilder = | 215 | + TrafficTreatment.Builder egressTreatmentBuilder = DefaultTrafficTreatment.builder(); |
215 | - DefaultTrafficTreatment.builder(intent.treatment()); | 216 | + if (intent.egressTreatments() != null && !intent.egressTreatments().isEmpty()) { |
216 | - outPorts.forEach(egressTreatmentBuilder::setOutput); | 217 | + for (PortNumber outPort : outPorts) { |
217 | - | 218 | + Optional<ConnectPoint> connectPoint = intent.egressPoints() |
219 | + .stream() | ||
220 | + .filter(egressPoint -> egressPoint.port().equals(outPort) | ||
221 | + && egressPoint.deviceId().equals(deviceId)) | ||
222 | + .findFirst(); | ||
223 | + if (connectPoint.isPresent()) { | ||
224 | + TrafficTreatment egressTreatment = intent.egressTreatments().get(connectPoint.get()); | ||
225 | + this.addTreatment(egressTreatmentBuilder, egressTreatment); | ||
226 | + egressTreatmentBuilder = this.updateBuilder(egressTreatmentBuilder, intent.selector()); | ||
227 | + egressTreatmentBuilder.setOutput(outPort); | ||
228 | + } else { | ||
229 | + throw new IntentCompilationException("Looking for connect point associated to " + | ||
230 | + "the treatment. outPort not in egressPoints"); | ||
231 | + } | ||
232 | + } | ||
233 | + } else { | ||
234 | + egressTreatmentBuilder = this | ||
235 | + .updateBuilder(DefaultTrafficTreatment.builder(intent.treatment()), intent.selector()); | ||
236 | + outPorts.forEach(egressTreatmentBuilder::setOutput); | ||
237 | + } | ||
218 | selectorBuilder = DefaultTrafficSelector.builder(intent.selector()); | 238 | selectorBuilder = DefaultTrafficSelector.builder(intent.selector()); |
219 | treatment = egressTreatmentBuilder.build(); | 239 | treatment = egressTreatmentBuilder.build(); |
220 | } else { | 240 | } else { |
... | @@ -230,10 +250,34 @@ public class LinkCollectionCompiler<T> { | ... | @@ -230,10 +250,34 @@ public class LinkCollectionCompiler<T> { |
230 | } | 250 | } |
231 | 251 | ||
232 | /** | 252 | /** |
253 | + * Update a builder using a treatment. | ||
254 | + * @param builder the builder to update | ||
255 | + * @param treatment the treatment to add | ||
256 | + * @return the new builder | ||
257 | + */ | ||
258 | + private TrafficTreatment.Builder addTreatment(TrafficTreatment.Builder builder, TrafficTreatment treatment) { | ||
259 | + builder.deferred(); | ||
260 | + for (Instruction instruction : treatment.deferred()) { | ||
261 | + builder.add(instruction); | ||
262 | + } | ||
263 | + builder.immediate(); | ||
264 | + for (Instruction instruction : treatment.immediate()) { | ||
265 | + builder.add(instruction); | ||
266 | + } | ||
267 | + return builder; | ||
268 | + } | ||
269 | + | ||
270 | + /** | ||
233 | * Update the original builder with the necessary operations | 271 | * Update the original builder with the necessary operations |
234 | * to have a correct forwarding given an ingress selector. | 272 | * to have a correct forwarding given an ingress selector. |
273 | + * TODO | ||
274 | + * This means that if the ingress selectors match on different vlanids and | ||
275 | + * the egress treatment rewrite the vlanid the forwarding works | ||
276 | + * but if we need to push for example an mpls label at the egress | ||
277 | + * we need to implement properly this method. | ||
235 | * | 278 | * |
236 | * @param treatmentBuilder the builder to modify | 279 | * @param treatmentBuilder the builder to modify |
280 | + * @param intentSelector the intent selector to use as input | ||
237 | * @return the new treatment created | 281 | * @return the new treatment created |
238 | */ | 282 | */ |
239 | private TrafficTreatment.Builder updateBuilder(TrafficTreatment.Builder treatmentBuilder, | 283 | private TrafficTreatment.Builder updateBuilder(TrafficTreatment.Builder treatmentBuilder, | ... | ... |
... | @@ -34,6 +34,8 @@ import org.onosproject.net.intent.FlowRuleIntent; | ... | @@ -34,6 +34,8 @@ import org.onosproject.net.intent.FlowRuleIntent; |
34 | import org.onosproject.net.intent.Intent; | 34 | import org.onosproject.net.intent.Intent; |
35 | import org.onosproject.net.intent.IntentCompiler; | 35 | import org.onosproject.net.intent.IntentCompiler; |
36 | import org.onosproject.net.intent.LinkCollectionIntent; | 36 | import org.onosproject.net.intent.LinkCollectionIntent; |
37 | +import org.slf4j.Logger; | ||
38 | +import org.slf4j.LoggerFactory; | ||
37 | 39 | ||
38 | import java.util.ArrayList; | 40 | import java.util.ArrayList; |
39 | import java.util.Collections; | 41 | import java.util.Collections; |
... | @@ -48,6 +50,9 @@ public class LinkCollectionIntentCompiler | ... | @@ -48,6 +50,9 @@ public class LinkCollectionIntentCompiler |
48 | extends LinkCollectionCompiler<FlowRule> | 50 | extends LinkCollectionCompiler<FlowRule> |
49 | implements IntentCompiler<LinkCollectionIntent> { | 51 | implements IntentCompiler<LinkCollectionIntent> { |
50 | 52 | ||
53 | + private static Logger log = LoggerFactory.getLogger(LinkCollectionIntentCompiler.class); | ||
54 | + | ||
55 | + | ||
51 | @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | 56 | @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) |
52 | protected IntentConfigurableRegistrator registrator; | 57 | protected IntentConfigurableRegistrator registrator; |
53 | 58 | ... | ... |
... | @@ -77,6 +77,7 @@ public class SinglePointToMultiPointIntentCompiler | ... | @@ -77,6 +77,7 @@ public class SinglePointToMultiPointIntentCompiler |
77 | .priority(intent.priority()) | 77 | .priority(intent.priority()) |
78 | .applyTreatmentOnEgress(true) | 78 | .applyTreatmentOnEgress(true) |
79 | .constraints(intent.constraints()) | 79 | .constraints(intent.constraints()) |
80 | + .egressTreatments(intent.egressTreatments()) | ||
80 | .build(); | 81 | .build(); |
81 | 82 | ||
82 | return Collections.singletonList(result); | 83 | return Collections.singletonList(result); | ... | ... |
... | @@ -64,13 +64,18 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -64,13 +64,18 @@ public class LinkCollectionIntentCompilerTest { |
64 | 64 | ||
65 | private final ApplicationId appId = new TestApplicationId("test"); | 65 | private final ApplicationId appId = new TestApplicationId("test"); |
66 | 66 | ||
67 | - private final ConnectPoint d1p1 = connectPoint("s1", 0); | 67 | + private final ConnectPoint d1p1 = connectPoint("s1", 1); |
68 | private final ConnectPoint d2p0 = connectPoint("s2", 0); | 68 | private final ConnectPoint d2p0 = connectPoint("s2", 0); |
69 | private final ConnectPoint d2p1 = connectPoint("s2", 1); | 69 | private final ConnectPoint d2p1 = connectPoint("s2", 1); |
70 | + private final ConnectPoint d2p2 = connectPoint("s2", 2); | ||
71 | + private final ConnectPoint d2p3 = connectPoint("s2", 3); | ||
70 | private final ConnectPoint d3p1 = connectPoint("s3", 1); | 72 | private final ConnectPoint d3p1 = connectPoint("s3", 1); |
71 | private final ConnectPoint d3p2 = connectPoint("s3", 9); | 73 | private final ConnectPoint d3p2 = connectPoint("s3", 9); |
72 | private final ConnectPoint d3p0 = connectPoint("s3", 10); | 74 | private final ConnectPoint d3p0 = connectPoint("s3", 10); |
73 | private final ConnectPoint d1p0 = connectPoint("s1", 10); | 75 | private final ConnectPoint d1p0 = connectPoint("s1", 10); |
76 | + private final ConnectPoint d4p1 = connectPoint("s4", 1); | ||
77 | + private final ConnectPoint d4p0 = connectPoint("s4", 10); | ||
78 | + | ||
74 | 79 | ||
75 | private final Set<Link> links = ImmutableSet.of( | 80 | private final Set<Link> links = ImmutableSet.of( |
76 | DefaultLink.builder().providerId(PID).src(d1p1).dst(d2p0).type(DIRECT).build(), | 81 | DefaultLink.builder().providerId(PID).src(d1p1).dst(d2p0).type(DIRECT).build(), |
... | @@ -80,6 +85,11 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -80,6 +85,11 @@ public class LinkCollectionIntentCompilerTest { |
80 | private final Set<Link> linksMultiple = ImmutableSet.of( | 85 | private final Set<Link> linksMultiple = ImmutableSet.of( |
81 | DefaultLink.builder().providerId(PID).src(d3p1).dst(d2p0).type(DIRECT).build()); | 86 | DefaultLink.builder().providerId(PID).src(d3p1).dst(d2p0).type(DIRECT).build()); |
82 | 87 | ||
88 | + private final Set<Link> linksMultiple2 = ImmutableSet.of( | ||
89 | + DefaultLink.builder().providerId(PID).src(d2p0).dst(d1p1).type(DIRECT).build(), | ||
90 | + DefaultLink.builder().providerId(PID).src(d2p1).dst(d3p1).type(DIRECT).build(), | ||
91 | + DefaultLink.builder().providerId(PID).src(d2p2).dst(d4p1).type(DIRECT).build()); | ||
92 | + | ||
83 | private final TrafficSelector selector = DefaultTrafficSelector.builder().build(); | 93 | private final TrafficSelector selector = DefaultTrafficSelector.builder().build(); |
84 | private final TrafficTreatment treatment = DefaultTrafficTreatment.builder().build(); | 94 | private final TrafficTreatment treatment = DefaultTrafficTreatment.builder().build(); |
85 | 95 | ||
... | @@ -101,14 +111,40 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -101,14 +111,40 @@ public class LinkCollectionIntentCompilerTest { |
101 | .setVlanId(egressVlan) | 111 | .setVlanId(egressVlan) |
102 | .build(); | 112 | .build(); |
103 | 113 | ||
114 | +private final VlanId ingressVlan = VlanId.vlanId("10"); | ||
115 | + private final TrafficSelector vlanSelector = DefaultTrafficSelector | ||
116 | + .builder() | ||
117 | + .matchVlanId(ingressVlan) | ||
118 | + .build(); | ||
119 | + | ||
120 | + private final VlanId egressVlan1 = VlanId.vlanId("20"); | ||
121 | + private final TrafficTreatment vlanTreatment1 = DefaultTrafficTreatment | ||
122 | + .builder() | ||
123 | + .setVlanId(egressVlan1) | ||
124 | + .build(); | ||
125 | + | ||
126 | + private final VlanId egressVlan2 = VlanId.vlanId("666"); | ||
127 | + private final TrafficTreatment vlanTreatment2 = DefaultTrafficTreatment | ||
128 | + .builder() | ||
129 | + .setVlanId(egressVlan2) | ||
130 | + .build(); | ||
131 | + | ||
132 | + private final VlanId egressVlan3 = VlanId.vlanId("69"); | ||
133 | + private final TrafficTreatment vlanTreatment3 = DefaultTrafficTreatment | ||
134 | + .builder() | ||
135 | + .setVlanId(egressVlan3) | ||
136 | + .build(); | ||
137 | + | ||
138 | + | ||
104 | private CoreService coreService; | 139 | private CoreService coreService; |
105 | private IntentExtensionService intentExtensionService; | 140 | private IntentExtensionService intentExtensionService; |
106 | private IntentConfigurableRegistrator registrator; | 141 | private IntentConfigurableRegistrator registrator; |
107 | private IdGenerator idGenerator = new MockIdGenerator(); | 142 | private IdGenerator idGenerator = new MockIdGenerator(); |
108 | 143 | ||
109 | private LinkCollectionIntent intent; | 144 | private LinkCollectionIntent intent; |
110 | - private LinkCollectionIntent intentMultiple; | 145 | + private LinkCollectionIntent intentMultipleSelectors; |
111 | - | 146 | + private LinkCollectionIntent intentMultipleTreatments; |
147 | + private LinkCollectionIntent intentMultipleTreatments2; | ||
112 | 148 | ||
113 | private LinkCollectionIntentCompiler sut; | 149 | private LinkCollectionIntentCompiler sut; |
114 | 150 | ||
... | @@ -130,7 +166,7 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -130,7 +166,7 @@ public class LinkCollectionIntentCompilerTest { |
130 | .ingressPoints(ImmutableSet.of(d1p1)) | 166 | .ingressPoints(ImmutableSet.of(d1p1)) |
131 | .egressPoints(ImmutableSet.of(d3p1)) | 167 | .egressPoints(ImmutableSet.of(d3p1)) |
132 | .build(); | 168 | .build(); |
133 | - intentMultiple = LinkCollectionIntent.builder() | 169 | + intentMultipleSelectors = LinkCollectionIntent.builder() |
134 | .appId(APP_ID) | 170 | .appId(APP_ID) |
135 | .treatment(vlanTreatment) | 171 | .treatment(vlanTreatment) |
136 | .links(linksMultiple) | 172 | .links(linksMultiple) |
... | @@ -138,6 +174,24 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -138,6 +174,24 @@ public class LinkCollectionIntentCompilerTest { |
138 | .egressPoints(ImmutableSet.of(d2p1)) | 174 | .egressPoints(ImmutableSet.of(d2p1)) |
139 | .ingressSelectors(this.createIngressSelectors()) | 175 | .ingressSelectors(this.createIngressSelectors()) |
140 | .build(); | 176 | .build(); |
177 | + intentMultipleTreatments = LinkCollectionIntent.builder() | ||
178 | + .appId(APP_ID) | ||
179 | + .selector(vlanSelector) | ||
180 | + .links(linksMultiple) | ||
181 | + .ingressPoints(ImmutableSet.of(d3p0)) | ||
182 | + .egressPoints(ImmutableSet.of(d2p1, d2p2)) | ||
183 | + .egressTreatments(this.createEgressTreatments()) | ||
184 | + .applyTreatmentOnEgress(true) | ||
185 | + .build(); | ||
186 | + intentMultipleTreatments2 = LinkCollectionIntent.builder() | ||
187 | + .appId(APP_ID) | ||
188 | + .selector(vlanSelector) | ||
189 | + .links(linksMultiple2) | ||
190 | + .ingressPoints(ImmutableSet.of(d2p3)) | ||
191 | + .egressPoints(ImmutableSet.of(d1p0, d3p0, d4p0)) | ||
192 | + .egressTreatments(this.createEgressTreatments2()) | ||
193 | + .applyTreatmentOnEgress(true) | ||
194 | + .build(); | ||
141 | 195 | ||
142 | intentExtensionService = createMock(IntentExtensionService.class); | 196 | intentExtensionService = createMock(IntentExtensionService.class); |
143 | intentExtensionService.registerCompiler(LinkCollectionIntent.class, sut); | 197 | intentExtensionService.registerCompiler(LinkCollectionIntent.class, sut); |
... | @@ -208,22 +262,22 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -208,22 +262,22 @@ public class LinkCollectionIntentCompilerTest { |
208 | sut.deactivate(); | 262 | sut.deactivate(); |
209 | } | 263 | } |
210 | 264 | ||
211 | - @Test | 265 | +@Test |
212 | public void testCompileMultipleSelectors() { | 266 | public void testCompileMultipleSelectors() { |
213 | sut.activate(); | 267 | sut.activate(); |
214 | 268 | ||
215 | - List<Intent> compiled = sut.compile(intentMultiple, Collections.emptyList()); | 269 | + List<Intent> compiled = sut.compile(intentMultipleSelectors, Collections.emptyList()); |
216 | assertThat(compiled, hasSize(1)); | 270 | assertThat(compiled, hasSize(1)); |
217 | 271 | ||
218 | 272 | ||
219 | Collection<FlowRule> rules = ((FlowRuleIntent) compiled.get(0)).flowRules(); | 273 | Collection<FlowRule> rules = ((FlowRuleIntent) compiled.get(0)).flowRules(); |
220 | - assertThat(rules, hasSize((linksMultiple.size()) + intentMultiple.ingressPoints().size())); | 274 | + assertThat(rules, hasSize((linksMultiple.size()) + intentMultipleSelectors.ingressPoints().size())); |
221 | 275 | ||
222 | Set<FlowRule> d3Rules = rules | 276 | Set<FlowRule> d3Rules = rules |
223 | .parallelStream() | 277 | .parallelStream() |
224 | .filter(rule -> rule.deviceId().equals(d3p0.deviceId())) | 278 | .filter(rule -> rule.deviceId().equals(d3p0.deviceId())) |
225 | .collect(Collectors.toSet()); | 279 | .collect(Collectors.toSet()); |
226 | - assertThat(d3Rules, hasSize(intentMultiple.ingressPoints().size())); | 280 | + assertThat(d3Rules, hasSize(intentMultipleSelectors.ingressPoints().size())); |
227 | 281 | ||
228 | FlowRule rule1 = rules.stream() | 282 | FlowRule rule1 = rules.stream() |
229 | .filter(rule -> rule.deviceId().equals(d3p0.deviceId()) | 283 | .filter(rule -> rule.deviceId().equals(d3p0.deviceId()) |
... | @@ -233,18 +287,18 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -233,18 +287,18 @@ public class LinkCollectionIntentCompilerTest { |
233 | .get(); | 287 | .get(); |
234 | assertThat(rule1.selector(), is( | 288 | assertThat(rule1.selector(), is( |
235 | DefaultTrafficSelector | 289 | DefaultTrafficSelector |
236 | - .builder(intentMultiple.selector()) | 290 | + .builder(intentMultipleSelectors.selector()) |
237 | .matchInPort(d3p0.port()) | 291 | .matchInPort(d3p0.port()) |
238 | .matchVlanId(ingressVlan1) | 292 | .matchVlanId(ingressVlan1) |
239 | .build() | 293 | .build() |
240 | )); | 294 | )); |
241 | assertThat(rule1.treatment(), is( | 295 | assertThat(rule1.treatment(), is( |
242 | DefaultTrafficTreatment | 296 | DefaultTrafficTreatment |
243 | - .builder(intentMultiple.treatment()) | 297 | + .builder(intentMultipleSelectors.treatment()) |
244 | .setOutput(d3p1.port()) | 298 | .setOutput(d3p1.port()) |
245 | .build() | 299 | .build() |
246 | )); | 300 | )); |
247 | - assertThat(rule1.priority(), is(intentMultiple.priority())); | 301 | + assertThat(rule1.priority(), is(intentMultipleSelectors.priority())); |
248 | 302 | ||
249 | FlowRule rule2 = rules.stream() | 303 | FlowRule rule2 = rules.stream() |
250 | .filter(rule -> rule.deviceId().equals(d3p0.deviceId()) | 304 | .filter(rule -> rule.deviceId().equals(d3p0.deviceId()) |
... | @@ -254,24 +308,24 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -254,24 +308,24 @@ public class LinkCollectionIntentCompilerTest { |
254 | .get(); | 308 | .get(); |
255 | assertThat(rule2.selector(), is( | 309 | assertThat(rule2.selector(), is( |
256 | DefaultTrafficSelector | 310 | DefaultTrafficSelector |
257 | - .builder(intentMultiple.selector()) | 311 | + .builder(intentMultipleSelectors.selector()) |
258 | .matchInPort(d3p2.port()) | 312 | .matchInPort(d3p2.port()) |
259 | .matchVlanId(ingressVlan2) | 313 | .matchVlanId(ingressVlan2) |
260 | .build() | 314 | .build() |
261 | )); | 315 | )); |
262 | assertThat(rule2.treatment(), is( | 316 | assertThat(rule2.treatment(), is( |
263 | DefaultTrafficTreatment | 317 | DefaultTrafficTreatment |
264 | - .builder(intentMultiple.treatment()) | 318 | + .builder(intentMultipleSelectors.treatment()) |
265 | .setOutput(d3p1.port()) | 319 | .setOutput(d3p1.port()) |
266 | .build() | 320 | .build() |
267 | )); | 321 | )); |
268 | - assertThat(rule1.priority(), is(intentMultiple.priority())); | 322 | + assertThat(rule2.priority(), is(intentMultipleSelectors.priority())); |
269 | 323 | ||
270 | Set<FlowRule> d2Rules = rules | 324 | Set<FlowRule> d2Rules = rules |
271 | .parallelStream() | 325 | .parallelStream() |
272 | .filter(rule -> rule.deviceId().equals(d2p0.deviceId())) | 326 | .filter(rule -> rule.deviceId().equals(d2p0.deviceId())) |
273 | .collect(Collectors.toSet()); | 327 | .collect(Collectors.toSet()); |
274 | - assertThat(d2Rules, hasSize(intentMultiple.egressPoints().size())); | 328 | + assertThat(d2Rules, hasSize(intentMultipleSelectors.egressPoints().size())); |
275 | 329 | ||
276 | // We do not need in_port filter | 330 | // We do not need in_port filter |
277 | FlowRule rule3 = rules.stream() | 331 | FlowRule rule3 = rules.stream() |
... | @@ -280,7 +334,7 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -280,7 +334,7 @@ public class LinkCollectionIntentCompilerTest { |
280 | .get(); | 334 | .get(); |
281 | assertThat(rule3.selector(), is( | 335 | assertThat(rule3.selector(), is( |
282 | DefaultTrafficSelector | 336 | DefaultTrafficSelector |
283 | - .builder(intentMultiple.selector()) | 337 | + .builder(intentMultipleSelectors.selector()) |
284 | .matchInPort(d2p0.port()) | 338 | .matchInPort(d2p0.port()) |
285 | .matchVlanId(egressVlan) | 339 | .matchVlanId(egressVlan) |
286 | .build() | 340 | .build() |
... | @@ -291,15 +345,216 @@ public class LinkCollectionIntentCompilerTest { | ... | @@ -291,15 +345,216 @@ public class LinkCollectionIntentCompilerTest { |
291 | .setOutput(d2p1.port()) | 345 | .setOutput(d2p1.port()) |
292 | .build() | 346 | .build() |
293 | )); | 347 | )); |
294 | - assertThat(rule3.priority(), is(intentMultiple.priority())); | 348 | + assertThat(rule3.priority(), is(intentMultipleSelectors.priority())); |
295 | 349 | ||
296 | sut.deactivate(); | 350 | sut.deactivate(); |
297 | } | 351 | } |
298 | 352 | ||
353 | + @Test | ||
354 | + public void testCompileMultipleTreatments() { | ||
355 | + sut.activate(); | ||
356 | + | ||
357 | + List<Intent> compiled = sut.compile(intentMultipleTreatments, Collections.emptyList()); | ||
358 | + assertThat(compiled, hasSize(1)); | ||
359 | + | ||
360 | + Collection<FlowRule> rules = ((FlowRuleIntent) compiled.get(0)).flowRules(); | ||
361 | + assertThat(rules, hasSize((linksMultiple.size() + intentMultipleTreatments.egressPoints().size()))); | ||
362 | + | ||
363 | + Set<FlowRule> d3Rules = rules | ||
364 | + .parallelStream() | ||
365 | + .filter(rule -> rule.deviceId().equals(d3p0.deviceId())) | ||
366 | + .collect(Collectors.toSet()); | ||
367 | + assertThat(d3Rules, hasSize(intentMultipleTreatments.ingressPoints().size())); | ||
368 | + | ||
369 | + FlowRule rule1 = rules.stream() | ||
370 | + .filter(rule -> rule.deviceId().equals(d3p0.deviceId())) | ||
371 | + .findFirst() | ||
372 | + .get(); | ||
373 | + assertThat(rule1.selector(), is( | ||
374 | + DefaultTrafficSelector | ||
375 | + .builder(intentMultipleTreatments.selector()) | ||
376 | + .matchInPort(d3p0.port()) | ||
377 | + .matchVlanId(ingressVlan) | ||
378 | + .build() | ||
379 | + )); | ||
380 | + assertThat(rule1.treatment(), is( | ||
381 | + DefaultTrafficTreatment | ||
382 | + .builder(intentMultipleTreatments.treatment()) | ||
383 | + .setOutput(d3p1.port()) | ||
384 | + .build() | ||
385 | + )); | ||
386 | + assertThat(rule1.priority(), is(intentMultipleTreatments.priority())); | ||
387 | + | ||
388 | + Set<FlowRule> d2Rules = rules | ||
389 | + .parallelStream() | ||
390 | + .filter(rule -> rule.deviceId().equals(d2p0.deviceId())) | ||
391 | + .collect(Collectors.toSet()); | ||
392 | + assertThat(d2Rules, hasSize(1)); | ||
393 | + | ||
394 | + FlowRule rule2 = rules.stream() | ||
395 | + .filter(rule -> rule.deviceId().equals(d2p0.deviceId())) | ||
396 | + .findFirst() | ||
397 | + .get(); | ||
398 | + assertThat(rule2.selector(), is( | ||
399 | + DefaultTrafficSelector | ||
400 | + .builder(intentMultipleTreatments.selector()) | ||
401 | + .matchInPort(d2p0.port()) | ||
402 | + .matchVlanId(ingressVlan) | ||
403 | + .build() | ||
404 | + )); | ||
405 | + assertThat(rule2.treatment(), is( | ||
406 | + DefaultTrafficTreatment | ||
407 | + .builder(intentMultipleTreatments.treatment()) | ||
408 | + .setVlanId(egressVlan1) | ||
409 | + .setOutput(d2p1.port()) | ||
410 | + .setVlanId(egressVlan2) | ||
411 | + .setOutput(d2p2.port()) | ||
412 | + .build() | ||
413 | + )); | ||
414 | + assertThat(rule2.priority(), is(intentMultipleTreatments.priority())); | ||
415 | + | ||
416 | + } | ||
417 | + | ||
418 | + @Test | ||
419 | + public void testCompileMultipleTreatments2() { | ||
420 | + sut.activate(); | ||
421 | + | ||
422 | + List<Intent> compiled = sut.compile(intentMultipleTreatments2, Collections.emptyList()); | ||
423 | + assertThat(compiled, hasSize(1)); | ||
424 | + | ||
425 | + | ||
426 | + Collection<FlowRule> rules = ((FlowRuleIntent) compiled.get(0)).flowRules(); | ||
427 | + assertThat(rules, hasSize((linksMultiple2.size() + intentMultipleTreatments2.egressPoints().size()))); | ||
428 | + | ||
429 | + | ||
430 | + Set<FlowRule> d2Rules = rules | ||
431 | + .parallelStream() | ||
432 | + .filter(rule -> rule.deviceId().equals(d2p0.deviceId())) | ||
433 | + .collect(Collectors.toSet()); | ||
434 | + assertThat(d2Rules, hasSize(1)); | ||
435 | + | ||
436 | + | ||
437 | + FlowRule rule1 = rules.stream() | ||
438 | + .filter(rule -> rule.deviceId().equals(d2p0.deviceId())) | ||
439 | + .findFirst() | ||
440 | + .get(); | ||
441 | + assertThat(rule1.selector(), is( | ||
442 | + DefaultTrafficSelector | ||
443 | + .builder(intentMultipleTreatments.selector()) | ||
444 | + .matchInPort(d2p3.port()) | ||
445 | + .matchVlanId(ingressVlan) | ||
446 | + .build() | ||
447 | + )); | ||
448 | + assertThat(rule1.treatment(), is( | ||
449 | + DefaultTrafficTreatment | ||
450 | + .builder(intentMultipleTreatments.treatment()) | ||
451 | + .setOutput(d2p0.port()) | ||
452 | + .setOutput(d2p1.port()) | ||
453 | + .setOutput(d2p2.port()) | ||
454 | + .build() | ||
455 | + )); | ||
456 | + assertThat(rule1.priority(), is(intentMultipleTreatments.priority())); | ||
457 | + | ||
458 | + Set<FlowRule> d1Rules = rules | ||
459 | + .parallelStream() | ||
460 | + .filter(rule -> rule.deviceId().equals(d1p0.deviceId())) | ||
461 | + .collect(Collectors.toSet()); | ||
462 | + assertThat(d1Rules, hasSize(1)); | ||
463 | + | ||
464 | + FlowRule rule2 = rules.stream() | ||
465 | + .filter(rule -> rule.deviceId().equals(d1p0.deviceId())) | ||
466 | + .findFirst() | ||
467 | + .get(); | ||
468 | + assertThat(rule2.selector(), is( | ||
469 | + DefaultTrafficSelector | ||
470 | + .builder(intentMultipleTreatments2.selector()) | ||
471 | + .matchInPort(d1p1.port()) | ||
472 | + .matchVlanId(ingressVlan) | ||
473 | + .build() | ||
474 | + )); | ||
475 | + assertThat(rule2.treatment(), is( | ||
476 | + DefaultTrafficTreatment | ||
477 | + .builder(intentMultipleTreatments2.treatment()) | ||
478 | + .setVlanId(egressVlan1) | ||
479 | + .setOutput(d1p0.port()) | ||
480 | + .build() | ||
481 | + )); | ||
482 | + assertThat(rule2.priority(), is(intentMultipleTreatments.priority())); | ||
483 | + | ||
484 | + Set<FlowRule> d3Rules = rules | ||
485 | + .parallelStream() | ||
486 | + .filter(rule -> rule.deviceId().equals(d3p0.deviceId())) | ||
487 | + .collect(Collectors.toSet()); | ||
488 | + assertThat(d3Rules, hasSize(1)); | ||
489 | + | ||
490 | + FlowRule rule3 = rules.stream() | ||
491 | + .filter(rule -> rule.deviceId().equals(d3p0.deviceId())) | ||
492 | + .findFirst() | ||
493 | + .get(); | ||
494 | + assertThat(rule3.selector(), is( | ||
495 | + DefaultTrafficSelector | ||
496 | + .builder(intentMultipleTreatments2.selector()) | ||
497 | + .matchInPort(d3p1.port()) | ||
498 | + .matchVlanId(ingressVlan) | ||
499 | + .build() | ||
500 | + )); | ||
501 | + assertThat(rule3.treatment(), is( | ||
502 | + DefaultTrafficTreatment | ||
503 | + .builder(intentMultipleTreatments2.treatment()) | ||
504 | + .setVlanId(egressVlan2) | ||
505 | + .setOutput(d3p0.port()) | ||
506 | + .build() | ||
507 | + )); | ||
508 | + assertThat(rule3.priority(), is(intentMultipleTreatments.priority())); | ||
509 | + | ||
510 | + Set<FlowRule> d4Rules = rules | ||
511 | + .parallelStream() | ||
512 | + .filter(rule -> rule.deviceId().equals(d4p0.deviceId())) | ||
513 | + .collect(Collectors.toSet()); | ||
514 | + assertThat(d4Rules, hasSize(1)); | ||
515 | + | ||
516 | + FlowRule rule4 = rules.stream() | ||
517 | + .filter(rule -> rule.deviceId().equals(d4p0.deviceId())) | ||
518 | + .findFirst() | ||
519 | + .get(); | ||
520 | + assertThat(rule4.selector(), is( | ||
521 | + DefaultTrafficSelector | ||
522 | + .builder(intentMultipleTreatments2.selector()) | ||
523 | + .matchInPort(d4p1.port()) | ||
524 | + .matchVlanId(ingressVlan) | ||
525 | + .build() | ||
526 | + )); | ||
527 | + assertThat(rule4.treatment(), is( | ||
528 | + DefaultTrafficTreatment | ||
529 | + .builder(intentMultipleTreatments2.treatment()) | ||
530 | + .setVlanId(egressVlan3) | ||
531 | + .setOutput(d4p0.port()) | ||
532 | + .build() | ||
533 | + )); | ||
534 | + assertThat(rule4.priority(), is(intentMultipleTreatments.priority())); | ||
535 | + | ||
536 | + } | ||
537 | + | ||
538 | + public Map<ConnectPoint, TrafficTreatment> createEgressTreatments() { | ||
539 | + Map<ConnectPoint, TrafficTreatment> mapToReturn = Maps.newHashMap(); | ||
540 | + mapToReturn.put(d2p1, vlanTreatment1); | ||
541 | + mapToReturn.put(d2p2, vlanTreatment2); | ||
542 | + return mapToReturn; | ||
543 | + } | ||
544 | + | ||
545 | + public Map<ConnectPoint, TrafficTreatment> createEgressTreatments2() { | ||
546 | + Map<ConnectPoint, TrafficTreatment> mapToReturn = Maps.newHashMap(); | ||
547 | + mapToReturn.put(d1p0, vlanTreatment1); | ||
548 | + mapToReturn.put(d3p0, vlanTreatment2); | ||
549 | + mapToReturn.put(d4p0, vlanTreatment3); | ||
550 | + return mapToReturn; | ||
551 | + } | ||
552 | + | ||
299 | public Map<ConnectPoint, TrafficSelector> createIngressSelectors() { | 553 | public Map<ConnectPoint, TrafficSelector> createIngressSelectors() { |
300 | Map<ConnectPoint, TrafficSelector> mapToReturn = Maps.newHashMap(); | 554 | Map<ConnectPoint, TrafficSelector> mapToReturn = Maps.newHashMap(); |
301 | mapToReturn.put(d3p0, selectorVlan1); | 555 | mapToReturn.put(d3p0, selectorVlan1); |
302 | mapToReturn.put(d3p2, selectorVlan2); | 556 | mapToReturn.put(d3p2, selectorVlan2); |
303 | return mapToReturn; | 557 | return mapToReturn; |
304 | } | 558 | } |
559 | + | ||
305 | } | 560 | } | ... | ... |
-
Please register or login to post a comment