Permalink
Browse files

o Refactoring of how expressions work

  Expressions used to be functions that, given a map of String->Object, returned
  a value. This lead to problems with parameters, which had to be encoded using
  magic strings in the map. Now an Expression takes an ExecutionContext instead,
  which allows parameters to be stored side by side with the result.

o Refactoring of how named paths are treated in the Query object
  Patterns are now duplicated - if a named path is declared, the pattern items it
  contains will be placed both in the named path field, but also in the patterns
  field. This is because named paths can come from multiple places these days, not
  only from matching.
  • Loading branch information...
1 parent ed0ff64 commit 47c15c6c2eab2e2bea3063a35715dd1bb3e71cc1 @systay committed Oct 15, 2012
Showing with 507 additions and 452 deletions.
  1. +3 −2 cypher/src/main/scala/org/neo4j/cypher/internal/commands/ComparablePredicate.scala
  2. +3 −2 cypher/src/main/scala/org/neo4j/cypher/internal/commands/InCollection.scala
  3. +9 −6 cypher/src/main/scala/org/neo4j/cypher/internal/commands/PathExpression.scala
  4. +16 −15 cypher/src/main/scala/org/neo4j/cypher/internal/commands/Predicate.scala
  5. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/Add.scala
  6. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/AggregationExpression.scala
  7. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/CoalesceFunction.scala
  8. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/Collection.scala
  9. +4 −3 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/Expression.scala
  10. +3 −2 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/ExtractFunction.scala
  11. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/FilterFunction.scala
  12. +2 −2 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/HeadFunction.scala
  13. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/IdFunction.scala
  14. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/Identifier.scala
  15. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/LastFunction.scala
  16. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/LengthFunction.scala
  17. +2 −3 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/Literal.scala
  18. +6 −5 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/MathFunction.scala
  19. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/NodesFunction.scala
  20. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/Null.scala
  21. +3 −3 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/NullInNullOutExpression.scala
  22. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/Nullable.scala
  23. +3 −13 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/ParameterExpression.scala
  24. +7 −8 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/Property.scala
  25. +5 −5 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/ReduceFunction.scala
  26. +2 −2 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/RelationshipFunction.scala
  27. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/RelationshipTypeFunction.scala
  28. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/ShortestPathExpression.scala
  29. +27 −20 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/StringFunctions.scala
  30. +2 −2 cypher/src/main/scala/org/neo4j/cypher/internal/commands/expressions/TailFunction.scala
  31. +2 −2 cypher/src/main/scala/org/neo4j/cypher/internal/executionplan/ExecutionPlanImpl.scala
  32. +1 −2 cypher/src/main/scala/org/neo4j/cypher/internal/executionplan/PartiallySolvedQuery.scala
  33. +3 −2 cypher/src/main/scala/org/neo4j/cypher/internal/executionplan/builders/ColumnFilterBuilder.scala
  34. +1 −1 cypher/src/main/scala/org/neo4j/cypher/internal/executionplan/builders/UpdateActionBuilder.scala
  35. +5 −4 cypher/src/main/scala/org/neo4j/cypher/internal/parser/v1_7/MatchClause.scala
  36. +4 −2 cypher/src/main/scala/org/neo4j/cypher/internal/parser/v1_8/MatchClause.scala
  37. +4 −2 cypher/src/main/scala/org/neo4j/cypher/internal/parser/v1_9/MatchClause.scala
  38. +5 −12 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/ColumnFilterPipe.scala
  39. +9 −13 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/EagerAggregationPipe.scala
  40. +3 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/ExecuteUpdateCommandsPipe.scala
  41. +1 −4 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/MatchPipe.scala
  42. +1 −15 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/ParameterPipe.scala
  43. +19 −6 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/Pipe.scala
  44. +0 −6 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/ShortestPathPipe.scala
  45. +1 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/SlicePipe.scala
  46. +15 −12 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/TraversalMatchPipe.scala
  47. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/aggregation/AggregationFunction.scala
  48. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/aggregation/AvgFunction.scala
  49. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/aggregation/CollectFunction.scala
  50. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/aggregation/CountFunction.scala
  51. +2 −2 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/aggregation/CountStarFunction.scala
  52. +2 −2 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/aggregation/DistinctFunction.scala
  53. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/aggregation/MaxFunction.scala
  54. +3 −2 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/aggregation/PercentileFunction.scala
  55. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/aggregation/SumFunction.scala
  56. +2 −16 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/BidirectionalTraversalMatcher.scala
  57. +4 −3 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/DoubleOptionalPatternMatcher.scala
  58. +19 −7 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/ExpanderStep.scala
  59. +5 −6 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/History.scala
  60. +6 −5 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/Joiner.scala
  61. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/JoinerBuilder.scala
  62. +3 −2 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/MatchingContext.scala
  63. +2 −7 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/MonodirectionalTraversalMatcher.scala
  64. +7 −5 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/PatterMatchingBuilder.scala
  65. +16 −9 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/PatternMatcher.scala
  66. +8 −10 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/SimplePatternMatcherBuilder.scala
  67. +2 −1 cypher/src/main/scala/org/neo4j/cypher/internal/pipes/matching/TraversalPathExpander.scala
  68. +19 −6 cypher/src/test/scala/org/neo4j/cypher/CypherParserTest.scala
  69. +4 −26 cypher/src/test/scala/org/neo4j/cypher/ExecutionEngineTest.scala
  70. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/commands/AddTest.scala
  71. +6 −5 cypher/src/test/scala/org/neo4j/cypher/internal/commands/CoalesceTest.scala
  72. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/commands/ExtractTest.scala
  73. +4 −3 cypher/src/test/scala/org/neo4j/cypher/internal/commands/HasRelationshipTest.scala
  74. +15 −14 cypher/src/test/scala/org/neo4j/cypher/internal/commands/MathFunctionsTest.scala
  75. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/commands/PathExpressionTest.scala
  76. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/commands/PropertyValueTest.scala
  77. +3 −2 cypher/src/test/scala/org/neo4j/cypher/internal/commands/ReduceTest.scala
  78. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/commands/SeqPredicateTest.scala
  79. +82 −55 cypher/src/test/scala/org/neo4j/cypher/internal/commands/StringFunctionsTest.scala
  80. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/commands/SubtractTest.scala
  81. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/commands/expressions/ExpressionTest.scala
  82. +1 −1 cypher/src/test/scala/org/neo4j/cypher/internal/executionplan/builders/BuilderTest.scala
  83. +1 −1 cypher/src/test/scala/org/neo4j/cypher/internal/mutation/CreateNodeActionTest.scala
  84. +1 −3 cypher/src/test/scala/org/neo4j/cypher/internal/mutation/DoubleCheckCreateUniqueTest.scala
  85. +1 −1 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/ColumnFilterPipeTest.scala
  86. +2 −2 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/MutationTest.scala
  87. +2 −3 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/aggregation/AggregateTest.scala
  88. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/aggregation/PercentileFunctionsTest.scala
  89. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/matching/ExpanderStepTest.scala
  90. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/matching/HistoryTest.scala
  91. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/matching/JoinerBuilderTest.scala
  92. +7 −4 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/matching/JoinerTest.scala
  93. +39 −36 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/matching/MatchingContextTest.scala
  94. +2 −2 cypher/src/test/scala/org/neo4j/cypher/internal/pipes/matching/TraversalMatcherTest.scala
  95. +2 −1 cypher/src/test/scala/org/neo4j/cypher/internal/symbols/SymbolTableTest.scala
