private static Field inferField()

in java/fury-format/src/main/java/org/apache/fury/format/type/TypeInference.java [136:238]


  private static Field inferField(
      String name, TypeRef<?> typeRef, LinkedHashSet<Class<?>> seenTypeSet) {
    Class<?> rawType = getRawType(typeRef);
    if (rawType == boolean.class) {
      return field(name, DataTypes.notNullFieldType(ArrowType.Bool.INSTANCE));
    } else if (rawType == byte.class) {
      return field(name, DataTypes.notNullFieldType(new ArrowType.Int(8, true)));
    } else if (rawType == short.class) {
      return field(name, DataTypes.notNullFieldType(new ArrowType.Int(16, true)));
    } else if (rawType == int.class) {
      return field(name, DataTypes.notNullFieldType(new ArrowType.Int(32, true)));
    } else if (rawType == long.class) {
      return field(name, DataTypes.notNullFieldType(new ArrowType.Int(64, true)));
    } else if (rawType == float.class) {
      return field(
          name,
          DataTypes.notNullFieldType(new ArrowType.FloatingPoint(FloatingPointPrecision.SINGLE)));
    } else if (rawType == double.class) {
      return field(
          name,
          DataTypes.notNullFieldType(new ArrowType.FloatingPoint(FloatingPointPrecision.DOUBLE)));
    } else if (rawType == Boolean.class) {
      return field(name, FieldType.nullable((ArrowType.Bool.INSTANCE)));
    } else if (rawType == Byte.class) {
      return field(name, FieldType.nullable((new ArrowType.Int(8, true))));
    } else if (rawType == Short.class) {
      return field(name, FieldType.nullable((new ArrowType.Int(16, true))));
    } else if (rawType == Integer.class) {
      return field(name, FieldType.nullable((new ArrowType.Int(32, true))));
    } else if (rawType == Long.class) {
      return field(name, FieldType.nullable((new ArrowType.Int(64, true))));
    } else if (rawType == Float.class) {
      return field(
          name, FieldType.nullable(new ArrowType.FloatingPoint(FloatingPointPrecision.SINGLE)));
    } else if (rawType == Double.class) {
      return field(
          name, FieldType.nullable(new ArrowType.FloatingPoint(FloatingPointPrecision.DOUBLE)));
    } else if (rawType == java.math.BigDecimal.class) {
      return field(
          name,
          FieldType.nullable(
              new ArrowType.Decimal(DecimalUtils.MAX_PRECISION, DecimalUtils.MAX_SCALE)));
    } else if (rawType == java.math.BigInteger.class) {
      return field(name, FieldType.nullable(new ArrowType.Decimal(DecimalUtils.MAX_PRECISION, 0)));
    } else if (rawType == java.time.LocalDate.class) {
      return field(name, FieldType.nullable(new ArrowType.Date(DateUnit.DAY)));
    } else if (rawType == java.sql.Date.class) {
      return field(name, FieldType.nullable(new ArrowType.Date(DateUnit.DAY)));
    } else if (rawType == java.sql.Timestamp.class) {
      return field(name, FieldType.nullable(new ArrowType.Timestamp(TimeUnit.MICROSECOND, null)));
    } else if (rawType == java.time.Instant.class) {
      return field(name, FieldType.nullable(new ArrowType.Timestamp(TimeUnit.MICROSECOND, null)));
    } else if (rawType == String.class) {
      return field(name, FieldType.nullable(ArrowType.Utf8.INSTANCE));
    } else if (rawType.isEnum()) {
      return field(name, FieldType.nullable(ArrowType.Utf8.INSTANCE));
    } else if (rawType.isArray()) { // array
      Field f =
          inferField(
              DataTypes.ARRAY_ITEM_NAME,
              Objects.requireNonNull(typeRef.getComponentType()),
              seenTypeSet);
      return DataTypes.arrayField(name, f);
    } else if (TypeUtils.ITERABLE_TYPE.isSupertypeOf(typeRef)) { // iterable
      // when type is both iterable and bean, we take it as iterable in row-format
      Field f =
          inferField(DataTypes.ARRAY_ITEM_NAME, TypeUtils.getElementType(typeRef), seenTypeSet);
      return DataTypes.arrayField(name, f);
    } else if (TypeUtils.MAP_TYPE.isSupertypeOf(typeRef)) {
      Tuple2<TypeRef<?>, TypeRef<?>> kvType = TypeUtils.getMapKeyValueType(typeRef);
      Field keyField = inferField(MapVector.KEY_NAME, kvType.f0, seenTypeSet);
      // Map's keys must be non-nullable
      FieldType keyFieldType =
          new FieldType(
              false, keyField.getType(), keyField.getDictionary(), keyField.getMetadata());
      keyField = DataTypes.field(keyField.getName(), keyFieldType, keyField.getChildren());
      Field valueField = inferField(MapVector.VALUE_NAME, kvType.f1, seenTypeSet);
      return DataTypes.mapField(name, keyField, valueField);
    } else if (TypeUtils.isBean(rawType)) { // bean field
      if (seenTypeSet.contains(rawType)) {
        String msg =
            String.format(
                "circular references in bean class is not allowed, but got " + "%s in %s",
                rawType, seenTypeSet);
        throw new UnsupportedOperationException(msg);
      }
      List<Field> fields =
          Descriptor.getDescriptors(rawType).stream()
              .map(
                  descriptor -> {
                    LinkedHashSet<Class<?>> newSeenTypeSet = new LinkedHashSet<>(seenTypeSet);
                    newSeenTypeSet.add(rawType);
                    String n = StringUtils.lowerCamelToLowerUnderscore(descriptor.getName());
                    return inferField(n, descriptor.getTypeRef(), newSeenTypeSet);
                  })
              .collect(Collectors.toList());
      return DataTypes.structField(name, true, fields);
    } else {
      throw new UnsupportedOperationException(
          String.format(
              "Unsupported type %s for field %s, seen type set is %s", typeRef, name, seenTypeSet));
    }
  }