'use strict';

Object.defineProperty(exports, '__esModule', { value: true });

var _enum = require('../components/_filters/filter-input/enum.js');
var utils$2 = require('../components/_inputs/date-range/utils.js');
var utils$1 = require('../components/_inputs/granular-date-range/utils.js');
var utils$3 = require('../components/_inputs/multi-select/utils.js');
var utils = require('../components/_reports/report-heading/report-columns/report-columns-form/utils.js');
var UserReports = require('../types/UserReports.js');
var logger = require('./logger.js');

/**
 * Gets the definition and fields by reportType
 *
 * @param {ReportType} reportType
 * @param {Services} services
 * @param {string} token
 * @param {string} reportId
 * @param {string} id
 * @param {string} [definitionsPath]
 */
const getDefinitionByType = async (reportType, services, token, reportId, id, definitionsPath) => {
    let definition;
    let fields;
    if (reportType === UserReports.ReportType.REPORT) {
        definition = await services.reportingService.getDefinition(token, reportId, id, definitionsPath);
        fields = getFields(definition);
    }
    else {
        definition = await services.dashboardService.getDefinition(token, reportId, id, definitionsPath);
        fields = getDashboardFields(definition);
    }
    if (!definition) {
        throw Error(`Unable to retrieve definition for ${reportType} with id:${id} & reportId:${reportId}`);
    }
    return {
        definition,
        fields,
    };
};
/**
 * Given a field id, gets its filter object
 *
 * @param {components['schemas']['FieldDefinition'][]} fields
 * @param {string} fieldId
 * @return {*}  {(components['schemas']['FilterDefinition'] | undefined)}
 */
const getFilter = (fields, fieldId) => {
    return fields.find((f) => f.name === fieldId)?.filter;
};
/**
 * Gets the current varaint definition
 *
 * @param {components['schemas']['ReportDefinitionSummary'][]} definitions
 * @param {string} reportId
 * @param {string} variantId
 * @return {*}  {(components['schemas']['VariantDefinition'] | undefined)}
 */
const getCurrentVariantDefinition = (definitions, reportId, variantId) => {
    if (!definitions) {
        logger.default.info('No definitions');
        return undefined;
    }
    let variantDef;
    const reportDef = definitions.find((report) => report.id === reportId);
    if (reportDef) {
        // TODO: this needs fixing, we should never be using `as unknown as`, but the types are very mixed up here
        variantDef = reportDef.variants.find((variant) => variantId === variant.id);
        return variantDef;
    }
    return undefined;
};
/**
 * Gets the display name of a field
 *
 * @param {(components['schemas']['FieldDefinition'][] | components['schemas']['SummaryField'][])} fields
 * @param {string} fieldId
 * @return {*}
 */
const getFieldDisplayName = (fields, fieldId) => {
    const ids = fieldId.split('.');
    const field = fields.find((f) => {
        return f.name === ids[0];
    });
    if (field) {
        return ids[1] ? `${field.display} ${ids[1]}` : field.display;
    }
    return fieldId;
};
/**
 * Gets a single field by its id/name
 *
 * @param {components['schemas']['FieldDefinition'][]} fields
 * @param {string} fieldId
 * @return {*}
 */
const getField = (fields, fieldId) => {
    return fields.find((field) => {
        return field.name === fieldId;
    });
};
/**
 * Get all fields from a definition
 *
 * @param {components['schemas']['SingleVariantReportDefinition']} definition
 * @return {*}  {components['schemas']['FieldDefinition'][]}
 */
const getFields = (definition) => {
    return definition.variant.specification?.fields || [];
};
/**
 * Get all fields from a definition
 *
 * @param {components['schemas']['SingleVariantReportDefinition']} definition
 * @return {*}  {components['schemas']['FieldDefinition'][]}
 */
const getDashboardFields = (definition) => {
    return definition.filterFields || [];
};
/**
 * Gets only the fields that have filters, from fields
 *
 * @param {components['schemas']['FieldDefinition'][]} fields
 * @return {*}  {FieldWithFilter[]}
 */
const getFieldsWithFilters = (fields) => {
    return fields.filter((f) => f.filter !== undefined);
};
/**
 * Gets the template type
 *
 * @param {components['schemas']['SingleVariantReportDefinition']} definition
 * @return {*}  {Template}
 */
const getTemplate = (definition) => {
    return definition.variant.specification?.template || 'list';
};
/**
 * Gets the filters from a variant
 *
 * @param {components['schemas']['FieldDefinition'][]} fields
 * @return {*}  {components['schemas']['FilterDefinition'][]}
 */
const getFilters = (fields) => {
    const filters = fields
        .filter((field) => field.filter)
        .map((field) => field.filter);
    return filters.length ? filters : [];
};
/**
 * Given an array of string names, will return the relative field types
 *
 * @param {string[]} names
 * @param {components['schemas']['FieldDefinition'][]} fields
 * @return {*}  {components['schemas']['FieldDefinition'][]}
 */
const getFieldsByName = (names, fields) => {
    return names.map((s) => fields.find((field) => field.name === s)).filter((field) => field !== undefined);
};
/**
 * Validates the definition
 *
 * @param {components['schemas']['SingleVariantReportDefinition']} definition
 * @return {*}
 */
const validateDefinition = (definition) => {
    const { variant } = definition;
    return validateVariant(variant, definition.id);
};
/**
 * Validates that the variant has a `specification`
 *
 * @param {components['schemas']['VariantDefinition']} variant
 * @return {*}
 */
