/* * Licensed 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 com.addthis.hydra.data.filter.bundle; import com.addthis.bundle.core.Bundle; import com.addthis.bundle.util.AutoField; import com.addthis.bundle.util.ValueUtil; import com.addthis.bundle.value.ValueObject; import com.addthis.hydra.data.filter.value.ValueFilterContains; import com.fasterxml.jackson.annotation.JsonCreator; import com.fasterxml.jackson.annotation.JsonProperty; /** * This {@link com.addthis.hydra.data.filter.bundle.BundleFilter BundleFilter} <span class="hydra-summary">tests if the input contains the target value</span>. * <p/> * <p>The input is the contents of the bundle field specified by {@link #field field}. * If the input is a map then only the values of the map are tested. * The target can either be a set of strings (in the {@link #value value} field) or * a value from another field (in the {@link #from from} field). The filter returns true * if the source field contains any of the test values as a substring. * Otherwise the filter returns false. The filter does not modify the bundle. * <p/> * <p>Example:</p> * <pre> * {contains {field:"SRC", value:["foo", "bar"]}} * {contains {field:"SRC", from:"TEST"}} * </pre> * * @user-reference */ public class BundleFilterContains implements BundleFilter { /** * The input field to test. This field is required. */ final private AutoField field; /** * An array of strings to test against the input field. */ final private String[] value; /** * The target field to test against the input field. */ final private AutoField from; /** * If true then return the negation of the contains operation. Default is false. */ final private boolean not; // Cache the value filter if-and-only-if the 'from' field is null. final private ValueFilterContains filter; @JsonCreator public BundleFilterContains(@JsonProperty("field") AutoField field, @JsonProperty("value") String[] value, @JsonProperty("from") AutoField from, @JsonProperty("not") boolean not) { this.field = field; this.value = value; this.from = from; this.not = not; if (from == null && value != null) { filter = new ValueFilterContains(value, null, false, false); } else { filter = null; } } @Override public boolean filter(Bundle row) { if (row == null) { return not; } ValueObject target = field.getValue(row); if (from != null) { String fieldString = target.asString().asNative(); String fromString = ValueUtil.asNativeString(from.getValue(row)); boolean match = fieldString.contains(fromString); return not ? !match : match; } else if (filter != null) { boolean match = filter.filterValue(target) != null; return not ? !match : match; } else { return not; } } }