package eu.dnetlib.scholix.api;

import eu.dnetlib.common.app.AbstractDnetApp;
import io.micrometer.core.aop.TimedAspect;
import io.micrometer.core.instrument.*;
import io.micrometer.core.instrument.config.MeterFilter;
import io.micrometer.core.instrument.distribution.DistributionStatisticConfig;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cache.annotation.EnableCaching;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.scheduling.annotation.EnableScheduling;
import springfox.documentation.builders.ApiInfoBuilder;
import springfox.documentation.builders.RequestHandlerSelectors;
import springfox.documentation.service.ApiInfo;
import springfox.documentation.spi.DocumentationType;
import springfox.documentation.spring.web.plugins.Docket;
import springfox.documentation.swagger2.annotations.EnableSwagger2;

import java.time.Duration;
import java.util.Arrays;
import java.util.List;

@SpringBootApplication
@EnableSwagger2
@EnableCaching
@EnableScheduling
@ComponentScan(basePackages = "eu.dnetlib")
public class MainApplication extends AbstractDnetApp {

	private double scale = 1000000000;

	private double[] histogramValues =new double[]{.005 * scale, .01 * scale, .25 * scale, .5 * scale, .75 * scale, scale, 2.5 * scale, 5.0 * scale, 7.5 * scale, 10.0 * scale};



	@Value("${dhp.swagger.api.host}")
	private String swaggetHost;

	@Value("${dhp.swagger.api.basePath}")
	private String swaggerPath;


	public static void main(final String[] args) {
		SpringApplication.run(MainApplication.class, args);
	}



	@Bean
	public TaggedCounter myCounter(MeterRegistry meterRegistry) {

		return new TaggedCounter(ScholixAPIConstants.SCHOLIX_MANAGER_COUNTER_NAME, ScholixAPIConstants.SCHOLIX_MANAGER_TAG_NAME,meterRegistry);
	}

	@Bean
	public TimedAspect timedAspect(MeterRegistry meterRegistry) {
		MeterFilter mf = new MeterFilter() {
			@Override
			public DistributionStatisticConfig configure(Meter.Id id, DistributionStatisticConfig config) {
				if (id.getName().startsWith(ScholixAPIConstants.SCHOLIX_COUNTER_PREFIX)) {

					return DistributionStatisticConfig.builder()
							.percentilesHistogram(false)
							.serviceLevelObjectives( histogramValues)
							.build()
							.merge(config);
				}
				return config;
			}
		};
		meterRegistry.config().meterFilter(mf);
		return new TimedAspect(meterRegistry);
	}


	@Override
	protected void configSwagger(final Docket docket) {
		docket
			.host(swaggetHost)
			.pathMapping(swaggerPath)
			.groupName(ScholixAPIConstants.API_V1_NAME)
			.select()
			.apis(RequestHandlerSelectors.any())
			.paths(p -> p.startsWith("/v1"))
			.build()
			.apiInfo(new ApiInfoBuilder()
				.title(ScholixAPIConstants.API_V1_NAME)
				.description(ScholixAPIConstants.API_DESCRIPTION)
				.version("1.0")
				.contact(ApiInfo.DEFAULT_CONTACT)
				.license("Apache 2.0")
				.licenseUrl("http://www.apache.org/licenses/LICENSE-2.0")
				.build());
	}



	@Bean (name = "SpringDocketv2")
	public Docket v2Docket() {
		final Docket docket = new Docket(DocumentationType.SWAGGER_2);
		docket
				.host(swaggetHost)
				.pathMapping(swaggerPath)
				.groupName(ScholixAPIConstants.API_V2_NAME)
				.select()
				.apis(RequestHandlerSelectors.any())
				.paths(p -> p.startsWith("/v2"))
				.build()
				.apiInfo(new ApiInfoBuilder()
						.title(ScholixAPIConstants.API_V2_NAME)
						.description(ScholixAPIConstants.API_DESCRIPTION)
						.version("2.0")
						.contact(ApiInfo.DEFAULT_CONTACT)
						.license("Apache 2.0")
						.licenseUrl("http://www.apache.org/licenses/LICENSE-2.0")
						.build());

		return docket;
	}

}