const validateVariant = (variant, defId) => {
    const { specification } = variant;
    if (!specification) {
        logger.default.error(`No specification found for definition ID: ${defId} variant ID: ${variant.id}`);
        throw new Error(`No specification found for definition ID: ${defId} variant ID: ${variant.id}`);
    }
    return { variant, specification };
};
/**
 * Determines whether there are any interactive filters
 * defined in the definition
 *
 * @param {components['schemas']['FieldDefinition'][]} fields
 * @return {*}
 */
const hasInteractiveFilters = (fields) => {
    const filters = getFilters(fields);
    return filters.some((filter) => filter.interactive);
};
const getReportSummary = (reportId, reportingService, token, definitionPath) => reportingService.getDefinitionSummary(token, reportId, definitionPath);
/**
 * Creates a the default filters querystring
 *
 * @param {components['schemas']['FieldDefinition'][]} fields
 * @return {*}  {DefaultFilterQueryStrings}
 */
const getDefaultFiltersQueryString = (fields) => {
    const defaultParams = new URLSearchParams();
    const interactiveParams = new URLSearchParams();
    const fieldsWithFilters = getFieldsWithFilters(fields);
    fieldsWithFilters.forEach((field) => {
        const { interactive = false } = field.filter;
        appendFilterDefaults(interactive ? interactiveParams : defaultParams, field);
    });
    return {
        defaultFiltersSearch: buildQueryString(defaultParams),
        interactiveDefaultFiltersSearch: buildQueryString(interactiveParams),
    };
};
/**
 * Sets the default sort query string
 *
 * @param {components['schemas']['FieldDefinition'][]} fields
 * @return {*}
 */
const getDefaultSortQueryString = (fields) => {
    const defaultSortField = fields.find((field) => field.defaultsort);
    if (!defaultSortField) {
        return '';
    }
    const defaultSortParams = new URLSearchParams();
    const isAsc = (defaultSortField.sortDirection ?? 'asc') === 'asc';
    defaultSortParams.set('sortColumn', defaultSortField.name);
    defaultSortParams.set('sortedAsc', String(isAsc));
    return buildQueryString(defaultSortParams);
};
/**
 * Builds the querystring
 *
 * @param {URLSearchParams} params
 * @return {*}  {string}
 */
const buildQueryString = (params) => {
    const qs = params.toString();
    return qs || '';
};
/**
 * Appends the filter value to a query string
 *
 * @param {URLSearchParams} params
 * @param {FieldWithFilter} field
 */
const appendFilterDefaults = (params, field) => {
    const { name, filter } = field;
    const { type, defaultValue, defaultQuickFilterValue } = filter;
    if (!defaultValue && !defaultQuickFilterValue)
        return;
    switch (type.toLowerCase()) {
        case _enum.FilterType.radio.toLowerCase():
        case _enum.FilterType.select.toLowerCase():
        case _enum.FilterType.text.toLowerCase():
        case _enum.FilterType.date.toLowerCase():
        case _enum.FilterType.autocomplete.toLowerCase(): {
            if (!defaultValue)
                break;
            params.append(`filters.${name}`, defaultValue);
            break;
        }
        case _enum.FilterType.multiselect.toLowerCase(): {
            if (!defaultValue)
                break;
            utils$3.appendMultiSelectValues(params, name, defaultValue);
            break;
        }
        case _enum.FilterType.dateRange.toLowerCase(): {
            const resolved = utils$2.resolveDateRangeDefaults(filter);
            if (!resolved)
                break;
            utils$2.appendDateRangeValue(params, name, resolved);
            break;
        }
        case _enum.FilterType.granularDateRange.toLowerCase(): {
            const resolved = utils$1.resolveGranularDateRangeDefaults(filter);
            if (!resolved)
                break;
            utils$1.appendGranularDateRangeValue(params, name, resolved);
            break;
        }
    }
};
/**
 * Get the default columns from the DPD
 * and creates a querystring
 *
 * @param {components['schemas']['FieldDefinition'][]} fields
 * @return {*}
 */
const getDefaultColumnsQueryString = (fields) => {
    const visibleCols = utils.visibleColumns(fields);
    const mandatoryCols = utils.mandatoryColumns(fields);
    const defaultColumns = Array.from(new Set([...mandatoryCols, ...visibleCols]));
    const params = new URLSearchParams();
    defaultColumns.forEach((column) => {
        params.append('columns', column);
    });
    return buildQueryString(params);
};
var DefinitionUtils = {
    getCurrentVariantDefinition,
    getFieldDisplayName,
    getField,
    getFields,
    getTemplate,
    getFilter,
    getFilters,
    getReportSummary,
    hasInteractiveFilters,
    getDefaultFiltersQueryString,
    getDefaultColumnsQueryString,
    getDefinitionByType,
};

exports.default = DefinitionUtils;
exports.getCurrentVariantDefinition = getCurrentVariantDefinition;
exports.getDashboardFields = getDashboardFields;
exports.getDefaultColumnsQueryString = getDefaultColumnsQueryString;
exports.getDefaultFiltersQueryString = getDefaultFiltersQueryString;
exports.getDefaultSortQueryString = getDefaultSortQueryString;
exports.getDefinitionByType = getDefinitionByType;
exports.getField = getField;
exports.getFieldDisplayName = getFieldDisplayName;
exports.getFields = getFields;
exports.getFieldsByName = getFieldsByName;
exports.getFieldsWithFilters = getFieldsWithFilters;
exports.getFilter = getFilter;
exports.getFilters = getFilters;
exports.getReportSummary = getReportSummary;
exports.getTemplate = getTemplate;
exports.hasInteractiveFilters = hasInteractiveFilters;
exports.validateDefinition = validateDefinition;
exports.validateVariant = validateVariant;
//# sourceMappingURL=definitionUtils.js.map
