package io.delphi.qa.auto.awsmfrw.suppliers;

import com.fasterxml.jackson.databind.MappingIterator;
import com.fasterxml.jackson.dataformat.csv.CsvMapper;
import com.google.common.base.CaseFormat;
import com.google.gson.annotations.SerializedName;
import io.delphi.qa.auto.awsmfrw.common_baby.EnDelphiFsResourceList;
import io.delphi.qa.auto.awsmfrw.common_baby.IsaConstants;
import io.delphi.qa.auto.awsmfrw.common_baby.delphi.aws.EnAwsSecrets;
import io.delphi.qa.auto.awsmfrw.common_baby.delphi.aws.ICanFetchAwsSecret;
import io.delphi.qa.auto.awsmfrw.common_baby.exceptions.FeatureNotImplementedException;
import io.delphi.qa.auto.awsmfrw.managers.HlFileSystem;
import io.delphi.qa.auto.awsmfrw.managers.MgDelphi;
import io.delphi.qa.auto.awsmfrw.managers.helpers.db.bigTable.RowKeyTikTokIsrcDateStringBuilder;
import io.delphi.qa.auto.awsmfrw.models.ICanFetch;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.*;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.ads.data_health.dsp.status.EnAdsDataHealthDspStatusItems;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.ads.performance.EnAdsPerformanceGroupBys;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.ads.performance.EnAdsPerformanceSortBys;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.amazon.charts.EnAmazonChartsSortBys;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.amazon.charts.EnAmazonChartsSortOrderBys;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.amazon.charts.EnAmazonChartsTrackPositionsSortBys;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.amazon.charts.EnAmazonChartsTrackPositionsSummarySortBys;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.amazon.stations.EnAmazonStationsSortBys;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.companies.EnCompaniesSortBys;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.dapd.track_positions.EnPublicTrackPositionsPlaylistsCurrentTracklistInclude;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.dapd.track_positions.EnPublicTrackPositionsPlaylistsInclude;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.dapd.track_positions.playlists.EnPublicTrackPositions2PrevoiusPlaylistsGroupBys;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.dapd.track_positions.playlists.PlPublicTrackPositions2Playlist;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.data_health.status.EnDataHealthDspStatusItems;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.methods.params.*;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.spotify.*;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.stream_dates.PlStreamDate;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.streams.IRestParams_StreamsProjects;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.streams_new_liteners.IStreamsNewListeners;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.test_case.MlApi_TC;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.tiktok.top.EnTiktokChartsPeriodItems;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.tiktok.tracks.analytics.EnTiktokTracksAnalyticsMetricItems;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.track_positions.EnTrackPositionsPlaylistsInclude;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.track_positions.playlists.*;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.video_analytics.EnVideoAnalyticsGroupByItems;
import io.delphi.qa.auto.awsmfrw.models.api.rest.v3.video_analytics.EnVideoAnalyticsOnlyItems;
import io.delphi.qa.auto.awsmfrw.models.db.bigTable.BigtableTableName;
import io.delphi.qa.auto.awsmfrw.models.db.sql.pg.EnDelphiDbResourceList;
import io.delphi.qa.auto.awsmfrw.models.etl.MlEtl_TC;
import io.delphi.qa.auto.awsmfrw.models.l2.MlFw_L2RtiArtistOnboardingInput;
import org.apache.commons.lang3.tuple.ImmutablePair;
import org.apache.commons.lang3.tuple.Pair;
import org.testng.annotations.DataProvider;

import java.io.File;
import java.io.IOException;
import java.lang.reflect.Field;
import java.util.Arrays;
import java.util.List;
import java.util.stream.Stream;

