From dccb0ca2d7f806e46dc6f684ee9a821f778aaa95 Mon Sep 17 00:00:00 2001 From: Patrik Nordwall Date: Tue, 19 Jun 2012 16:00:45 +0200 Subject: [PATCH] Avoid gossip merge when singleton cluster, see #2250 --- .../src/main/scala/akka/cluster/Cluster.scala | 6 +- .../scala/akka/cluster/SunnyWeatherSpec.scala | 4 +- .../scala/akka/cluster/TransitionSpec.scala | 67 +++++-------------- 3 files changed, 23 insertions(+), 54 deletions(-) diff --git a/akka-cluster/src/main/scala/akka/cluster/Cluster.scala b/akka-cluster/src/main/scala/akka/cluster/Cluster.scala index d9496b3235..78015078f3 100644 --- a/akka-cluster/src/main/scala/akka/cluster/Cluster.scala +++ b/akka-cluster/src/main/scala/akka/cluster/Cluster.scala @@ -893,7 +893,11 @@ class Cluster(system: ExtendedActorSystem, val failureDetector: FailureDetector) val localGossip = localState.latestGossip val winningGossip = - if (remoteGossip.version <> localGossip.version) { + if (isSingletonCluster(localState) && localGossip.overview.unreachable.isEmpty && remoteGossip.members.contains(self)) { + // a fresh singleton cluster that is joining, no need to merge, use received gossip + remoteGossip + + } else if (remoteGossip.version <> localGossip.version) { // concurrent val mergedGossip = remoteGossip merge localGossip val versionedMergedGossip = mergedGossip :+ vclockNode diff --git a/akka-cluster/src/multi-jvm/scala/akka/cluster/SunnyWeatherSpec.scala b/akka-cluster/src/multi-jvm/scala/akka/cluster/SunnyWeatherSpec.scala index c283665b30..3c74bc02e2 100644 --- a/akka-cluster/src/multi-jvm/scala/akka/cluster/SunnyWeatherSpec.scala +++ b/akka-cluster/src/multi-jvm/scala/akka/cluster/SunnyWeatherSpec.scala @@ -19,11 +19,11 @@ object SunnyWeatherMultiJvmSpec extends MultiNodeConfig { val fourth = role("fourth") val fifth = role("fifth") + // Note that this test uses default configuration, + // not MultiNodeClusterSpec.clusterConfig commonConfig(ConfigFactory.parseString(""" akka.cluster { nr-of-deputy-nodes = 0 - # FIXME remove this (use default) when ticket #2239 has been fixed - gossip-interval = 400 ms } akka.loglevel = INFO """)) diff --git a/akka-cluster/src/multi-jvm/scala/akka/cluster/TransitionSpec.scala b/akka-cluster/src/multi-jvm/scala/akka/cluster/TransitionSpec.scala index 60594d145e..57b973390d 100644 --- a/akka-cluster/src/multi-jvm/scala/akka/cluster/TransitionSpec.scala +++ b/akka-cluster/src/multi-jvm/scala/akka/cluster/TransitionSpec.scala @@ -118,33 +118,18 @@ abstract class TransitionSpec awaitMembers(first, second) memberStatus(first) must be(Up) memberStatus(second) must be(Joining) + seenLatestGossip must be(Set(first)) cluster.convergence.isDefined must be(false) } enterBarrier("second-joined") first gossipTo second - runOn(second) { - members must be(Set(first, second)) - memberStatus(first) must be(Up) - memberStatus(second) must be(Joining) - // we got a conflicting version in second, and therefore not convergence in second - seenLatestGossip must be(Set(second)) - cluster.convergence.isDefined must be(false) - } - second gossipTo first - runOn(first) { - seenLatestGossip must be(Set(first, second)) - } - - first gossipTo second - runOn(second) { - seenLatestGossip must be(Set(first, second)) - } runOn(first, second) { memberStatus(first) must be(Up) memberStatus(second) must be(Joining) + seenLatestGossip must be(Set(first, second)) cluster.convergence.isDefined must be(true) } enterBarrier("convergence-joining-2") @@ -191,42 +176,20 @@ abstract class TransitionSpec second gossipTo first runOn(first) { members must be(Set(first, second, third)) - cluster.convergence.isDefined must be(false) memberStatus(third) must be(Joining) + seenLatestGossip must be(Set(first, second)) + cluster.convergence.isDefined must be(false) } first gossipTo third - runOn(third) { - members must be(Set(first, second, third)) - cluster.convergence.isDefined must be(false) - memberStatus(third) must be(Joining) - // conflicting version - seenLatestGossip must be(Set(third)) - } - third gossipTo first third gossipTo second - runOn(first, second) { - seenLatestGossip must be(Set(myself, third)) - } - - first gossipTo second - runOn(second) { - seenLatestGossip must be(Set(first, second, third)) - cluster.convergence.isDefined must be(true) - } - - runOn(first, third) { - cluster.convergence.isDefined must be(false) - } - - second gossipTo first - second gossipTo third runOn(first, second, third) { - seenLatestGossip must be(Set(first, second, third)) + members must be(Set(first, second, third)) memberStatus(first) must be(Up) memberStatus(second) must be(Up) memberStatus(third) must be(Joining) + seenLatestGossip must be(Set(first, second, third)) cluster.convergence.isDefined must be(true) } @@ -283,19 +246,21 @@ abstract class TransitionSpec "startup a second separated cluster consisting of nodes fourth and fifth" taggedAs LongRunningTest in { runOn(fourth) { cluster.join(fifth) - awaitMembers(fourth, fifth) - cluster.gossipTo(fifth) - awaitSeen(fourth, fifth) - cluster.convergence.isDefined must be(true) } runOn(fifth) { awaitMembers(fourth, fifth) - cluster.gossipTo(fourth) - awaitSeen(fourth, fifth) - cluster.gossipTo(fourth) + } + testConductor.enter("fourth-joined") + + fifth gossipTo fourth + fourth gossipTo fifth + + runOn(fourth, fifth) { + memberStatus(fourth) must be(Joining) + memberStatus(fifth) must be(Up) + seenLatestGossip must be(Set(fourth, fifth)) cluster.convergence.isDefined must be(true) } - enterBarrier("fourth-joined-fifth") enterBarrier("after-4") }