diff options
Diffstat (limited to 'config-model/src/main/java/com/yahoo/schema/document/ComplexAttributeFieldUtils.java')
-rw-r--r-- | config-model/src/main/java/com/yahoo/schema/document/ComplexAttributeFieldUtils.java | 123 |
1 files changed, 123 insertions, 0 deletions
diff --git a/config-model/src/main/java/com/yahoo/schema/document/ComplexAttributeFieldUtils.java b/config-model/src/main/java/com/yahoo/schema/document/ComplexAttributeFieldUtils.java new file mode 100644 index 00000000000..993bf16405a --- /dev/null +++ b/config-model/src/main/java/com/yahoo/schema/document/ComplexAttributeFieldUtils.java @@ -0,0 +1,123 @@ +// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +package com.yahoo.schema.document; + +import com.yahoo.document.ArrayDataType; +import com.yahoo.document.DataType; +import com.yahoo.document.MapDataType; +import com.yahoo.document.StructDataType; + +/** + * Utils used to check whether a complex field supports being represented as struct field attributes. + * + * Currently we support: + * - array of simple struct + * - map of primitive type to simple struct + * - map of primitive type to primitive type + * + * A simple struct can contain fields of any type, but only fields of primitive type can be defined as + * struct field attributes in the complex field using the simple struct. + * + * @author geirst + */ +public class ComplexAttributeFieldUtils { + + public static boolean isSupportedComplexField(ImmutableSDField field) { + return (isArrayOfSimpleStruct(field) || + isMapOfSimpleStruct(field) || + isMapOfPrimitiveType(field)); + } + + public static boolean isArrayOfSimpleStruct(ImmutableSDField field) { + if (field.getDataType() instanceof ArrayDataType) { + ArrayDataType arrayType = (ArrayDataType)field.getDataType(); + return isStructWithPrimitiveStructFieldAttributes(arrayType.getNestedType(), field); + } else { + return false; + } + } + + public static boolean isMapOfSimpleStruct(ImmutableSDField field) { + if (field.getDataType() instanceof MapDataType) { + MapDataType mapType = (MapDataType)field.getDataType(); + return isPrimitiveType(mapType.getKeyType()) && + isStructWithPrimitiveStructFieldAttributes(mapType.getValueType(), + field.getStructField("value")); + } else { + return false; + } + } + + public static boolean isMapOfPrimitiveType(ImmutableSDField field) { + if (field.getDataType() instanceof MapDataType) { + MapDataType mapType = (MapDataType)field.getDataType(); + return isPrimitiveType(mapType.getKeyType()) && + isPrimitiveType(mapType.getValueType()); + } else { + return false; + } + } + + private static boolean isStructWithPrimitiveStructFieldAttributes(DataType type, ImmutableSDField field) { + if (type instanceof StructDataType && ! GeoPos.isPos(type)) { + for (ImmutableSDField structField : field.getStructFields()) { + Attribute attribute = structField.getAttributes().get(structField.getName()); + if (attribute != null) { + if (!isPrimitiveType(attribute)) { + return false; + } + } else if (structField.wasConfiguredToDoAttributing()) { + if (!isPrimitiveType(structField.getDataType())) { + return false; + } + } + } + return true; + } else { + return false; + } + } + + public static boolean isPrimitiveType(Attribute attribute) { + return attribute.getCollectionType().equals(Attribute.CollectionType.SINGLE) && + isPrimitiveType(attribute.getDataType()); + } + + public static boolean isPrimitiveType(DataType dataType) { + return dataType.equals(DataType.BYTE) || + dataType.equals(DataType.INT) || + dataType.equals(DataType.LONG) || + dataType.equals(DataType.FLOAT) || + dataType.equals(DataType.DOUBLE) || + dataType.equals(DataType.STRING); + } + + public static boolean isComplexFieldWithOnlyStructFieldAttributes(ImmutableSDField field) { + if (isArrayOfSimpleStruct(field)) { + return hasOnlyStructFieldAttributes(field); + } else if (isMapOfSimpleStruct(field)) { + return hasSingleAttribute(field.getStructField("key")) && + hasOnlyStructFieldAttributes(field.getStructField("value")); + } else if (isMapOfPrimitiveType(field)) { + return hasSingleAttribute(field.getStructField("key")) && + hasSingleAttribute(field.getStructField("value")); + } + return false; + } + + private static boolean hasOnlyStructFieldAttributes(ImmutableSDField field) { + for (ImmutableSDField structField : field.getStructFields()) { + if (!hasSingleAttribute(structField)) { + return false; + } + } + return true; + } + + private static boolean hasSingleAttribute(ImmutableSDField field) { + if (field.getAttributes().size() != 1) { + return false; + } + return (field.getAttributes().get(field.getName()) != null); + } + +} |