Skip to content

Commit

Permalink
Merge remote-tracking branch 'upstream/3.0' into 3.1
Browse files Browse the repository at this point in the history
  • Loading branch information
systay committed Mar 6, 2017
2 parents 760a2bb + bf1e789 commit 3e8c046
Show file tree
Hide file tree
Showing 2 changed files with 30 additions and 8 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,24 @@ import org.scalatest.matchers.{MatchResult, Matcher}

class MatchAggregationsBackedByCountStoreAcceptanceTest extends ExecutionEngineFunSuite with QueryStatisticsTestSupport with NewPlannerTestSupport {

test("do not plan counts store lookup for loop matches") {
val n = createNode()
// two loops
relate(n, n)
relate(n, n)
// one non-loop
relate(n, createNode())

val resultStar = executeWithAllPlannersAndCompatibilityMode("MATCH (a)-->(a) RETURN count(*)")
val resultVar = executeWithAllPlannersAndCompatibilityMode("MATCH (a)-[r]->(a) RETURN count(r)")

resultStar.toList should equal(List(Map("count(*)" -> 2)))
resultVar.toList should equal(List(Map("count(r)" -> 2)))

resultStar.executionPlanDescription() shouldNot includeOperation("RelationshipCountFromCountStore")
resultVar.executionPlanDescription() shouldNot includeOperation("RelationshipCountFromCountStore")
}

test("counts nodes using count store") {
// Given
withModel(
Expand All @@ -34,7 +52,7 @@ class MatchAggregationsBackedByCountStoreAcceptanceTest extends ExecutionEngineF
query = "MATCH (n) RETURN count(n)", f = { result =>

// Then
result.columnAs("count(n)").toSet[Int] should equal(Set(2))
result.columnAs("count(n)").toSet[Int] should equal(Set(3))

})
}
Expand All @@ -47,7 +65,7 @@ class MatchAggregationsBackedByCountStoreAcceptanceTest extends ExecutionEngineF
query = "MATCH (n) RETURN COUNT(n)", f = { result =>

// Then
result.columnAs("COUNT(n)").toSet[Int] should equal(Set(2))
result.columnAs("COUNT(n)").toSet[Int] should equal(Set(3))

})
}
Expand All @@ -60,7 +78,7 @@ class MatchAggregationsBackedByCountStoreAcceptanceTest extends ExecutionEngineF
query = "MATCH (n) RETURN count(*)", f = { result =>

// Then
result.columnAs("count(*)").toSet[Int] should equal(Set(2))
result.columnAs("count(*)").toSet[Int] should equal(Set(3))

})
}
Expand Down Expand Up @@ -96,10 +114,10 @@ class MatchAggregationsBackedByCountStoreAcceptanceTest extends ExecutionEngineF
withModel(

// When
query = "MATCH (n) RETURN count(n)/2*5 as someNum", f = { result =>
query = "MATCH (n) RETURN count(n)/2.0*5 as someNum", f = { result =>

// Then
result.columnAs("someNum").toSet[Int] should equal(Set(5))
result.columnAs("someNum").toSet[Int] should equal(Set(7.5))

})
}
Expand All @@ -112,7 +130,7 @@ class MatchAggregationsBackedByCountStoreAcceptanceTest extends ExecutionEngineF
query = "MATCH ()-[r]->() RETURN count(r)", f = { result =>

// Then
result.columnAs("count(r)").toSet[Int] should equal(Set(1))
result.columnAs("count(r)").toSet[Int] should equal(Set(2))

})
}
Expand All @@ -125,7 +143,7 @@ class MatchAggregationsBackedByCountStoreAcceptanceTest extends ExecutionEngineF
query = "MATCH ()-->() RETURN count(*)", f = { result =>

// Then
result.columnAs("count(*)").toSet[Int] should equal(Set(1))
result.columnAs("count(*)").toSet[Int] should equal(Set(2))

})
}
Expand Down Expand Up @@ -608,6 +626,7 @@ class MatchAggregationsBackedByCountStoreAcceptanceTest extends ExecutionEngineF
|CREATE (p:$label1 {name: 'Petra'})
|CREATE (s:$label2 {name: 'Steve'})
|CREATE (p)-[:$type1]->(s)
|CREATE (a)-[:LOOP]->(a)
""".stripMargin)

val result: InternalExecutionResult = executeWithAllPlannersAndCompatibilityMode(query)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -88,13 +88,16 @@ case object countStorePlanner {
val lpp = context.logicalPlanProducer
val aggregation1 = lpp.planCountStoreNodeAggregation(query, IdName(columnName), label, argumentIds)(context)
labelCheck(label)(Some(aggregation1))
} else if (patternRelationships.size == 1) { // MATCH ()-[r]->(), MATCH ()-[r:X]->(), MATCH ()-[r:X|Y]->()
} else if (patternRelationships.size == 1 && notLoop(patternRelationships.head)) { // MATCH ()-[r]->(), MATCH ()-[r:X]->(), MATCH ()-[r:X|Y]->()
labelCheck(None)(
trySolveRelationshipAggregation(query, columnName, variableName, patternRelationships, argumentIds, selections)
)
} else None
}

// the counts store counts loops twice
private def notLoop(r: PatternRelationship) = r.nodes._1 != r.nodes._2

private def trySolveRelationshipAggregation(query: PlannerQuery, columnName: String, variableName: Option[String],
patternRelationships: Set[PatternRelationship], argumentIds: Set[IdName],
selections: Selections)(implicit context: LogicalPlanningContext): Option[RelationshipCountFromCountStore] = {
Expand Down

0 comments on commit 3e8c046

Please sign in to comment.