ConfigMapper { static Object convertToObject(final String value, final Type genericType) { if (value == null) { return null; } Class<?> type = getDataType(genericType); try { if (type.equals(String.class)) { return value; } else if (type.equals(Byte.class) || type.equals(byte.class)) { return Byte.valueOf(value); } else if (type.equals(Integer.class) || type.equals(int.class)) { return Integer.valueOf(value); } else if (type.equals(Long.class) || type.equals(long.class)) { return Long.valueOf(value); } else if (type.equals(Short.class) || type.equals(short.class)) { return Short.valueOf(value); } else if (type.equals(Float.class) || type.equals(float.class)) { return Float.valueOf(value); } else if (type.equals(Double.class) || type.equals(double.class)) { return Double.valueOf(value); } else if (type.equals(Boolean.class) || type.equals(boolean.class)) { return parseBoolean(value); } else if ((type.equals(Character.class) || type.equals(char.class)) && value.length() > 0) { return value.charAt(0); } else if (List.class.isAssignableFrom(type)) { final Class<?> itemType = getGenericsParam(genericType, 0); return stringToList(value, itemType); } else if (Map.class.isAssignableFrom(type)) { final Class<?> keyType = getGenericsParam(genericType, 0); final Class<?> valueType = getGenericsParam(genericType, 1); return stringToMap(value, keyType, valueType); } else if (type.equals(DocRef.class)) { return stringToDocRef(value); } else if (Enum.class.isAssignableFrom(type)) { return stringToEnum(value, type); } else if (Path.class.isAssignableFrom(type)) { return Path.of(value); } else if (StroomDuration.class.isAssignableFrom(type)) { return StroomDuration.parse(value); } else if (ByteSize.class.isAssignableFrom(type)) { return ByteSize.parse(value); } } catch (Exception e) { LOGGER.debug(() -> LogUtil.message( "Unable to convert value [{}] to type {} due to: {}", value, genericType, e.getMessage()), e); throw new ConfigPropertyValidationException(LogUtil.message( "Unable to convert value [{}] to type {} due to: {}", value, getDataTypeName(genericType), e.getMessage()), e); } LOGGER.error("Unable to convert value [{}] of type [{}] to an Object", value, type); throw new ConfigPropertyValidationException(LogUtil.message( "Type [{}] is not supported for value [{}]", genericType, value)); } @Inject  ConfigMapper(final AppConfig appConfig); static void decorateWithPropertyPaths(final AppConfig appConfig); boolean validatePropertyPath(final PropertyPath fullPath); Optional<Prop> getProp(final PropertyPath propertyPath); static final String LIST_EXAMPLE; static final String MAP_EXAMPLE; static final String DOCREF_EXAMPLE; }
@Test void updateValues() { doUpdateValueTest( "stroom.primitive.booleanProp", tc -> tc.getTestPrimitiveConfig().isBooleanProp(), "true", Boolean::valueOf); doUpdateValueTest( "stroom.boxed.booleanProp", tc -> tc.getTestBoxedConfig().getBooleanProp(), "true", Boolean::valueOf); doUpdateValueTest( "stroom.primitive.intProp", tc -> tc.getTestPrimitiveConfig().getIntProp(), "999", Integer::parseInt); doUpdateValueTest( "stroom.boxed.intProp", tc -> tc.getTestBoxedConfig().getIntProp(), "999", Integer::parseInt); doUpdateValueTest( "stroom.primitive.longProp", tc -> tc.getTestPrimitiveConfig().getLongProp(), "999", Long::parseLong); doUpdateValueTest( "stroom.boxed.longProp", tc -> tc.getTestBoxedConfig().getLongProp(), "999", Long::parseLong); doUpdateValueTest( "stroom.stringProp", TestConfig::getStringProp, "yyyyyy", Function.identity()); doUpdateValueTest( "stroom.stroomDurationProp", TestConfig::getStroomDurationProp, "P1DT6H", StroomDuration::parse); doUpdateValueTest( "stroom.byteSizeProp", TestConfig::getByteSizeProp, "1MiB", ByteSize::parse); doUpdateValueTest( "stroom.docRefProp", TestConfig::getDocRefProp, ",docRef(aaaaaa,bbbbbbb,ccccccc)", str -> ConfigMapper.convertToObject(str, DocRef.class)); doUpdateValueTest( "stroom.stateProp", TestConfig::getStateProp, "ON", TestConfig.State::valueOf); }