class StructuredData {

  public static synchronized void initFromConfiguration(IndexingService indexingService) {
    ImmutableList.Builder<DateTimeParser> listBuilder = new ImmutableList.Builder<>();
    listBuilder.addAll(DEFAULT_DATETIME_PARSERS);
    List<String> dateTimePatterns =
        Configuration.getMultiValue(
            DATETIME_PATTERNS, Collections.emptyList(), Configuration.STRING_PARSER,
            DATETIME_PATTERNS_DELIMITER)
        .get();
    InvalidConfigurationException patternErrors = null;
    for (String pattern : dateTimePatterns) {
      try {
        listBuilder.add(new DateTimeParser(pattern));
      } catch (IllegalArgumentException e) {
        InvalidConfigurationException ice = new InvalidConfigurationException(
            "Invalid date-time pattern \"" + pattern + "\": " + e.getMessage());
        if (patternErrors == null) {
          patternErrors = ice;
        } else {
          patternErrors.addSuppressed(ice);
        }
      }
    }
    if (patternErrors != null) {
      throw patternErrors;
    }
    dateTimeParsers.set(listBuilder.build());

    Schema schema;
    String localSchemaPath = Configuration.getString(LOCAL_SCHEMA, "").get();
    if (!localSchemaPath.isEmpty()) {
      Path localSchema = Paths.get(localSchemaPath);
      if (!Files.exists(localSchema)) {
        throw new InvalidConfigurationException(
            "Local schema file " + localSchemaPath + " does not exist");
      }

      try {
        InputStreamReader inputStreamReader = new InputStreamReader(
            localSchema.toUri().toURL().openStream(), defaultCharset());
        schema = JSON_PARSER.parseAndClose(inputStreamReader, Schema.class);
      } catch (IOException e) {
        throw new StartupException("Failed to parse local schema file " + localSchemaPath, e);
      }
    } else {
      try {
        schema = indexingService.getSchema();
      } catch (IOException e) {
        throw new StartupException("Failed to initialize StructuredData", e);
      }
    }
    init(schema);
  }

  private  StructuredData(ObjectDefinition objectDefinition);

}