ArrayAccess extends EvaluationExpression { @Override public IJsonNode evaluate(final IJsonNode node, final IJsonNode target, final EvaluationContext context) { if (!node.isArray()) return MissingNode.getInstance(); final IArrayNode arrayNode = (IArrayNode) node; if (this.isSelectingAll()) { final IArrayNode targetArray = SopremoUtil.reinitializeTarget(target, ArrayNode.class); targetArray.addAll(arrayNode); return targetArray; } final int size = arrayNode.size(); if (this.isSelectingRange()) { final IArrayNode targetArray = SopremoUtil.reinitializeTarget(target, ArrayNode.class); int index = this.resolveIndex(this.startIndex, size); final int endIndex = this.resolveIndex(this.endIndex, size); final int increment = index < endIndex ? 1 : -1; for (boolean moreElements = true; moreElements; index += increment) { targetArray.add(arrayNode.get(index)); moreElements = index != endIndex; } return targetArray; } final IJsonNode value = arrayNode.get(this.resolveIndex(this.startIndex, size)); return value == null ? NullNode.getInstance() : value; } ArrayAccess();  ArrayAccess(final int index);  ArrayAccess(final int startIndex, final int endIndex); @Override boolean equals(final Object obj); @Override IJsonNode evaluate(final IJsonNode node, final IJsonNode target, final EvaluationContext context); int getEndIndex(); int getStartIndex(); @Override int hashCode(); boolean isSelectingAll(); boolean isSelectingRange(); @Override IJsonNode set(final IJsonNode node, final IJsonNode value, final EvaluationContext context); @Override void toString(final StringBuilder builder); static EvaluationExpression arrayWithIndices(final int... indices);  }
@Test public void shouldAccessAllElements() { final IJsonNode result = new ArrayAccess().evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), null, this.context); Assert.assertEquals(createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), result); }
@Test public void shouldAccessOneElement() { final IJsonNode result = new ArrayAccess(1).evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3)), null, this.context); Assert.assertEquals(createObjectNode("fieldName", 2), result); }
@Test public void shouldAccessOneElementWithNegativeIndex() { final IJsonNode result = new ArrayAccess(-1).evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3)), null, this.context); Assert.assertEquals(createObjectNode("fieldName", 3), result); }
@Test public void shouldAccessRangeOfElement() { final IJsonNode result = new ArrayAccess(1, 3).evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), null, this.context); Assert.assertEquals(createArrayNode(createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4)), result); }
@Test public void shouldAccessRangeOfElementWithNegativeEndIndex() { final IJsonNode result = new ArrayAccess(1, -1).evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), null, this.context); Assert.assertEquals(createArrayNode(createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), result); }
@Test public void shouldAccessRangeOfElementWithNegativeStartAndEndIndex() { final IJsonNode result = new ArrayAccess(-3, -1).evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), null, this.context); Assert.assertEquals(createArrayNode(createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), result); }
@Test public void shouldAccessRangeOfElementWithNegativeStartIndex() { final IJsonNode result = new ArrayAccess(-3, 4).evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), null, this.context); Assert.assertEquals(createArrayNode(createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), result); }
@Test public void shouldAccessReversedRangeOfElements() { final IJsonNode result = new ArrayAccess(3, 1).evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), null, this.context); Assert.assertEquals(createArrayNode(createObjectNode("fieldName", 4), createObjectNode("fieldName", 3), createObjectNode("fieldName", 2)), result); }
@Test public void shouldReuseTargetIfWholeNodeIsAccessed() { final IJsonNode target = new ArrayNode(); final IJsonNode result = new ArrayAccess().evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), target, this.context); Assert.assertEquals(createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), result); Assert.assertSame(target, result); }
@Test public void shouldNotReuseTargetIfWrongType() { final IJsonNode target = new ObjectNode(); final IJsonNode result = new ArrayAccess().evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2)), target, this.context); Assert .assertEquals(createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2)), result); Assert.assertNotSame(target, result); }
@Test public void shouldReuseTargetIfRangeIsAccessed() { final IJsonNode target = new ArrayNode(); final IJsonNode result = new ArrayAccess(2, 4).evaluate( createArrayNode(createObjectNode("fieldName", 1), createObjectNode("fieldName", 2), createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), target, this.context); Assert.assertEquals(createArrayNode(createObjectNode("fieldName", 3), createObjectNode("fieldName", 4), createObjectNode("fieldName", 5)), result); Assert.assertSame(target, result); }