Merge branch 'master' of ssh://gerrit.onlab.us:29418/onos-next
Showing
55 changed files
with
1823 additions
and
609 deletions
... | @@ -23,6 +23,10 @@ import org.apache.felix.scr.annotations.ReferenceCardinality; | ... | @@ -23,6 +23,10 @@ import org.apache.felix.scr.annotations.ReferenceCardinality; |
23 | import org.onlab.onos.cluster.ClusterEvent; | 23 | import org.onlab.onos.cluster.ClusterEvent; |
24 | import org.onlab.onos.cluster.ClusterEventListener; | 24 | import org.onlab.onos.cluster.ClusterEventListener; |
25 | import org.onlab.onos.cluster.ClusterService; | 25 | import org.onlab.onos.cluster.ClusterService; |
26 | +import org.onlab.onos.cluster.NodeId; | ||
27 | +import org.onlab.onos.mastership.MastershipEvent; | ||
28 | +import org.onlab.onos.mastership.MastershipListener; | ||
29 | +import org.onlab.onos.mastership.MastershipService; | ||
26 | import org.onlab.onos.net.device.DeviceEvent; | 30 | import org.onlab.onos.net.device.DeviceEvent; |
27 | import org.onlab.onos.net.device.DeviceListener; | 31 | import org.onlab.onos.net.device.DeviceListener; |
28 | import org.onlab.onos.net.device.DeviceService; | 32 | import org.onlab.onos.net.device.DeviceService; |
... | @@ -50,15 +54,20 @@ public class FooComponent { | ... | @@ -50,15 +54,20 @@ public class FooComponent { |
50 | @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | 54 | @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) |
51 | protected IntentService intentService; | 55 | protected IntentService intentService; |
52 | 56 | ||
57 | + @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
58 | + protected MastershipService mastershipService; | ||
59 | + | ||
53 | private final ClusterEventListener clusterListener = new InnerClusterListener(); | 60 | private final ClusterEventListener clusterListener = new InnerClusterListener(); |
54 | private final DeviceListener deviceListener = new InnerDeviceListener(); | 61 | private final DeviceListener deviceListener = new InnerDeviceListener(); |
55 | private final IntentListener intentListener = new InnerIntentListener(); | 62 | private final IntentListener intentListener = new InnerIntentListener(); |
63 | + private final MastershipListener mastershipListener = new InnerMastershipListener(); | ||
56 | 64 | ||
57 | @Activate | 65 | @Activate |
58 | public void activate() { | 66 | public void activate() { |
59 | clusterService.addListener(clusterListener); | 67 | clusterService.addListener(clusterListener); |
60 | deviceService.addListener(deviceListener); | 68 | deviceService.addListener(deviceListener); |
61 | intentService.addListener(intentListener); | 69 | intentService.addListener(intentListener); |
70 | + mastershipService.addListener(mastershipListener); | ||
62 | log.info("Started"); | 71 | log.info("Started"); |
63 | } | 72 | } |
64 | 73 | ||
... | @@ -67,6 +76,7 @@ public class FooComponent { | ... | @@ -67,6 +76,7 @@ public class FooComponent { |
67 | clusterService.removeListener(clusterListener); | 76 | clusterService.removeListener(clusterListener); |
68 | deviceService.removeListener(deviceListener); | 77 | deviceService.removeListener(deviceListener); |
69 | intentService.removeListener(intentListener); | 78 | intentService.removeListener(intentListener); |
79 | + mastershipService.removeListener(mastershipListener); | ||
70 | log.info("Stopped"); | 80 | log.info("Stopped"); |
71 | } | 81 | } |
72 | 82 | ||
... | @@ -100,6 +110,18 @@ public class FooComponent { | ... | @@ -100,6 +110,18 @@ public class FooComponent { |
100 | log.info(message, event.subject()); | 110 | log.info(message, event.subject()); |
101 | } | 111 | } |
102 | } | 112 | } |
113 | + | ||
114 | + private class InnerMastershipListener implements MastershipListener { | ||
115 | + @Override | ||
116 | + public void event(MastershipEvent event) { | ||
117 | + final NodeId myId = clusterService.getLocalNode().id(); | ||
118 | + if (myId.equals(event.roleInfo().master())) { | ||
119 | + log.info("I have control/I wish you luck {}", event); | ||
120 | + } else { | ||
121 | + log.info("you have control {}", event); | ||
122 | + } | ||
123 | + } | ||
124 | + } | ||
103 | } | 125 | } |
104 | 126 | ||
105 | 127 | ... | ... |
... | @@ -15,14 +15,16 @@ | ... | @@ -15,14 +15,16 @@ |
15 | */ | 15 | */ |
16 | package org.onlab.onos.cli.net; | 16 | package org.onlab.onos.cli.net; |
17 | 17 | ||
18 | +import java.util.List; | ||
19 | + | ||
18 | import org.apache.karaf.shell.commands.Argument; | 20 | import org.apache.karaf.shell.commands.Argument; |
19 | import org.apache.karaf.shell.commands.Command; | 21 | import org.apache.karaf.shell.commands.Command; |
20 | -import org.onlab.onos.cli.AbstractShellCommand; | ||
21 | import org.onlab.onos.net.HostId; | 22 | import org.onlab.onos.net.HostId; |
22 | import org.onlab.onos.net.flow.DefaultTrafficSelector; | 23 | import org.onlab.onos.net.flow.DefaultTrafficSelector; |
23 | import org.onlab.onos.net.flow.DefaultTrafficTreatment; | 24 | import org.onlab.onos.net.flow.DefaultTrafficTreatment; |
24 | import org.onlab.onos.net.flow.TrafficSelector; | 25 | import org.onlab.onos.net.flow.TrafficSelector; |
25 | import org.onlab.onos.net.flow.TrafficTreatment; | 26 | import org.onlab.onos.net.flow.TrafficTreatment; |
27 | +import org.onlab.onos.net.intent.Constraint; | ||
26 | import org.onlab.onos.net.intent.HostToHostIntent; | 28 | import org.onlab.onos.net.intent.HostToHostIntent; |
27 | import org.onlab.onos.net.intent.IntentService; | 29 | import org.onlab.onos.net.intent.IntentService; |
28 | 30 | ||
... | @@ -31,7 +33,7 @@ import org.onlab.onos.net.intent.IntentService; | ... | @@ -31,7 +33,7 @@ import org.onlab.onos.net.intent.IntentService; |
31 | */ | 33 | */ |
32 | @Command(scope = "onos", name = "add-host-intent", | 34 | @Command(scope = "onos", name = "add-host-intent", |
33 | description = "Installs host-to-host connectivity intent") | 35 | description = "Installs host-to-host connectivity intent") |
34 | -public class AddHostToHostIntentCommand extends AbstractShellCommand { | 36 | +public class AddHostToHostIntentCommand extends ConnectivityIntentCommand { |
35 | 37 | ||
36 | @Argument(index = 0, name = "one", description = "One host ID", | 38 | @Argument(index = 0, name = "one", description = "One host ID", |
37 | required = true, multiValued = false) | 39 | required = true, multiValued = false) |
... | @@ -50,9 +52,11 @@ public class AddHostToHostIntentCommand extends AbstractShellCommand { | ... | @@ -50,9 +52,11 @@ public class AddHostToHostIntentCommand extends AbstractShellCommand { |
50 | 52 | ||
51 | TrafficSelector selector = DefaultTrafficSelector.builder().build(); | 53 | TrafficSelector selector = DefaultTrafficSelector.builder().build(); |
52 | TrafficTreatment treatment = DefaultTrafficTreatment.builder().build(); | 54 | TrafficTreatment treatment = DefaultTrafficTreatment.builder().build(); |
55 | + List<Constraint> constraints = buildConstraints(); | ||
53 | 56 | ||
54 | HostToHostIntent intent = new HostToHostIntent(appId(), oneId, twoId, | 57 | HostToHostIntent intent = new HostToHostIntent(appId(), oneId, twoId, |
55 | - selector, treatment); | 58 | + selector, treatment, |
59 | + constraints); | ||
56 | service.submit(intent); | 60 | service.submit(intent); |
57 | } | 61 | } |
58 | 62 | ... | ... |
... | @@ -23,11 +23,13 @@ import org.onlab.onos.net.PortNumber; | ... | @@ -23,11 +23,13 @@ import org.onlab.onos.net.PortNumber; |
23 | import org.onlab.onos.net.flow.DefaultTrafficTreatment; | 23 | import org.onlab.onos.net.flow.DefaultTrafficTreatment; |
24 | import org.onlab.onos.net.flow.TrafficSelector; | 24 | import org.onlab.onos.net.flow.TrafficSelector; |
25 | import org.onlab.onos.net.flow.TrafficTreatment; | 25 | import org.onlab.onos.net.flow.TrafficTreatment; |
26 | +import org.onlab.onos.net.intent.Constraint; | ||
26 | import org.onlab.onos.net.intent.Intent; | 27 | import org.onlab.onos.net.intent.Intent; |
27 | import org.onlab.onos.net.intent.IntentService; | 28 | import org.onlab.onos.net.intent.IntentService; |
28 | import org.onlab.onos.net.intent.MultiPointToSinglePointIntent; | 29 | import org.onlab.onos.net.intent.MultiPointToSinglePointIntent; |
29 | 30 | ||
30 | import java.util.HashSet; | 31 | import java.util.HashSet; |
32 | +import java.util.List; | ||
31 | import java.util.Set; | 33 | import java.util.Set; |
32 | 34 | ||
33 | import static org.onlab.onos.net.DeviceId.deviceId; | 35 | import static org.onlab.onos.net.DeviceId.deviceId; |
... | @@ -69,9 +71,11 @@ public class AddMultiPointToSinglePointIntentCommand extends ConnectivityIntentC | ... | @@ -69,9 +71,11 @@ public class AddMultiPointToSinglePointIntentCommand extends ConnectivityIntentC |
69 | 71 | ||
70 | TrafficSelector selector = buildTrafficSelector(); | 72 | TrafficSelector selector = buildTrafficSelector(); |
71 | TrafficTreatment treatment = DefaultTrafficTreatment.builder().build(); | 73 | TrafficTreatment treatment = DefaultTrafficTreatment.builder().build(); |
74 | + List<Constraint> constraints = buildConstraints(); | ||
72 | 75 | ||
73 | Intent intent = new MultiPointToSinglePointIntent(appId(), selector, treatment, | 76 | Intent intent = new MultiPointToSinglePointIntent(appId(), selector, treatment, |
74 | - ingressPoints, egress); | 77 | + ingressPoints, egress, |
78 | + constraints); | ||
75 | service.submit(intent); | 79 | service.submit(intent); |
76 | } | 80 | } |
77 | 81 | ... | ... |
... | @@ -15,6 +15,8 @@ | ... | @@ -15,6 +15,8 @@ |
15 | */ | 15 | */ |
16 | package org.onlab.onos.cli.net; | 16 | package org.onlab.onos.cli.net; |
17 | 17 | ||
18 | +import java.util.List; | ||
19 | + | ||
18 | import org.apache.karaf.shell.commands.Argument; | 20 | import org.apache.karaf.shell.commands.Argument; |
19 | import org.apache.karaf.shell.commands.Command; | 21 | import org.apache.karaf.shell.commands.Command; |
20 | import org.onlab.onos.net.ConnectPoint; | 22 | import org.onlab.onos.net.ConnectPoint; |
... | @@ -22,6 +24,7 @@ import org.onlab.onos.net.DeviceId; | ... | @@ -22,6 +24,7 @@ import org.onlab.onos.net.DeviceId; |
22 | import org.onlab.onos.net.PortNumber; | 24 | import org.onlab.onos.net.PortNumber; |
23 | import org.onlab.onos.net.flow.TrafficSelector; | 25 | import org.onlab.onos.net.flow.TrafficSelector; |
24 | import org.onlab.onos.net.flow.TrafficTreatment; | 26 | import org.onlab.onos.net.flow.TrafficTreatment; |
27 | +import org.onlab.onos.net.intent.Constraint; | ||
25 | import org.onlab.onos.net.intent.Intent; | 28 | import org.onlab.onos.net.intent.Intent; |
26 | import org.onlab.onos.net.intent.IntentService; | 29 | import org.onlab.onos.net.intent.IntentService; |
27 | import org.onlab.onos.net.intent.PointToPointIntent; | 30 | import org.onlab.onos.net.intent.PointToPointIntent; |
... | @@ -63,8 +66,10 @@ public class AddPointToPointIntentCommand extends ConnectivityIntentCommand { | ... | @@ -63,8 +66,10 @@ public class AddPointToPointIntentCommand extends ConnectivityIntentCommand { |
63 | TrafficSelector selector = buildTrafficSelector(); | 66 | TrafficSelector selector = buildTrafficSelector(); |
64 | TrafficTreatment treatment = builder().build(); | 67 | TrafficTreatment treatment = builder().build(); |
65 | 68 | ||
69 | + List<Constraint> constraints = buildConstraints(); | ||
70 | + | ||
66 | Intent intent = new PointToPointIntent(appId(), selector, treatment, | 71 | Intent intent = new PointToPointIntent(appId(), selector, treatment, |
67 | - ingress, egress); | 72 | + ingress, egress, constraints); |
68 | service.submit(intent); | 73 | service.submit(intent); |
69 | } | 74 | } |
70 | 75 | ... | ... |
1 | -/* | ||
2 | - * Licensed to the Apache Software Foundation (ASF) under one | ||
3 | - * or more contributor license agreements. See the NOTICE file | ||
4 | - * distributed with this work for additional information | ||
5 | - * regarding copyright ownership. The ASF licenses this file | ||
6 | - * to you under the Apache License, Version 2.0 (the | ||
7 | - * "License"); you may not use this file except in compliance | ||
8 | - * with the License. You may obtain a copy of the License at | ||
9 | - * | ||
10 | - * http://www.apache.org/licenses/LICENSE-2.0 | ||
11 | - * | ||
12 | - * Unless required by applicable law or agreed to in writing, | ||
13 | - * software distributed under the License is distributed on an | ||
14 | - * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY | ||
15 | - * KIND, either express or implied. See the License for the | ||
16 | - * specific language governing permissions and limitations | ||
17 | - * under the License. | ||
18 | - */ | ||
19 | -package org.onlab.onos.cli.net; | ||
20 | - | ||
21 | -import org.apache.karaf.shell.commands.Argument; | ||
22 | -import org.apache.karaf.shell.commands.Command; | ||
23 | -import org.onlab.onos.net.ConnectPoint; | ||
24 | -import org.onlab.onos.net.DeviceId; | ||
25 | -import org.onlab.onos.net.PortNumber; | ||
26 | -import org.onlab.onos.net.flow.TrafficSelector; | ||
27 | -import org.onlab.onos.net.flow.TrafficTreatment; | ||
28 | -import org.onlab.onos.net.intent.Intent; | ||
29 | -import org.onlab.onos.net.intent.IntentService; | ||
30 | -import org.onlab.onos.net.intent.PointToPointIntent; | ||
31 | - | ||
32 | -import static org.onlab.onos.net.DeviceId.deviceId; | ||
33 | -import static org.onlab.onos.net.PortNumber.portNumber; | ||
34 | -import static org.onlab.onos.net.flow.DefaultTrafficTreatment.builder; | ||
35 | - | ||
36 | -/** | ||
37 | - * Installs point-to-point connectivity intents. | ||
38 | - */ | ||
39 | -@Command(scope = "onos", name = "add-point-intent-bw", | ||
40 | - description = "Installs point-to-point connectivity intent with bandwidth constraint") | ||
41 | -public class AddPointToPointIntentWithBandwidthConstraintCommand extends ConnectivityIntentCommand { | ||
42 | - | ||
43 | - @Argument(index = 0, name = "ingressDevice", | ||
44 | - description = "Ingress Device/Port Description", | ||
45 | - required = true, multiValued = false) | ||
46 | - String ingressDeviceString = null; | ||
47 | - | ||
48 | - @Argument(index = 1, name = "egressDevice", | ||
49 | - description = "Egress Device/Port Description", | ||
50 | - required = true, multiValued = false) | ||
51 | - String egressDeviceString = null; | ||
52 | - | ||
53 | - @Argument(index = 2, name = "bandwidth", | ||
54 | - description = "Bandwidth", | ||
55 | - required = true, multiValued = false) | ||
56 | - String bandwidthString = null; | ||
57 | - | ||
58 | - @Override | ||
59 | - protected void execute() { | ||
60 | - IntentService service = get(IntentService.class); | ||
61 | - | ||
62 | - DeviceId ingressDeviceId = deviceId(getDeviceId(ingressDeviceString)); | ||
63 | - PortNumber ingressPortNumber = portNumber(getPortNumber(ingressDeviceString)); | ||
64 | - ConnectPoint ingress = new ConnectPoint(ingressDeviceId, ingressPortNumber); | ||
65 | - | ||
66 | - DeviceId egressDeviceId = deviceId(getDeviceId(egressDeviceString)); | ||
67 | - PortNumber egressPortNumber = portNumber(getPortNumber(egressDeviceString)); | ||
68 | - ConnectPoint egress = new ConnectPoint(egressDeviceId, egressPortNumber); | ||
69 | - | ||
70 | - long bandwidth = Long.parseLong(bandwidthString); | ||
71 | - | ||
72 | - TrafficSelector selector = buildTrafficSelector(); | ||
73 | - TrafficTreatment treatment = builder().build(); | ||
74 | - | ||
75 | - // FIXME: add bandwitdh constraint | ||
76 | - Intent intent = new PointToPointIntent( | ||
77 | - appId(), selector, treatment, | ||
78 | - ingress, egress); | ||
79 | - service.submit(intent); | ||
80 | - } | ||
81 | - | ||
82 | - /** | ||
83 | - * Extracts the port number portion of the ConnectPoint. | ||
84 | - * | ||
85 | - * @param deviceString string representing the device/port | ||
86 | - * @return port number as a string, empty string if the port is not found | ||
87 | - */ | ||
88 | - private String getPortNumber(String deviceString) { | ||
89 | - int slash = deviceString.indexOf('/'); | ||
90 | - if (slash <= 0) { | ||
91 | - return ""; | ||
92 | - } | ||
93 | - return deviceString.substring(slash + 1, deviceString.length()); | ||
94 | - } | ||
95 | - | ||
96 | - /** | ||
97 | - * Extracts the device ID portion of the ConnectPoint. | ||
98 | - * | ||
99 | - * @param deviceString string representing the device/port | ||
100 | - * @return device ID string | ||
101 | - */ | ||
102 | - private String getDeviceId(String deviceString) { | ||
103 | - int slash = deviceString.indexOf('/'); | ||
104 | - if (slash <= 0) { | ||
105 | - return ""; | ||
106 | - } | ||
107 | - return deviceString.substring(0, slash); | ||
108 | - } | ||
109 | -} |
... | @@ -15,14 +15,21 @@ | ... | @@ -15,14 +15,21 @@ |
15 | */ | 15 | */ |
16 | package org.onlab.onos.cli.net; | 16 | package org.onlab.onos.cli.net; |
17 | 17 | ||
18 | +import java.util.LinkedList; | ||
19 | +import java.util.List; | ||
20 | + | ||
18 | import org.apache.karaf.shell.commands.Option; | 21 | import org.apache.karaf.shell.commands.Option; |
19 | import org.onlab.onos.cli.AbstractShellCommand; | 22 | import org.onlab.onos.cli.AbstractShellCommand; |
20 | import org.onlab.onos.net.flow.DefaultTrafficSelector; | 23 | import org.onlab.onos.net.flow.DefaultTrafficSelector; |
21 | import org.onlab.onos.net.flow.TrafficSelector; | 24 | import org.onlab.onos.net.flow.TrafficSelector; |
25 | +import org.onlab.onos.net.intent.Constraint; | ||
26 | +import org.onlab.onos.net.intent.constraint.BandwidthConstraint; | ||
27 | +import org.onlab.onos.net.intent.constraint.LambdaConstraint; | ||
28 | +import org.onlab.onos.net.resource.Bandwidth; | ||
22 | import org.onlab.packet.Ethernet; | 29 | import org.onlab.packet.Ethernet; |
23 | import org.onlab.packet.MacAddress; | 30 | import org.onlab.packet.MacAddress; |
24 | 31 | ||
25 | -import com.google.common.base.Strings; | 32 | +import static com.google.common.base.Strings.isNullOrEmpty; |
26 | 33 | ||
27 | /** | 34 | /** |
28 | * Base class for command line operations for connectivity based intents. | 35 | * Base class for command line operations for connectivity based intents. |
... | @@ -41,6 +48,14 @@ public abstract class ConnectivityIntentCommand extends AbstractShellCommand { | ... | @@ -41,6 +48,14 @@ public abstract class ConnectivityIntentCommand extends AbstractShellCommand { |
41 | required = false, multiValued = false) | 48 | required = false, multiValued = false) |
42 | private String ethTypeString = ""; | 49 | private String ethTypeString = ""; |
43 | 50 | ||
51 | + @Option(name = "-b", aliases = "--bandwidth", description = "Bandwidth", | ||
52 | + required = false, multiValued = false) | ||
53 | + private String bandwidthString = ""; | ||
54 | + | ||
55 | + @Option(name = "-l", aliases = "--lambda", description = "Lambda", | ||
56 | + required = false, multiValued = false) | ||
57 | + private boolean lambda = false; | ||
58 | + | ||
44 | /** | 59 | /** |
45 | * Constructs a traffic selector based on the command line arguments | 60 | * Constructs a traffic selector based on the command line arguments |
46 | * presented to the command. | 61 | * presented to the command. |
... | @@ -50,21 +65,43 @@ public abstract class ConnectivityIntentCommand extends AbstractShellCommand { | ... | @@ -50,21 +65,43 @@ public abstract class ConnectivityIntentCommand extends AbstractShellCommand { |
50 | TrafficSelector.Builder selectorBuilder = DefaultTrafficSelector.builder(); | 65 | TrafficSelector.Builder selectorBuilder = DefaultTrafficSelector.builder(); |
51 | Short ethType = Ethernet.TYPE_IPV4; | 66 | Short ethType = Ethernet.TYPE_IPV4; |
52 | 67 | ||
53 | - if (!Strings.isNullOrEmpty(ethTypeString)) { | 68 | + if (!isNullOrEmpty(ethTypeString)) { |
54 | EthType ethTypeParameter = EthType.valueOf(ethTypeString); | 69 | EthType ethTypeParameter = EthType.valueOf(ethTypeString); |
55 | ethType = ethTypeParameter.value(); | 70 | ethType = ethTypeParameter.value(); |
56 | } | 71 | } |
57 | selectorBuilder.matchEthType(ethType); | 72 | selectorBuilder.matchEthType(ethType); |
58 | 73 | ||
59 | - if (!Strings.isNullOrEmpty(srcMacString)) { | 74 | + if (!isNullOrEmpty(srcMacString)) { |
60 | selectorBuilder.matchEthSrc(MacAddress.valueOf(srcMacString)); | 75 | selectorBuilder.matchEthSrc(MacAddress.valueOf(srcMacString)); |
61 | } | 76 | } |
62 | 77 | ||
63 | - if (!Strings.isNullOrEmpty(dstMacString)) { | 78 | + if (!isNullOrEmpty(dstMacString)) { |
64 | selectorBuilder.matchEthDst(MacAddress.valueOf(dstMacString)); | 79 | selectorBuilder.matchEthDst(MacAddress.valueOf(dstMacString)); |
65 | } | 80 | } |
66 | 81 | ||
67 | return selectorBuilder.build(); | 82 | return selectorBuilder.build(); |
68 | } | 83 | } |
69 | 84 | ||
85 | + /** | ||
86 | + * Builds the constraint list for this command based on the command line | ||
87 | + * parameters. | ||
88 | + * | ||
89 | + * @return List of constraint objects describing the constraints requested | ||
90 | + */ | ||
91 | + protected List<Constraint> buildConstraints() { | ||
92 | + final List<Constraint> constraints = new LinkedList<>(); | ||
93 | + | ||
94 | + // Check for a bandwidth specification | ||
95 | + if (!isNullOrEmpty(bandwidthString)) { | ||
96 | + final double bandwidthValue = Double.parseDouble(bandwidthString); | ||
97 | + constraints.add(new BandwidthConstraint(Bandwidth.valueOf(bandwidthValue))); | ||
98 | + } | ||
99 | + | ||
100 | + // Check for a lambda specification | ||
101 | + if (lambda) { | ||
102 | + constraints.add(new LambdaConstraint(null)); | ||
103 | + } | ||
104 | + | ||
105 | + return constraints; | ||
106 | + } | ||
70 | } | 107 | } | ... | ... |
... | @@ -25,6 +25,7 @@ import org.apache.karaf.shell.commands.Option; | ... | @@ -25,6 +25,7 @@ import org.apache.karaf.shell.commands.Option; |
25 | import org.onlab.onos.cli.Comparators; | 25 | import org.onlab.onos.cli.Comparators; |
26 | import org.onlab.onos.net.Device; | 26 | import org.onlab.onos.net.Device; |
27 | import org.onlab.onos.net.Port; | 27 | import org.onlab.onos.net.Port; |
28 | +import org.onlab.onos.net.PortNumber; | ||
28 | import org.onlab.onos.net.device.DeviceService; | 29 | import org.onlab.onos.net.device.DeviceService; |
29 | 30 | ||
30 | import java.util.ArrayList; | 31 | import java.util.ArrayList; |
... | @@ -108,7 +109,7 @@ public class DevicePortsListCommand extends DevicesListCommand { | ... | @@ -108,7 +109,7 @@ public class DevicePortsListCommand extends DevicesListCommand { |
108 | for (Port port : service.getPorts(device.id())) { | 109 | for (Port port : service.getPorts(device.id())) { |
109 | if (isIncluded(port)) { | 110 | if (isIncluded(port)) { |
110 | ports.add(mapper.createObjectNode() | 111 | ports.add(mapper.createObjectNode() |
111 | - .put("port", port.number().toString()) | 112 | + .put("port", portName(port.number())) |
112 | .put("isEnabled", port.isEnabled()) | 113 | .put("isEnabled", port.isEnabled()) |
113 | .put("type", port.type().toString().toLowerCase()) | 114 | .put("type", port.type().toString().toLowerCase()) |
114 | .put("portSpeed", port.portSpeed()) | 115 | .put("portSpeed", port.portSpeed()) |
... | @@ -120,6 +121,10 @@ public class DevicePortsListCommand extends DevicesListCommand { | ... | @@ -120,6 +121,10 @@ public class DevicePortsListCommand extends DevicesListCommand { |
120 | return result; | 121 | return result; |
121 | } | 122 | } |
122 | 123 | ||
124 | + private String portName(PortNumber port) { | ||
125 | + return port.equals(PortNumber.LOCAL) ? "local" : port.toString(); | ||
126 | + } | ||
127 | + | ||
123 | // Determines if a port should be included in output. | 128 | // Determines if a port should be included in output. |
124 | private boolean isIncluded(Port port) { | 129 | private boolean isIncluded(Port port) { |
125 | return enabled && port.isEnabled() || disabled && !port.isEnabled() || | 130 | return enabled && port.isEnabled() || disabled && !port.isEnabled() || |
... | @@ -133,7 +138,8 @@ public class DevicePortsListCommand extends DevicesListCommand { | ... | @@ -133,7 +138,8 @@ public class DevicePortsListCommand extends DevicesListCommand { |
133 | Collections.sort(ports, Comparators.PORT_COMPARATOR); | 138 | Collections.sort(ports, Comparators.PORT_COMPARATOR); |
134 | for (Port port : ports) { | 139 | for (Port port : ports) { |
135 | if (isIncluded(port)) { | 140 | if (isIncluded(port)) { |
136 | - print(FMT, port.number(), port.isEnabled() ? "enabled" : "disabled", | 141 | + print(FMT, portName(port.number()), |
142 | + port.isEnabled() ? "enabled" : "disabled", | ||
137 | port.type().toString().toLowerCase(), port.portSpeed(), | 143 | port.type().toString().toLowerCase(), port.portSpeed(), |
138 | annotations(port.annotations())); | 144 | annotations(port.annotations())); |
139 | } | 145 | } | ... | ... |
... | @@ -116,17 +116,6 @@ | ... | @@ -116,17 +116,6 @@ |
116 | </optional-completers> | 116 | </optional-completers> |
117 | </command> | 117 | </command> |
118 | <command> | 118 | <command> |
119 | - <action class="org.onlab.onos.cli.net.AddPointToPointIntentWithBandwidthConstraintCommand"/> | ||
120 | - <completers> | ||
121 | - <ref component-id="connectPointCompleter"/> | ||
122 | - <ref component-id="connectPointCompleter"/> | ||
123 | - <null/> | ||
124 | - </completers> | ||
125 | - <optional-completers> | ||
126 | - <entry key="-t" value-ref="ethTypeCompleter"/> | ||
127 | - </optional-completers> | ||
128 | - </command> | ||
129 | - <command> | ||
130 | <action class="org.onlab.onos.cli.net.AddOpticalIntentCommand"/> | 119 | <action class="org.onlab.onos.cli.net.AddOpticalIntentCommand"/> |
131 | <completers> | 120 | <completers> |
132 | <ref component-id="connectPointCompleter"/> | 121 | <ref component-id="connectPointCompleter"/> | ... | ... |
... | @@ -40,6 +40,10 @@ | ... | @@ -40,6 +40,10 @@ |
40 | <groupId>joda-time</groupId> | 40 | <groupId>joda-time</groupId> |
41 | <artifactId>joda-time</artifactId> | 41 | <artifactId>joda-time</artifactId> |
42 | </dependency> | 42 | </dependency> |
43 | + <dependency> | ||
44 | + <groupId>org.easymock</groupId> | ||
45 | + <artifactId>easymock</artifactId> | ||
46 | + </dependency> | ||
43 | </dependencies> | 47 | </dependencies> |
44 | 48 | ||
45 | </project> | 49 | </project> | ... | ... |
... | @@ -105,6 +105,7 @@ public final class HostToHostIntent extends ConnectivityIntent { | ... | @@ -105,6 +105,7 @@ public final class HostToHostIntent extends ConnectivityIntent { |
105 | .add("appId", appId()) | 105 | .add("appId", appId()) |
106 | .add("selector", selector()) | 106 | .add("selector", selector()) |
107 | .add("treatment", treatment()) | 107 | .add("treatment", treatment()) |
108 | + .add("constraints", constraints()) | ||
108 | .add("one", one) | 109 | .add("one", one) |
109 | .add("two", two) | 110 | .add("two", two) |
110 | .toString(); | 111 | .toString(); | ... | ... |
... | @@ -22,6 +22,7 @@ import org.onlab.onos.net.ConnectPoint; | ... | @@ -22,6 +22,7 @@ import org.onlab.onos.net.ConnectPoint; |
22 | import org.onlab.onos.net.flow.TrafficSelector; | 22 | import org.onlab.onos.net.flow.TrafficSelector; |
23 | import org.onlab.onos.net.flow.TrafficTreatment; | 23 | import org.onlab.onos.net.flow.TrafficTreatment; |
24 | 24 | ||
25 | +import java.util.List; | ||
25 | import java.util.Set; | 26 | import java.util.Set; |
26 | 27 | ||
27 | import static com.google.common.base.Preconditions.checkArgument; | 28 | import static com.google.common.base.Preconditions.checkArgument; |
... | @@ -65,6 +66,38 @@ public final class MultiPointToSinglePointIntent extends ConnectivityIntent { | ... | @@ -65,6 +66,38 @@ public final class MultiPointToSinglePointIntent extends ConnectivityIntent { |
65 | } | 66 | } |
66 | 67 | ||
67 | /** | 68 | /** |
69 | + * Creates a new multi-to-single point connectivity intent for the specified | ||
70 | + * traffic selector and treatment. | ||
71 | + * | ||
72 | + * @param appId application identifier | ||
73 | + * @param selector traffic selector | ||
74 | + * @param treatment treatment | ||
75 | + * @param ingressPoints set of ports from which ingress traffic originates | ||
76 | + * @param egressPoint port to which traffic will egress | ||
77 | + * @param constraints constraints to apply to the intent | ||
78 | + * @throws NullPointerException if {@code ingressPoints} or | ||
79 | + * {@code egressPoint} is null. | ||
80 | + * @throws IllegalArgumentException if the size of {@code ingressPoints} is | ||
81 | + * not more than 1 | ||
82 | + */ | ||
83 | + public MultiPointToSinglePointIntent(ApplicationId appId, | ||
84 | + TrafficSelector selector, | ||
85 | + TrafficTreatment treatment, | ||
86 | + Set<ConnectPoint> ingressPoints, | ||
87 | + ConnectPoint egressPoint, | ||
88 | + List<Constraint> constraints) { | ||
89 | + super(id(MultiPointToSinglePointIntent.class, selector, treatment, | ||
90 | + ingressPoints, egressPoint), appId, null, selector, treatment, | ||
91 | + constraints); | ||
92 | + | ||
93 | + checkNotNull(ingressPoints); | ||
94 | + checkArgument(!ingressPoints.isEmpty(), "Ingress point set cannot be empty"); | ||
95 | + | ||
96 | + this.ingressPoints = Sets.newHashSet(ingressPoints); | ||
97 | + this.egressPoint = checkNotNull(egressPoint); | ||
98 | + } | ||
99 | + | ||
100 | + /** | ||
68 | * Constructor for serializer. | 101 | * Constructor for serializer. |
69 | */ | 102 | */ |
70 | protected MultiPointToSinglePointIntent() { | 103 | protected MultiPointToSinglePointIntent() { |
... | @@ -101,6 +134,7 @@ public final class MultiPointToSinglePointIntent extends ConnectivityIntent { | ... | @@ -101,6 +134,7 @@ public final class MultiPointToSinglePointIntent extends ConnectivityIntent { |
101 | .add("treatment", treatment()) | 134 | .add("treatment", treatment()) |
102 | .add("ingress", ingressPoints()) | 135 | .add("ingress", ingressPoints()) |
103 | .add("egress", egressPoint()) | 136 | .add("egress", egressPoint()) |
137 | + .add("constraints", constraints()) | ||
104 | .toString(); | 138 | .toString(); |
105 | } | 139 | } |
106 | } | 140 | } | ... | ... |
... | @@ -15,6 +15,8 @@ | ... | @@ -15,6 +15,8 @@ |
15 | */ | 15 | */ |
16 | package org.onlab.onos.net.intent; | 16 | package org.onlab.onos.net.intent; |
17 | 17 | ||
18 | +import java.util.List; | ||
19 | + | ||
18 | import com.google.common.base.MoreObjects; | 20 | import com.google.common.base.MoreObjects; |
19 | import org.onlab.onos.core.ApplicationId; | 21 | import org.onlab.onos.core.ApplicationId; |
20 | import org.onlab.onos.net.Path; | 22 | import org.onlab.onos.net.Path; |
... | @@ -46,6 +48,24 @@ public class PathIntent extends ConnectivityIntent { | ... | @@ -46,6 +48,24 @@ public class PathIntent extends ConnectivityIntent { |
46 | } | 48 | } |
47 | 49 | ||
48 | /** | 50 | /** |
51 | + * Creates a new point-to-point intent with the supplied ingress/egress | ||
52 | + * ports and using the specified explicit path. | ||
53 | + * | ||
54 | + * @param appId application identifier | ||
55 | + * @param selector traffic selector | ||
56 | + * @param treatment treatment | ||
57 | + * @param path traversed links | ||
58 | + * @param constraints optional list of constraints | ||
59 | + * @throws NullPointerException {@code path} is null | ||
60 | + */ | ||
61 | + public PathIntent(ApplicationId appId, TrafficSelector selector, | ||
62 | + TrafficTreatment treatment, Path path, List<Constraint> constraints) { | ||
63 | + super(id(PathIntent.class, selector, treatment, path, constraints), appId, | ||
64 | + resources(path.links()), selector, treatment, constraints); | ||
65 | + this.path = path; | ||
66 | + } | ||
67 | + | ||
68 | + /** | ||
49 | * Constructor for serializer. | 69 | * Constructor for serializer. |
50 | */ | 70 | */ |
51 | protected PathIntent() { | 71 | protected PathIntent() { |
... | @@ -75,6 +95,7 @@ public class PathIntent extends ConnectivityIntent { | ... | @@ -75,6 +95,7 @@ public class PathIntent extends ConnectivityIntent { |
75 | .add("appId", appId()) | 95 | .add("appId", appId()) |
76 | .add("selector", selector()) | 96 | .add("selector", selector()) |
77 | .add("treatment", treatment()) | 97 | .add("treatment", treatment()) |
98 | + .add("constraints", constraints()) | ||
78 | .add("path", path) | 99 | .add("path", path) |
79 | .toString(); | 100 | .toString(); |
80 | } | 101 | } | ... | ... |
1 | +/* | ||
2 | + * Copyright 2014 Open Networking Laboratory | ||
3 | + * | ||
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
5 | + * you may not use this file except in compliance with the License. | ||
6 | + * You may obtain a copy of the License at | ||
7 | + * | ||
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
9 | + * | ||
10 | + * Unless required by applicable law or agreed to in writing, software | ||
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
13 | + * See the License for the specific language governing permissions and | ||
14 | + * limitations under the License. | ||
15 | + */ | ||
16 | +package org.onlab.onos.net.intent.constraint; | ||
17 | + | ||
18 | +import com.google.common.base.MoreObjects; | ||
19 | +import com.google.common.collect.ImmutableList; | ||
20 | +import org.onlab.onos.net.ElementId; | ||
21 | +import org.onlab.onos.net.Link; | ||
22 | +import org.onlab.onos.net.Path; | ||
23 | +import org.onlab.onos.net.intent.Constraint; | ||
24 | +import org.onlab.onos.net.resource.LinkResourceService; | ||
25 | + | ||
26 | +import java.util.LinkedList; | ||
27 | +import java.util.List; | ||
28 | +import java.util.Objects; | ||
29 | + | ||
30 | +import static com.google.common.base.Preconditions.checkArgument; | ||
31 | +import static com.google.common.base.Preconditions.checkNotNull; | ||
32 | + | ||
33 | +/** | ||
34 | + * Constraint that evaluates elements passed through in order. | ||
35 | + */ | ||
36 | +public class WaypointConstraint implements Constraint { | ||
37 | + | ||
38 | + private final List<ElementId> waypoints; | ||
39 | + | ||
40 | + /** | ||
41 | + * Creates a new waypoint constraint. | ||
42 | + * | ||
43 | + * @param waypoints waypoints | ||
44 | + */ | ||
45 | + public WaypointConstraint(ElementId... waypoints) { | ||
46 | + checkNotNull(waypoints, "waypoints cannot be null"); | ||
47 | + checkArgument(waypoints.length > 0, "length of waypoints should be more than 0"); | ||
48 | + this.waypoints = ImmutableList.copyOf(waypoints); | ||
49 | + } | ||
50 | + | ||
51 | + public List<ElementId> waypoints() { | ||
52 | + return waypoints; | ||
53 | + } | ||
54 | + | ||
55 | + @Override | ||
56 | + public double cost(Link link, LinkResourceService resourceService) { | ||
57 | + // Always consider the number of hops | ||
58 | + return 1; | ||
59 | + } | ||
60 | + | ||
61 | + @Override | ||
62 | + public boolean validate(Path path, LinkResourceService resourceService) { | ||
63 | + LinkedList<ElementId> waypoints = new LinkedList<>(this.waypoints); | ||
64 | + ElementId current = waypoints.poll(); | ||
65 | + // This is safe because Path class ensures the number of links are more than 0 | ||
66 | + Link firstLink = path.links().get(0); | ||
67 | + if (firstLink.src().elementId().equals(current)) { | ||
68 | + current = waypoints.poll(); | ||
69 | + } | ||
70 | + | ||
71 | + for (Link link : path.links()) { | ||
72 | + if (link.dst().elementId().equals(current)) { | ||
73 | + current = waypoints.poll(); | ||
74 | + // Empty waypoints means passing through all waypoints in the specified order | ||
75 | + if (current == null) { | ||
76 | + return true; | ||
77 | + } | ||
78 | + } | ||
79 | + } | ||
80 | + | ||
81 | + return false; | ||
82 | + } | ||
83 | + | ||
84 | + @Override | ||
85 | + public int hashCode() { | ||
86 | + return Objects.hash(waypoints); | ||
87 | + } | ||
88 | + | ||
89 | + @Override | ||
90 | + public boolean equals(Object obj) { | ||
91 | + if (this == obj) { | ||
92 | + return true; | ||
93 | + } | ||
94 | + | ||
95 | + if (!(obj instanceof WaypointConstraint)) { | ||
96 | + return false; | ||
97 | + } | ||
98 | + | ||
99 | + final WaypointConstraint that = (WaypointConstraint) obj; | ||
100 | + return Objects.equals(this.waypoints, that.waypoints); | ||
101 | + } | ||
102 | + | ||
103 | + @Override | ||
104 | + public String toString() { | ||
105 | + return MoreObjects.toStringHelper(this) | ||
106 | + .add("waypoints", waypoints) | ||
107 | + .toString(); | ||
108 | + } | ||
109 | +} |
1 | package org.onlab.onos.store.service; | 1 | package org.onlab.onos.store.service; |
2 | 2 | ||
3 | +import static com.google.common.base.Preconditions.checkNotNull; | ||
4 | + | ||
5 | +import java.util.Objects; | ||
6 | + | ||
3 | import com.google.common.base.MoreObjects; | 7 | import com.google.common.base.MoreObjects; |
4 | 8 | ||
5 | /** | 9 | /** |
... | @@ -10,9 +14,21 @@ public class ReadRequest { | ... | @@ -10,9 +14,21 @@ public class ReadRequest { |
10 | private final String tableName; | 14 | private final String tableName; |
11 | private final String key; | 15 | private final String key; |
12 | 16 | ||
17 | + /** | ||
18 | + * Creates a read request, | ||
19 | + * which will retrieve the specified key from the table. | ||
20 | + * | ||
21 | + * @param tableName name of the table | ||
22 | + * @param key key in the table | ||
23 | + * @return ReadRequest | ||
24 | + */ | ||
25 | + public static ReadRequest get(String tableName, String key) { | ||
26 | + return new ReadRequest(tableName, key); | ||
27 | + } | ||
28 | + | ||
13 | public ReadRequest(String tableName, String key) { | 29 | public ReadRequest(String tableName, String key) { |
14 | - this.tableName = tableName; | 30 | + this.tableName = checkNotNull(tableName); |
15 | - this.key = key; | 31 | + this.key = checkNotNull(key); |
16 | } | 32 | } |
17 | 33 | ||
18 | /** | 34 | /** |
... | @@ -38,4 +54,26 @@ public class ReadRequest { | ... | @@ -38,4 +54,26 @@ public class ReadRequest { |
38 | .add("key", key) | 54 | .add("key", key) |
39 | .toString(); | 55 | .toString(); |
40 | } | 56 | } |
57 | + | ||
58 | + @Override | ||
59 | + public int hashCode() { | ||
60 | + return Objects.hash(key, tableName); | ||
61 | + } | ||
62 | + | ||
63 | + @Override | ||
64 | + public boolean equals(Object obj) { | ||
65 | + if (this == obj) { | ||
66 | + return true; | ||
67 | + } | ||
68 | + if (obj == null) { | ||
69 | + return false; | ||
70 | + } | ||
71 | + if (getClass() != obj.getClass()) { | ||
72 | + return false; | ||
73 | + } | ||
74 | + ReadRequest other = (ReadRequest) obj; | ||
75 | + return Objects.equals(this.key, other.key) && | ||
76 | + Objects.equals(this.tableName, other.tableName); | ||
77 | + } | ||
78 | + | ||
41 | } | 79 | } |
... | \ No newline at end of file | ... | \ No newline at end of file | ... | ... |
... | @@ -38,6 +38,28 @@ public class VersionedValue { | ... | @@ -38,6 +38,28 @@ public class VersionedValue { |
38 | return version; | 38 | return version; |
39 | } | 39 | } |
40 | 40 | ||
41 | + /** | ||
42 | + * Creates a copy of given VersionedValue. | ||
43 | + * | ||
44 | + * @param original VersionedValue to create a copy | ||
45 | + * @return same as original if original or it's value is null, | ||
46 | + * otherwise creates a copy. | ||
47 | + */ | ||
48 | + public static VersionedValue copy(VersionedValue original) { | ||
49 | + if (original == null) { | ||
50 | + return null; | ||
51 | + } | ||
52 | + if (original.value == null) { | ||
53 | + // immutable, no need to copy | ||
54 | + return original; | ||
55 | + } else { | ||
56 | + return new VersionedValue( | ||
57 | + Arrays.copyOf(original.value, | ||
58 | + original.value.length), | ||
59 | + original.version); | ||
60 | + } | ||
61 | + } | ||
62 | + | ||
41 | @Override | 63 | @Override |
42 | public String toString() { | 64 | public String toString() { |
43 | return MoreObjects.toStringHelper(getClass()) | 65 | return MoreObjects.toStringHelper(getClass()) | ... | ... |
1 | +/* | ||
2 | + * Copyright 2014 Open Networking Laboratory | ||
3 | + * | ||
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
5 | + * you may not use this file except in compliance with the License. | ||
6 | + * You may obtain a copy of the License at | ||
7 | + * | ||
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
9 | + * | ||
10 | + * Unless required by applicable law or agreed to in writing, software | ||
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
13 | + * See the License for the specific language governing permissions and | ||
14 | + * limitations under the License. | ||
15 | + */ | ||
16 | +package org.onlab.onos.net.intent.constraint; | ||
17 | + | ||
18 | +import com.google.common.testing.EqualsTester; | ||
19 | +import org.junit.Before; | ||
20 | +import org.junit.Test; | ||
21 | +import org.onlab.onos.net.DefaultLink; | ||
22 | +import org.onlab.onos.net.DefaultPath; | ||
23 | +import org.onlab.onos.net.DeviceId; | ||
24 | +import org.onlab.onos.net.Path; | ||
25 | +import org.onlab.onos.net.PortNumber; | ||
26 | +import org.onlab.onos.net.intent.Constraint; | ||
27 | +import org.onlab.onos.net.provider.ProviderId; | ||
28 | +import org.onlab.onos.net.resource.LinkResourceService; | ||
29 | + | ||
30 | +import java.util.Arrays; | ||
31 | + | ||
32 | +import static org.easymock.EasyMock.createMock; | ||
33 | +import static org.hamcrest.Matchers.is; | ||
34 | +import static org.junit.Assert.assertThat; | ||
35 | +import static org.onlab.onos.net.DefaultLinkTest.cp; | ||
36 | +import static org.onlab.onos.net.DeviceId.deviceId; | ||
37 | +import static org.onlab.onos.net.Link.Type.DIRECT; | ||
38 | + | ||
39 | +/** | ||
40 | + * Test for constraint of intermediate elements. | ||
41 | + */ | ||
42 | +public class WaypointConstraintTest { | ||
43 | + | ||
44 | + public static final DeviceId DID1 = deviceId("of:1"); | ||
45 | + public static final DeviceId DID2 = deviceId("of:2"); | ||
46 | + public static final DeviceId DID3 = deviceId("of:3"); | ||
47 | + public static final DeviceId DID4 = deviceId("of:4"); | ||
48 | + public static final PortNumber PN1 = PortNumber.portNumber(1); | ||
49 | + public static final PortNumber PN2 = PortNumber.portNumber(2); | ||
50 | + public static final PortNumber PN3 = PortNumber.portNumber(3); | ||
51 | + public static final PortNumber PN4 = PortNumber.portNumber(4); | ||
52 | + public static final ProviderId PROVIDER_ID = new ProviderId("of", "foo"); | ||
53 | + | ||
54 | + private WaypointConstraint sut; | ||
55 | + private LinkResourceService linkResourceService; | ||
56 | + | ||
57 | + private Path path; | ||
58 | + private DefaultLink link2; | ||
59 | + private DefaultLink link1; | ||
60 | + | ||
61 | + @Before | ||
62 | + public void setUp() { | ||
63 | + linkResourceService = createMock(LinkResourceService.class); | ||
64 | + | ||
65 | + link1 = new DefaultLink(PROVIDER_ID, cp(DID1, PN1), cp(DID2, PN2), DIRECT); | ||
66 | + link2 = new DefaultLink(PROVIDER_ID, cp(DID2, PN3), cp(DID3, PN4), DIRECT); | ||
67 | + path = new DefaultPath(PROVIDER_ID, Arrays.asList(link1, link2), 10); | ||
68 | + } | ||
69 | + | ||
70 | + /** | ||
71 | + * Tests that all of the specified waypoints are included in the specified path in order. | ||
72 | + */ | ||
73 | + @Test | ||
74 | + public void testSatisfyWaypoints() { | ||
75 | + sut = new WaypointConstraint(DID1, DID2, DID3); | ||
76 | + | ||
77 | + assertThat(sut.validate(path, linkResourceService), is(true)); | ||
78 | + } | ||
79 | + | ||
80 | + /** | ||
81 | + * Tests that the specified path does not includes the specified waypoint. | ||
82 | + */ | ||
83 | + @Test | ||
84 | + public void testNotSatisfyWaypoint() { | ||
85 | + sut = new WaypointConstraint(DID4); | ||
86 | + | ||
87 | + assertThat(sut.validate(path, linkResourceService), is(false)); | ||
88 | + } | ||
89 | + | ||
90 | + @Test | ||
91 | + public void testEquality() { | ||
92 | + Constraint c1 = new WaypointConstraint(DID1, DID2); | ||
93 | + Constraint c2 = new WaypointConstraint(DID1, DID2); | ||
94 | + | ||
95 | + Constraint c3 = new WaypointConstraint(DID2); | ||
96 | + Constraint c4 = new WaypointConstraint(DID3); | ||
97 | + | ||
98 | + new EqualsTester() | ||
99 | + .addEqualityGroup(c1, c2) | ||
100 | + .addEqualityGroup(c3) | ||
101 | + .addEqualityGroup(c4) | ||
102 | + .testEquals(); | ||
103 | + } | ||
104 | +} |
... | @@ -118,13 +118,14 @@ public abstract class ConnectivityIntentCompiler<T extends ConnectivityIntent> | ... | @@ -118,13 +118,14 @@ public abstract class ConnectivityIntentCompiler<T extends ConnectivityIntent> |
118 | 118 | ||
119 | @Override | 119 | @Override |
120 | public double weight(TopologyEdge edge) { | 120 | public double weight(TopologyEdge edge) { |
121 | - if (constraints == null) { | 121 | + if (constraints == null || !constraints.iterator().hasNext()) { |
122 | return 1.0; | 122 | return 1.0; |
123 | } | 123 | } |
124 | 124 | ||
125 | // iterate over all constraints in order and return the weight of | 125 | // iterate over all constraints in order and return the weight of |
126 | // the first one with fast fail over the first failure | 126 | // the first one with fast fail over the first failure |
127 | Iterator<Constraint> it = constraints.iterator(); | 127 | Iterator<Constraint> it = constraints.iterator(); |
128 | + | ||
128 | double cost = it.next().cost(edge.link(), resourceService); | 129 | double cost = it.next().cost(edge.link(), resourceService); |
129 | while (it.hasNext() && cost > 0) { | 130 | while (it.hasNext() && cost > 0) { |
130 | if (it.next().cost(edge.link(), resourceService) < 0) { | 131 | if (it.next().cost(edge.link(), resourceService) < 0) { |
... | @@ -132,6 +133,7 @@ public abstract class ConnectivityIntentCompiler<T extends ConnectivityIntent> | ... | @@ -132,6 +133,7 @@ public abstract class ConnectivityIntentCompiler<T extends ConnectivityIntent> |
132 | } | 133 | } |
133 | } | 134 | } |
134 | return cost; | 135 | return cost; |
136 | + | ||
135 | } | 137 | } |
136 | } | 138 | } |
137 | 139 | ... | ... |
... | @@ -70,7 +70,8 @@ public class HostToHostIntentCompiler | ... | @@ -70,7 +70,8 @@ public class HostToHostIntentCompiler |
70 | HostToHostIntent intent) { | 70 | HostToHostIntent intent) { |
71 | TrafficSelector selector = builder(intent.selector()) | 71 | TrafficSelector selector = builder(intent.selector()) |
72 | .matchEthSrc(src.mac()).matchEthDst(dst.mac()).build(); | 72 | .matchEthSrc(src.mac()).matchEthDst(dst.mac()).build(); |
73 | - return new PathIntent(intent.appId(), selector, intent.treatment(), path); | 73 | + return new PathIntent(intent.appId(), selector, intent.treatment(), |
74 | + path, intent.constraints()); | ||
74 | } | 75 | } |
75 | 76 | ||
76 | } | 77 | } | ... | ... |
... | @@ -77,7 +77,7 @@ import com.google.common.collect.Lists; | ... | @@ -77,7 +77,7 @@ import com.google.common.collect.Lists; |
77 | @Service | 77 | @Service |
78 | public class IntentManager | 78 | public class IntentManager |
79 | implements IntentService, IntentExtensionService { | 79 | implements IntentService, IntentExtensionService { |
80 | - private final Logger log = getLogger(getClass()); | 80 | + private static final Logger log = getLogger(IntentManager.class); |
81 | 81 | ||
82 | public static final String INTENT_NULL = "Intent cannot be null"; | 82 | public static final String INTENT_NULL = "Intent cannot be null"; |
83 | public static final String INTENT_ID_NULL = "Intent ID cannot be null"; | 83 | public static final String INTENT_ID_NULL = "Intent ID cannot be null"; | ... | ... |
... | @@ -77,7 +77,8 @@ public class PointToPointIntentCompiler | ... | @@ -77,7 +77,8 @@ public class PointToPointIntentCompiler |
77 | private Intent createPathIntent(Path path, | 77 | private Intent createPathIntent(Path path, |
78 | PointToPointIntent intent) { | 78 | PointToPointIntent intent) { |
79 | return new PathIntent(intent.appId(), | 79 | return new PathIntent(intent.appId(), |
80 | - intent.selector(), intent.treatment(), path); | 80 | + intent.selector(), intent.treatment(), path, |
81 | + intent.constraints()); | ||
81 | } | 82 | } |
82 | 83 | ||
83 | } | 84 | } | ... | ... |
... | @@ -28,6 +28,7 @@ import org.onlab.onos.cluster.DefaultControllerNode; | ... | @@ -28,6 +28,7 @@ import org.onlab.onos.cluster.DefaultControllerNode; |
28 | import org.onlab.onos.cluster.NodeId; | 28 | import org.onlab.onos.cluster.NodeId; |
29 | import org.onlab.onos.event.impl.TestEventDispatcher; | 29 | import org.onlab.onos.event.impl.TestEventDispatcher; |
30 | import org.onlab.onos.mastership.MastershipService; | 30 | import org.onlab.onos.mastership.MastershipService; |
31 | +import org.onlab.onos.mastership.MastershipStore; | ||
31 | import org.onlab.onos.mastership.MastershipTermService; | 32 | import org.onlab.onos.mastership.MastershipTermService; |
32 | import org.onlab.onos.net.DeviceId; | 33 | import org.onlab.onos.net.DeviceId; |
33 | import org.onlab.onos.store.trivial.impl.SimpleMastershipStore; | 34 | import org.onlab.onos.store.trivial.impl.SimpleMastershipStore; |
... | @@ -57,9 +58,9 @@ public class MastershipManagerTest { | ... | @@ -57,9 +58,9 @@ public class MastershipManagerTest { |
57 | public void setUp() { | 58 | public void setUp() { |
58 | mgr = new MastershipManager(); | 59 | mgr = new MastershipManager(); |
59 | service = mgr; | 60 | service = mgr; |
60 | - mgr.store = new SimpleMastershipStore(); | ||
61 | mgr.eventDispatcher = new TestEventDispatcher(); | 61 | mgr.eventDispatcher = new TestEventDispatcher(); |
62 | mgr.clusterService = new TestClusterService(); | 62 | mgr.clusterService = new TestClusterService(); |
63 | + mgr.store = new TestSimpleMastershipStore(mgr.clusterService); | ||
63 | mgr.activate(); | 64 | mgr.activate(); |
64 | } | 65 | } |
65 | 66 | ||
... | @@ -74,7 +75,8 @@ public class MastershipManagerTest { | ... | @@ -74,7 +75,8 @@ public class MastershipManagerTest { |
74 | @Test | 75 | @Test |
75 | public void setRole() { | 76 | public void setRole() { |
76 | mgr.setRole(NID_OTHER, DEV_MASTER, MASTER); | 77 | mgr.setRole(NID_OTHER, DEV_MASTER, MASTER); |
77 | - assertEquals("wrong local role:", STANDBY, mgr.getLocalRole(DEV_MASTER)); | 78 | + assertEquals("wrong local role:", NONE, mgr.getLocalRole(DEV_MASTER)); |
79 | + assertEquals("wrong obtained role:", STANDBY, mgr.requestRoleFor(DEV_MASTER)); | ||
78 | 80 | ||
79 | //set to master | 81 | //set to master |
80 | mgr.setRole(NID_LOCAL, DEV_MASTER, MASTER); | 82 | mgr.setRole(NID_LOCAL, DEV_MASTER, MASTER); |
... | @@ -182,4 +184,12 @@ public class MastershipManagerTest { | ... | @@ -182,4 +184,12 @@ public class MastershipManagerTest { |
182 | } | 184 | } |
183 | 185 | ||
184 | } | 186 | } |
187 | + | ||
188 | + private final class TestSimpleMastershipStore extends SimpleMastershipStore | ||
189 | + implements MastershipStore { | ||
190 | + | ||
191 | + public TestSimpleMastershipStore(ClusterService clusterService) { | ||
192 | + super.clusterService = clusterService; | ||
193 | + } | ||
194 | + } | ||
185 | } | 195 | } | ... | ... |
... | @@ -64,6 +64,12 @@ | ... | @@ -64,6 +64,12 @@ |
64 | --> | 64 | --> |
65 | 65 | ||
66 | <dependency> | 66 | <dependency> |
67 | + <groupId>org.mapdb</groupId> | ||
68 | + <artifactId>mapdb</artifactId> | ||
69 | + <version>1.0.6</version> | ||
70 | + </dependency> | ||
71 | + | ||
72 | + <dependency> | ||
67 | <groupId>com.fasterxml.jackson.core</groupId> | 73 | <groupId>com.fasterxml.jackson.core</groupId> |
68 | <artifactId>jackson-databind</artifactId> | 74 | <artifactId>jackson-databind</artifactId> |
69 | </dependency> | 75 | </dependency> | ... | ... |
... | @@ -159,7 +159,7 @@ public class ClusterCommunicationManager | ... | @@ -159,7 +159,7 @@ public class ClusterCommunicationManager |
159 | return messagingService.sendAndReceive(nodeEp, message.subject().value(), SERIALIZER.encode(message)); | 159 | return messagingService.sendAndReceive(nodeEp, message.subject().value(), SERIALIZER.encode(message)); |
160 | 160 | ||
161 | } catch (IOException e) { | 161 | } catch (IOException e) { |
162 | - log.error("Failed interaction with remote nodeId: " + toNodeId, e); | 162 | + log.trace("Failed interaction with remote nodeId: " + toNodeId, e); |
163 | throw e; | 163 | throw e; |
164 | } | 164 | } |
165 | } | 165 | } | ... | ... |
... | @@ -283,16 +283,15 @@ implements MastershipStore { | ... | @@ -283,16 +283,15 @@ implements MastershipStore { |
283 | case MASTER: | 283 | case MASTER: |
284 | NodeId newMaster = reelect(nodeId, deviceId, rv); | 284 | NodeId newMaster = reelect(nodeId, deviceId, rv); |
285 | rv.reassign(nodeId, NONE, STANDBY); | 285 | rv.reassign(nodeId, NONE, STANDBY); |
286 | + updateTerm(deviceId); | ||
286 | if (newMaster != null) { | 287 | if (newMaster != null) { |
287 | - updateTerm(deviceId); | ||
288 | roleMap.put(deviceId, rv); | 288 | roleMap.put(deviceId, rv); |
289 | return new MastershipEvent(MASTER_CHANGED, deviceId, rv.roleInfo()); | 289 | return new MastershipEvent(MASTER_CHANGED, deviceId, rv.roleInfo()); |
290 | } else { | 290 | } else { |
291 | // no master candidate | 291 | // no master candidate |
292 | roleMap.put(deviceId, rv); | 292 | roleMap.put(deviceId, rv); |
293 | - // FIXME: Should there be new event type? | 293 | + // TODO: Should there be new event type for no MASTER? |
294 | - // or should we issue null Master event? | 294 | + return new MastershipEvent(MASTER_CHANGED, deviceId, rv.roleInfo()); |
295 | - return null; | ||
296 | } | 295 | } |
297 | case STANDBY: | 296 | case STANDBY: |
298 | return null; | 297 | return null; | ... | ... |
... | @@ -149,12 +149,12 @@ public class ClusterMessagingProtocol | ... | @@ -149,12 +149,12 @@ public class ClusterMessagingProtocol |
149 | 149 | ||
150 | @Activate | 150 | @Activate |
151 | public void activate() { | 151 | public void activate() { |
152 | - log.info("Started."); | 152 | + log.info("Started"); |
153 | } | 153 | } |
154 | 154 | ||
155 | @Deactivate | 155 | @Deactivate |
156 | public void deactivate() { | 156 | public void deactivate() { |
157 | - log.info("Stopped."); | 157 | + log.info("Stopped"); |
158 | } | 158 | } |
159 | 159 | ||
160 | @Override | 160 | @Override | ... | ... |
... | @@ -132,8 +132,8 @@ public class ClusterMessagingProtocolClient implements ProtocolClient { | ... | @@ -132,8 +132,8 @@ public class ClusterMessagingProtocolClient implements ProtocolClient { |
132 | } catch (IOException | InterruptedException | ExecutionException | TimeoutException e) { | 132 | } catch (IOException | InterruptedException | ExecutionException | TimeoutException e) { |
133 | if (message.subject().equals(ClusterMessagingProtocol.COPYCAT_SYNC) || | 133 | if (message.subject().equals(ClusterMessagingProtocol.COPYCAT_SYNC) || |
134 | message.subject().equals(ClusterMessagingProtocol.COPYCAT_PING)) { | 134 | message.subject().equals(ClusterMessagingProtocol.COPYCAT_PING)) { |
135 | - log.warn("Request to {} failed. Will retry " | 135 | + log.warn("{} Request to {} failed. Will retry in {} ms", |
136 | - + "in {} ms", remoteNode, RETRY_INTERVAL_MILLIS); | 136 | + message.subject(), remoteNode, RETRY_INTERVAL_MILLIS); |
137 | THREAD_POOL.schedule( | 137 | THREAD_POOL.schedule( |
138 | this, | 138 | this, |
139 | RETRY_INTERVAL_MILLIS, | 139 | RETRY_INTERVAL_MILLIS, | ... | ... |
... | @@ -3,12 +3,17 @@ package org.onlab.onos.store.service.impl; | ... | @@ -3,12 +3,17 @@ package org.onlab.onos.store.service.impl; |
3 | import static org.slf4j.LoggerFactory.getLogger; | 3 | import static org.slf4j.LoggerFactory.getLogger; |
4 | 4 | ||
5 | import java.util.concurrent.CompletableFuture; | 5 | import java.util.concurrent.CompletableFuture; |
6 | +import java.util.function.BiConsumer; | ||
6 | 7 | ||
7 | import net.kuujo.copycat.protocol.PingRequest; | 8 | import net.kuujo.copycat.protocol.PingRequest; |
9 | +import net.kuujo.copycat.protocol.PingResponse; | ||
8 | import net.kuujo.copycat.protocol.PollRequest; | 10 | import net.kuujo.copycat.protocol.PollRequest; |
11 | +import net.kuujo.copycat.protocol.PollResponse; | ||
9 | import net.kuujo.copycat.protocol.RequestHandler; | 12 | import net.kuujo.copycat.protocol.RequestHandler; |
10 | import net.kuujo.copycat.protocol.SubmitRequest; | 13 | import net.kuujo.copycat.protocol.SubmitRequest; |
14 | +import net.kuujo.copycat.protocol.SubmitResponse; | ||
11 | import net.kuujo.copycat.protocol.SyncRequest; | 15 | import net.kuujo.copycat.protocol.SyncRequest; |
16 | +import net.kuujo.copycat.protocol.SyncResponse; | ||
12 | import net.kuujo.copycat.spi.protocol.ProtocolServer; | 17 | import net.kuujo.copycat.spi.protocol.ProtocolServer; |
13 | 18 | ||
14 | import org.onlab.onos.store.cluster.messaging.ClusterCommunicationService; | 19 | import org.onlab.onos.store.cluster.messaging.ClusterCommunicationService; |
... | @@ -57,37 +62,37 @@ public class ClusterMessagingProtocolServer implements ProtocolServer { | ... | @@ -57,37 +62,37 @@ public class ClusterMessagingProtocolServer implements ProtocolServer { |
57 | public void handle(ClusterMessage message) { | 62 | public void handle(ClusterMessage message) { |
58 | T request = ClusterMessagingProtocol.SERIALIZER.decode(message.payload()); | 63 | T request = ClusterMessagingProtocol.SERIALIZER.decode(message.payload()); |
59 | if (request.getClass().equals(PingRequest.class)) { | 64 | if (request.getClass().equals(PingRequest.class)) { |
60 | - handler.ping((PingRequest) request).whenComplete((response, error) -> { | 65 | + handler.ping((PingRequest) request).whenComplete(new PostExecutionTask<PingResponse>(message)); |
61 | - try { | ||
62 | - message.respond(ClusterMessagingProtocol.SERIALIZER.encode(response)); | ||
63 | - } catch (Exception e) { | ||
64 | - log.error("Failed to respond to ping request", e); | ||
65 | - } | ||
66 | - }); | ||
67 | } else if (request.getClass().equals(PollRequest.class)) { | 66 | } else if (request.getClass().equals(PollRequest.class)) { |
68 | - handler.poll((PollRequest) request).whenComplete((response, error) -> { | 67 | + handler.poll((PollRequest) request).whenComplete(new PostExecutionTask<PollResponse>(message)); |
69 | - try { | ||
70 | - message.respond(ClusterMessagingProtocol.SERIALIZER.encode(response)); | ||
71 | - } catch (Exception e) { | ||
72 | - log.error("Failed to respond to poll request", e); | ||
73 | - } | ||
74 | - }); | ||
75 | } else if (request.getClass().equals(SyncRequest.class)) { | 68 | } else if (request.getClass().equals(SyncRequest.class)) { |
76 | - handler.sync((SyncRequest) request).whenComplete((response, error) -> { | 69 | + handler.sync((SyncRequest) request).whenComplete(new PostExecutionTask<SyncResponse>(message)); |
77 | - try { | ||
78 | - message.respond(ClusterMessagingProtocol.SERIALIZER.encode(response)); | ||
79 | - } catch (Exception e) { | ||
80 | - log.error("Failed to respond to sync request", e); | ||
81 | - } | ||
82 | - }); | ||
83 | } else if (request.getClass().equals(SubmitRequest.class)) { | 70 | } else if (request.getClass().equals(SubmitRequest.class)) { |
84 | - handler.submit((SubmitRequest) request).whenComplete((response, error) -> { | 71 | + handler.submit((SubmitRequest) request).whenComplete(new PostExecutionTask<SubmitResponse>(message)); |
72 | + } else { | ||
73 | + throw new IllegalStateException("Unknown request type: " + request.getClass().getName()); | ||
74 | + } | ||
75 | + } | ||
76 | + | ||
77 | + private class PostExecutionTask<R> implements BiConsumer<R, Throwable> { | ||
78 | + | ||
79 | + private final ClusterMessage message; | ||
80 | + | ||
81 | + public PostExecutionTask(ClusterMessage message) { | ||
82 | + this.message = message; | ||
83 | + } | ||
84 | + | ||
85 | + @Override | ||
86 | + public void accept(R response, Throwable t) { | ||
87 | + if (t != null) { | ||
88 | + log.error("Processing for " + message.subject() + " failed.", t); | ||
89 | + } else { | ||
85 | try { | 90 | try { |
86 | message.respond(ClusterMessagingProtocol.SERIALIZER.encode(response)); | 91 | message.respond(ClusterMessagingProtocol.SERIALIZER.encode(response)); |
87 | } catch (Exception e) { | 92 | } catch (Exception e) { |
88 | - log.error("Failed to respond to submit request", e); | 93 | + log.error("Failed to respond to " + response.getClass().getName(), e); |
89 | } | 94 | } |
90 | - }); | 95 | + } |
91 | } | 96 | } |
92 | } | 97 | } |
93 | } | 98 | } | ... | ... |
... | @@ -5,20 +5,26 @@ import static org.slf4j.LoggerFactory.getLogger; | ... | @@ -5,20 +5,26 @@ import static org.slf4j.LoggerFactory.getLogger; |
5 | import java.util.ArrayList; | 5 | import java.util.ArrayList; |
6 | import java.util.Arrays; | 6 | import java.util.Arrays; |
7 | import java.util.List; | 7 | import java.util.List; |
8 | +import java.util.concurrent.CountDownLatch; | ||
9 | +import java.util.concurrent.TimeUnit; | ||
8 | 10 | ||
9 | import net.kuujo.copycat.Copycat; | 11 | import net.kuujo.copycat.Copycat; |
10 | import net.kuujo.copycat.StateMachine; | 12 | import net.kuujo.copycat.StateMachine; |
13 | +import net.kuujo.copycat.cluster.ClusterConfig; | ||
11 | import net.kuujo.copycat.cluster.TcpCluster; | 14 | import net.kuujo.copycat.cluster.TcpCluster; |
12 | import net.kuujo.copycat.cluster.TcpClusterConfig; | 15 | import net.kuujo.copycat.cluster.TcpClusterConfig; |
13 | import net.kuujo.copycat.cluster.TcpMember; | 16 | import net.kuujo.copycat.cluster.TcpMember; |
14 | import net.kuujo.copycat.log.InMemoryLog; | 17 | import net.kuujo.copycat.log.InMemoryLog; |
15 | import net.kuujo.copycat.log.Log; | 18 | import net.kuujo.copycat.log.Log; |
19 | + | ||
16 | import org.apache.felix.scr.annotations.Activate; | 20 | import org.apache.felix.scr.annotations.Activate; |
17 | import org.apache.felix.scr.annotations.Component; | 21 | import org.apache.felix.scr.annotations.Component; |
18 | import org.apache.felix.scr.annotations.Deactivate; | 22 | import org.apache.felix.scr.annotations.Deactivate; |
19 | import org.apache.felix.scr.annotations.Reference; | 23 | import org.apache.felix.scr.annotations.Reference; |
20 | import org.apache.felix.scr.annotations.ReferenceCardinality; | 24 | import org.apache.felix.scr.annotations.ReferenceCardinality; |
21 | import org.apache.felix.scr.annotations.Service; | 25 | import org.apache.felix.scr.annotations.Service; |
26 | +import org.onlab.onos.cluster.ClusterEvent; | ||
27 | +import org.onlab.onos.cluster.ClusterEventListener; | ||
22 | import org.onlab.onos.cluster.ClusterService; | 28 | import org.onlab.onos.cluster.ClusterService; |
23 | import org.onlab.onos.cluster.ControllerNode; | 29 | import org.onlab.onos.cluster.ControllerNode; |
24 | import org.onlab.onos.store.service.DatabaseAdminService; | 30 | import org.onlab.onos.store.service.DatabaseAdminService; |
... | @@ -35,8 +41,6 @@ import org.onlab.onos.store.service.WriteRequest; | ... | @@ -35,8 +41,6 @@ import org.onlab.onos.store.service.WriteRequest; |
35 | import org.onlab.onos.store.service.WriteResult; | 41 | import org.onlab.onos.store.service.WriteResult; |
36 | import org.slf4j.Logger; | 42 | import org.slf4j.Logger; |
37 | 43 | ||
38 | -import com.google.common.collect.Lists; | ||
39 | - | ||
40 | /** | 44 | /** |
41 | * Strongly consistent and durable state management service based on | 45 | * Strongly consistent and durable state management service based on |
42 | * Copycat implementation of Raft consensus protocol. | 46 | * Copycat implementation of Raft consensus protocol. |
... | @@ -58,17 +62,34 @@ public class DatabaseManager implements DatabaseService, DatabaseAdminService { | ... | @@ -58,17 +62,34 @@ public class DatabaseManager implements DatabaseService, DatabaseAdminService { |
58 | private Copycat copycat; | 62 | private Copycat copycat; |
59 | private DatabaseClient client; | 63 | private DatabaseClient client; |
60 | 64 | ||
65 | + // guarded by synchronized block | ||
66 | + private ClusterConfig<TcpMember> clusterConfig; | ||
67 | + | ||
68 | + private CountDownLatch clusterEventLatch; | ||
69 | + | ||
70 | + private ClusterEventListener clusterEventListener; | ||
71 | + | ||
61 | @Activate | 72 | @Activate |
62 | public void activate() { | 73 | public void activate() { |
63 | - log.info("Starting."); | ||
64 | 74 | ||
65 | - // TODO: Not every node can be part of the consensus ring. | 75 | + // TODO: Not every node should be part of the consensus ring. |
66 | 76 | ||
77 | + final ControllerNode localNode = clusterService.getLocalNode(); | ||
67 | TcpMember localMember = | 78 | TcpMember localMember = |
68 | new TcpMember( | 79 | new TcpMember( |
69 | - clusterService.getLocalNode().ip().toString(), | 80 | + localNode.ip().toString(), |
70 | - clusterService.getLocalNode().tcpPort()); | 81 | + localNode.tcpPort()); |
71 | - List<TcpMember> remoteMembers = Lists.newArrayList(); | 82 | + |
83 | + clusterConfig = new TcpClusterConfig(); | ||
84 | + clusterConfig.setLocalMember(localMember); | ||
85 | + | ||
86 | + List<TcpMember> remoteMembers = new ArrayList<>(clusterService.getNodes().size()); | ||
87 | + | ||
88 | + clusterEventLatch = new CountDownLatch(1); | ||
89 | + clusterEventListener = new InternalClusterEventListener(); | ||
90 | + clusterService.addListener(clusterEventListener); | ||
91 | + | ||
92 | + // note: from this point beyond, clusterConfig requires synchronization | ||
72 | 93 | ||
73 | for (ControllerNode node : clusterService.getNodes()) { | 94 | for (ControllerNode node : clusterService.getNodes()) { |
74 | TcpMember member = new TcpMember(node.ip().toString(), node.tcpPort()); | 95 | TcpMember member = new TcpMember(node.ip().toString(), node.tcpPort()); |
... | @@ -77,20 +98,37 @@ public class DatabaseManager implements DatabaseService, DatabaseAdminService { | ... | @@ -77,20 +98,37 @@ public class DatabaseManager implements DatabaseService, DatabaseAdminService { |
77 | } | 98 | } |
78 | } | 99 | } |
79 | 100 | ||
80 | - // Configure the cluster. | 101 | + if (remoteMembers.isEmpty()) { |
81 | - TcpClusterConfig config = new TcpClusterConfig(); | 102 | + log.info("This node is the only node in the cluster. " |
103 | + + "Waiting for others to show up."); | ||
104 | + // FIXME: hack trying to relax cases forming multiple consensus rings. | ||
105 | + // add seed node configuration to avoid this | ||
106 | + | ||
107 | + // If the node is alone on it's own, wait some time | ||
108 | + // hoping other will come up soon | ||
109 | + try { | ||
110 | + if (!clusterEventLatch.await(120, TimeUnit.SECONDS)) { | ||
111 | + log.info("Starting as single node cluster"); | ||
112 | + } | ||
113 | + } catch (InterruptedException e) { | ||
114 | + log.info("Interrupted waiting for others", e); | ||
115 | + } | ||
116 | + } | ||
117 | + | ||
118 | + final TcpCluster cluster; | ||
119 | + synchronized (clusterConfig) { | ||
120 | + clusterConfig.addRemoteMembers(remoteMembers); | ||
82 | 121 | ||
83 | - config.setLocalMember(localMember); | 122 | + // Create the cluster. |
84 | - config.setRemoteMembers(remoteMembers.toArray(new TcpMember[]{})); | 123 | + cluster = new TcpCluster(clusterConfig); |
124 | + } | ||
125 | + log.info("Starting cluster: {}", cluster); | ||
85 | 126 | ||
86 | - // Create the cluster. | ||
87 | - TcpCluster cluster = new TcpCluster(config); | ||
88 | 127 | ||
89 | StateMachine stateMachine = new DatabaseStateMachine(); | 128 | StateMachine stateMachine = new DatabaseStateMachine(); |
90 | - ControllerNode thisNode = clusterService.getLocalNode(); | ||
91 | // FIXME resolve Chronicle + OSGi issue | 129 | // FIXME resolve Chronicle + OSGi issue |
92 | //Log consensusLog = new ChronicleLog(LOG_FILE_PREFIX + "_" + thisNode.id()); | 130 | //Log consensusLog = new ChronicleLog(LOG_FILE_PREFIX + "_" + thisNode.id()); |
93 | - Log consensusLog = new InMemoryLog(); | 131 | + Log consensusLog = new KryoRegisteredInMemoryLog(); |
94 | 132 | ||
95 | copycat = new Copycat(stateMachine, consensusLog, cluster, copycatMessagingProtocol); | 133 | copycat = new Copycat(stateMachine, consensusLog, cluster, copycatMessagingProtocol); |
96 | copycat.start(); | 134 | copycat.start(); |
... | @@ -102,6 +140,7 @@ public class DatabaseManager implements DatabaseService, DatabaseAdminService { | ... | @@ -102,6 +140,7 @@ public class DatabaseManager implements DatabaseService, DatabaseAdminService { |
102 | 140 | ||
103 | @Deactivate | 141 | @Deactivate |
104 | public void deactivate() { | 142 | public void deactivate() { |
143 | + clusterService.removeListener(clusterEventListener); | ||
105 | copycat.stop(); | 144 | copycat.stop(); |
106 | log.info("Stopped."); | 145 | log.info("Stopped."); |
107 | } | 146 | } |
... | @@ -179,6 +218,53 @@ public class DatabaseManager implements DatabaseService, DatabaseAdminService { | ... | @@ -179,6 +218,53 @@ public class DatabaseManager implements DatabaseService, DatabaseAdminService { |
179 | 218 | ||
180 | } | 219 | } |
181 | 220 | ||
221 | + private final class InternalClusterEventListener | ||
222 | + implements ClusterEventListener { | ||
223 | + | ||
224 | + @Override | ||
225 | + public void event(ClusterEvent event) { | ||
226 | + // TODO: Not every node should be part of the consensus ring. | ||
227 | + | ||
228 | + final ControllerNode node = event.subject(); | ||
229 | + final TcpMember tcpMember = new TcpMember(node.ip().toString(), | ||
230 | + node.tcpPort()); | ||
231 | + | ||
232 | + log.trace("{}", event); | ||
233 | + switch (event.type()) { | ||
234 | + case INSTANCE_ACTIVATED: | ||
235 | + case INSTANCE_ADDED: | ||
236 | + log.info("{} was added to the cluster", tcpMember); | ||
237 | + synchronized (clusterConfig) { | ||
238 | + clusterConfig.addRemoteMember(tcpMember); | ||
239 | + } | ||
240 | + break; | ||
241 | + case INSTANCE_DEACTIVATED: | ||
242 | + case INSTANCE_REMOVED: | ||
243 | + log.info("{} was removed from the cluster", tcpMember); | ||
244 | + synchronized (clusterConfig) { | ||
245 | + clusterConfig.removeRemoteMember(tcpMember); | ||
246 | + } | ||
247 | + break; | ||
248 | + default: | ||
249 | + break; | ||
250 | + } | ||
251 | + if (copycat != null) { | ||
252 | + log.debug("Current cluster: {}", copycat.cluster()); | ||
253 | + } | ||
254 | + clusterEventLatch.countDown(); | ||
255 | + } | ||
256 | + | ||
257 | + } | ||
258 | + | ||
259 | + public static final class KryoRegisteredInMemoryLog extends InMemoryLog { | ||
260 | + public KryoRegisteredInMemoryLog() { | ||
261 | + super(); | ||
262 | + // required to deserialize object across bundles | ||
263 | + super.kryo.register(TcpMember.class, new TcpMemberSerializer()); | ||
264 | + super.kryo.register(TcpClusterConfig.class, new TcpClusterConfigSerializer()); | ||
265 | + } | ||
266 | + } | ||
267 | + | ||
182 | private class DatabaseOperationResult<R, E extends DatabaseException> implements OptionalResult<R, E> { | 268 | private class DatabaseOperationResult<R, E extends DatabaseException> implements OptionalResult<R, E> { |
183 | 269 | ||
184 | private final R result; | 270 | private final R result; | ... | ... |
1 | package org.onlab.onos.store.service.impl; | 1 | package org.onlab.onos.store.service.impl; |
2 | 2 | ||
3 | +import static org.slf4j.LoggerFactory.getLogger; | ||
4 | + | ||
3 | import java.util.ArrayList; | 5 | import java.util.ArrayList; |
4 | import java.util.List; | 6 | import java.util.List; |
5 | import java.util.Map; | 7 | import java.util.Map; |
6 | -import java.util.Set; | ||
7 | - | ||
8 | import net.kuujo.copycat.Command; | 8 | import net.kuujo.copycat.Command; |
9 | import net.kuujo.copycat.Query; | 9 | import net.kuujo.copycat.Query; |
10 | import net.kuujo.copycat.StateMachine; | 10 | import net.kuujo.copycat.StateMachine; |
... | @@ -16,7 +16,9 @@ import org.onlab.onos.store.service.VersionedValue; | ... | @@ -16,7 +16,9 @@ import org.onlab.onos.store.service.VersionedValue; |
16 | import org.onlab.onos.store.service.WriteRequest; | 16 | import org.onlab.onos.store.service.WriteRequest; |
17 | import org.onlab.onos.store.service.WriteResult; | 17 | import org.onlab.onos.store.service.WriteResult; |
18 | import org.onlab.util.KryoNamespace; | 18 | import org.onlab.util.KryoNamespace; |
19 | +import org.slf4j.Logger; | ||
19 | 20 | ||
21 | +import com.google.common.collect.ImmutableList; | ||
20 | import com.google.common.collect.Maps; | 22 | import com.google.common.collect.Maps; |
21 | 23 | ||
22 | /** | 24 | /** |
... | @@ -28,6 +30,8 @@ import com.google.common.collect.Maps; | ... | @@ -28,6 +30,8 @@ import com.google.common.collect.Maps; |
28 | */ | 30 | */ |
29 | public class DatabaseStateMachine implements StateMachine { | 31 | public class DatabaseStateMachine implements StateMachine { |
30 | 32 | ||
33 | + private final Logger log = getLogger(getClass()); | ||
34 | + | ||
31 | public static final KryoSerializer SERIALIZER = new KryoSerializer() { | 35 | public static final KryoSerializer SERIALIZER = new KryoSerializer() { |
32 | @Override | 36 | @Override |
33 | protected void setupKryoPool() { | 37 | protected void setupKryoPool() { |
... | @@ -59,8 +63,8 @@ public class DatabaseStateMachine implements StateMachine { | ... | @@ -59,8 +63,8 @@ public class DatabaseStateMachine implements StateMachine { |
59 | } | 63 | } |
60 | 64 | ||
61 | @Query | 65 | @Query |
62 | - public Set<String> listTables() { | 66 | + public List<String> listTables() { |
63 | - return state.getTables().keySet(); | 67 | + return ImmutableList.copyOf(state.getTables().keySet()); |
64 | } | 68 | } |
65 | 69 | ||
66 | @Query | 70 | @Query |
... | @@ -72,7 +76,7 @@ public class DatabaseStateMachine implements StateMachine { | ... | @@ -72,7 +76,7 @@ public class DatabaseStateMachine implements StateMachine { |
72 | results.add(new InternalReadResult(InternalReadResult.Status.NO_SUCH_TABLE, null)); | 76 | results.add(new InternalReadResult(InternalReadResult.Status.NO_SUCH_TABLE, null)); |
73 | continue; | 77 | continue; |
74 | } | 78 | } |
75 | - VersionedValue value = table.get(request.key()); | 79 | + VersionedValue value = VersionedValue.copy(table.get(request.key())); |
76 | results.add(new InternalReadResult( | 80 | results.add(new InternalReadResult( |
77 | InternalReadResult.Status.OK, | 81 | InternalReadResult.Status.OK, |
78 | new ReadResult( | 82 | new ReadResult( |
... | @@ -85,6 +89,8 @@ public class DatabaseStateMachine implements StateMachine { | ... | @@ -85,6 +89,8 @@ public class DatabaseStateMachine implements StateMachine { |
85 | 89 | ||
86 | @Command | 90 | @Command |
87 | public List<InternalWriteResult> write(List<WriteRequest> requests) { | 91 | public List<InternalWriteResult> write(List<WriteRequest> requests) { |
92 | + | ||
93 | + // applicability check | ||
88 | boolean abort = false; | 94 | boolean abort = false; |
89 | List<InternalWriteResult.Status> validationResults = new ArrayList<>(requests.size()); | 95 | List<InternalWriteResult.Status> validationResults = new ArrayList<>(requests.size()); |
90 | for (WriteRequest request : requests) { | 96 | for (WriteRequest request : requests) { |
... | @@ -128,8 +134,13 @@ public class DatabaseStateMachine implements StateMachine { | ... | @@ -128,8 +134,13 @@ public class DatabaseStateMachine implements StateMachine { |
128 | return results; | 134 | return results; |
129 | } | 135 | } |
130 | 136 | ||
137 | + // apply changes | ||
131 | for (WriteRequest request : requests) { | 138 | for (WriteRequest request : requests) { |
132 | Map<String, VersionedValue> table = state.getTables().get(request.tableName()); | 139 | Map<String, VersionedValue> table = state.getTables().get(request.tableName()); |
140 | + // FIXME: If this method could be called by multiple thread, | ||
141 | + // synchronization scope is wrong. | ||
142 | + // Whole function including applicability check needs to be protected. | ||
143 | + // Confirm copycat's thread safety requirement for StateMachine | ||
133 | synchronized (table) { | 144 | synchronized (table) { |
134 | VersionedValue previousValue = | 145 | VersionedValue previousValue = |
135 | table.put(request.key(), new VersionedValue(request.newValue(), state.nextVersion())); | 146 | table.put(request.key(), new VersionedValue(request.newValue(), state.nextVersion())); |
... | @@ -161,8 +172,8 @@ public class DatabaseStateMachine implements StateMachine { | ... | @@ -161,8 +172,8 @@ public class DatabaseStateMachine implements StateMachine { |
161 | try { | 172 | try { |
162 | return SERIALIZER.encode(state); | 173 | return SERIALIZER.encode(state); |
163 | } catch (Exception e) { | 174 | } catch (Exception e) { |
164 | - e.printStackTrace(); | 175 | + log.error("Failed to take snapshot", e); |
165 | - return null; | 176 | + throw new SnapshotException(e); |
166 | } | 177 | } |
167 | } | 178 | } |
168 | 179 | ||
... | @@ -171,7 +182,8 @@ public class DatabaseStateMachine implements StateMachine { | ... | @@ -171,7 +182,8 @@ public class DatabaseStateMachine implements StateMachine { |
171 | try { | 182 | try { |
172 | this.state = SERIALIZER.decode(data); | 183 | this.state = SERIALIZER.decode(data); |
173 | } catch (Exception e) { | 184 | } catch (Exception e) { |
174 | - e.printStackTrace(); | 185 | + log.error("Failed to install from snapshot", e); |
186 | + throw new SnapshotException(e); | ||
175 | } | 187 | } |
176 | } | 188 | } |
177 | } | 189 | } | ... | ... |
1 | +package org.onlab.onos.store.service.impl; | ||
2 | + | ||
3 | +import static com.google.common.base.Preconditions.checkArgument; | ||
4 | +import static com.google.common.base.Preconditions.checkState; | ||
5 | + | ||
6 | +import java.io.File; | ||
7 | +import java.io.IOException; | ||
8 | +import java.util.ArrayList; | ||
9 | +import java.util.Arrays; | ||
10 | +import java.util.List; | ||
11 | +import java.util.concurrent.ConcurrentNavigableMap; | ||
12 | + | ||
13 | +import net.kuujo.copycat.log.Entry; | ||
14 | +import net.kuujo.copycat.log.Log; | ||
15 | +import net.kuujo.copycat.log.LogIndexOutOfBoundsException; | ||
16 | + | ||
17 | +import org.mapdb.Atomic; | ||
18 | +import org.mapdb.BTreeMap; | ||
19 | +import org.mapdb.DB; | ||
20 | +import org.mapdb.DBMaker; | ||
21 | +import org.mapdb.TxBlock; | ||
22 | +import org.mapdb.TxMaker; | ||
23 | +import org.onlab.onos.store.serializers.StoreSerializer; | ||
24 | + | ||
25 | +import com.google.common.collect.Lists; | ||
26 | + | ||
27 | +/** | ||
28 | + * MapDB based log implementation. | ||
29 | + */ | ||
30 | +public class MapDBLog implements Log { | ||
31 | + | ||
32 | + private final File dbFile; | ||
33 | + private TxMaker txMaker; | ||
34 | + private final StoreSerializer serializer; | ||
35 | + private static final String LOG_NAME = "log"; | ||
36 | + private static final String SIZE_FIELD_NAME = "size"; | ||
37 | + | ||
38 | + public MapDBLog(File dbFile, StoreSerializer serializer) { | ||
39 | + this.dbFile = dbFile; | ||
40 | + this.serializer = serializer; | ||
41 | + } | ||
42 | + | ||
43 | + @Override | ||
44 | + public void open() throws IOException { | ||
45 | + txMaker = DBMaker | ||
46 | + .newFileDB(dbFile) | ||
47 | + .makeTxMaker(); | ||
48 | + } | ||
49 | + | ||
50 | + @Override | ||
51 | + public void close() throws IOException { | ||
52 | + assertIsOpen(); | ||
53 | + txMaker.close(); | ||
54 | + txMaker = null; | ||
55 | + } | ||
56 | + | ||
57 | + @Override | ||
58 | + public boolean isOpen() { | ||
59 | + return txMaker != null; | ||
60 | + } | ||
61 | + | ||
62 | + protected void assertIsOpen() { | ||
63 | + checkState(isOpen(), "The log is not currently open."); | ||
64 | + } | ||
65 | + | ||
66 | + @Override | ||
67 | + public long appendEntry(Entry entry) { | ||
68 | + checkArgument(entry != null, "expecting non-null entry"); | ||
69 | + return appendEntries(entry).get(0); | ||
70 | + } | ||
71 | + | ||
72 | + @Override | ||
73 | + public List<Long> appendEntries(Entry... entries) { | ||
74 | + checkArgument(entries != null, "expecting non-null entries"); | ||
75 | + return appendEntries(Arrays.asList(entries)); | ||
76 | + } | ||
77 | + | ||
78 | + @Override | ||
79 | + public List<Long> appendEntries(List<Entry> entries) { | ||
80 | + assertIsOpen(); | ||
81 | + checkArgument(entries != null, "expecting non-null entries"); | ||
82 | + final List<Long> indices = Lists.newArrayList(); | ||
83 | + | ||
84 | + txMaker.execute(new TxBlock() { | ||
85 | + @Override | ||
86 | + public void tx(DB db) { | ||
87 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
88 | + Atomic.Long size = db.getAtomicLong(SIZE_FIELD_NAME); | ||
89 | + long nextIndex = log.isEmpty() ? 1 : log.lastKey() + 1; | ||
90 | + for (Entry entry : entries) { | ||
91 | + byte[] entryBytes = serializer.encode(entry); | ||
92 | + log.put(nextIndex, entryBytes); | ||
93 | + size.addAndGet(entryBytes.length); | ||
94 | + indices.add(nextIndex); | ||
95 | + nextIndex++; | ||
96 | + } | ||
97 | + } | ||
98 | + }); | ||
99 | + | ||
100 | + return indices; | ||
101 | + } | ||
102 | + | ||
103 | + @Override | ||
104 | + public boolean containsEntry(long index) { | ||
105 | + assertIsOpen(); | ||
106 | + DB db = txMaker.makeTx(); | ||
107 | + try { | ||
108 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
109 | + return log.containsKey(index); | ||
110 | + } finally { | ||
111 | + db.close(); | ||
112 | + } | ||
113 | + } | ||
114 | + | ||
115 | + @Override | ||
116 | + public void delete() throws IOException { | ||
117 | + assertIsOpen(); | ||
118 | + txMaker.execute(new TxBlock() { | ||
119 | + @Override | ||
120 | + public void tx(DB db) { | ||
121 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
122 | + Atomic.Long size = db.getAtomicLong(SIZE_FIELD_NAME); | ||
123 | + log.clear(); | ||
124 | + size.set(0); | ||
125 | + } | ||
126 | + }); | ||
127 | + } | ||
128 | + | ||
129 | + @Override | ||
130 | + public <T extends Entry> T firstEntry() { | ||
131 | + assertIsOpen(); | ||
132 | + DB db = txMaker.makeTx(); | ||
133 | + try { | ||
134 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
135 | + return log.isEmpty() ? null : serializer.decode(log.firstEntry().getValue()); | ||
136 | + } finally { | ||
137 | + db.close(); | ||
138 | + } | ||
139 | + } | ||
140 | + | ||
141 | + @Override | ||
142 | + public long firstIndex() { | ||
143 | + assertIsOpen(); | ||
144 | + DB db = txMaker.makeTx(); | ||
145 | + try { | ||
146 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
147 | + return log.isEmpty() ? 0 : log.firstKey(); | ||
148 | + } finally { | ||
149 | + db.close(); | ||
150 | + } | ||
151 | + } | ||
152 | + | ||
153 | + @Override | ||
154 | + public <T extends Entry> List<T> getEntries(long from, long to) { | ||
155 | + assertIsOpen(); | ||
156 | + DB db = txMaker.makeTx(); | ||
157 | + try { | ||
158 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
159 | + if (log.isEmpty()) { | ||
160 | + throw new LogIndexOutOfBoundsException("Log is empty"); | ||
161 | + } else if (from < log.firstKey()) { | ||
162 | + throw new LogIndexOutOfBoundsException("From index out of bounds."); | ||
163 | + } else if (to > log.lastKey()) { | ||
164 | + throw new LogIndexOutOfBoundsException("To index out of bounds."); | ||
165 | + } | ||
166 | + List<T> entries = new ArrayList<>((int) (to - from + 1)); | ||
167 | + for (long i = from; i <= to; i++) { | ||
168 | + T entry = serializer.decode(log.get(i)); | ||
169 | + entries.add(entry); | ||
170 | + } | ||
171 | + return entries; | ||
172 | + } finally { | ||
173 | + db.close(); | ||
174 | + } | ||
175 | + } | ||
176 | + | ||
177 | + @Override | ||
178 | + public <T extends Entry> T getEntry(long index) { | ||
179 | + assertIsOpen(); | ||
180 | + DB db = txMaker.makeTx(); | ||
181 | + try { | ||
182 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
183 | + byte[] entryBytes = log.get(index); | ||
184 | + return entryBytes == null ? null : serializer.decode(entryBytes); | ||
185 | + } finally { | ||
186 | + db.close(); | ||
187 | + } | ||
188 | + } | ||
189 | + | ||
190 | + @Override | ||
191 | + public boolean isEmpty() { | ||
192 | + assertIsOpen(); | ||
193 | + DB db = txMaker.makeTx(); | ||
194 | + try { | ||
195 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
196 | + return log.isEmpty(); | ||
197 | + } finally { | ||
198 | + db.close(); | ||
199 | + } | ||
200 | + } | ||
201 | + | ||
202 | + @Override | ||
203 | + public <T extends Entry> T lastEntry() { | ||
204 | + assertIsOpen(); | ||
205 | + DB db = txMaker.makeTx(); | ||
206 | + try { | ||
207 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
208 | + return log.isEmpty() ? null : serializer.decode(log.lastEntry().getValue()); | ||
209 | + } finally { | ||
210 | + db.close(); | ||
211 | + } | ||
212 | + } | ||
213 | + | ||
214 | + @Override | ||
215 | + public long lastIndex() { | ||
216 | + assertIsOpen(); | ||
217 | + DB db = txMaker.makeTx(); | ||
218 | + try { | ||
219 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
220 | + return log.isEmpty() ? 0 : log.lastKey(); | ||
221 | + } finally { | ||
222 | + db.close(); | ||
223 | + } | ||
224 | + } | ||
225 | + | ||
226 | + @Override | ||
227 | + public void removeAfter(long index) { | ||
228 | + assertIsOpen(); | ||
229 | + txMaker.execute(new TxBlock() { | ||
230 | + @Override | ||
231 | + public void tx(DB db) { | ||
232 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
233 | + Atomic.Long size = db.getAtomicLong(SIZE_FIELD_NAME); | ||
234 | + long startIndex = index + 1; | ||
235 | + long endIndex = log.lastKey(); | ||
236 | + for (long i = startIndex; i <= endIndex; ++i) { | ||
237 | + byte[] entryBytes = log.remove(i); | ||
238 | + size.addAndGet(-1L * entryBytes.length); | ||
239 | + } | ||
240 | + } | ||
241 | + }); | ||
242 | + } | ||
243 | + | ||
244 | + @Override | ||
245 | + public long size() { | ||
246 | + assertIsOpen(); | ||
247 | + DB db = txMaker.makeTx(); | ||
248 | + try { | ||
249 | + Atomic.Long size = db.getAtomicLong(SIZE_FIELD_NAME); | ||
250 | + return size.get(); | ||
251 | + } finally { | ||
252 | + db.close(); | ||
253 | + } | ||
254 | + } | ||
255 | + | ||
256 | + @Override | ||
257 | + public void sync() throws IOException { | ||
258 | + assertIsOpen(); | ||
259 | + } | ||
260 | + | ||
261 | + @Override | ||
262 | + public void compact(long index, Entry entry) throws IOException { | ||
263 | + | ||
264 | + assertIsOpen(); | ||
265 | + txMaker.execute(new TxBlock() { | ||
266 | + @Override | ||
267 | + public void tx(DB db) { | ||
268 | + BTreeMap<Long, byte[]> log = db.getTreeMap(LOG_NAME); | ||
269 | + Atomic.Long size = db.getAtomicLong(SIZE_FIELD_NAME); | ||
270 | + ConcurrentNavigableMap<Long, byte[]> headMap = log.headMap(index); | ||
271 | + long deletedBytes = headMap.keySet().stream().mapToLong(i -> log.remove(i).length).sum(); | ||
272 | + size.addAndGet(-1 * deletedBytes); | ||
273 | + byte[] entryBytes = serializer.encode(entry); | ||
274 | + byte[] existingEntry = log.put(index, entryBytes); | ||
275 | + size.addAndGet(entryBytes.length - existingEntry.length); | ||
276 | + db.compact(); | ||
277 | + } | ||
278 | + }); | ||
279 | + } | ||
280 | +} | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
1 | +package org.onlab.onos.store.service.impl; | ||
2 | + | ||
3 | +import org.onlab.onos.store.service.DatabaseException; | ||
4 | + | ||
5 | +/** | ||
6 | + * Exception that indicates a problem with the state machine snapshotting. | ||
7 | + */ | ||
8 | +@SuppressWarnings("serial") | ||
9 | +public class SnapshotException extends DatabaseException { | ||
10 | + public SnapshotException(Throwable t) { | ||
11 | + super(t); | ||
12 | + } | ||
13 | +} |
core/store/dist/src/main/java/org/onlab/onos/store/service/impl/TcpClusterConfigSerializer.java
0 → 100644
1 | +package org.onlab.onos.store.service.impl; | ||
2 | + | ||
3 | +import java.util.Collection; | ||
4 | + | ||
5 | +import net.kuujo.copycat.cluster.TcpClusterConfig; | ||
6 | +import net.kuujo.copycat.cluster.TcpMember; | ||
7 | + | ||
8 | +import com.esotericsoftware.kryo.Kryo; | ||
9 | +import com.esotericsoftware.kryo.Serializer; | ||
10 | +import com.esotericsoftware.kryo.io.Input; | ||
11 | +import com.esotericsoftware.kryo.io.Output; | ||
12 | + | ||
13 | +public class TcpClusterConfigSerializer extends Serializer<TcpClusterConfig> { | ||
14 | + | ||
15 | + @Override | ||
16 | + public void write(Kryo kryo, Output output, TcpClusterConfig object) { | ||
17 | + kryo.writeClassAndObject(output, object.getLocalMember()); | ||
18 | + kryo.writeClassAndObject(output, object.getRemoteMembers()); | ||
19 | + } | ||
20 | + | ||
21 | + @Override | ||
22 | + public TcpClusterConfig read(Kryo kryo, Input input, | ||
23 | + Class<TcpClusterConfig> type) { | ||
24 | + TcpMember localMember = (TcpMember) kryo.readClassAndObject(input); | ||
25 | + @SuppressWarnings("unchecked") | ||
26 | + Collection<TcpMember> remoteMembers = (Collection<TcpMember>) kryo.readClassAndObject(input); | ||
27 | + return new TcpClusterConfig(localMember, remoteMembers); | ||
28 | + } | ||
29 | + | ||
30 | +} |
1 | +package org.onlab.onos.store.service.impl; | ||
2 | + | ||
3 | +import net.kuujo.copycat.cluster.TcpMember; | ||
4 | + | ||
5 | +import com.esotericsoftware.kryo.Kryo; | ||
6 | +import com.esotericsoftware.kryo.Serializer; | ||
7 | +import com.esotericsoftware.kryo.io.Input; | ||
8 | +import com.esotericsoftware.kryo.io.Output; | ||
9 | + | ||
10 | +public class TcpMemberSerializer extends Serializer<TcpMember> { | ||
11 | + | ||
12 | + @Override | ||
13 | + public void write(Kryo kryo, Output output, TcpMember object) { | ||
14 | + output.writeString(object.host()); | ||
15 | + output.writeInt(object.port()); | ||
16 | + } | ||
17 | + | ||
18 | + @Override | ||
19 | + public TcpMember read(Kryo kryo, Input input, Class<TcpMember> type) { | ||
20 | + String host = input.readString(); | ||
21 | + int port = input.readInt(); | ||
22 | + return new TcpMember(host, port); | ||
23 | + } | ||
24 | +} |
1 | +package org.onlab.onos.store.service.impl; | ||
2 | + | ||
3 | +import java.io.File; | ||
4 | +import java.io.IOException; | ||
5 | +import java.nio.file.Files; | ||
6 | +import java.util.List; | ||
7 | + | ||
8 | +import net.kuujo.copycat.internal.log.OperationEntry; | ||
9 | +import net.kuujo.copycat.log.Entry; | ||
10 | +import net.kuujo.copycat.log.Log; | ||
11 | + | ||
12 | +import org.junit.After; | ||
13 | +import org.junit.Assert; | ||
14 | +import org.junit.Before; | ||
15 | +import org.junit.Test; | ||
16 | +import org.onlab.onos.store.serializers.StoreSerializer; | ||
17 | + | ||
18 | +import com.google.common.testing.EqualsTester; | ||
19 | + | ||
20 | +/** | ||
21 | + * Test the MapDBLog implementation. | ||
22 | + */ | ||
23 | +public class MapDBLogTest { | ||
24 | + | ||
25 | + private static final String DB_FILE_NAME = "mapdbTest"; | ||
26 | + private static final StoreSerializer SERIALIZER = ClusterMessagingProtocol.SERIALIZER; | ||
27 | + private static final Entry TEST_ENTRY1 = new OperationEntry(1, "test1"); | ||
28 | + private static final Entry TEST_ENTRY2 = new OperationEntry(2, "test12"); | ||
29 | + private static final Entry TEST_ENTRY3 = new OperationEntry(3, "test123"); | ||
30 | + private static final Entry TEST_ENTRY4 = new OperationEntry(4, "test1234"); | ||
31 | + | ||
32 | + private static final Entry TEST_SNAPSHOT_ENTRY = new OperationEntry(5, "snapshot"); | ||
33 | + | ||
34 | + private static final long TEST_ENTRY1_SIZE = SERIALIZER.encode(TEST_ENTRY1).length; | ||
35 | + private static final long TEST_ENTRY2_SIZE = SERIALIZER.encode(TEST_ENTRY2).length; | ||
36 | + private static final long TEST_ENTRY3_SIZE = SERIALIZER.encode(TEST_ENTRY3).length; | ||
37 | + private static final long TEST_ENTRY4_SIZE = SERIALIZER.encode(TEST_ENTRY4).length; | ||
38 | + | ||
39 | + private static final long TEST_SNAPSHOT_ENTRY_SIZE = SERIALIZER.encode(TEST_SNAPSHOT_ENTRY).length; | ||
40 | + | ||
41 | + @Before | ||
42 | + public void setUp() throws Exception { | ||
43 | + } | ||
44 | + | ||
45 | + @After | ||
46 | + public void tearDown() throws Exception { | ||
47 | + Files.deleteIfExists(new File(DB_FILE_NAME).toPath()); | ||
48 | + Files.deleteIfExists(new File(DB_FILE_NAME + ".t").toPath()); | ||
49 | + Files.deleteIfExists(new File(DB_FILE_NAME + ".p").toPath()); | ||
50 | + } | ||
51 | + | ||
52 | + @Test(expected = IllegalStateException.class) | ||
53 | + public void testAssertOpen() { | ||
54 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
55 | + log.size(); | ||
56 | + } | ||
57 | + | ||
58 | + @Test | ||
59 | + public void testAppendEntry() throws IOException { | ||
60 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
61 | + log.open(); | ||
62 | + log.appendEntry(TEST_ENTRY1); | ||
63 | + OperationEntry first = log.firstEntry(); | ||
64 | + OperationEntry last = log.lastEntry(); | ||
65 | + new EqualsTester() | ||
66 | + .addEqualityGroup(first, last, TEST_ENTRY1) | ||
67 | + .testEquals(); | ||
68 | + Assert.assertEquals(TEST_ENTRY1_SIZE, log.size()); | ||
69 | + Assert.assertEquals(1, log.firstIndex()); | ||
70 | + Assert.assertEquals(1, log.lastIndex()); | ||
71 | + } | ||
72 | + | ||
73 | + @Test | ||
74 | + public void testAppendEntries() throws IOException { | ||
75 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
76 | + log.open(); | ||
77 | + log.appendEntries(TEST_ENTRY1, TEST_ENTRY2, TEST_ENTRY3); | ||
78 | + OperationEntry first = log.firstEntry(); | ||
79 | + OperationEntry last = log.lastEntry(); | ||
80 | + new EqualsTester() | ||
81 | + .addEqualityGroup(first, TEST_ENTRY1) | ||
82 | + .addEqualityGroup(last, TEST_ENTRY3) | ||
83 | + .testEquals(); | ||
84 | + Assert.assertEquals(TEST_ENTRY1_SIZE + TEST_ENTRY2_SIZE, TEST_ENTRY3_SIZE, log.size()); | ||
85 | + Assert.assertEquals(1, log.firstIndex()); | ||
86 | + Assert.assertEquals(3, log.lastIndex()); | ||
87 | + Assert.assertTrue(log.containsEntry(1)); | ||
88 | + Assert.assertTrue(log.containsEntry(2)); | ||
89 | + } | ||
90 | + | ||
91 | + @Test | ||
92 | + public void testDelete() throws IOException { | ||
93 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
94 | + log.open(); | ||
95 | + log.appendEntries(TEST_ENTRY1, TEST_ENTRY2); | ||
96 | + log.delete(); | ||
97 | + Assert.assertEquals(0, log.size()); | ||
98 | + Assert.assertTrue(log.isEmpty()); | ||
99 | + Assert.assertEquals(0, log.firstIndex()); | ||
100 | + Assert.assertNull(log.firstEntry()); | ||
101 | + Assert.assertEquals(0, log.lastIndex()); | ||
102 | + Assert.assertNull(log.lastEntry()); | ||
103 | + } | ||
104 | + | ||
105 | + @Test | ||
106 | + public void testGetEntries() throws IOException { | ||
107 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
108 | + log.open(); | ||
109 | + log.appendEntries(TEST_ENTRY1, TEST_ENTRY2, TEST_ENTRY3, TEST_ENTRY4); | ||
110 | + Assert.assertEquals( | ||
111 | + TEST_ENTRY1_SIZE + | ||
112 | + TEST_ENTRY2_SIZE + | ||
113 | + TEST_ENTRY3_SIZE + | ||
114 | + TEST_ENTRY4_SIZE, log.size()); | ||
115 | + | ||
116 | + List<Entry> entries = log.getEntries(2, 3); | ||
117 | + new EqualsTester() | ||
118 | + .addEqualityGroup(log.getEntry(4), TEST_ENTRY4) | ||
119 | + .addEqualityGroup(entries.get(0), TEST_ENTRY2) | ||
120 | + .addEqualityGroup(entries.get(1), TEST_ENTRY3) | ||
121 | + .testEquals(); | ||
122 | + } | ||
123 | + | ||
124 | + @Test | ||
125 | + public void testRemoveAfter() throws IOException { | ||
126 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
127 | + log.open(); | ||
128 | + log.appendEntries(TEST_ENTRY1, TEST_ENTRY2, TEST_ENTRY3, TEST_ENTRY4); | ||
129 | + log.removeAfter(1); | ||
130 | + Assert.assertEquals(TEST_ENTRY1_SIZE, log.size()); | ||
131 | + new EqualsTester() | ||
132 | + .addEqualityGroup(log.firstEntry(), log.lastEntry(), TEST_ENTRY1) | ||
133 | + .testEquals(); | ||
134 | + } | ||
135 | + | ||
136 | + @Test | ||
137 | + public void testAddAfterRemove() throws IOException { | ||
138 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
139 | + log.open(); | ||
140 | + log.appendEntries(TEST_ENTRY1, TEST_ENTRY2, TEST_ENTRY3, TEST_ENTRY4); | ||
141 | + log.removeAfter(1); | ||
142 | + log.appendEntry(TEST_ENTRY4); | ||
143 | + Assert.assertEquals(TEST_ENTRY1_SIZE + TEST_ENTRY4_SIZE, log.size()); | ||
144 | + new EqualsTester() | ||
145 | + .addEqualityGroup(log.firstEntry(), TEST_ENTRY1) | ||
146 | + .addEqualityGroup(log.lastEntry(), TEST_ENTRY4) | ||
147 | + .addEqualityGroup(log.size(), TEST_ENTRY1_SIZE + TEST_ENTRY4_SIZE) | ||
148 | + .testEquals(); | ||
149 | + } | ||
150 | + | ||
151 | + @Test | ||
152 | + public void testClose() throws IOException { | ||
153 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
154 | + Assert.assertFalse(log.isOpen()); | ||
155 | + log.open(); | ||
156 | + Assert.assertTrue(log.isOpen()); | ||
157 | + log.close(); | ||
158 | + Assert.assertFalse(log.isOpen()); | ||
159 | + } | ||
160 | + | ||
161 | + @Test | ||
162 | + public void testReopen() throws IOException { | ||
163 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
164 | + log.open(); | ||
165 | + log.appendEntries(TEST_ENTRY1, TEST_ENTRY2, TEST_ENTRY3, TEST_ENTRY4); | ||
166 | + log.close(); | ||
167 | + log.open(); | ||
168 | + | ||
169 | + new EqualsTester() | ||
170 | + .addEqualityGroup(log.firstEntry(), TEST_ENTRY1) | ||
171 | + .addEqualityGroup(log.getEntry(2), TEST_ENTRY2) | ||
172 | + .addEqualityGroup(log.lastEntry(), TEST_ENTRY4) | ||
173 | + .addEqualityGroup(log.size(), | ||
174 | + TEST_ENTRY1_SIZE + | ||
175 | + TEST_ENTRY2_SIZE + | ||
176 | + TEST_ENTRY3_SIZE + | ||
177 | + TEST_ENTRY4_SIZE) | ||
178 | + .testEquals(); | ||
179 | + } | ||
180 | + | ||
181 | + @Test | ||
182 | + public void testCompact() throws IOException { | ||
183 | + Log log = new MapDBLog(new File(DB_FILE_NAME), SERIALIZER); | ||
184 | + log.open(); | ||
185 | + log.appendEntries(TEST_ENTRY1, TEST_ENTRY2, TEST_ENTRY3, TEST_ENTRY4); | ||
186 | + log.compact(3, TEST_SNAPSHOT_ENTRY); | ||
187 | + new EqualsTester() | ||
188 | + .addEqualityGroup(log.firstEntry(), TEST_SNAPSHOT_ENTRY) | ||
189 | + .addEqualityGroup(log.lastEntry(), TEST_ENTRY4) | ||
190 | + .addEqualityGroup(log.size(), | ||
191 | + TEST_SNAPSHOT_ENTRY_SIZE + | ||
192 | + TEST_ENTRY4_SIZE) | ||
193 | + .testEquals(); | ||
194 | + } | ||
195 | +} |
... | @@ -103,6 +103,20 @@ import com.google.common.collect.ImmutableSet; | ... | @@ -103,6 +103,20 @@ import com.google.common.collect.ImmutableSet; |
103 | 103 | ||
104 | public final class KryoNamespaces { | 104 | public final class KryoNamespaces { |
105 | 105 | ||
106 | + public static final KryoNamespace BASIC = KryoNamespace.newBuilder() | ||
107 | + .register(ImmutableMap.class, new ImmutableMapSerializer()) | ||
108 | + .register(ImmutableList.class, new ImmutableListSerializer()) | ||
109 | + .register(ImmutableSet.class, new ImmutableSetSerializer()) | ||
110 | + .register( | ||
111 | + ArrayList.class, | ||
112 | + Arrays.asList().getClass(), | ||
113 | + HashMap.class, | ||
114 | + HashSet.class, | ||
115 | + LinkedList.class, | ||
116 | + byte[].class | ||
117 | + ) | ||
118 | + .build(); | ||
119 | + | ||
106 | /** | 120 | /** |
107 | * KryoNamespace which can serialize ON.lab misc classes. | 121 | * KryoNamespace which can serialize ON.lab misc classes. |
108 | */ | 122 | */ |
... | @@ -123,19 +137,8 @@ public final class KryoNamespaces { | ... | @@ -123,19 +137,8 @@ public final class KryoNamespaces { |
123 | */ | 137 | */ |
124 | public static final KryoNamespace API = KryoNamespace.newBuilder() | 138 | public static final KryoNamespace API = KryoNamespace.newBuilder() |
125 | .register(MISC) | 139 | .register(MISC) |
126 | - .register(ImmutableMap.class, new ImmutableMapSerializer()) | 140 | + .register(BASIC) |
127 | - .register(ImmutableList.class, new ImmutableListSerializer()) | ||
128 | - .register(ImmutableSet.class, new ImmutableSetSerializer()) | ||
129 | .register( | 141 | .register( |
130 | - // | ||
131 | - ArrayList.class, | ||
132 | - Arrays.asList().getClass(), | ||
133 | - HashMap.class, | ||
134 | - HashSet.class, | ||
135 | - LinkedList.class, | ||
136 | - byte[].class, | ||
137 | - // | ||
138 | - // | ||
139 | ControllerNode.State.class, | 142 | ControllerNode.State.class, |
140 | Device.Type.class, | 143 | Device.Type.class, |
141 | Port.Type.class, | 144 | Port.Type.class, | ... | ... |
... | @@ -29,8 +29,13 @@ import java.util.concurrent.atomic.AtomicInteger; | ... | @@ -29,8 +29,13 @@ import java.util.concurrent.atomic.AtomicInteger; |
29 | import org.apache.felix.scr.annotations.Activate; | 29 | import org.apache.felix.scr.annotations.Activate; |
30 | import org.apache.felix.scr.annotations.Component; | 30 | import org.apache.felix.scr.annotations.Component; |
31 | import org.apache.felix.scr.annotations.Deactivate; | 31 | import org.apache.felix.scr.annotations.Deactivate; |
32 | +import org.apache.felix.scr.annotations.Reference; | ||
33 | +import org.apache.felix.scr.annotations.ReferenceCardinality; | ||
32 | import org.apache.felix.scr.annotations.Service; | 34 | import org.apache.felix.scr.annotations.Service; |
35 | +import org.onlab.onos.cluster.ClusterEventListener; | ||
36 | +import org.onlab.onos.cluster.ClusterService; | ||
33 | import org.onlab.onos.cluster.ControllerNode; | 37 | import org.onlab.onos.cluster.ControllerNode; |
38 | +import org.onlab.onos.cluster.ControllerNode.State; | ||
34 | import org.onlab.onos.cluster.DefaultControllerNode; | 39 | import org.onlab.onos.cluster.DefaultControllerNode; |
35 | import org.onlab.onos.cluster.NodeId; | 40 | import org.onlab.onos.cluster.NodeId; |
36 | import org.onlab.onos.cluster.RoleInfo; | 41 | import org.onlab.onos.cluster.RoleInfo; |
... | @@ -44,7 +49,8 @@ import org.onlab.onos.store.AbstractStore; | ... | @@ -44,7 +49,8 @@ import org.onlab.onos.store.AbstractStore; |
44 | import org.onlab.packet.IpAddress; | 49 | import org.onlab.packet.IpAddress; |
45 | import org.slf4j.Logger; | 50 | import org.slf4j.Logger; |
46 | 51 | ||
47 | -import com.google.common.collect.Lists; | 52 | +import com.google.common.collect.ImmutableList; |
53 | +import com.google.common.collect.ImmutableSet; | ||
48 | 54 | ||
49 | import static org.onlab.onos.mastership.MastershipEvent.Type.*; | 55 | import static org.onlab.onos.mastership.MastershipEvent.Type.*; |
50 | 56 | ||
... | @@ -60,23 +66,65 @@ public class SimpleMastershipStore | ... | @@ -60,23 +66,65 @@ public class SimpleMastershipStore |
60 | 66 | ||
61 | private final Logger log = getLogger(getClass()); | 67 | private final Logger log = getLogger(getClass()); |
62 | 68 | ||
63 | - public static final IpAddress LOCALHOST = IpAddress.valueOf("127.0.0.1"); | ||
64 | - | ||
65 | private static final int NOTHING = 0; | 69 | private static final int NOTHING = 0; |
66 | private static final int INIT = 1; | 70 | private static final int INIT = 1; |
67 | 71 | ||
68 | - private ControllerNode instance = | 72 | + @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) |
69 | - new DefaultControllerNode(new NodeId("local"), LOCALHOST); | 73 | + protected ClusterService clusterService; |
70 | 74 | ||
71 | //devices mapped to their masters, to emulate multiple nodes | 75 | //devices mapped to their masters, to emulate multiple nodes |
72 | protected final Map<DeviceId, NodeId> masterMap = new HashMap<>(); | 76 | protected final Map<DeviceId, NodeId> masterMap = new HashMap<>(); |
73 | //emulate backups with pile of nodes | 77 | //emulate backups with pile of nodes |
74 | - protected final Set<NodeId> backups = new HashSet<>(); | 78 | + protected final Map<DeviceId, List<NodeId>> backups = new HashMap<>(); |
75 | //terms | 79 | //terms |
76 | protected final Map<DeviceId, AtomicInteger> termMap = new HashMap<>(); | 80 | protected final Map<DeviceId, AtomicInteger> termMap = new HashMap<>(); |
77 | 81 | ||
78 | @Activate | 82 | @Activate |
79 | public void activate() { | 83 | public void activate() { |
84 | + if (clusterService == null) { | ||
85 | + // just for ease of unit test | ||
86 | + final ControllerNode instance = | ||
87 | + new DefaultControllerNode(new NodeId("local"), | ||
88 | + IpAddress.valueOf("127.0.0.1")); | ||
89 | + | ||
90 | + clusterService = new ClusterService() { | ||
91 | + | ||
92 | + @Override | ||
93 | + public ControllerNode getLocalNode() { | ||
94 | + return instance; | ||
95 | + } | ||
96 | + | ||
97 | + @Override | ||
98 | + public Set<ControllerNode> getNodes() { | ||
99 | + return ImmutableSet.of(instance); | ||
100 | + } | ||
101 | + | ||
102 | + @Override | ||
103 | + public ControllerNode getNode(NodeId nodeId) { | ||
104 | + if (instance.id().equals(nodeId)) { | ||
105 | + return instance; | ||
106 | + } | ||
107 | + return null; | ||
108 | + } | ||
109 | + | ||
110 | + @Override | ||
111 | + public State getState(NodeId nodeId) { | ||
112 | + if (instance.id().equals(nodeId)) { | ||
113 | + return State.ACTIVE; | ||
114 | + } else { | ||
115 | + return State.INACTIVE; | ||
116 | + } | ||
117 | + } | ||
118 | + | ||
119 | + @Override | ||
120 | + public void addListener(ClusterEventListener listener) { | ||
121 | + } | ||
122 | + | ||
123 | + @Override | ||
124 | + public void removeListener(ClusterEventListener listener) { | ||
125 | + } | ||
126 | + }; | ||
127 | + } | ||
80 | log.info("Started"); | 128 | log.info("Started"); |
81 | } | 129 | } |
82 | 130 | ||
... | @@ -86,31 +134,27 @@ public class SimpleMastershipStore | ... | @@ -86,31 +134,27 @@ public class SimpleMastershipStore |
86 | } | 134 | } |
87 | 135 | ||
88 | @Override | 136 | @Override |
89 | - public MastershipEvent setMaster(NodeId nodeId, DeviceId deviceId) { | 137 | + public synchronized MastershipEvent setMaster(NodeId nodeId, DeviceId deviceId) { |
90 | - MastershipRole role = getRole(nodeId, deviceId); | ||
91 | 138 | ||
92 | - synchronized (this) { | 139 | + MastershipRole role = getRole(nodeId, deviceId); |
93 | - switch (role) { | 140 | + switch (role) { |
94 | - case MASTER: | 141 | + case MASTER: |
95 | - return null; | 142 | + // no-op |
96 | - case STANDBY: | 143 | + return null; |
97 | - masterMap.put(deviceId, nodeId); | 144 | + case STANDBY: |
98 | - termMap.get(deviceId).incrementAndGet(); | 145 | + case NONE: |
99 | - backups.add(nodeId); | 146 | + NodeId prevMaster = masterMap.put(deviceId, nodeId); |
100 | - break; | 147 | + incrementTerm(deviceId); |
101 | - case NONE: | 148 | + removeFromBackups(deviceId, nodeId); |
102 | - masterMap.put(deviceId, nodeId); | 149 | + addToBackup(deviceId, prevMaster); |
103 | - termMap.put(deviceId, new AtomicInteger(INIT)); | 150 | + break; |
104 | - backups.add(nodeId); | 151 | + default: |
105 | - break; | 152 | + log.warn("unknown Mastership Role {}", role); |
106 | - default: | 153 | + return null; |
107 | - log.warn("unknown Mastership Role {}", role); | ||
108 | - return null; | ||
109 | - } | ||
110 | } | 154 | } |
111 | 155 | ||
112 | return new MastershipEvent(MASTER_CHANGED, deviceId, | 156 | return new MastershipEvent(MASTER_CHANGED, deviceId, |
113 | - new RoleInfo(nodeId, Lists.newLinkedList(backups))); | 157 | + getNodes(deviceId)); |
114 | } | 158 | } |
115 | 159 | ||
116 | @Override | 160 | @Override |
... | @@ -118,12 +162,11 @@ public class SimpleMastershipStore | ... | @@ -118,12 +162,11 @@ public class SimpleMastershipStore |
118 | return masterMap.get(deviceId); | 162 | return masterMap.get(deviceId); |
119 | } | 163 | } |
120 | 164 | ||
165 | + // synchronized for atomic read | ||
121 | @Override | 166 | @Override |
122 | - public RoleInfo getNodes(DeviceId deviceId) { | 167 | + public synchronized RoleInfo getNodes(DeviceId deviceId) { |
123 | - List<NodeId> nodes = new ArrayList<>(); | 168 | + return new RoleInfo(masterMap.get(deviceId), |
124 | - nodes.addAll(backups); | 169 | + backups.getOrDefault(deviceId, ImmutableList.of())); |
125 | - | ||
126 | - return new RoleInfo(masterMap.get(deviceId), nodes); | ||
127 | } | 170 | } |
128 | 171 | ||
129 | @Override | 172 | @Override |
... | @@ -134,69 +177,97 @@ public class SimpleMastershipStore | ... | @@ -134,69 +177,97 @@ public class SimpleMastershipStore |
134 | ids.add(d.getKey()); | 177 | ids.add(d.getKey()); |
135 | } | 178 | } |
136 | } | 179 | } |
137 | - return Collections.unmodifiableSet(ids); | 180 | + return ids; |
138 | } | 181 | } |
139 | 182 | ||
140 | @Override | 183 | @Override |
141 | - public MastershipRole requestRole(DeviceId deviceId) { | 184 | + public synchronized MastershipRole requestRole(DeviceId deviceId) { |
142 | //query+possible reelection | 185 | //query+possible reelection |
143 | - NodeId node = instance.id(); | 186 | + NodeId node = clusterService.getLocalNode().id(); |
144 | MastershipRole role = getRole(node, deviceId); | 187 | MastershipRole role = getRole(node, deviceId); |
145 | 188 | ||
146 | switch (role) { | 189 | switch (role) { |
147 | case MASTER: | 190 | case MASTER: |
148 | - break; | 191 | + return MastershipRole.MASTER; |
149 | case STANDBY: | 192 | case STANDBY: |
150 | - synchronized (this) { | 193 | + if (getMaster(deviceId) == null) { |
151 | - //try to "re-elect", since we're really not distributed | 194 | + // no master => become master |
152 | - NodeId rel = reelect(node); | 195 | + masterMap.put(deviceId, node); |
153 | - if (rel == null) { | 196 | + incrementTerm(deviceId); |
154 | - masterMap.put(deviceId, node); | 197 | + // remove from backup list |
155 | - termMap.put(deviceId, new AtomicInteger(INIT)); | 198 | + removeFromBackups(deviceId, node); |
156 | - role = MastershipRole.MASTER; | 199 | + notifyDelegate(new MastershipEvent(MASTER_CHANGED, deviceId, |
157 | - } | 200 | + getNodes(deviceId))); |
158 | - backups.add(node); | 201 | + return MastershipRole.MASTER; |
159 | } | 202 | } |
160 | - break; | 203 | + return MastershipRole.STANDBY; |
161 | case NONE: | 204 | case NONE: |
162 | - //first to get to it, say we are master | 205 | + if (getMaster(deviceId) == null) { |
163 | - synchronized (this) { | 206 | + // no master => become master |
164 | masterMap.put(deviceId, node); | 207 | masterMap.put(deviceId, node); |
165 | - termMap.put(deviceId, new AtomicInteger(INIT)); | 208 | + incrementTerm(deviceId); |
166 | - backups.add(node); | 209 | + notifyDelegate(new MastershipEvent(MASTER_CHANGED, deviceId, |
167 | - role = MastershipRole.MASTER; | 210 | + getNodes(deviceId))); |
211 | + return MastershipRole.MASTER; | ||
168 | } | 212 | } |
169 | - break; | 213 | + // add to backup list |
214 | + if (addToBackup(deviceId, node)) { | ||
215 | + notifyDelegate(new MastershipEvent(BACKUPS_CHANGED, deviceId, | ||
216 | + getNodes(deviceId))); | ||
217 | + } | ||
218 | + return MastershipRole.STANDBY; | ||
170 | default: | 219 | default: |
171 | log.warn("unknown Mastership Role {}", role); | 220 | log.warn("unknown Mastership Role {}", role); |
172 | } | 221 | } |
173 | return role; | 222 | return role; |
174 | } | 223 | } |
175 | 224 | ||
225 | + // add to backup if not there already, silently ignores null node | ||
226 | + private synchronized boolean addToBackup(DeviceId deviceId, NodeId nodeId) { | ||
227 | + boolean modified = false; | ||
228 | + List<NodeId> stbys = backups.getOrDefault(deviceId, new ArrayList<>()); | ||
229 | + if (nodeId != null && !stbys.contains(nodeId)) { | ||
230 | + stbys.add(nodeId); | ||
231 | + modified = true; | ||
232 | + } | ||
233 | + backups.put(deviceId, stbys); | ||
234 | + return modified; | ||
235 | + } | ||
236 | + | ||
237 | + private synchronized boolean removeFromBackups(DeviceId deviceId, NodeId node) { | ||
238 | + List<NodeId> stbys = backups.getOrDefault(deviceId, new ArrayList<>()); | ||
239 | + boolean modified = stbys.remove(node); | ||
240 | + backups.put(deviceId, stbys); | ||
241 | + return modified; | ||
242 | + } | ||
243 | + | ||
244 | + private synchronized void incrementTerm(DeviceId deviceId) { | ||
245 | + AtomicInteger term = termMap.getOrDefault(deviceId, new AtomicInteger(NOTHING)); | ||
246 | + term.incrementAndGet(); | ||
247 | + termMap.put(deviceId, term); | ||
248 | + } | ||
249 | + | ||
176 | @Override | 250 | @Override |
177 | public MastershipRole getRole(NodeId nodeId, DeviceId deviceId) { | 251 | public MastershipRole getRole(NodeId nodeId, DeviceId deviceId) { |
178 | //just query | 252 | //just query |
179 | NodeId current = masterMap.get(deviceId); | 253 | NodeId current = masterMap.get(deviceId); |
180 | MastershipRole role; | 254 | MastershipRole role; |
181 | 255 | ||
182 | - if (current == null) { | 256 | + if (current != null && current.equals(nodeId)) { |
183 | - if (backups.contains(nodeId)) { | 257 | + return MastershipRole.MASTER; |
184 | - role = MastershipRole.STANDBY; | 258 | + } |
185 | - } else { | 259 | + |
186 | - role = MastershipRole.NONE; | 260 | + if (backups.getOrDefault(deviceId, Collections.emptyList()).contains(nodeId)) { |
187 | - } | 261 | + role = MastershipRole.STANDBY; |
188 | } else { | 262 | } else { |
189 | - if (current.equals(nodeId)) { | 263 | + role = MastershipRole.NONE; |
190 | - role = MastershipRole.MASTER; | ||
191 | - } else { | ||
192 | - role = MastershipRole.STANDBY; | ||
193 | - } | ||
194 | } | 264 | } |
195 | return role; | 265 | return role; |
196 | } | 266 | } |
197 | 267 | ||
268 | + // synchronized for atomic read | ||
198 | @Override | 269 | @Override |
199 | - public MastershipTerm getTermFor(DeviceId deviceId) { | 270 | + public synchronized MastershipTerm getTermFor(DeviceId deviceId) { |
200 | if ((termMap.get(deviceId) == null)) { | 271 | if ((termMap.get(deviceId) == null)) { |
201 | return MastershipTerm.of(masterMap.get(deviceId), NOTHING); | 272 | return MastershipTerm.of(masterMap.get(deviceId), NOTHING); |
202 | } | 273 | } |
... | @@ -205,72 +276,71 @@ public class SimpleMastershipStore | ... | @@ -205,72 +276,71 @@ public class SimpleMastershipStore |
205 | } | 276 | } |
206 | 277 | ||
207 | @Override | 278 | @Override |
208 | - public MastershipEvent setStandby(NodeId nodeId, DeviceId deviceId) { | 279 | + public synchronized MastershipEvent setStandby(NodeId nodeId, DeviceId deviceId) { |
209 | MastershipRole role = getRole(nodeId, deviceId); | 280 | MastershipRole role = getRole(nodeId, deviceId); |
210 | - synchronized (this) { | 281 | + switch (role) { |
211 | - switch (role) { | 282 | + case MASTER: |
212 | - case MASTER: | 283 | + NodeId backup = reelect(deviceId, nodeId); |
213 | - NodeId backup = reelect(nodeId); | 284 | + if (backup == null) { |
214 | - if (backup == null) { | 285 | + // no master alternative |
215 | - masterMap.remove(deviceId); | 286 | + masterMap.remove(deviceId); |
216 | - } else { | 287 | + // TODO: Should there be new event type for no MASTER? |
217 | - masterMap.put(deviceId, backup); | 288 | + return new MastershipEvent(MASTER_CHANGED, deviceId, |
218 | - termMap.get(deviceId).incrementAndGet(); | 289 | + getNodes(deviceId)); |
219 | - return new MastershipEvent(MASTER_CHANGED, deviceId, | 290 | + } else { |
220 | - new RoleInfo(backup, Lists.newLinkedList(backups))); | 291 | + NodeId prevMaster = masterMap.put(deviceId, backup); |
221 | - } | 292 | + incrementTerm(deviceId); |
222 | - case STANDBY: | 293 | + addToBackup(deviceId, prevMaster); |
223 | - case NONE: | 294 | + return new MastershipEvent(MASTER_CHANGED, deviceId, |
224 | - if (!termMap.containsKey(deviceId)) { | 295 | + getNodes(deviceId)); |
225 | - termMap.put(deviceId, new AtomicInteger(INIT)); | 296 | + } |
226 | - } | 297 | + case STANDBY: |
227 | - backups.add(nodeId); | 298 | + case NONE: |
228 | - break; | 299 | + boolean modified = addToBackup(deviceId, nodeId); |
229 | - default: | 300 | + if (modified) { |
230 | - log.warn("unknown Mastership Role {}", role); | 301 | + return new MastershipEvent(BACKUPS_CHANGED, deviceId, |
302 | + getNodes(deviceId)); | ||
231 | } | 303 | } |
304 | + default: | ||
305 | + log.warn("unknown Mastership Role {}", role); | ||
232 | } | 306 | } |
233 | return null; | 307 | return null; |
234 | } | 308 | } |
235 | 309 | ||
236 | //dumbly selects next-available node that's not the current one | 310 | //dumbly selects next-available node that's not the current one |
237 | //emulate leader election | 311 | //emulate leader election |
238 | - private NodeId reelect(NodeId nodeId) { | 312 | + private synchronized NodeId reelect(DeviceId did, NodeId nodeId) { |
313 | + List<NodeId> stbys = backups.getOrDefault(did, Collections.emptyList()); | ||
239 | NodeId backup = null; | 314 | NodeId backup = null; |
240 | - for (NodeId n : backups) { | 315 | + for (NodeId n : stbys) { |
241 | if (!n.equals(nodeId)) { | 316 | if (!n.equals(nodeId)) { |
242 | backup = n; | 317 | backup = n; |
243 | break; | 318 | break; |
244 | } | 319 | } |
245 | } | 320 | } |
246 | - backups.remove(backup); | 321 | + stbys.remove(backup); |
247 | return backup; | 322 | return backup; |
248 | } | 323 | } |
249 | 324 | ||
250 | @Override | 325 | @Override |
251 | - public MastershipEvent relinquishRole(NodeId nodeId, DeviceId deviceId) { | 326 | + public synchronized MastershipEvent relinquishRole(NodeId nodeId, DeviceId deviceId) { |
252 | MastershipRole role = getRole(nodeId, deviceId); | 327 | MastershipRole role = getRole(nodeId, deviceId); |
253 | - synchronized (this) { | 328 | + switch (role) { |
254 | - switch (role) { | 329 | + case MASTER: |
255 | - case MASTER: | 330 | + NodeId backup = reelect(deviceId, nodeId); |
256 | - NodeId backup = reelect(nodeId); | 331 | + masterMap.put(deviceId, backup); |
257 | - backups.remove(nodeId); | 332 | + incrementTerm(deviceId); |
258 | - if (backup == null) { | 333 | + return new MastershipEvent(MASTER_CHANGED, deviceId, |
259 | - masterMap.remove(deviceId); | 334 | + getNodes(deviceId)); |
260 | - } else { | 335 | + case STANDBY: |
261 | - masterMap.put(deviceId, backup); | 336 | + if (removeFromBackups(deviceId, nodeId)) { |
262 | - termMap.get(deviceId).incrementAndGet(); | 337 | + return new MastershipEvent(BACKUPS_CHANGED, deviceId, |
263 | - return new MastershipEvent(MASTER_CHANGED, deviceId, | 338 | + getNodes(deviceId)); |
264 | - new RoleInfo(backup, Lists.newLinkedList(backups))); | ||
265 | - } | ||
266 | - case STANDBY: | ||
267 | - backups.remove(nodeId); | ||
268 | - case NONE: | ||
269 | - default: | ||
270 | - log.warn("unknown Mastership Role {}", role); | ||
271 | } | 339 | } |
340 | + case NONE: | ||
341 | + default: | ||
342 | + log.warn("unknown Mastership Role {}", role); | ||
272 | } | 343 | } |
273 | return null; | 344 | return null; |
274 | } | 345 | } |
275 | - | ||
276 | } | 346 | } | ... | ... |
... | @@ -15,6 +15,8 @@ | ... | @@ -15,6 +15,8 @@ |
15 | */ | 15 | */ |
16 | package org.onlab.onos.store.trivial.impl; | 16 | package org.onlab.onos.store.trivial.impl; |
17 | 17 | ||
18 | +import java.util.ArrayList; | ||
19 | +import java.util.List; | ||
18 | import java.util.Set; | 20 | import java.util.Set; |
19 | import java.util.concurrent.atomic.AtomicInteger; | 21 | import java.util.concurrent.atomic.AtomicInteger; |
20 | 22 | ||
... | @@ -22,6 +24,7 @@ import org.junit.After; | ... | @@ -22,6 +24,7 @@ import org.junit.After; |
22 | import org.junit.Before; | 24 | import org.junit.Before; |
23 | import org.junit.Test; | 25 | import org.junit.Test; |
24 | import org.onlab.onos.cluster.NodeId; | 26 | import org.onlab.onos.cluster.NodeId; |
27 | +import org.onlab.onos.mastership.MastershipEvent; | ||
25 | import org.onlab.onos.mastership.MastershipTerm; | 28 | import org.onlab.onos.mastership.MastershipTerm; |
26 | import org.onlab.onos.net.DeviceId; | 29 | import org.onlab.onos.net.DeviceId; |
27 | 30 | ||
... | @@ -74,6 +77,7 @@ public class SimpleMastershipStoreTest { | ... | @@ -74,6 +77,7 @@ public class SimpleMastershipStoreTest { |
74 | assertEquals("wrong role", MASTER, sms.getRole(N2, DID3)); | 77 | assertEquals("wrong role", MASTER, sms.getRole(N2, DID3)); |
75 | 78 | ||
76 | //N2 is master but N1 is only in backups set | 79 | //N2 is master but N1 is only in backups set |
80 | + put(DID4, N1, false, true); | ||
77 | put(DID4, N2, true, false); | 81 | put(DID4, N2, true, false); |
78 | assertEquals("wrong role", STANDBY, sms.getRole(N1, DID4)); | 82 | assertEquals("wrong role", STANDBY, sms.getRole(N1, DID4)); |
79 | } | 83 | } |
... | @@ -127,12 +131,12 @@ public class SimpleMastershipStoreTest { | ... | @@ -127,12 +131,12 @@ public class SimpleMastershipStoreTest { |
127 | put(DID1, N1, false, false); | 131 | put(DID1, N1, false, false); |
128 | assertEquals("wrong role", MASTER, sms.requestRole(DID1)); | 132 | assertEquals("wrong role", MASTER, sms.requestRole(DID1)); |
129 | 133 | ||
130 | - //STANDBY without backup - become MASTER | 134 | + //was STANDBY - become MASTER |
131 | put(DID2, N1, false, true); | 135 | put(DID2, N1, false, true); |
132 | assertEquals("wrong role", MASTER, sms.requestRole(DID2)); | 136 | assertEquals("wrong role", MASTER, sms.requestRole(DID2)); |
133 | 137 | ||
134 | - //STANDBY with backup - stay STANDBY | 138 | + //other MASTER - stay STANDBY |
135 | - put(DID3, N2, false, true); | 139 | + put(DID3, N2, true, false); |
136 | assertEquals("wrong role", STANDBY, sms.requestRole(DID3)); | 140 | assertEquals("wrong role", STANDBY, sms.requestRole(DID3)); |
137 | 141 | ||
138 | //local (N1) is MASTER - stay MASTER | 142 | //local (N1) is MASTER - stay MASTER |
... | @@ -145,30 +149,34 @@ public class SimpleMastershipStoreTest { | ... | @@ -145,30 +149,34 @@ public class SimpleMastershipStoreTest { |
145 | //NONE - record backup but take no other action | 149 | //NONE - record backup but take no other action |
146 | put(DID1, N1, false, false); | 150 | put(DID1, N1, false, false); |
147 | sms.setStandby(N1, DID1); | 151 | sms.setStandby(N1, DID1); |
148 | - assertTrue("not backed up", sms.backups.contains(N1)); | 152 | + assertTrue("not backed up", sms.backups.get(DID1).contains(N1)); |
149 | - sms.termMap.clear(); | 153 | + int prev = sms.termMap.get(DID1).get(); |
150 | sms.setStandby(N1, DID1); | 154 | sms.setStandby(N1, DID1); |
151 | - assertTrue("term not set", sms.termMap.containsKey(DID1)); | 155 | + assertEquals("term should not change", prev, sms.termMap.get(DID1).get()); |
152 | 156 | ||
153 | //no backup, MASTER | 157 | //no backup, MASTER |
154 | - put(DID1, N1, true, true); | 158 | + put(DID1, N1, true, false); |
155 | - assertNull("wrong event", sms.setStandby(N1, DID1)); | 159 | + assertNull("expect no MASTER event", sms.setStandby(N1, DID1).roleInfo().master()); |
156 | assertNull("wrong node", sms.masterMap.get(DID1)); | 160 | assertNull("wrong node", sms.masterMap.get(DID1)); |
157 | 161 | ||
158 | //backup, switch | 162 | //backup, switch |
159 | sms.masterMap.clear(); | 163 | sms.masterMap.clear(); |
160 | put(DID1, N1, true, true); | 164 | put(DID1, N1, true, true); |
165 | + put(DID1, N2, false, true); | ||
161 | put(DID2, N2, true, true); | 166 | put(DID2, N2, true, true); |
162 | - assertEquals("wrong event", MASTER_CHANGED, sms.setStandby(N1, DID1).type()); | 167 | + MastershipEvent event = sms.setStandby(N1, DID1); |
168 | + assertEquals("wrong event", MASTER_CHANGED, event.type()); | ||
169 | + assertEquals("wrong master", N2, event.roleInfo().master()); | ||
163 | } | 170 | } |
164 | 171 | ||
165 | //helper to populate master/backup structures | 172 | //helper to populate master/backup structures |
166 | - private void put(DeviceId dev, NodeId node, boolean store, boolean backup) { | 173 | + private void put(DeviceId dev, NodeId node, boolean master, boolean backup) { |
167 | - if (store) { | 174 | + if (master) { |
168 | sms.masterMap.put(dev, node); | 175 | sms.masterMap.put(dev, node); |
169 | - } | 176 | + } else if (backup) { |
170 | - if (backup) { | 177 | + List<NodeId> stbys = sms.backups.getOrDefault(dev, new ArrayList<>()); |
171 | - sms.backups.add(node); | 178 | + stbys.add(node); |
179 | + sms.backups.put(dev, stbys); | ||
172 | } | 180 | } |
173 | sms.termMap.put(dev, new AtomicInteger()); | 181 | sms.termMap.put(dev, new AtomicInteger()); |
174 | } | 182 | } | ... | ... |
... | @@ -56,6 +56,9 @@ | ... | @@ -56,6 +56,9 @@ |
56 | <bundle>mvn:org.codehaus.jackson/jackson-mapper-asl/1.9.13</bundle> | 56 | <bundle>mvn:org.codehaus.jackson/jackson-mapper-asl/1.9.13</bundle> |
57 | 57 | ||
58 | <bundle>mvn:org.onlab.onos/onlab-thirdparty/1.0.0-SNAPSHOT</bundle> | 58 | <bundle>mvn:org.onlab.onos/onlab-thirdparty/1.0.0-SNAPSHOT</bundle> |
59 | + | ||
60 | + <bundle>mvn:org.mapdb/mapdb/1.0.6</bundle> | ||
61 | + | ||
59 | <!-- FIXME: resolce Chronicle's dependency issue | 62 | <!-- FIXME: resolce Chronicle's dependency issue |
60 | <bundle>mvn:net.openhft/lang/6.4.6</bundle> | 63 | <bundle>mvn:net.openhft/lang/6.4.6</bundle> |
61 | <bundle>mvn:net.openhft/affinity/2.1.1</bundle> | 64 | <bundle>mvn:net.openhft/affinity/2.1.1</bundle> | ... | ... |
1 | <?xml version="1.0" encoding="UTF-8" standalone="no"?> | 1 | <?xml version="1.0" encoding="UTF-8" standalone="no"?> |
2 | <profiles version="12"> | 2 | <profiles version="12"> |
3 | <profile kind="CodeFormatterProfile" name="ONOS-formatter" version="12"> | 3 | <profile kind="CodeFormatterProfile" name="ONOS-formatter" version="12"> |
4 | -<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags" value="insert"/> | ||
5 | -<setting id="org.eclipse.jdt.core.formatter.disabling_tag" value="@formatter:off"/> | ||
6 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation" value="insert"/> | ||
7 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters" value="do not insert"/> | ||
8 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration" value="insert"/> | ||
9 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments" value="insert"/> | ||
10 | -<setting id="org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration" value="end_of_line"/> | ||
11 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case" value="do not insert"/> | ||
12 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer" value="insert"/> | ||
13 | -<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_block_boundaries" value="true"/> | ||
14 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_annotation_declaration" value="insert"/> | ||
15 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer" value="do not insert"/> | ||
16 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation" value="do not insert"/> | ||
17 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_field" value="0"/> | ||
18 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while" value="do not insert"/> | ||
19 | -<setting id="org.eclipse.jdt.core.formatter.use_on_off_tags" value="true"/> | ||
20 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration" value="do not insert"/> | ||
21 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement" value="do not insert"/> | ||
22 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator" value="do not insert"/> | ||
23 | -<setting id="org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line" value="false"/> | ||
24 | <setting id="org.eclipse.jdt.core.formatter.insert_space_after_ellipsis" value="insert"/> | 4 | <setting id="org.eclipse.jdt.core.formatter.insert_space_after_ellipsis" value="insert"/> |
5 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations" value="insert"/> | ||
6 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_annotation_declaration" value="insert"/> | ||
7 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression" value="do not insert"/> | ||
8 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration" value="insert"/> | ||
9 | +<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_block_boundaries" value="true"/> | ||
10 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters" value="insert"/> | ||
25 | <setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter" value="do not insert"/> | 11 | <setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter" value="do not insert"/> |
26 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration" value="insert"/> | 12 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_package" value="insert"/> |
27 | -<setting id="org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases" value="true"/> | ||
28 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation" value="do not insert"/> | ||
29 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_multiple_fields" value="16"/> | ||
30 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer" value="18"/> | ||
31 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_conditional_expression" value="82"/> | ||
32 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for" value="insert"/> | ||
33 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_binary_operator" value="insert"/> | ||
34 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard" value="do not insert"/> | ||
35 | -<setting id="org.eclipse.jdt.core.formatter.brace_position_for_array_initializer" value="end_of_line"/> | ||
36 | <setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant" value="do not insert"/> | 13 | <setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant" value="do not insert"/> |
37 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement" value="do not insert"/> | 14 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_imports" value="1"/> |
38 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable" value="insert"/> | 15 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while" value="do not insert"/> |
39 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement" value="do not insert"/> | 16 | +<setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags" value="insert"/> |
40 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while" value="insert"/> | 17 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration" value="do not insert"/> |
41 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_package" value="1"/> | 18 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws" value="do not insert"/> |
42 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters" value="insert"/> | 19 | +<setting id="org.eclipse.jdt.core.formatter.comment.format_javadoc_comments" value="true"/> |
43 | -<setting id="org.eclipse.jdt.core.formatter.continuation_indentation" value="2"/> | ||
44 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator" value="do not insert"/> | ||
45 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation" value="18"/> | ||
46 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments" value="do not insert"/> | ||
47 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces" value="do not insert"/> | ||
48 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk" value="1"/> | ||
49 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_binary_operator" value="insert"/> | ||
50 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_package" value="0"/> | ||
51 | -<setting id="org.eclipse.jdt.core.compiler.source" value="1.8"/> | ||
52 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments" value="insert"/> | ||
53 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration" value="do not insert"/> | ||
54 | -<setting id="org.eclipse.jdt.core.formatter.comment.format_line_comments" value="true"/> | ||
55 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments" value="insert"/> | ||
56 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations" value="insert"/> | ||
57 | -<setting id="org.eclipse.jdt.core.formatter.join_wrapped_lines" value="true"/> | ||
58 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block" value="insert"/> | ||
59 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call" value="18"/> | ||
60 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments" value="do not insert"/> | ||
61 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_member_type" value="1"/> | ||
62 | -<setting id="org.eclipse.jdt.core.formatter.align_type_members_on_columns" value="false"/> | ||
63 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant" value="do not insert"/> | ||
64 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for" value="do not insert"/> | ||
65 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration" value="insert"/> | ||
66 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation" value="16"/> | ||
67 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch" value="do not insert"/> | ||
68 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_unary_operator" value="do not insert"/> | ||
69 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case" value="insert"/> | ||
70 | -<setting id="org.eclipse.jdt.core.formatter.comment.indent_parameter_description" value="true"/> | ||
71 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_lambda_arrow" value="insert"/> | ||
72 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration" value="do not insert"/> | ||
73 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch" value="do not insert"/> | ||
74 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration" value="insert"/> | ||
75 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters" value="do not insert"/> | ||
76 | -<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment" value="false"/> | ||
77 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_type_declaration" value="insert"/> | ||
78 | -<setting id="org.eclipse.jdt.core.formatter.lineSplit" value="80"/> | ||
79 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if" value="insert"/> | ||
80 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference" value="do not insert"/> | ||
81 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression" value="do not insert"/> | ||
82 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments" value="do not insert"/> | ||
83 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration" value="insert"/> | ||
84 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration" value="0"/> | ||
85 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_method" value="insert"/> | ||
86 | <setting id="org.eclipse.jdt.core.formatter.indentation.size" value="8"/> | 20 | <setting id="org.eclipse.jdt.core.formatter.indentation.size" value="8"/> |
87 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration" value="do not insert"/> | 21 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator" value="do not insert"/> |
22 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments" value="insert"/> | ||
23 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments" value="insert"/> | ||
24 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits" value="do not insert"/> | ||
25 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_anonymous_type_declaration" value="insert"/> | ||
26 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for" value="insert"/> | ||
27 | +<setting id="org.eclipse.jdt.core.formatter.disabling_tag" value="@formatter:off"/> | ||
28 | +<setting id="org.eclipse.jdt.core.formatter.continuation_indentation" value="2"/> | ||
29 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_enum_constants" value="16"/> | ||
30 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_imports" value="1"/> | ||
31 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_package" value="1"/> | ||
32 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_binary_operator" value="insert"/> | ||
33 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations" value="insert"/> | ||
34 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant" value="0"/> | ||
35 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/> | ||
36 | +<setting id="org.eclipse.jdt.core.formatter.comment.indent_root_tags" value="true"/> | ||
37 | +<setting id="org.eclipse.jdt.core.formatter.wrap_before_or_operator_multicatch" value="true"/> | ||
88 | <setting id="org.eclipse.jdt.core.formatter.enabling_tag" value="@formatter:on"/> | 38 | <setting id="org.eclipse.jdt.core.formatter.enabling_tag" value="@formatter:on"/> |
89 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant" value="do not insert"/> | 39 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block" value="insert"/> |
90 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration" value="32"/> | ||
91 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_assignment" value="0"/> | ||
92 | -<setting id="org.eclipse.jdt.core.compiler.problem.assertIdentifier" value="error"/> | ||
93 | -<setting id="org.eclipse.jdt.core.formatter.tabulation.char" value="space"/> | ||
94 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters" value="insert"/> | ||
95 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_try_resources" value="insert"/> | ||
96 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator" value="do not insert"/> | ||
97 | -<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_body" value="true"/> | ||
98 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_method" value="1"/> | ||
99 | -<setting id="org.eclipse.jdt.core.formatter.wrap_outer_expressions_when_nested" value="true"/> | ||
100 | -<setting id="org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line" value="false"/> | ||
101 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for" value="insert"/> | ||
102 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast" value="do not insert"/> | ||
103 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration" value="16"/> | ||
104 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement" value="insert"/> | ||
105 | -<setting id="org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration" value="end_of_line"/> | ||
106 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_method_body" value="insert"/> | ||
107 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_method_declaration" value="0"/> | ||
108 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation" value="do not insert"/> | ||
109 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_try" value="do not insert"/> | ||
110 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression" value="do not insert"/> | ||
111 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant" value="insert"/> | ||
112 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation" value="do not insert"/> | ||
113 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration" value="do not insert"/> | ||
114 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws" value="do not insert"/> | ||
115 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if" value="do not insert"/> | ||
116 | -<setting id="org.eclipse.jdt.core.formatter.brace_position_for_switch" value="end_of_line"/> | ||
117 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws" value="insert"/> | ||
118 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return" value="insert"/> | 40 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return" value="insert"/> |
41 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration" value="32"/> | ||
42 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter" value="do not insert"/> | ||
43 | +<setting id="org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line" value="false"/> | ||
44 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_field" value="insert"/> | ||
45 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments" value="insert"/> | ||
46 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_block" value="insert"/> | ||
47 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator" value="do not insert"/> | ||
48 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations" value="1"/> | ||
49 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer" value="insert"/> | ||
50 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for" value="do not insert"/> | ||
51 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch" value="do not insert"/> | ||
52 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments" value="do not insert"/> | ||
53 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_method" value="insert"/> | ||
54 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch" value="do not insert"/> | ||
55 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration" value="insert"/> | ||
56 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression" value="do not insert"/> | ||
57 | +<setting id="org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column" value="false"/> | ||
58 | +<setting id="org.eclipse.jdt.core.compiler.problem.enumIdentifier" value="error"/> | ||
59 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter" value="insert"/> | ||
60 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits" value="insert"/> | ||
61 | +<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_block" value="true"/> | ||
62 | +<setting id="org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration" value="end_of_line"/> | ||
63 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard" value="do not insert"/> | ||
119 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation" value="do not insert"/> | 64 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation" value="do not insert"/> |
120 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional" value="insert"/> | 65 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments" value="do not insert"/> |
121 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard" value="do not insert"/> | 66 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch" value="insert"/> |
122 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_try" value="do not insert"/> | 67 | +<setting id="org.eclipse.jdt.core.formatter.comment.line_length" value="80"/> |
123 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression" value="do not insert"/> | 68 | +<setting id="org.eclipse.jdt.core.formatter.use_on_off_tags" value="true"/> |
69 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression" value="do not insert"/> | ||
70 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant" value="insert"/> | ||
71 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation" value="do not insert"/> | ||
72 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator" value="insert"/> | ||
73 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration" value="insert"/> | ||
74 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for" value="do not insert"/> | ||
124 | <setting id="org.eclipse.jdt.core.formatter.comment.preserve_white_space_between_code_and_line_comments" value="false"/> | 75 | <setting id="org.eclipse.jdt.core.formatter.comment.preserve_white_space_between_code_and_line_comments" value="false"/> |
125 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw" value="insert"/> | 76 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable" value="insert"/> |
126 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments" value="do not insert"/> | ||
127 | -<setting id="org.eclipse.jdt.core.compiler.problem.enumIdentifier" value="error"/> | ||
128 | -<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch" value="false"/> | ||
129 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_ellipsis" value="do not insert"/> | ||
130 | -<setting id="org.eclipse.jdt.core.formatter.brace_position_for_block" value="end_of_line"/> | ||
131 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits" value="do not insert"/> | ||
132 | <setting id="org.eclipse.jdt.core.formatter.brace_position_for_method_declaration" value="end_of_line"/> | 77 | <setting id="org.eclipse.jdt.core.formatter.brace_position_for_method_declaration" value="end_of_line"/> |
133 | -<setting id="org.eclipse.jdt.core.formatter.compact_else_if" value="true"/> | 78 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation" value="do not insert"/> |
134 | -<setting id="org.eclipse.jdt.core.formatter.wrap_before_or_operator_multicatch" value="true"/> | ||
135 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer" value="do not insert"/> | ||
136 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments" value="insert"/> | ||
137 | -<setting id="org.eclipse.jdt.core.formatter.format_line_comment_starting_on_first_column" value="true"/> | ||
138 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference" value="do not insert"/> | ||
139 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_field" value="insert"/> | ||
140 | -<setting id="org.eclipse.jdt.core.formatter.comment.indent_root_tags" value="true"/> | ||
141 | -<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_constant" value="end_of_line"/> | ||
142 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations" value="do not insert"/> | ||
143 | <setting id="org.eclipse.jdt.core.formatter.alignment_for_union_type_in_multicatch" value="16"/> | 79 | <setting id="org.eclipse.jdt.core.formatter.alignment_for_union_type_in_multicatch" value="16"/> |
144 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments" value="insert"/> | 80 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for" value="insert"/> |
145 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch" value="insert"/> | 81 | +<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body" value="0"/> |
146 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters" value="do not insert"/> | 82 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments" value="insert"/> |
83 | +<setting id="org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line" value="false"/> | ||
84 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_binary_expression" value="16"/> | ||
85 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference" value="insert"/> | ||
86 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer" value="do not insert"/> | ||
87 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations" value="insert"/> | ||
88 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation" value="do not insert"/> | ||
89 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call" value="18"/> | ||
90 | +<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header" value="true"/> | ||
147 | <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces" value="insert"/> | 91 | <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces" value="insert"/> |
148 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression" value="do not insert"/> | 92 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default" value="do not insert"/> |
149 | -<setting id="org.eclipse.jdt.core.formatter.tabulation.size" value="4"/> | 93 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional" value="insert"/> |
150 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference" value="do not insert"/> | 94 | +<setting id="org.eclipse.jdt.core.formatter.brace_position_for_block" value="end_of_line"/> |
151 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer" value="do not insert"/> | 95 | +<setting id="org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration" value="end_of_line"/> |
152 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block" value="insert"/> | 96 | +<setting id="org.eclipse.jdt.core.formatter.brace_position_for_lambda_body" value="end_of_line"/> |
153 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference" value="do not insert"/> | 97 | +<setting id="org.eclipse.jdt.core.formatter.compact_else_if" value="true"/> |
154 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_constant" value="insert"/> | 98 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters" value="do not insert"/> |
155 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments" value="do not insert"/> | 99 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch" value="insert"/> |
156 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration" value="do not insert"/> | 100 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation" value="do not insert"/> |
157 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws" value="do not insert"/> | 101 | +<setting id="org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line" value="true"/> |
158 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if" value="do not insert"/> | 102 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration" value="18"/> |
159 | -<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment" value="false"/> | 103 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments" value="insert"/> |
104 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation" value="18"/> | ||
160 | <setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration" value="32"/> | 105 | <setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration" value="32"/> |
161 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator" value="insert"/> | 106 | +<setting id="org.eclipse.jdt.core.compiler.problem.assertIdentifier" value="error"/> |
162 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator" value="insert"/> | 107 | +<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment" value="false"/> |
163 | -<setting id="org.eclipse.jdt.core.formatter.indent_empty_lines" value="false"/> | 108 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement" value="do not insert"/> |
164 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized" value="do not insert"/> | 109 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_try" value="insert"/> |
165 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast" value="insert"/> | 110 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing" value="insert"/> |
166 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters" value="insert"/> | 111 | +<setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment" value="false"/> |
112 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer" value="insert"/> | ||
113 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_binary_operator" value="insert"/> | ||
114 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_unary_operator" value="do not insert"/> | ||
115 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer" value="18"/> | ||
116 | +<setting id="org.eclipse.jdt.core.formatter.format_line_comment_starting_on_first_column" value="true"/> | ||
117 | +<setting id="org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve" value="1"/> | ||
118 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case" value="insert"/> | ||
119 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_ellipsis" value="do not insert"/> | ||
120 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_try_resources" value="do not insert"/> | ||
121 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert" value="insert"/> | ||
122 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if" value="do not insert"/> | ||
123 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments" value="do not insert"/> | ||
124 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter" value="insert"/> | ||
125 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_type_declaration" value="insert"/> | ||
126 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression" value="do not insert"/> | ||
127 | +<setting id="org.eclipse.jdt.core.formatter.comment.format_line_comments" value="true"/> | ||
128 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement" value="insert"/> | ||
129 | +<setting id="org.eclipse.jdt.core.formatter.align_type_members_on_columns" value="false"/> | ||
130 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_assignment" value="0"/> | ||
131 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_method_body" value="insert"/> | ||
132 | +<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header" value="true"/> | ||
133 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration" value="do not insert"/> | ||
134 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant" value="do not insert"/> | ||
135 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration" value="32"/> | ||
136 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration" value="0"/> | ||
137 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_conditional_expression" value="82"/> | ||
138 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer" value="do not insert"/> | ||
139 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters" value="do not insert"/> | ||
140 | +<setting id="org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line" value="false"/> | ||
141 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if" value="insert"/> | ||
142 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_type" value="insert"/> | ||
143 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block" value="insert"/> | ||
144 | +<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration" value="end_of_line"/> | ||
167 | <setting id="org.eclipse.jdt.core.formatter.brace_position_for_block_in_case" value="end_of_line"/> | 145 | <setting id="org.eclipse.jdt.core.formatter.brace_position_for_block_in_case" value="end_of_line"/> |
168 | -<setting id="org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve" value="1"/> | ||
169 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration" value="do not insert"/> | ||
170 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch" value="do not insert"/> | ||
171 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration" value="do not insert"/> | 146 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration" value="do not insert"/> |
172 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation" value="do not insert"/> | 147 | +<setting id="org.eclipse.jdt.core.formatter.comment.format_header" value="false"/> |
148 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression" value="18"/> | ||
149 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation" value="do not insert"/> | ||
150 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while" value="insert"/> | ||
151 | +<setting id="org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode" value="enabled"/> | ||
152 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch" value="do not insert"/> | ||
153 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_method_declaration" value="0"/> | ||
154 | +<setting id="org.eclipse.jdt.core.formatter.join_wrapped_lines" value="true"/> | ||
155 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration" value="do not insert"/> | ||
156 | +<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases" value="true"/> | ||
157 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression" value="do not insert"/> | ||
158 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized" value="do not insert"/> | ||
159 | +<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_javadoc_boundaries" value="true"/> | ||
160 | +<setting id="org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration" value="end_of_line"/> | ||
161 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for" value="insert"/> | ||
162 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_resources_in_try" value="80"/> | ||
163 | +<setting id="org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations" value="false"/> | ||
164 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation" value="16"/> | ||
165 | +<setting id="org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column" value="false"/> | ||
166 | +<setting id="org.eclipse.jdt.core.compiler.source" value="1.8"/> | ||
167 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized" value="do not insert"/> | ||
168 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws" value="insert"/> | ||
169 | +<setting id="org.eclipse.jdt.core.formatter.tabulation.size" value="4"/> | ||
170 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_constant" value="insert"/> | ||
171 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression" value="insert"/> | ||
173 | <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference" value="do not insert"/> | 172 | <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference" value="do not insert"/> |
174 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression" value="18"/> | 173 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional" value="insert"/> |
175 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter" value="insert"/> | 174 | +<setting id="org.eclipse.jdt.core.formatter.comment.format_source_code" value="true"/> |
176 | -<setting id="org.eclipse.jdt.core.compiler.compliance" value="1.8"/> | 175 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer" value="insert"/> |
176 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_try" value="do not insert"/> | ||
177 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_try_resources" value="insert"/> | ||
178 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_field" value="0"/> | ||
179 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation" value="do not insert"/> | ||
177 | <setting id="org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer" value="2"/> | 180 | <setting id="org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer" value="2"/> |
178 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression" value="do not insert"/> | 181 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard" value="do not insert"/> |
179 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration" value="insert"/> | 182 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_method" value="1"/> |
180 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression" value="18"/> | 183 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration" value="32"/> |
181 | -<setting id="org.eclipse.jdt.core.formatter.brace_position_for_lambda_body" value="end_of_line"/> | 184 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration" value="32"/> |
182 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast" value="do not insert"/> | 185 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw" value="insert"/> |
183 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_unary_operator" value="do not insert"/> | 186 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement" value="do not insert"/> |
184 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference" value="do not insert"/> | 187 | +<setting id="org.eclipse.jdt.core.compiler.codegen.targetPlatform" value="1.8"/> |
185 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration" value="insert"/> | 188 | +<setting id="org.eclipse.jdt.core.formatter.brace_position_for_switch" value="end_of_line"/> |
186 | -<setting id="org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line" value="false"/> | 189 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces" value="do not insert"/> |
187 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_declaration" value="insert"/> | 190 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters" value="insert"/> |
188 | <setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_type_annotation" value="do not insert"/> | 191 | <setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_type_annotation" value="do not insert"/> |
189 | -<setting id="org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line" value="false"/> | 192 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer" value="insert"/> |
190 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters" value="do not insert"/> | 193 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression" value="do not insert"/> |
194 | +<setting id="org.eclipse.jdt.core.formatter.comment.format_html" value="true"/> | ||
195 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration" value="do not insert"/> | ||
191 | <setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters" value="insert"/> | 196 | <setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters" value="insert"/> |
192 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement" value="do not insert"/> | 197 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_compact_if" value="16"/> |
193 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing" value="insert"/> | 198 | +<setting id="org.eclipse.jdt.core.formatter.indent_empty_lines" value="false"/> |
194 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for" value="insert"/> | ||
195 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference" value="do not insert"/> | 199 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference" value="do not insert"/> |
196 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration" value="32"/> | 200 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_unary_operator" value="do not insert"/> |
197 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_binary_expression" value="16"/> | 201 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant" value="do not insert"/> |
198 | -<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration" value="end_of_line"/> | 202 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_annotation" value="0"/> |
199 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_type" value="insert"/> | 203 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations" value="do not insert"/> |
200 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while" value="do not insert"/> | 204 | +<setting id="org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line" value="false"/> |
201 | -<setting id="org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode" value="enabled"/> | 205 | +<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch" value="false"/> |
202 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_try" value="insert"/> | 206 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement" value="do not insert"/> |
203 | -<setting id="org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line" value="true"/> | 207 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator" value="insert"/> |
208 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration" value="do not insert"/> | ||
209 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk" value="1"/> | ||
204 | <setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_label" value="do not insert"/> | 210 | <setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_label" value="do not insert"/> |
205 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter" value="do not insert"/> | 211 | +<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header" value="true"/> |
206 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters" value="do not insert"/> | 212 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression" value="do not insert"/> |
207 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation" value="do not insert"/> | 213 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration" value="do not insert"/> |
214 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional" value="insert"/> | ||
215 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/> | ||
216 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters" value="do not insert"/> | ||
217 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments" value="do not insert"/> | ||
218 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast" value="do not insert"/> | ||
219 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert" value="insert"/> | ||
220 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_member_type" value="1"/> | ||
208 | <setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement" value="do not insert"/> | 221 | <setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement" value="do not insert"/> |
209 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant" value="0"/> | 222 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference" value="do not insert"/> |
210 | -<setting id="org.eclipse.jdt.core.formatter.comment.format_javadoc_comments" value="true"/> | 223 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference" value="do not insert"/> |
211 | -<setting id="org.eclipse.jdt.core.formatter.comment.line_length" value="80"/> | 224 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression" value="18"/> |
212 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_package" value="insert"/> | 225 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer" value="do not insert"/> |
213 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_import_groups" value="1"/> | 226 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_declaration" value="insert"/> |
214 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments" value="do not insert"/> | 227 | +<setting id="org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases" value="true"/> |
228 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration" value="do not insert"/> | ||
229 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if" value="do not insert"/> | ||
215 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon" value="do not insert"/> | 230 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon" value="do not insert"/> |
216 | -<setting id="org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration" value="end_of_line"/> | ||
217 | -<setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body" value="0"/> | ||
218 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional" value="insert"/> | ||
219 | -<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header" value="true"/> | ||
220 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration" value="do not insert"/> | ||
221 | -<setting id="org.eclipse.jdt.core.formatter.wrap_before_binary_operator" value="true"/> | ||
222 | -<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header" value="true"/> | ||
223 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations" value="1"/> | ||
224 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized" value="do not insert"/> | ||
225 | -<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_block" value="true"/> | ||
226 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration" value="32"/> | ||
227 | -<setting id="org.eclipse.jdt.core.formatter.join_lines_in_comments" value="true"/> | ||
228 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional" value="insert"/> | ||
229 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations" value="do not insert"/> | ||
230 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_compact_if" value="16"/> | ||
231 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits" value="insert"/> | ||
232 | -<setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases" value="true"/> | ||
233 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer" value="insert"/> | ||
234 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default" value="do not insert"/> | ||
235 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter" value="insert"/> | ||
236 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration" value="do not insert"/> | ||
237 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_imports" value="1"/> | ||
238 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert" value="insert"/> | ||
239 | -<setting id="org.eclipse.jdt.core.formatter.comment.format_html" value="true"/> | ||
240 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration" value="32"/> | ||
241 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters" value="do not insert"/> | ||
242 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression" value="do not insert"/> | ||
243 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_anonymous_type_declaration" value="insert"/> | ||
244 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional" value="insert"/> | ||
245 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/> | ||
246 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for" value="do not insert"/> | ||
247 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator" value="do not insert"/> | 231 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator" value="do not insert"/> |
248 | -<setting id="org.eclipse.jdt.core.formatter.comment.format_source_code" value="true"/> | 232 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_try" value="do not insert"/> |
249 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized" value="insert"/> | 233 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments" value="do not insert"/> |
250 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression" value="insert"/> | 234 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast" value="do not insert"/> |
251 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws" value="insert"/> | ||
252 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration" value="18"/> | ||
253 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer" value="insert"/> | ||
254 | -<setting id="org.eclipse.jdt.core.compiler.codegen.targetPlatform" value="1.8"/> | ||
255 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_resources_in_try" value="80"/> | ||
256 | -<setting id="org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations" value="false"/> | ||
257 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_annotation" value="0"/> | ||
258 | -<setting id="org.eclipse.jdt.core.formatter.comment.format_header" value="false"/> | ||
259 | <setting id="org.eclipse.jdt.core.formatter.comment.format_block_comments" value="true"/> | 235 | <setting id="org.eclipse.jdt.core.formatter.comment.format_block_comments" value="true"/> |
260 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant" value="do not insert"/> | ||
261 | -<setting id="org.eclipse.jdt.core.formatter.alignment_for_enum_constants" value="16"/> | ||
262 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_lambda_arrow" value="insert"/> | 236 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_lambda_arrow" value="insert"/> |
263 | -<setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_block" value="insert"/> | 237 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration" value="do not insert"/> |
264 | -<setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header" value="true"/> | 238 | +<setting id="org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line" value="false"/> |
265 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression" value="do not insert"/> | 239 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration" value="insert"/> |
266 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression" value="do not insert"/> | 240 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration" value="18"/> |
241 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference" value="do not insert"/> | ||
242 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters" value="do not insert"/> | ||
243 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for" value="do not insert"/> | ||
244 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws" value="insert"/> | ||
245 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression" value="do not insert"/> | ||
246 | +<setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_body" value="true"/> | ||
247 | +<setting id="org.eclipse.jdt.core.formatter.alignment_for_multiple_fields" value="16"/> | ||
248 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments" value="insert"/> | ||
249 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator" value="do not insert"/> | ||
250 | +<setting id="org.eclipse.jdt.core.formatter.brace_position_for_array_initializer" value="end_of_line"/> | ||
251 | +<setting id="org.eclipse.jdt.core.formatter.wrap_before_binary_operator" value="true"/> | ||
252 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration" value="insert"/> | ||
253 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters" value="insert"/> | ||
267 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch" value="do not insert"/> | 254 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch" value="do not insert"/> |
255 | +<setting id="org.eclipse.jdt.core.compiler.compliance" value="1.8"/> | ||
256 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference" value="do not insert"/> | ||
257 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation" value="insert"/> | ||
258 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments" value="do not insert"/> | ||
259 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer" value="do not insert"/> | ||
260 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case" value="do not insert"/> | ||
268 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations" value="do not insert"/> | 261 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations" value="do not insert"/> |
269 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch" value="insert"/> | 262 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration" value="insert"/> |
270 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments" value="do not insert"/> | 263 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference" value="do not insert"/> |
271 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation" value="do not insert"/> | 264 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration" value="do not insert"/> |
272 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert" value="insert"/> | 265 | +<setting id="org.eclipse.jdt.core.formatter.wrap_outer_expressions_when_nested" value="true"/> |
266 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast" value="insert"/> | ||
267 | +<setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_constant" value="end_of_line"/> | ||
273 | <setting id="org.eclipse.jdt.core.formatter.brace_position_for_type_declaration" value="end_of_line"/> | 268 | <setting id="org.eclipse.jdt.core.formatter.brace_position_for_type_declaration" value="end_of_line"/> |
274 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer" value="insert"/> | 269 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_before_package" value="0"/> |
275 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer" value="do not insert"/> | 270 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for" value="insert"/> |
276 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration" value="do not insert"/> | 271 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized" value="insert"/> |
277 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for" value="do not insert"/> | 272 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments" value="do not insert"/> |
278 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch" value="insert"/> | 273 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration" value="do not insert"/> |
279 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/> | 274 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while" value="do not insert"/> |
280 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations" value="insert"/> | 275 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant" value="do not insert"/> |
276 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments" value="do not insert"/> | ||
281 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation" value="do not insert"/> | 277 | <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation" value="do not insert"/> |
282 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference" value="insert"/> | 278 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters" value="do not insert"/> |
283 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments" value="insert"/> | ||
284 | -<setting id="org.eclipse.jdt.core.formatter.comment.new_lines_at_javadoc_boundaries" value="true"/> | ||
285 | -<setting id="org.eclipse.jdt.core.formatter.blank_lines_after_imports" value="1"/> | ||
286 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations" value="insert"/> | ||
287 | <setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header" value="true"/> | 279 | <setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header" value="true"/> |
288 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for" value="insert"/> | 280 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_lambda_arrow" value="insert"/> |
289 | -<setting id="org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column" value="false"/> | 281 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration" value="insert"/> |
290 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_try_resources" value="do not insert"/> | 282 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws" value="do not insert"/> |
291 | -<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments" value="do not insert"/> | 283 | +<setting id="org.eclipse.jdt.core.formatter.join_lines_in_comments" value="true"/> |
292 | -<setting id="org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column" value="false"/> | 284 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters" value="do not insert"/> |
293 | -<setting id="org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line" value="false"/> | 285 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional" value="insert"/> |
286 | +<setting id="org.eclipse.jdt.core.formatter.comment.indent_parameter_description" value="true"/> | ||
287 | +<setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement" value="do not insert"/> | ||
288 | +<setting id="org.eclipse.jdt.core.formatter.tabulation.char" value="space"/> | ||
289 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations" value="do not insert"/> | ||
290 | +<setting id="org.eclipse.jdt.core.formatter.blank_lines_between_import_groups" value="1"/> | ||
291 | +<setting id="org.eclipse.jdt.core.formatter.lineSplit" value="80"/> | ||
292 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation" value="do not insert"/> | ||
293 | +<setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch" value="insert"/> | ||
294 | </profile> | 294 | </profile> |
295 | </profiles> | 295 | </profiles> | ... | ... |
... | @@ -15,7 +15,7 @@ | ... | @@ -15,7 +15,7 @@ |
15 | */ | 15 | */ |
16 | 16 | ||
17 | /* | 17 | /* |
18 | - ONOS GUI -- Masthead | 18 | + ONOS GUI -- Masthead script |
19 | 19 | ||
20 | Defines the masthead for the UI. Injects logo and title, as well as providing | 20 | Defines the masthead for the UI. Injects logo and title, as well as providing |
21 | the placeholder for a set of radio buttons. | 21 | the placeholder for a set of radio buttons. |
... | @@ -53,4 +53,4 @@ | ... | @@ -53,4 +53,4 @@ |
53 | class: 'right' | 53 | class: 'right' |
54 | }); | 54 | }); |
55 | 55 | ||
56 | -}(ONOS)); | ||
... | \ No newline at end of file | ... | \ No newline at end of file |
56 | +}(ONOS)); | ... | ... |
... | @@ -407,7 +407,8 @@ | ... | @@ -407,7 +407,8 @@ |
407 | height: this.height, | 407 | height: this.height, |
408 | uid: this.uid, | 408 | uid: this.uid, |
409 | setRadio: this.setRadio, | 409 | setRadio: this.setRadio, |
410 | - setKeys: this.setKeys | 410 | + setKeys: this.setKeys, |
411 | + dataLoadError: this.dataLoadError | ||
411 | } | 412 | } |
412 | }, | 413 | }, |
413 | 414 | ||
... | @@ -498,6 +499,16 @@ | ... | @@ -498,6 +499,16 @@ |
498 | 499 | ||
499 | uid: function (id) { | 500 | uid: function (id) { |
500 | return makeUid(this, id); | 501 | return makeUid(this, id); |
502 | + }, | ||
503 | + | ||
504 | + // TODO : implement custom dialogs (don't use alerts) | ||
505 | + | ||
506 | + dataLoadError: function (err, url) { | ||
507 | + var msg = 'Data Load Error\n\n' + | ||
508 | + err.status + ' -- ' + err.statusText + '\n\n' + | ||
509 | + 'relative-url: "' + url + '"\n\n' + | ||
510 | + 'complete-url: "' + err.responseURL + '"'; | ||
511 | + alert(msg); | ||
501 | } | 512 | } |
502 | 513 | ||
503 | // TODO: consider schedule, clearTimer, etc. | 514 | // TODO: consider schedule, clearTimer, etc. | ... | ... |
... | @@ -25,7 +25,7 @@ | ... | @@ -25,7 +25,7 @@ |
25 | 25 | ||
26 | // configuration data | 26 | // configuration data |
27 | var config = { | 27 | var config = { |
28 | - useLiveData: false, | 28 | + useLiveData: true, |
29 | debugOn: false, | 29 | debugOn: false, |
30 | debug: { | 30 | debug: { |
31 | showNodeXY: false, | 31 | showNodeXY: false, |
... | @@ -56,12 +56,24 @@ | ... | @@ -56,12 +56,24 @@ |
56 | opt: 'img/opt.png' | 56 | opt: 'img/opt.png' |
57 | }, | 57 | }, |
58 | force: { | 58 | force: { |
59 | - marginLR: 20, | 59 | + note: 'node.class or link.class is used to differentiate', |
60 | - marginTB: 20, | 60 | + linkDistance: { |
61 | + infra: 200, | ||
62 | + host: 40 | ||
63 | + }, | ||
64 | + linkStrength: { | ||
65 | + infra: 1.0, | ||
66 | + host: 1.0 | ||
67 | + }, | ||
68 | + charge: { | ||
69 | + device: -400, | ||
70 | + host: -100 | ||
71 | + }, | ||
72 | + pad: 20, | ||
61 | translate: function() { | 73 | translate: function() { |
62 | return 'translate(' + | 74 | return 'translate(' + |
63 | - config.force.marginLR + ',' + | 75 | + config.force.pad + ',' + |
64 | - config.force.marginTB + ')'; | 76 | + config.force.pad + ')'; |
65 | } | 77 | } |
66 | } | 78 | } |
67 | }; | 79 | }; |
... | @@ -94,7 +106,11 @@ | ... | @@ -94,7 +106,11 @@ |
94 | // D3 selections | 106 | // D3 selections |
95 | var svg, | 107 | var svg, |
96 | bgImg, | 108 | bgImg, |
97 | - topoG; | 109 | + topoG, |
110 | + nodeG, | ||
111 | + linkG, | ||
112 | + node, | ||
113 | + link; | ||
98 | 114 | ||
99 | // ============================== | 115 | // ============================== |
100 | // For Debugging / Development | 116 | // For Debugging / Development |
... | @@ -175,23 +191,146 @@ | ... | @@ -175,23 +191,146 @@ |
175 | // ============================== | 191 | // ============================== |
176 | // Private functions | 192 | // Private functions |
177 | 193 | ||
178 | - // set the size of the given element to that of the view | 194 | + // set the size of the given element to that of the view (reduced if padded) |
179 | - function setSize(el, view) { | 195 | + function setSize(el, view, pad) { |
196 | + var padding = pad ? pad * 2 : 0; | ||
180 | el.attr({ | 197 | el.attr({ |
181 | - width: view.width(), | 198 | + width: view.width() - padding, |
182 | - height: view.height() | 199 | + height: view.height() - padding |
183 | }); | 200 | }); |
184 | } | 201 | } |
185 | 202 | ||
186 | - | ||
187 | function getNetworkData(view) { | 203 | function getNetworkData(view) { |
188 | var url = getTopoUrl(); | 204 | var url = getTopoUrl(); |
189 | 205 | ||
190 | - // TODO ... | 206 | + console.log('Fetching JSON: ' + url); |
207 | + d3.json(url, function(err, data) { | ||
208 | + if (err) { | ||
209 | + view.dataLoadError(err, url); | ||
210 | + } else { | ||
211 | + network.data = data; | ||
212 | + drawNetwork(view); | ||
213 | + } | ||
214 | + }); | ||
215 | + } | ||
216 | + | ||
217 | + function drawNetwork(view) { | ||
218 | + preprocessData(view); | ||
219 | + updateLayout(view); | ||
220 | + } | ||
221 | + | ||
222 | + function preprocessData(view) { | ||
223 | + var w = view.width(), | ||
224 | + h = view.height(), | ||
225 | + hDevice = h * 0.6, | ||
226 | + hHost = h * 0.3, | ||
227 | + data = network.data, | ||
228 | + deviceLayout = computeInitLayout(w, hDevice, data.devices.length), | ||
229 | + hostLayout = computeInitLayout(w, hHost, data.hosts.length); | ||
230 | + | ||
231 | + network.lookup = {}; | ||
232 | + network.nodes = []; | ||
233 | + network.links = []; | ||
234 | + // we created new arrays, so need to set the refs in the force layout | ||
235 | + network.force.nodes(network.nodes); | ||
236 | + network.force.links(network.links); | ||
237 | + | ||
238 | + // let's just start with the nodes | ||
239 | + | ||
240 | + // note that both 'devices' and 'hosts' get mapped into the nodes array | ||
241 | + function makeNode(d, cls, layout) { | ||
242 | + var node = { | ||
243 | + id: d.id, | ||
244 | + labels: d.labels, | ||
245 | + class: cls, | ||
246 | + icon: cls, | ||
247 | + type: d.type, | ||
248 | + x: layout.x(), | ||
249 | + y: layout.y() | ||
250 | + }; | ||
251 | + network.lookup[d.id] = node; | ||
252 | + network.nodes.push(node); | ||
253 | + } | ||
254 | + | ||
255 | + // first the devices... | ||
256 | + network.data.devices.forEach(function (d) { | ||
257 | + makeNode(d, 'device', deviceLayout); | ||
258 | + }); | ||
259 | + | ||
260 | + // then the hosts... | ||
261 | + network.data.hosts.forEach(function (d) { | ||
262 | + makeNode(d, 'host', hostLayout); | ||
263 | + }); | ||
264 | + | ||
265 | + // TODO: process links | ||
266 | + } | ||
267 | + | ||
268 | + function computeInitLayout(w, h, n) { | ||
269 | + var maxdw = 60, | ||
270 | + compdw, dw, ox, layout; | ||
271 | + | ||
272 | + if (n < 2) { | ||
273 | + layout = { ox: w/2, dw: 0 } | ||
274 | + } else { | ||
275 | + compdw = (0.8 * w) / (n - 1); | ||
276 | + dw = Math.min(maxdw, compdw); | ||
277 | + ox = w/2 - ((n - 1)/2 * dw); | ||
278 | + layout = { ox: ox, dw: dw } | ||
279 | + } | ||
280 | + | ||
281 | + layout.i = 0; | ||
282 | + | ||
283 | + layout.x = function () { | ||
284 | + var x = layout.ox + layout.i*layout.dw; | ||
285 | + layout.i++; | ||
286 | + return x; | ||
287 | + }; | ||
288 | + | ||
289 | + layout.y = function () { | ||
290 | + return h; | ||
291 | + }; | ||
292 | + | ||
293 | + return layout; | ||
294 | + } | ||
295 | + | ||
296 | + function linkId(d) { | ||
297 | + return d.source.id + '~' + d.target.id; | ||
298 | + } | ||
299 | + | ||
300 | + function nodeId(d) { | ||
301 | + return d.id; | ||
302 | + } | ||
191 | 303 | ||
304 | + function updateLayout(view) { | ||
305 | + link = link.data(network.force.links(), linkId); | ||
306 | + link.enter().append('line') | ||
307 | + .attr('class', 'link'); | ||
308 | + link.exit().remove(); | ||
309 | + | ||
310 | + node = node.data(network.force.nodes(), nodeId); | ||
311 | + node.enter().append('circle') | ||
312 | + .attr('id', function (d) { return 'nodeId-' + d.id; }) | ||
313 | + .attr('class', function (d) { return 'node'; }) | ||
314 | + .attr('r', 12); | ||
315 | + | ||
316 | + network.force.start(); | ||
192 | } | 317 | } |
193 | 318 | ||
194 | 319 | ||
320 | + function tick() { | ||
321 | + node.attr({ | ||
322 | + cx: function(d) { return d.x; }, | ||
323 | + cy: function(d) { return d.y; } | ||
324 | + }); | ||
325 | + | ||
326 | + link.attr({ | ||
327 | + x1: function (d) { return d.source.x; }, | ||
328 | + y1: function (d) { return d.source.y; }, | ||
329 | + x2: function (d) { return d.target.x; }, | ||
330 | + y2: function (d) { return d.target.y; } | ||
331 | + }); | ||
332 | + } | ||
333 | + | ||
195 | // ============================== | 334 | // ============================== |
196 | // View life-cycle callbacks | 335 | // View life-cycle callbacks |
197 | 336 | ||
... | @@ -199,15 +338,15 @@ | ... | @@ -199,15 +338,15 @@ |
199 | var w = view.width(), | 338 | var w = view.width(), |
200 | h = view.height(), | 339 | h = view.height(), |
201 | idBg = view.uid('bg'), | 340 | idBg = view.uid('bg'), |
202 | - showBg = config.options.showBackground ? 'visible' : 'hidden'; | 341 | + showBg = config.options.showBackground ? 'visible' : 'hidden', |
342 | + fcfg = config.force, | ||
343 | + fpad = fcfg.pad, | ||
344 | + forceDim = [w - 2*fpad, h - 2*fpad]; | ||
203 | 345 | ||
204 | // NOTE: view.$div is a D3 selection of the view's div | 346 | // NOTE: view.$div is a D3 selection of the view's div |
205 | svg = view.$div.append('svg'); | 347 | svg = view.$div.append('svg'); |
206 | setSize(svg, view); | 348 | setSize(svg, view); |
207 | 349 | ||
208 | - topoG = svg.append('g') | ||
209 | - .attr('transform', config.force.translate()); | ||
210 | - | ||
211 | // load the background image | 350 | // load the background image |
212 | bgImg = svg.append('svg:image') | 351 | bgImg = svg.append('svg:image') |
213 | .attr({ | 352 | .attr({ |
... | @@ -219,6 +358,28 @@ | ... | @@ -219,6 +358,28 @@ |
219 | .style({ | 358 | .style({ |
220 | visibility: showBg | 359 | visibility: showBg |
221 | }); | 360 | }); |
361 | + | ||
362 | + // group for the topology | ||
363 | + topoG = svg.append('g') | ||
364 | + .attr('transform', fcfg.translate()); | ||
365 | + | ||
366 | + // subgroups for links and nodes | ||
367 | + linkG = topoG.append('g').attr('id', 'links'); | ||
368 | + nodeG = topoG.append('g').attr('id', 'nodes'); | ||
369 | + | ||
370 | + // selection of nodes and links | ||
371 | + link = linkG.selectAll('.link'); | ||
372 | + node = nodeG.selectAll('.node'); | ||
373 | + | ||
374 | + // set up the force layout | ||
375 | + network.force = d3.layout.force() | ||
376 | + .size(forceDim) | ||
377 | + .nodes(network.nodes) | ||
378 | + .links(network.links) | ||
379 | + .charge(function (d) { return fcfg.charge[d.class]; }) | ||
380 | + .linkDistance(function (d) { return fcfg.linkDistance[d.class]; }) | ||
381 | + .linkStrength(function (d) { return fcfg.linkStrength[d.class]; }) | ||
382 | + .on('tick', tick); | ||
222 | } | 383 | } |
223 | 384 | ||
224 | 385 | ... | ... |
-
Please register or login to post a comment