Skip to content

Commit

Permalink
Adding integ test for faiss
Browse files Browse the repository at this point in the history
Signed-off-by: Martin Gaievski <[email protected]>
  • Loading branch information
martin-gaievski committed Jul 24, 2024
1 parent 55ba99e commit b670b11
Showing 1 changed file with 81 additions and 0 deletions.
81 changes: 81 additions & 0 deletions src/test/java/org/opensearch/knn/index/FaissIT.java
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
import org.opensearch.common.settings.Settings;
import org.opensearch.client.ResponseException;
import org.opensearch.core.xcontent.XContentBuilder;
import org.opensearch.index.query.QueryBuilder;
import org.opensearch.index.query.QueryBuilders;
import org.opensearch.index.query.TermQueryBuilder;
import org.opensearch.knn.KNNRestTestCase;
Expand Down Expand Up @@ -83,6 +84,15 @@ public class FaissIT extends KNNRestTestCase {
private static final String COLOR_FIELD_NAME = "color";
private static final String TASTE_FIELD_NAME = "taste";

private static final String DIMENSION_FIELD_NAME = "dimension";
private static final int VECTOR_DIMENSION = 3;
private static final String KNN_VECTOR_TYPE = "knn_vector";
private static final String PROPERTIES_FIELD_NAME = "properties";
private static final String TYPE_FIELD_NAME = "type";
private static final String INTEGER_FIELD_NAME = "int_field";
private static final String FILED_TYPE_INTEGER = "integer";
private static final String NON_EXISTENT_INTEGER_FIELD_NAME = "nonexistent_int_field";

static TestUtils.TestData testData;

@BeforeClass
Expand Down Expand Up @@ -1712,6 +1722,77 @@ public void testIVF_whenBinaryFormat_whenIVF_thenSuccess() {
validateGraphEviction();
}

@SneakyThrows
public void testQueryWithFilter_whenNonExistingFieldUsedInFilter_thenSuccessful() {
XContentBuilder builder = XContentFactory.jsonBuilder()
.startObject()
.startObject(PROPERTIES_FIELD_NAME)
.startObject(FIELD_NAME)
.field(TYPE_FIELD_NAME, KNN_VECTOR_TYPE)
.field(DIMENSION_FIELD_NAME, VECTOR_DIMENSION)
.startObject(KNNConstants.KNN_METHOD)
.field(KNNConstants.NAME, KNNEngine.FAISS.getMethod(METHOD_HNSW).getMethodComponent().getName())
.field(KNNConstants.METHOD_PARAMETER_SPACE_TYPE, SpaceType.L2.getValue())
.field(KNNConstants.KNN_ENGINE, KNNEngine.LUCENE.getName())
.endObject()
.endObject()
.startObject(INTEGER_FIELD_NAME)
.field(TYPE_FIELD_NAME, FILED_TYPE_INTEGER)
.endObject()
.endObject()
.endObject();
Map<String, Object> mappingMap = xContentBuilderToMap(builder);
String mapping = builder.toString();

createKnnIndex(INDEX_NAME, mapping);

Float[] vector = new Float[] { 2.0f, 4.5f, 6.5f };

String documentAsString = XContentFactory.jsonBuilder()
.startObject()
.field(INTEGER_FIELD_NAME, 5)
.field(FIELD_NAME, vector)
.endObject()
.toString();

addKnnDoc(INDEX_NAME, DOC_ID_1, documentAsString);

refreshIndex(INDEX_NAME);
assertEquals(1, getDocCount(INDEX_NAME));

float[] searchVector = new float[] { 1.0f, 2.1f, 3.9f };
int k = 10;

// use filter where nonexistent field is must, we should have no results
QueryBuilder filterWithRequiredNonExistentField = QueryBuilders.boolQuery()
.must(QueryBuilders.rangeQuery(NON_EXISTENT_INTEGER_FIELD_NAME).gte(1));
Response searchWithRequiredNonExistentFiledInFilterResponse = searchKNNIndex(
INDEX_NAME,
new KNNQueryBuilder(FIELD_NAME, searchVector, k, filterWithRequiredNonExistentField),
k
);
List<KNNResult> resultsQuery1 = parseSearchResponse(
EntityUtils.toString(searchWithRequiredNonExistentFiledInFilterResponse.getEntity()),
FIELD_NAME
);
assertTrue(resultsQuery1.isEmpty());

// use filter with non existent field as optional, we should have some results
QueryBuilder filterWithOptionalNonExistentField = QueryBuilders.boolQuery()
.should(QueryBuilders.rangeQuery(NON_EXISTENT_INTEGER_FIELD_NAME).gte(1))
.must(QueryBuilders.rangeQuery(INTEGER_FIELD_NAME).gte(1));
Response searchWithOptionalNonExistentFiledInFilterResponse = searchKNNIndex(
INDEX_NAME,
new KNNQueryBuilder(FIELD_NAME, searchVector, k, filterWithOptionalNonExistentField),
k
);
List<KNNResult> resultsQuery2 = parseSearchResponse(
EntityUtils.toString(searchWithOptionalNonExistentFiledInFilterResponse.getEntity()),
FIELD_NAME
);
assertEquals(1, resultsQuery2.size());
}

protected void setupKNNIndexForFilterQuery() throws Exception {
// Create Mappings
XContentBuilder builder = XContentFactory.jsonBuilder()
Expand Down

0 comments on commit b670b11

Please sign in to comment.