@@ -26,11 +26,12 @@ import java.lang.String
import org.neo4j.cypher.internal.symbols._
import collection.Map
import org.neo4j.cypher.internal.helpers.IsCollection
+import org.neo4j.cypher.internal.pipes.ExecutionContext
abstract sealed class ComparablePredicate(left: Expression, right: Expression) extends Predicate with Comparer {
def compare(comparisonResult: Int): Boolean
- def isMatch(m: Map[String, Any]): Boolean = {
+ def isMatch(m: ExecutionContext): Boolean = {
val l: Any = left(m)
val r: Any = right(m)
@@ -55,7 +56,7 @@ abstract sealed class ComparablePredicate(left: Expression, right: Expression) e
case class Equals(a: Expression, b: Expression) extends Predicate with Comparer {
- def isMatch(m: Map[String, Any]): Boolean = {
+ def isMatch(m: ExecutionContext): Boolean = {
val a1 = a(m)
val b1 = b(m)
@@ -24,18 +24,19 @@ import expressions.{Closure, Expression}
import org.neo4j.cypher.internal.symbols._
import collection.Map
import org.neo4j.cypher.internal.helpers.CollectionSupport
+import org.neo4j.cypher.internal.pipes.ExecutionContext
abstract class InCollection(collection: Expression, id: String, predicate: Predicate)
extends Predicate
with CollectionSupport
with Closure {
def seqMethod[U](f: Seq[U]): ((U) => Boolean) => Boolean
- def isMatch(m: Map[String, Any]): Boolean = {
+ def isMatch(m: ExecutionContext): Boolean = {
val seq = makeTraversable(collection(m)).toSeq
seqMethod(seq)(item => {
- val innerMap = m ++ Map(id -> item)
+ val innerMap = m.newWith(id -> item)
predicate.isMatch(innerMap)
})
}
@@ -27,6 +27,7 @@ import collection.Map
import org.neo4j.helpers.ThisShouldNotHappenError
import org.neo4j.graphdb.Path
import org.neo4j.cypher.internal.executionplan.builders.PatternGraphBuilder
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class PathExpression(pathPattern: Seq[Pattern])
extends Expression
@@ -41,21 +42,23 @@ case class PathExpression(pathPattern: Seq[Pattern])
filter(isNamed).
distinct
- def apply(m: Map[String, Any]): Any = {
+ def apply(m: ExecutionContext): Any = {
+ // If any of the points we need is null, the whole expression will return null
val returnNull = interestingPoints.exists(key => m.get(key) match {
- case None => throw new ThisShouldNotHappenError("Andres", "This execution plan should not exist.")
+ case None => throw new ThisShouldNotHappenError("Andres", "This execution plan should not exist.")
case Some(null) => true
- case Some(x) => false
+ case Some(x) => false
})
+
if (returnNull) {
null
} else {
- getMatches(m.filterKeys(interestingPoints.contains)) //Only pass on to the pattern matcher
- } //the points it should care about, nothing else.
+ getMatches(m)
+ }
}
- def getMatches(v1: Map[String, Any]): Traversable[Path] = {
+ def getMatches(v1: ExecutionContext): Traversable[Path] = {
val matches = matchingContext.getMatches(v1)
matches.map(getPath)
}
@@ -29,11 +29,12 @@ import org.neo4j.helpers.ThisShouldNotHappenError
import collection.Map
import org.neo4j.cypher.CypherTypeException
import org.neo4j.cypher.internal.helpers.{IsCollection, CollectionSupport}
+import org.neo4j.cypher.internal.pipes.ExecutionContext
abstract class Predicate extends Expression {
- def apply(m: Map[String, Any]) = isMatch(m)
+ def apply(m: ExecutionContext) = isMatch(m)
def ++(other: Predicate): Predicate = And(this, other)
- def isMatch(m: Map[String, Any]): Boolean
+ def isMatch(m: ExecutionContext): Boolean
// This is the un-dividable list of predicates. They can all be ANDed
// together
@@ -49,7 +50,7 @@ abstract class Predicate extends Expression {
}
case class NullablePredicate(inner: Predicate, exp: Seq[(Expression, Boolean)]) extends Predicate {
- def isMatch(m: Map[String, Any]) = {
+ def isMatch(m: ExecutionContext) = {
val nullValue = exp.find {
case (e, res) => e(m) == null
}
@@ -79,7 +80,7 @@ case class NullablePredicate(inner: Predicate, exp: Seq[(Expression, Boolean)])
case class And(a: Predicate, b: Predicate) extends Predicate {
- def isMatch(m: Map[String, Any]): Boolean = a.isMatch(m) && b.isMatch(m)
+ def isMatch(m: ExecutionContext): Boolean = a.isMatch(m) && b.isMatch(m)
def atoms: Seq[Predicate] = a.atoms ++ b.atoms
override def toString(): String = "(" + a + " AND " + b + ")"
def containsIsNull = a.containsIsNull||b.containsIsNull
@@ -95,7 +96,7 @@ case class And(a: Predicate, b: Predicate) extends Predicate {
}
case class Or(a: Predicate, b: Predicate) extends Predicate {
- def isMatch(m: Map[String, Any]): Boolean = a.isMatch(m) || b.isMatch(m)
+ def isMatch(m: ExecutionContext): Boolean = a.isMatch(m) || b.isMatch(m)
def atoms: Seq[Predicate] = Seq(this)
override def toString(): String = "(" + a + " OR " + b + ")"
def containsIsNull = a.containsIsNull||b.containsIsNull
@@ -111,7 +112,7 @@ case class Or(a: Predicate, b: Predicate) extends Predicate {
}
case class Not(a: Predicate) extends Predicate {
- def isMatch(m: Map[String, Any]): Boolean = !a.isMatch(m)
+ def isMatch(m: ExecutionContext): Boolean = !a.isMatch(m)
def atoms: Seq[Predicate] = a.atoms.map(Not(_))
override def toString(): String = "NOT(" + a + ")"
def containsIsNull = a.containsIsNull
@@ -125,7 +126,7 @@ case class Not(a: Predicate) extends Predicate {
}
case class HasRelationshipTo(from: Expression, to: Expression, dir: Direction, relType: Seq[String]) extends Predicate {
- def isMatch(m: Map[String, Any]): Boolean = {
+ def isMatch(m: ExecutionContext): Boolean = {
val fromNode = from(m).asInstanceOf[Node]
val toNode = to(m).asInstanceOf[Node]
@@ -155,7 +156,7 @@ case class HasRelationshipTo(from: Expression, to: Expression, dir: Direction, r
}
case class HasRelationship(from: Expression, dir: Direction, relType: Seq[String]) extends Predicate {
- def isMatch(m: Map[String, Any]): Boolean = {
+ def isMatch(m: ExecutionContext): Boolean = {
val fromNode = from(m).asInstanceOf[Node]
if (fromNode == null) {
@@ -181,7 +182,7 @@ case class HasRelationship(from: Expression, dir: Direction, relType: Seq[String
}
case class IsNull(expression: Expression) extends Predicate {
- def isMatch(m: Map[String, Any]): Boolean = expression(m) == null
+ def isMatch(m: ExecutionContext): Boolean = expression(m) == null
def atoms: Seq[Predicate] = Seq(this)
override def toString(): String = expression + " IS NULL"
def containsIsNull = true
@@ -194,7 +195,7 @@ case class IsNull(expression: Expression) extends Predicate {
}
case class True() extends Predicate {
- def isMatch(m: Map[String, Any]): Boolean = true
+ def isMatch(m: ExecutionContext): Boolean = true
def atoms: Seq[Predicate] = Seq(this)
override def toString(): String = "true"
def containsIsNull = false
@@ -208,7 +209,7 @@ case class True() extends Predicate {
}
case class Has(property: Property) extends Predicate {
- def isMatch(m: Map[String, Any]): Boolean = property match {
+ def isMatch(m: ExecutionContext): Boolean = property match {
case Property(identifier, propertyName) => {
val propContainer = m(identifier).asInstanceOf[PropertyContainer]
propContainer != null && propContainer.hasProperty(propertyName)
@@ -231,9 +232,9 @@ case class Has(property: Property) extends Predicate {
}
case class LiteralRegularExpression(a: Expression, regex: Literal) extends Predicate {
- lazy val pattern = regex(Map()).asInstanceOf[String].r.pattern
+ lazy val pattern = regex(ExecutionContext.empty).asInstanceOf[String].r.pattern
- def isMatch(m: Map[String, Any]) = pattern.matcher(a(m).asInstanceOf[String]).matches()
+ def isMatch(m: ExecutionContext) = pattern.matcher(a(m).asInstanceOf[String]).matches()
def atoms = Seq(this)
def containsIsNull = false
def rewrite(f: (Expression) => Expression) = regex.rewrite(f) match {
@@ -251,7 +252,7 @@ case class LiteralRegularExpression(a: Expression, regex: Literal) extends Predi
}
case class RegularExpression(a: Expression, regex: Expression) extends Predicate {
- def isMatch(m: Map[String, Any]): Boolean = {
+ def isMatch(m: ExecutionContext): Boolean = {
val value = a(m).asInstanceOf[String]
val regularExp = regex(m).asInstanceOf[String]
@@ -275,7 +276,7 @@ case class RegularExpression(a: Expression, regex: Expression) extends Predicate
}
case class NonEmpty(collection:Expression) extends Predicate with CollectionSupport {
- def isMatch(m: Map[String, Any]): Boolean = {
+ def isMatch(m: ExecutionContext): Boolean = {
collection(m) match {
case IsCollection(x) => this.makeTraversable(collection(m)).nonEmpty
case null => false
@@ -23,9 +23,10 @@ import org.neo4j.cypher.internal.symbols._
import org.neo4j.cypher.CypherTypeException
import collection.Map
import org.neo4j.cypher.internal.helpers.IsCollection
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class Add(a: Expression, b: Expression) extends Expression {
- def apply(m: Map[String, Any]) = {
+ def apply(m: ExecutionContext) = {
val aVal = a(m)
val bVal = b(m)
@@ -25,9 +25,10 @@ import org.neo4j.cypher.internal.symbols._
import org.neo4j.cypher.SyntaxException
import collection.Map
import org.neo4j.helpers.ThisShouldNotHappenError
+import org.neo4j.cypher.internal.pipes.ExecutionContext
abstract class AggregationExpression extends Expression {
- def apply(m: Map[String, Any]) = throw new ThisShouldNotHappenError("Andres", "Aggregations should not be used like this.")
+ def apply(m: ExecutionContext) = throw new ThisShouldNotHappenError("Andres", "Aggregations should not be used like this.")
def createAggregationFunction: AggregationFunction
}
@@ -21,9 +21,10 @@ package org.neo4j.cypher.internal.commands.expressions
import org.neo4j.cypher.internal.symbols._
import collection.Map
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class CoalesceFunction(expressions: Expression*) extends Expression {
- def apply(m: Map[String, Any]): Any = expressions.toStream.map(expression => expression(m)).find(value => value != null) match {
+ def apply(m: ExecutionContext): Any = expressions.toStream.map(expression => expression(m)).find(value => value != null) match {
case None => null
case Some(x) => x
}
@@ -21,9 +21,10 @@ package org.neo4j.cypher.internal.commands.expressions
import org.neo4j.cypher.internal.symbols._
import collection.Map
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class Collection(expressions: Expression*) extends Expression {
- def apply(m: Map[String, Any]): Any = expressions.map(e => e(m))
+ def apply(m: ExecutionContext): Any = expressions.map(e => e(m))
def rewrite(f: (Expression) => Expression): Expression = f(Collection(expressions.map(f): _*))
@@ -20,10 +20,11 @@
package org.neo4j.cypher.internal.commands.expressions
import org.neo4j.cypher._
+import internal.pipes.ExecutionContext
import internal.symbols._
import collection.Map
-abstract class Expression extends (Map[String, Any] => Any)
+abstract class Expression extends (ExecutionContext => Any)
with Typed
with TypeSafe {
def rewrite(f: Expression => Expression): Expression
@@ -55,7 +56,7 @@ with TypeSafe {
}
case class CachedExpression(key:String, typ:CypherType) extends Expression {
- def apply(m: Map[String, Any]) = m(key)
+ def apply(m: ExecutionContext) = m(key)
def rewrite(f: (Expression) => Expression) = f(this)
def filter(f: (Expression) => Boolean) = if(f(this)) Seq(this) else Seq()
@@ -73,7 +74,7 @@ abstract class Arithmetics(left: Expression, right: Expression)
throw new CypherTypeException("Don't know how to " + this + " `" + bVal + "` with `" + aVal + "`")
}
- def apply(m: Map[String, Any]) = {
+ def apply(m: ExecutionContext) = {
val aVal = left(m)
val bVal = right(m)
@@ -22,15 +22,16 @@ package org.neo4j.cypher.internal.commands.expressions
import org.neo4j.cypher.internal.symbols._
import collection.Map
import org.neo4j.cypher.internal.helpers.CollectionSupport
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class ExtractFunction(collection: Expression, id: String, expression: Expression)
extends NullInNullOutExpression(collection)
with CollectionSupport
with Closure {
- def compute(value: Any, m: Map[String, Any]) = makeTraversable(value).map {
+ def compute(value: Any, m: ExecutionContext) = makeTraversable(value).map {
case iterValue =>
- val innerMap = m + (id -> iterValue)
+ val innerMap = m.newWith(id -> iterValue)
expression(innerMap)
}.toList
@@ -23,12 +23,13 @@ import org.neo4j.cypher.internal.helpers.CollectionSupport
import org.neo4j.cypher.internal.commands.Predicate
import org.neo4j.cypher.internal.symbols._
import collection.Map
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class FilterFunction(collection: Expression, id: String, predicate: Predicate)
extends NullInNullOutExpression(collection)
with CollectionSupport
with Closure {
- def compute(value: Any, m: Map[String, Any]) = makeTraversable(value).filter(element => predicate.isMatch(m + (id -> element)))
+ def compute(value: Any, m: ExecutionContext) = makeTraversable(value).filter(element => predicate.isMatch(m.newWith(id -> element)))
def rewrite(f: (Expression) => Expression) = f(FilterFunction(collection.rewrite(f), id, predicate.rewrite(f)))
@@ -18,12 +18,12 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.neo4j.cypher.internal.commands.expressions
-import collection.Map
import org.neo4j.cypher.internal.symbols._
import org.neo4j.cypher.internal.helpers.CollectionSupport
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class HeadFunction(collection: Expression) extends NullInNullOutExpression(collection) with CollectionSupport {
- def compute(value: Any, m: Map[String, Any]) = makeTraversable(value).head
+ def compute(value: Any, m: ExecutionContext) = makeTraversable(value).head
def rewrite(f: (Expression) => Expression) = f(HeadFunction(collection.rewrite(f)))
@@ -23,9 +23,10 @@ import org.neo4j.graphdb.{Relationship, Node}
import org.neo4j.cypher.internal.symbols._
import collection.Map
import org.neo4j.cypher.CypherTypeException
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class IdFunction(inner: Expression) extends NullInNullOutExpression(inner) {
- def compute(value: Any, m: Map[String, Any]) = value match {
+ def compute(value: Any, m: ExecutionContext) = value match {
case node: Node => node.getId
case rel: Relationship => rel.getId
case x => throw new CypherTypeException("Expected `%s` to be a node or relationship, but it was ``".format(inner, x.getClass.getSimpleName))
@@ -23,6 +23,7 @@ import org.neo4j.graphdb.NotFoundException
import org.neo4j.cypher.internal.symbols._
import collection.Map
import org.neo4j.helpers.ThisShouldNotHappenError
+import org.neo4j.cypher.internal.pipes.ExecutionContext
object Identifier {
@@ -33,7 +34,7 @@ object Identifier {
case class Identifier(entityName: String) extends Expression with Typed {
- def apply(m: Map[String, Any]): Any = m.getOrElse(entityName, throw new NotFoundException("Unknown identifier `%s`".format(entityName)))
+ def apply(m: ExecutionContext): Any = m.getOrElse(entityName, throw new NotFoundException("Unknown identifier `%s`".format(entityName)))
override def toString(): String = entityName
@@ -21,9 +21,10 @@ package org.neo4j.cypher.internal.commands.expressions
import collection.Map
import org.neo4j.cypher.internal.symbols._
import org.neo4j.cypher.internal.helpers.CollectionSupport
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class LastFunction(collection: Expression) extends NullInNullOutExpression(collection) with CollectionSupport {
- def compute(value: Any, m: Map[String, Any]) = makeTraversable(value).last
+ def compute(value: Any, m: ExecutionContext) = makeTraversable(value).last
def rewrite(f: (Expression) => Expression) = f(LastFunction(collection.rewrite(f)))
@@ -23,12 +23,13 @@ import org.neo4j.graphdb.Path
import org.neo4j.cypher.internal.symbols._
import collection.Map
import org.neo4j.cypher.internal.helpers.CollectionSupport
+import org.neo4j.cypher.internal.pipes.ExecutionContext
case class LengthFunction(inner: Expression)
extends NullInNullOutExpression(inner)
with CollectionSupport
with ExpressionWInnerExpression {
- def compute(value: Any, m: Map[String, Any]) = value match {
+ def compute(value: Any, m: ExecutionContext) = value match {
case path: Path => path.length()
case s: String => s.length()
case x => makeTraversable(x).toSeq.length
Oops, something went wrong. Retry.

1 comment on commit 47c15c6

@freeeve

I like what you did to clean up my tests to be more DRY. You snuck that one in there...

Please sign in to comment.