@SuppressWarnings("DataProviderReturnType")
public class DelphiDataProvider
    implements IsaConstants,
        ICanFetchDsps,
        ICanFetchCountryCodes,
        ICanFetchVideoIds,
        ICanFetchChartGroups,
        ICanFetchIsrcs,
        ICanFetchProductFamilyNos,
        ICanFetchConfigKeys,
        ICanFetchConfigCatKeys,
        ICanFetchArtistIds,
        ICanFetchShazamCityIds,
        ICanFetchChartIds {

  protected static <T> String[] getSortBys(Class<T> clazz) {
    Field[] clazzFields = clazz.getDeclaredFields();
    return Arrays.stream(clazzFields)
        .filter(
            field ->
                Arrays.stream(field.getAnnotations())
                    .anyMatch(
                        annotation -> annotation.annotationType().getSimpleName().equals("SortBy")))
        .map(
            simple -> {
              try {
                return ((SerializedName)
                        Arrays.stream(simple.getAnnotations())
                            .filter(
                                o -> o.annotationType().getSimpleName().equals("SerializedName"))
                            .findFirst()
                            .orElseThrow(null))
                    .value();
              } catch (Exception e) {
                return CaseFormat.LOWER_CAMEL.to(CaseFormat.LOWER_UNDERSCORE, simple.getName());
              }
            })
        .toArray(String[]::new);
  }

  protected static final MgDelphi delphi = new MgDelphi();

  @DataProvider(parallel = true)
  public static Object[] withAIsrc() {
    String START_DATE = ICanFetch.fetchItem(EnDelphiFsResourceList.D365);
    Pair<String, String> rowKey = new ImmutablePair<>(new RowKeyTikTokIsrcDateStringBuilder("isrc_date_week", "0",
            START_DATE).toString(), "");
    return delphi.db().bigTable(ICanFetchAwsSecret.pullAwsSecret(EnAwsSecrets.DELPHI_API_BT_PARAMS))
            .getRowValuesFromBigTable(BigtableTableName.FACT_TIKTOK_TOP_ISRC_SOUNDS_WEEKLY, rowKey, List.of("isrc"))
            .stream().map(a->a.get("isrc")).toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withAdsDataHealthStatusItems() {
    return Arrays.stream(EnAdsDataHealthDspStatusItems.values())
        .map(EnAdsDataHealthDspStatusItems::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withAdsPerformanceGroupBys() {
    return Arrays.stream(EnAdsPerformanceGroupBys.values())
        .map(EnAdsPerformanceGroupBys::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withAmazonStationSortBys() {
    return Arrays.stream(EnAmazonStationsSortBys.values())
            .map(EnAmazonStationsSortBys::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withAmazonChartsSortBys() {
    return Arrays.stream(EnAmazonChartsSortBys.values())
            .map(EnAmazonChartsSortBys::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withAmazonChartsTrackPositionsSortBys() {
    return Arrays.stream(EnAmazonChartsTrackPositionsSortBys.values())
            .map(EnAmazonChartsTrackPositionsSortBys::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withAmazonChartsTrackPositionsSummarySortBys() {
    return Arrays.stream(EnAmazonChartsTrackPositionsSummarySortBys.values())
            .map(EnAmazonChartsTrackPositionsSummarySortBys::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withAmazonChartsSortOrderBys() {
    return Arrays.stream(EnAmazonChartsSortOrderBys.values())
            .map(EnAmazonChartsSortOrderBys::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withAdsPerformanceSortBys() {
    return Arrays.stream(EnAdsPerformanceSortBys.values())
        .map(EnAdsPerformanceSortBys::get)
        .toArray();
  }

  private static Object[] withCombinations(Object[] baseObjects, Object[] objects) {
    Object[] data = new Object[baseObjects.length * objects.length][];
    int k = 0;
    for (int j = 0; j < baseObjects.length; j++) {
      for (int i = 0; i < objects.length; i++) {
        data[j + i + k] = new Object[] {baseObjects[j], objects[i]};
      }
      k = objects.length - 1;
    }
    //    return Arrays.stream(data).filter(Objects::nonNull).toArray(Object[]::new);
    return data;
  }

  @DataProvider(parallel = true)
  public static Object[] withCompaniesSortBys() {
    return Arrays.stream(EnCompaniesSortBys.values()).map(EnCompaniesSortBys::name).toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withDae4506ChartIds() {
    return Stream.generate(String::new).map(o -> "youtube_trending_us").limit(100).toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withDataHealthStatusItems() {
    return Arrays.stream(EnDataHealthDspStatusItems.values())
        .map(EnDataHealthDspStatusItems::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withTiktokTopTracksChartsPeriods() {
    return Arrays.stream(EnTiktokChartsPeriodItems.values())
        .map(EnTiktokChartsPeriodItems::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withDebugIds() {
    return Stream.generate(String::new).map(o -> "GRAS_92274").limit(100).toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withGroupByOther() {
    return Arrays.stream(EnAdsPerformanceGroupBys.values())
        .map(EnAdsPerformanceGroupBys::name)
        .map(String::toLowerCase)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withPlaylistTypes() {
    return Arrays.stream(EnDelphiApiV3_PlaylistTypeItems.values())
        .map(EnDelphiApiV3_PlaylistTypeItems::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withSortByOther() {
    return Arrays.stream(EnAdsPerformanceSortBys.values())
        .map(EnAdsPerformanceSortBys::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withSortOrders() {
    return Arrays.stream(EnDelphiApiV3_SortOrderItems.values())
        .map(EnDelphiApiV3_SortOrderItems::name)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withSortOrders_andAdsPerformanceSortBys() {
    return withCombinations(withSortOrders(), withAdsPerformanceSortBys());
  }

  @DataProvider(parallel = true)
  public static Object[] withSortOrders_andStreamDatesSortBys() {
    return withCombinations(withSortOrders(), withStreamDatesSortBys());
  }

  @DataProvider(parallel = true)
  public static Object[] withSortOrders_andTrackPosition2PlaylistSortBys() {
    return withCombinations(withSortOrders(), withTrackPosition2PlaylistSortBys());
  }

  @DataProvider(parallel = true)
  public static Object[] withSortOrders_andTrackPosition2PlaylistDatesSortBys() {
    return withCombinations(withSortOrders(), withTrackPosition2PlaylistDatesGroupBys());
  }

  @DataProvider(parallel = true)
  public static Object[] withSortOrders_andTrackPosition2PlaylistCurrentTracklistSortBys() {
    return withCombinations(withSortOrders(), withTrackPosition2PlaylistCurrentTracklistGroupBys());
  }

  @DataProvider(parallel = true)
  public static Object[] withSortOrders_andPublicTrackPosition2PlaylistSortBys() {
    return withCombinations(withSortOrders(), withPublicTrackPosition2PlaylistSortBys());
  }

  @DataProvider(parallel = true)
  public static Object[] withPublicTrackPosition2PlaylistSortBys() {
    return getSortBys(PlPublicTrackPositions2Playlist.class);
  }

  @DataProvider(parallel = true)
  public static Object[] withSortOrders_andTrackPosition2PreviousPlaylistSortBys() {
    return withCombinations(withSortOrders(), withTrackPosition2PreviousPlaylistGroupBys());
  }

  @DataProvider(parallel = true)
  public static Object[] withSortOrders_andPublicTrackPosition2PreviousPlaylistSortBys() {
    return withCombinations(withSortOrders(), withPublicTrackPosition2PreviousPlaylistGroupBys());
  }

  @DataProvider(parallel = true)
  public static Object[] withPublicTrackPosition2PreviousPlaylistGroupBys() {
    return Arrays.stream(EnPublicTrackPositions2PrevoiusPlaylistsGroupBys.values())
            .map(EnPublicTrackPositions2PrevoiusPlaylistsGroupBys::name)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withTrackPosition2PreviousPlaylistGroupBys() {
    return Arrays.stream(EnTrackPositions2PrevoiusPlaylistsGroupBys.values())
            .map(EnTrackPositions2PrevoiusPlaylistsGroupBys::name)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withTrackPosition2PlaylistDatesGroupBys() {
    return Arrays.stream(EnTrackPositions2PlaylistsDatesGroupBys.values())
            .map(EnTrackPositions2PlaylistsDatesGroupBys::name)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withTrackPosition2PlaylistCurrentTracklistGroupBys() {
    return Arrays.stream(EnTrackPositions2PlaylistsCurrentTracklistGroupBys.values())
            .map(EnTrackPositions2PlaylistsCurrentTracklistGroupBys::name)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withStreamDatesSortBys() {
    return getSortBys(PlStreamDate.class);
  }

  @DataProvider(parallel = true)
  public static Object[] withTiktokTracksAnalyticsMetrics() {
    return Arrays.stream(EnTiktokTracksAnalyticsMetricItems.values())
        .map(EnTiktokTracksAnalyticsMetricItems::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withTrackPosition2PlaylistGroupBys() {
    return Arrays.stream(EnTrackPositions2PlaylistsGroupBys.values())
        .map(EnTrackPositions2PlaylistsGroupBys::name)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withTrackPosition2PlaylistIncludes() {
    return Arrays.stream(EnTrackPositionsPlaylistsInclude.values())
        .map(EnTrackPositionsPlaylistsInclude::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withPublicTrackPosition2PlaylistIncludes() {
    return Arrays.stream(EnPublicTrackPositionsPlaylistsInclude.values())
            .map(EnPublicTrackPositionsPlaylistsInclude::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withStreamItemsIncludes() {
    return Arrays.stream(EnDelphiApiV3_StreamsItems.values())
            .map(EnDelphiApiV3_StreamsItems::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withPublicTrackPosition2PlaylistCurrentTracklistIncludes() {
    return Arrays.stream(EnPublicTrackPositionsPlaylistsCurrentTracklistInclude.values())
            .map(EnPublicTrackPositionsPlaylistsCurrentTracklistInclude::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withTrackPosition2PlaylistSortBys() {
    return getSortBys(PlTrackPositions2Playlist.class);
  }

  @DataProvider(parallel = true)
  public static Object[] withChartsTracksTrackStateIncludes() {
    return Arrays.stream(EnDelphiApiChartsTracksIncludeItems.values())
            .map(EnDelphiApiChartsTracksIncludeItems::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public static Object[] withTracksChartsTrackStateIncludes() {
    return Arrays.stream(EnDelphiApiTracksChartsIncludeItems.values())
            .map(EnDelphiApiTracksChartsIncludeItems::get)
            .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withArtistIds(String platform) {
    return fetchArtistIds(
            DelphiDataContainer.genMlAdsPerformance(platform)
                    .withIsAssigned(true)
                    .withIsPending(null))
            .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withChartGroups() {
    return fetchChartGroups().toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withConfigCatKeys() {
    return fetchConfigCatKeys().toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withConfigKeys() {
    return ICanFetch.fetchItems(EnDelphiDbResourceList.CONFIG_KEY).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withCountryCodes() {
    return fetchCountryCodes(false).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withDelphiApiGetAdsPerformanceTcs() {
    return new HlFileSystem()
        .listObjectsFromJson(
            new MlApi_TC(),
            EnDelphiFsResourceList.GENERIC_TEST_CASE_API_GET_ADS_PERFORMANCE.resourceLocator()
                + EnDelphiFsResourceList.GENERIC_TEST_CASE_API_GET_ADS_PERFORMANCE.resourceName())
        .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withDelphiApiGetProductsTcs() {
    return new HlFileSystem()
        .listObjectsFromJson(
            new MlApi_TC(),
            EnDelphiFsResourceList.GENERIC_TEST_CASE_API_GET_PRODUCTS.resourceLocator()
                + EnDelphiFsResourceList.GENERIC_TEST_CASE_API_GET_PRODUCTS.resourceName())
        .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withDelphiApiGetVideoPositionsChartsSummaryTcs() {
    return new HlFileSystem()
        .listObjectsFromJson(
            new MlApi_TC(),
            EnDelphiFsResourceList.GENERIC_TEST_CASE_API_GET_VIDEO_POSITIONS_CHARTS_SUMMARY
                    .resourceLocator()
                + EnDelphiFsResourceList.GENERIC_TEST_CASE_API_GET_VIDEO_POSITIONS_CHARTS_SUMMARY
                    .resourceName())
        .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withEtlSnowflakeExportToPostgresLinkfireTcs() {
    return new HlFileSystem()
        .listObjectsFromJson(
            new MlEtl_TC(),
            EnDelphiFsResourceList.GENERIC_TEST_CASE_ETL_LINKFIRE.resourceLocator()
                + EnDelphiFsResourceList.GENERIC_TEST_CASE_ETL_LINKFIRE.resourceName())
        .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withGroupBys_andAdsPerformanceArtistIds() {
    return withCombinations(withAdsPerformanceGroupBys(), withArtistIds("Facebook"));
  }

  @DataProvider(parallel = true)
  public Object[] withIsrcs() {
    return fetchIsrcs().stream().limit(10).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withDapdPlaylistIds() {
    return fetchDapdPlaylists().stream().limit(10).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withTopIsrcs() {
    return fetchTopIsrcs().stream().limit(10).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withL2DapdIsrc() {
    return fetchDapdIsrcs().stream().limit(10).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withL2DapdAmazonIsrc() {
    return fetchDapdAmazonIsrcs().stream().limit(10).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withL2RtiArtistOnboardingCsvTcs() {
    try {
      MappingIterator<MlFw_L2RtiArtistOnboardingInput> mappingIterator =
          new CsvMapper()
              .readerFor(MlFw_L2RtiArtistOnboardingInput.class)
              .with(new CsvMapper().schemaWithHeader())
              .readValues(
                  new File(
                      EnDelphiFsResourceList.GENERIC_TEST_CASE_L2_RTI_ONBOARDING_CSV
                              .resourceLocator()
                          + EnDelphiFsResourceList.GENERIC_TEST_CASE_L2_RTI_ONBOARDING_CSV
                              .resourceName()));
      return mappingIterator.readAll().toArray();
    } catch (IOException e) {
      throw new FeatureNotImplementedException(e.getMessage());
    }
  }

  @DataProvider(parallel = true)
  public Object[] withL2RtiArtistOnboardingJsonTcs() {
    return new HlFileSystem()
        .listObjectsFromJson(
            new MlFw_L2RtiArtistOnboardingInput(),
            EnDelphiFsResourceList.GENERIC_TEST_CASE_L2_RTI_ONBOARDING.resourceLocator()
                + EnDelphiFsResourceList.GENERIC_TEST_CASE_L2_RTI_ONBOARDING.resourceName())
        .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withL2SupportArtistOnboardedArtistIds() {
    try {
      MappingIterator<MlFw_L2RtiArtistOnboardingInput> mappingIterator =
          new CsvMapper()
              .readerFor(MlFw_L2RtiArtistOnboardingInput.class)
              .with(new CsvMapper().schemaWithHeader())
              .readValues(
                  new File(
                      EnDelphiFsResourceList.GENERIC_TEST_CASE_L2_RTI_ONBOARDING_CSV
                              .resourceLocator()
                          + EnDelphiFsResourceList.GENERIC_TEST_CASE_L2_RTI_ONBOARDING_CSV
                              .resourceName()));
      return mappingIterator.readAll().stream()
          .map(MlFw_L2RtiArtistOnboardingInput::getGrasId)
          .map(o -> String.format("GRAS_%s", o))
          .toArray(String[]::new);
    } catch (IOException e) {
      throw new FeatureNotImplementedException(e.getMessage());
    }
  }

  @DataProvider(parallel = true)
  public Object[] withProductFamilyNos() {
    return fetchProductFamilyNos().toArray();
  }

  // List<MlEtl_TestCase[]> etlTestCases = delphi.fs().listObjectsFromJson(new MlEtl_TestCase[],
  // "src/test/resources/tdata/etl/snowflake2postgres/tcs_linkfire.json");

  @DataProvider(parallel = true)
  public Object[] withShazamChartId_andTopCountryCode() {
    String countryCode = fetchCountryCode(true);
    return withCombinations(fetchShazamChartIds(countryCode).toArray(), new String[] {countryCode});
  }

  @DataProvider(parallel = true)
  public Object[] withShazamChartIds() {
    String countryCode = fetchCountryCode(true);
    return fetchShazamChartIds(countryCode).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withSortOrdersAndStreamDsps() {
    return withCombinations(withSortOrders(), withStreamDsps());
  }

  @DataProvider(parallel = true)
  public Object[] withSpotifyChartTypes() {
    return Arrays.stream(EnDelphiApiChartsTypeItems.values())
        .map(EnDelphiApiChartsTypeItems::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withSpotifyChartMetrics() {
    return Arrays.stream(EnDelphiApiSpotifyChartsAnalyticsMetricsItems.values())
        .map(EnDelphiApiSpotifyChartsAnalyticsMetricsItems::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withChartBreakdowns() {
    return Arrays.stream(EnDelphiApiSpotifyChartBreakdownItems.values())
        .map(EnDelphiApiSpotifyChartBreakdownItems::get)
        .toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withStreamDsps() {
    return fetchStreamDsps().toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withTopCountryCodes() {
    return fetchCountryCodes(true).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withVideoDsps() {
    return fetchVideoDsps().toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withVideoIds() {
    return
    //        envConfig.env().equals("stage")
    //        ? new String[] {
    //          "youtube_bQOh1cvMo00",
    //          "youtube_TToMr95Zt6s",
    //          "youtube_hqnbKS_SNCM",
    //          "youtube_Ix4L9am2Kwk",
    //          "youtube_JXgV1rXUoME",
    //          "youtube_NJea386275c",
    //          "youtube_OjHAOvR8kps",
    //          "youtube_TToMr95Zt6s"
    //        }
    //        :
    fetchVideoIds().stream().limit(5).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withVideoIsrcs() {
    return envConfig.env().equals("stage")
        ? new String[] {"USQX92003025", "USSM10804556", "USSM12004756", "USSM11912587"}
        : fetchVideoIsrcs().stream().limit(5).toArray();
  }

  @DataProvider(parallel = true)
  public Object[] withAppleMusicChartMetrics() {
      return new String[]{"positions"};
  }

    @DataProvider(parallel = true)
    public Object[] withMetricsDimensions() {
        return Arrays.stream(EnDelphiApiV3_MetricsDimensions.values())
                .map(EnDelphiApiV3_MetricsDimensions::get)
                .toArray();
    }

    @DataProvider
    public static Object[] withStreamsProjectSortBys() {
        return IRestParams_StreamsProjects.sortByData().toArray();
    }

    @DataProvider
    public static Object[] withStreamsNewListenersSortBys() {
        return IStreamsNewListeners.sortByData().toArray();
    }

    @DataProvider(parallel = true)
    public static Object[] withChartsDataHealthStatuses() {
        return Arrays.stream(EnDelphiApiV3_ChartsDataHealthStatus.values())
                .map(EnDelphiApiV3_ChartsDataHealthStatus::get)
                .toArray();
    }

    @DataProvider(parallel = true)
    public static Object[] withVideoAnalyticsOnly() {
        return Arrays.stream(EnVideoAnalyticsOnlyItems.values())
                .map(EnVideoAnalyticsOnlyItems::name)
                .toArray();
    }

    @DataProvider(parallel = true)
    public static Object[] withVideoAnalyticsGroupBy() {
        return Arrays.stream(EnVideoAnalyticsGroupByItems.values())
                .map(EnVideoAnalyticsGroupByItems::name)
                .toArray();
    }

    @DataProvider(parallel = true)
    public static Object[] withTiktokChartTypes() {
        return new String[]{
                "top50_1day_isrc_period_creations_worldwide",
                "top50_7day_isrc_period_creations_worldwide",
                "top50_1day_isrc_period_creations_change_worldwide",
                "top50_7day_isrc_period_creations_change_worldwide",
                "top50_1day_product_family_period_creations_worldwide",
                "top50_7day_product_family_period_creations_worldwide",
            "top50_1day_product_family_period_creations_change_worldwide",
            "top50_7day_product_family_period_creations_change_worldwide"};
  }

  @DataProvider(parallel = true)
  public static Object[] withSortByRange() {
    return new String[]{
            "streams_days_7",
            "streams_days_8_14",
            "streams_change_7_to_14_days",
            "streams_change_percent_7_to_14_days"};
  }
}
