Repository: gora Updated Branches: refs/heads/master 61f6977cb -> 26b189b83
GORA-454 Implement FilterList tests Project: http://git-wip-us.apache.org/repos/asf/gora/repo Commit: http://git-wip-us.apache.org/repos/asf/gora/commit/18bd38a0 Tree: http://git-wip-us.apache.org/repos/asf/gora/tree/18bd38a0 Diff: http://git-wip-us.apache.org/repos/asf/gora/diff/18bd38a0 Branch: refs/heads/master Commit: 18bd38a0a1f90729b03e4d5a3ce8d450d3f9ff9d Parents: 0e6a309 Author: Lewis John McGibbney <lewis.j.mcgibb...@jpl.nasa.gov> Authored: Thu Jan 7 10:05:03 2016 -0800 Committer: Lewis John McGibbney <lewis.j.mcgibb...@jpl.nasa.gov> Committed: Thu Jan 7 10:05:03 2016 -0800 ---------------------------------------------------------------------- CHANGES.txt | 4 +- .../java/org/apache/gora/filter/FilterList.java | 45 ++++-- .../java/org/apache/gora/filter/FilterOp.java | 1 + .../apache/gora/filter/MapFieldValueFilter.java | 7 +- .../gora/filter/SingleFieldValueFilter.java | 22 +-- .../org/apache/gora/filter/TestFilterList.java | 156 +++++++++++++++++++ 6 files changed, 211 insertions(+), 24 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/gora/blob/18bd38a0/CHANGES.txt ---------------------------------------------------------------------- diff --git a/CHANGES.txt b/CHANGES.txt index 33f1fb3..5c486dd 100644 --- a/CHANGES.txt +++ b/CHANGES.txt @@ -4,7 +4,9 @@ Current Development -* GORA-452 Upgrade goraci prior to Chef and the ComputeService implementations +* GORA-454 Implement FilterList tests (lewismc) + +* GORA-452 Upgrade goraci prior to Chef and the ComputeService implementations (lewismc) * GORA-439 Remove Unused Method Parameters (Furkan KAMACI) http://git-wip-us.apache.org/repos/asf/gora/blob/18bd38a0/gora-core/src/main/java/org/apache/gora/filter/FilterList.java ---------------------------------------------------------------------- diff --git a/gora-core/src/main/java/org/apache/gora/filter/FilterList.java b/gora-core/src/main/java/org/apache/gora/filter/FilterList.java index 3700c89..e9d5a18 100644 --- a/gora-core/src/main/java/org/apache/gora/filter/FilterList.java +++ b/gora-core/src/main/java/org/apache/gora/filter/FilterList.java @@ -28,6 +28,14 @@ import java.io.IOException; import java.util.ArrayList; import java.util.List; +/** + * {@link FilterList} enables us to utilize conditional operands + * for advanced filtering within the construction and + * execution of Gora queries. + * + * @param <K> + * @param <T> + */ public class FilterList<K, T extends PersistentBase> implements Filter<K, T> { /** set operator */ public static enum Operator { @@ -36,21 +44,21 @@ public class FilterList<K, T extends PersistentBase> implements Filter<K, T> { /** !OR */ MUST_PASS_ONE } - + private Operator operator = Operator.MUST_PASS_ALL; private List<Filter<K, T>> filters = new ArrayList<>(); - + public FilterList() { } - + public FilterList(final List<Filter<K, T>> rowFilters) { this.filters = rowFilters; } - + public FilterList(final Operator operator) { this.operator = operator; } - + public FilterList(final Operator operator, final List<Filter<K, T>> rowFilters) { this.filters = rowFilters; this.operator = operator; @@ -59,15 +67,15 @@ public class FilterList<K, T extends PersistentBase> implements Filter<K, T> { public List<Filter<K, T>> getFilters() { return filters; } - + public Operator getOperator() { return operator; } - + public void addFilter(Filter<K, T> filter) { this.filters.add(filter); } - + @Override public void readFields(DataInput in) throws IOException { byte opByte = in.readByte(); @@ -101,8 +109,25 @@ public class FilterList<K, T extends PersistentBase> implements Filter<K, T> { @Override public boolean filter(K key, T persistent) { - // TODO not yet implemented - return false; + boolean filtered = false; + //OR + if (operator.equals(Operator.MUST_PASS_ONE)) { + for (Filter<K, T> filter: filters) { + if (!filter.filter(key, persistent)) { + return !filtered; + } + } + //AND + } else if (operator.equals(Operator.MUST_PASS_ALL)) { + for (Filter<K, T> filter: filters) { + if (filter.filter(key, persistent)) { + return !filtered; + } + } + } else { + throw new IllegalStateException(operator + " not yet implemented!"); + } + return filtered; } } http://git-wip-us.apache.org/repos/asf/gora/blob/18bd38a0/gora-core/src/main/java/org/apache/gora/filter/FilterOp.java ---------------------------------------------------------------------- diff --git a/gora-core/src/main/java/org/apache/gora/filter/FilterOp.java b/gora-core/src/main/java/org/apache/gora/filter/FilterOp.java index a2c52eb..7b9b5b3 100644 --- a/gora-core/src/main/java/org/apache/gora/filter/FilterOp.java +++ b/gora-core/src/main/java/org/apache/gora/filter/FilterOp.java @@ -19,6 +19,7 @@ package org.apache.gora.filter; /** * Defines a set of common filter compare operations. + * TODO N.B. Currently only EQUALS and NOT_EQUALS are implemented. */ public enum FilterOp { EQUALS, http://git-wip-us.apache.org/repos/asf/gora/blob/18bd38a0/gora-core/src/main/java/org/apache/gora/filter/MapFieldValueFilter.java ---------------------------------------------------------------------- diff --git a/gora-core/src/main/java/org/apache/gora/filter/MapFieldValueFilter.java b/gora-core/src/main/java/org/apache/gora/filter/MapFieldValueFilter.java index f4c4383..0fa70a4 100644 --- a/gora-core/src/main/java/org/apache/gora/filter/MapFieldValueFilter.java +++ b/gora-core/src/main/java/org/apache/gora/filter/MapFieldValueFilter.java @@ -45,8 +45,8 @@ public class MapFieldValueFilter<K, T extends PersistentBase> implements Filter< protected List<Object> operands = new ArrayList<>(); protected boolean filterIfMissing = false; - private Configuration conf = new Configuration(); // just create empty conf, - // needed for ObjectWritable + //just create empty conf needed for ObjectWritable + private Configuration conf = new Configuration(); @Override public void write(DataOutput out) throws IOException { @@ -123,7 +123,8 @@ public class MapFieldValueFilter<K, T extends PersistentBase> implements Filter< boolean equals = value.equals(operand); return equals; } else { - throw new IllegalStateException(filterOp + " not yet implemented"); + //TODO Currently only EQUALS and NOT_EQUALS are implemented. + throw new IllegalStateException(filterOp + " not yet implemented!"); } } http://git-wip-us.apache.org/repos/asf/gora/blob/18bd38a0/gora-core/src/main/java/org/apache/gora/filter/SingleFieldValueFilter.java ---------------------------------------------------------------------- diff --git a/gora-core/src/main/java/org/apache/gora/filter/SingleFieldValueFilter.java b/gora-core/src/main/java/org/apache/gora/filter/SingleFieldValueFilter.java index 5b701a3..9846c59 100644 --- a/gora-core/src/main/java/org/apache/gora/filter/SingleFieldValueFilter.java +++ b/gora-core/src/main/java/org/apache/gora/filter/SingleFieldValueFilter.java @@ -43,8 +43,9 @@ public class SingleFieldValueFilter<K, T extends PersistentBase> implements Filt protected List<Object> operands = new ArrayList<>(); protected boolean filterIfMissing = false; - private Configuration conf = new Configuration(); //just create empty conf, - //needed for ObjectWritable + //just create empty conf needed for ObjectWritable + private Configuration conf = new Configuration(); + @Override public void write(DataOutput out) throws IOException { Text.writeString(out, fieldName); @@ -81,7 +82,7 @@ public class SingleFieldValueFilter<K, T extends PersistentBase> implements Filt } out.writeBoolean(filterIfMissing); } - + @Override public void readFields(DataInput in) throws IOException { fieldName = Text.readString(in); @@ -100,7 +101,8 @@ public class SingleFieldValueFilter<K, T extends PersistentBase> implements Filt @Override public boolean filter(K key, T persistent) { - int fieldIndex = persistent.getSchema().getField(fieldName).pos(); //.getIndexNamed(fieldName); throws org.apache.avro.AvroRuntimeException: Not a union: + //.getIndexNamed(fieldName); throws org.apache.avro.AvroRuntimeException: Not a union: + int fieldIndex = persistent.getSchema().getField(fieldName).pos(); Object fieldValue = persistent.get(fieldIndex); Object operand = operands.get(0); if (fieldValue == null) { @@ -112,19 +114,19 @@ public class SingleFieldValueFilter<K, T extends PersistentBase> implements Filt } else if (filterOp.equals(FilterOp.NOT_EQUALS)) { boolean equals = operand.equals(fieldValue); return equals; - // TODO implement other FilterOp operators + //TODO Currently only EQUALS and NOT_EQUALS are implemented. } else { - throw new IllegalStateException(filterOp + " not yet implemented"); + throw new IllegalStateException(filterOp + " not yet implemented!"); } } - + public String getFieldName() { return fieldName; } public void setFieldName(String fieldName) { this.fieldName = fieldName; } - + public FilterOp getFilterOp() { return filterOp; } @@ -138,11 +140,11 @@ public class SingleFieldValueFilter<K, T extends PersistentBase> implements Filt public void setOperands(List<Object> operands) { this.operands = operands; } - + public void setFilterIfMissing(boolean filterIfMissing) { this.filterIfMissing = filterIfMissing; } - + public boolean isFilterIfMissing() { return filterIfMissing; } http://git-wip-us.apache.org/repos/asf/gora/blob/18bd38a0/gora-core/src/test/java/org/apache/gora/filter/TestFilterList.java ---------------------------------------------------------------------- diff --git a/gora-core/src/test/java/org/apache/gora/filter/TestFilterList.java b/gora-core/src/test/java/org/apache/gora/filter/TestFilterList.java new file mode 100644 index 0000000..23b1149 --- /dev/null +++ b/gora-core/src/test/java/org/apache/gora/filter/TestFilterList.java @@ -0,0 +1,156 @@ +/** + * Licensed to the Apache Software Foundation (ASF) under one + * or more contributor license agreements. See the NOTICE file + * distributed with this work for additional information + * regarding copyright ownership. The ASF licenses this file + * to you under the Apache License, Version 2.0 (the + * "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.apache.gora.filter; + +import static org.junit.Assert.*; + +import java.util.ArrayList; +import java.util.List; + +import org.apache.avro.util.Utf8; +import org.apache.gora.examples.generated.WebPage; +import org.apache.gora.filter.FilterList.Operator; +import org.junit.After; +import org.junit.Before; +import org.junit.Test; + +/** + * Test cases which test and validate functionality + * of {@link org.apache.gora.filter.FilterList} + * + */ +public class TestFilterList { + + private MapFieldValueFilter<String, WebPage> filter1 = null; + + private SingleFieldValueFilter<String, WebPage> filter2 = null; + + private FilterList<String, WebPage> filterList = null; + + private List<Filter<String, WebPage>> fList; + + /** + * Setup involves creating a FilterList comprising two filters + * which are applied with MUST_PASS_ALL (e.g. AND) set operator. + * @throws java.lang.Exception + */ + @Before + public void setUp() throws Exception { + filter1 = new MapFieldValueFilter<>(); + filter2 = new SingleFieldValueFilter<>(); + fList = new ArrayList<>(); + fList.add(filter1); + fList.add(filter2); + } + + /** + * @throws java.lang.Exception + */ + @After + public void tearDown() throws Exception { + filter1 = null; + filter2 = null; + filterList = null; + fList = null; + } + + /** + * Test method for {@link org.apache.gora.filter.FilterList#getFilters()}. + */ + @Test + public void testGetFilters() { + filterList = new FilterList<>(Operator.MUST_PASS_ALL, fList); + List<Filter<String, WebPage>> copyList = filterList.getFilters(); + assertEquals(2, filterList.getFilters().size()); + assertEquals(2, copyList.size()); + } + + /** + * Test method for {@link org.apache.gora.filter.FilterList#getOperator()}. + */ + @Test + public void testGetOperator() { + filterList = new FilterList<>(Operator.MUST_PASS_ALL, fList); + assertEquals(Operator.MUST_PASS_ALL, filterList.getOperator()); + } + + /** + * Test method for {@link org.apache.gora.filter.FilterList#addFilter(org.apache.gora.filter.Filter)}. + */ + @Test + public void testAddFilter() { + filterList = new FilterList<>(Operator.MUST_PASS_ALL, fList); + int a = 3; + for (int i = 0; i < 10; i++) { + filterList.addFilter(new SingleFieldValueFilter<String, WebPage>()); + assertEquals(a++, filterList.getFilters().size()); + } + } + + /** + * Test method for verifying + * {@link org.apache.gora.filter.FilterList.Operator#MUST_PASS_ALL} + * functionality. + */ + @Test + public void testOperatorMustPassAll() { + filter1.setFieldName(WebPage.Field.OUTLINKS.toString()); + filter1.setMapKey(new Utf8("example")); + filter1.setFilterOp(FilterOp.EQUALS); + filter1.setFilterIfMissing(true); + filter1.getOperands().add(new Utf8("http://example.org")); + + filter2.setFieldName(WebPage.Field.OUTLINKS.toString()); + filter2.setFilterOp(FilterOp.EQUALS); + filter2.setFilterIfMissing(true); + filter2.getOperands().add(new Utf8("http://example.org")); + + WebPage page = WebPage.newBuilder().build(); + page.getOutlinks().put(new Utf8("example"), new Utf8("http://example.org")); + + filterList = new FilterList<>(Operator.MUST_PASS_ALL, fList); + assertTrue(filterList.filter("irrelevant", page)); + } + + /** + * Test method for verifying + * {@link org.apache.gora.filter.FilterList.Operator#MUST_PASS_ONE} + * functionality. + */ + @Test + public void testOperatorMustPassOne() { + filter1.setFieldName(WebPage.Field.OUTLINKS.toString()); + filter1.setMapKey(new Utf8("example")); + filter1.setFilterOp(FilterOp.EQUALS); + filter1.setFilterIfMissing(true); + filter1.getOperands().add(new Utf8("http://example.org")); + + filter2.setFieldName(WebPage.Field.OUTLINKS.toString()); + filter2.setFilterOp(FilterOp.EQUALS); + filter2.setFilterIfMissing(true); + filter2.getOperands().add(new Utf8("http://example2.org")); + + WebPage page = WebPage.newBuilder().build(); + page.getOutlinks().put(new Utf8("example"), new Utf8("http://example.org")); + + filterList = new FilterList<>(Operator.MUST_PASS_ONE, fList); + assertTrue(filterList.filter("irrelevant", page)); + + } + +}