class PersistentQueryMetadata extends QueryMetadata {

  public synchronized void restart() {
    if (isClosed()) {
      throw new IllegalStateException(String.format(
          "Query with application id %s is already closed, cannot restart.",
          getQueryApplicationId()));
    }

    closeKafkaStreams();

    final KafkaStreams newKafkaStreams = buildKafkaStreams();
    materializationProvider = materializationProviderBuilder.flatMap(
        builder -> builder.apply(newKafkaStreams));

    resetKafkaStreams(newKafkaStreams);
    start();
  }

  public  PersistentQueryMetadata(
      final String statementString,
      final PhysicalSchema schema,
      final Set<SourceName> sourceNames,
      final DataSource sinkDataSource,
      final String executionPlan,
      final QueryId id,
      final Optional<MaterializationProviderBuilderFactory.MaterializationProviderBuilder>
          materializationProviderBuilder,
      final String queryApplicationId,
      final Topology topology,
      final KafkaStreamsBuilder kafkaStreamsBuilder,
      final QuerySchemas schemas,
      final Map<String, Object> streamsProperties,
      final Map<String, Object> overriddenProperties,
      final Consumer<QueryMetadata> closeCallback,
      final long closeTimeout,
      final QueryErrorClassifier errorClassifier,
      final ExecutionStep<?> physicalPlan,
      final int maxQueryErrorsQueueSize,
      final ProcessingLogger processingLogger
  );
  protected  PersistentQueryMetadata(
      final PersistentQueryMetadata other,
      final Consumer<QueryMetadata> closeCallback
  );

}