{% extends 'template.html' %}

{% block title %}Module Search{% endblock %}

{% block header %}

<script>

    let currentSearchMeta = undefined;

    function toggleChildCheckbox(event)
    {
        let checkbox = $(event.target).find("input")[0];
        checkbox.checked = !checkbox.checked;
        performSearch();
    }

    function prevResults() {
        if (currentSearchMeta && currentSearchMeta.prev_offset !== undefined) {
            performSearch(currentSearchMeta.prev_offset);
        }
    }
    function nextResults() {
        if (currentSearchMeta && currentSearchMeta.next_offset !== undefined) {
            performSearch(currentSearchMeta.next_offset);
        }
    }

    function getFilterProviders() {
        let providers = [];
        // Iterate over provider filter checkboxes and generate
        // query string
        $('#provider-filters').find('input').each((index, element) => {
            let j_element = $(element);
            if (j_element.is(':checked')) {
                providers.push(j_element.data('providerName'));
            }
        });
        return providers;
    }
    function getFilterNamespaces() {
        let namespaces = [];
        // Iterate over namespace filter checkboxes and generate
        // query string
        $('#namespace-filters').find('input').each((index, element) => {
            let j_element = $(element);
            if (j_element.is(':checked')) {
                namespaces.push(j_element.data('namespaceName'));
            }
        });
        return namespaces;
    }

    let previousSearchString = undefined;
    function performSearch(new_offset) {

        let searchQuery = $('#search-query-string')[0].value;

        // Mark search query breadcrumb as active
        document.getElementById('searchQueryBreadcrumbParent').className = "is-active";
        document.getElementById('searchBreadcrumb').className = "";

        // Display search breadcrumb
        $('#searchQueryBreadcrumbParent')[0].style.display = 'flex';

        // Update link and text in search query breadcrumb
        document.getElementById('searchQueryBreadcrumb').setAttribute('href', '/modules/search?q=' + encodeURIComponent(searchQuery));
        document.getElementById('searchQueryBreadcrumb').innerHTML = searchQuery;

        if (new_offset === undefined) {
            new_offset = 0;
        }

        // Clear any existing provider logo TOS
        // Check if element exists - on initial page load,
        // the element will not be present
        // on the page at this point.
        if ($('#provider-tos')[0] !== undefined) {
            $('#provider-tos')[0].innerHTML = '';
        }

        let query_string = '';
        getFilterProviders().forEach((provider) => {
            query_string += `&provider=${provider}`;
        });

        getFilterNamespaces().forEach((namespace) => {
            query_string += `&namespace=${namespace}`;
        });

        if ($('#search-terraform-version').val()) {
            query_string += `&target_terraform_version=${$('#search-terraform-version').val()}`;
        }

        // Perform AJAX query to obtain results
        $.get(`/v1/modules/search?` +
                `q=${encodeURIComponent(searchQuery)}&` +
                `offset=${new_offset}&` +
                `verified=${$('#search-verified').is(':checked')}&` +
                `trusted_namespaces=${$('#search-trusted-namespaces').is(':checked')}&` +
                `contributed=${$('#search-contributed').is(':checked')}&` +
                'include_count=true' +
                query_string,
                function(data, status) {

            // Update result count
            $('#result-count').text(`Showing results ${Math.min(data.meta.current_offset + 1, data.count)} - ${Math.min(data.meta.current_offset + data.meta.limit, data.count)} of ${data.count}`);

            if (data.modules.length == 0) {
                $('#results').html(`
                    No modules match your search criteria.
                    <br />
                    Please check for spelling errors and try again.
                `);

                // Disable prev/next buttons
                $('#prevButton').prop('disabled', true);
                $('#nextButton').prop('disabled', true);
                currentSearchMeta = undefined;
            } else {
                // Clear reuslts panel before adding results
                $('#results').html('');

                $('#prevButton').prop('disabled', (data.meta.prev_offset === undefined));
                $('#nextButton').prop('disabled', (data.meta.next_offset === undefined));
                currentSearchMeta = data.meta;

                // Iterate through modules
                data.modules.forEach((module) => {
                    createSearchResultCard('results', 'module', module);
                });
            }
        });

        if (searchQuery != previousSearchString) {

            // Update list of search filters
            $.get(`/v1/terrareg/modules/search/filters?q=${encodeURIComponent(searchQuery)}`, (data, status) => {
                $('#search-verified-count').html(data.verified);
                $('#search-trusted-namespaces-count').html(data.trusted_namespaces);
                $('#search-contributed-count').html(data.contributed);

                let current_filtered_provider = getFilterProviders();

                // Clear all providers
                $('#provider-filters').find('a').remove();
                Object.keys(data.providers).forEach((provider_name) => {

                    // Check if provider already exists and is checked
                    let checked = current_filtered_provider.indexOf(provider_name) !== -1;

                    // Add providers to provider filter
                    $('#provider-filters').append(`
                    <a class="panel-block" onclick="toggleChildCheckbox(event);">
                        <input data-provider-name="${provider_name}" id="provider-filter-${provider_name}" onchange="performSearch();" ${checked ? 'checked' : ''} type="checkbox" />
                            ${provider_name}
                        <span class="tag">${data.providers[provider_name]}</span>
                    </a>
                    `);
                });


                let current_filtered_namespaces = getFilterNamespaces();
                // Clear all namespaces
                $('#namespace-filters').find('a').remove();
                Object.keys(data.namespaces).forEach(async (namespaceName) => {

                    let namespaceDisplayName = namespaceName;
                    let namespaceDetails = await getNamespaceDetails(namespaceName);
                    if (namespaceDetails.display_name) {
                        namespaceDisplayName = namespaceDetails.display_name;
                    }

                    // Check if provider already exists and is checked
                    let checked = current_filtered_namespaces.indexOf(namespaceName) !== -1;

                    // Add providers to provider filter
                    $('#namespace-filters').append(`
                    <a class="panel-block" onclick="toggleChildCheckbox(event);">
                        <input data-namespace-name="${namespaceName}" id="namespace-filter-${namespaceName}" onchange="performSearch();" ${checked ? 'checked' : ''} type="checkbox" />
                            ${namespaceDisplayName}
                        <span class="tag">${data.namespaces[namespaceName]}</span>
                    </a>
                    `);
                });
            });

            previousSearchString = searchQuery;
        }
    }

    async function loadSearchUserPreferences() {
        let userPreferences = await getUserPreferences();
        $('#search-terraform-version').val(userPreferences['terraform-compatibility-version']);
    }

    function updateTerraformCompatibility() {
        // Store new terraform compatibility in user preferences
        userPreferencesUpdateTerraformCompatibilityVersion($('#search-terraform-version').val());

        // Perform search, using current offset
        performSearch(currentSearchMeta?.current_offset);
    }

    $(document).ready(async function () {
        const queryString = window.location.search;
        const urlParams = new URLSearchParams(queryString);
        const searchQuery = urlParams.get('q');

        await loadSearchUserPreferences();

        if (searchQuery) {
            $('#search-query-string').val(searchQuery);
        }
        performSearch();
    });
</script>
{% endblock %}

{% block content %}

<nav class="breadcrumb" aria-label="breadcrumbs">
    <ul>
        <li id="searchBreadcrumb"><a href="/modules/search">Search</a></li>
        <li id="searchQueryBreadcrumbParent"><a id="searchQueryBreadcrumb" href=""></a></li>
    </ul>
</nav>


<div class="columns">
    <div class="column is-one-fifth">
        <nav id="query-filters" class="panel">
            <p class="panel-heading">
              Search Query
            </p>
            <span class="panel-block">
                <p class="control has-icons-left">
                    <input class="input" type="text" id="search-query-string" placeholder="Query">
                    <span class="icon is-left">
                        <i class="fas fa-filter" aria-hidden="true"></i>
                    </span>
                </p>
            </span>
            <span class="panel-block">
                <button id="query-search-button" class="button" onclick="performSearch();">Search</button>
            </span>
        </nav>

        <nav class="panel">
            <p class="panel-heading">
              Filters
            </p>

            <a class="panel-block is-active" onclick="toggleChildCheckbox(event);">
                <input id="search-verified" onchange="performSearch();" type="checkbox" />
                <span class="panel-icon">
                    <i class="fas fa-thumbs-up" aria-hidden="true"></i>
                </span>
                {{ VERIFIED_MODULE_LABEL }}
                <span id="search-verified-count" class="tag"></span>
            </a>
            <a class="panel-block is-active" onclick="toggleChildCheckbox(event);">
                <input id="search-trusted-namespaces" onchange="performSearch();" type="checkbox" checked="checked" />
                <span class="panel-icon">
                    <i class="fas fa-check-circle" aria-hidden="true"></i>
                </span>
                {{ TRUSTED_NAMESPACE_LABEL }}
                <span id="search-trusted-namespaces-count" class="tag"></span>
            </a>
            <a class="panel-block" onclick="toggleChildCheckbox(event);">
                <input id="search-contributed" onchange="performSearch();" type="checkbox" />
                {{ CONTRIBUTED_NAMESPACE_LABEL }}
                <span id="search-contributed-count" class="tag"></span>
            </a>
        </nav>

        <nav id="provider-filters" class="panel">
            <p class="panel-heading">
              Providers
            </p>
        </nav>

        <nav id="namespace-filters" class="panel">
            <p class="panel-heading">
              Namespaces
            </p>
        </nav>

        <nav id="terraform-version-filters" class="panel">
            <p class="panel-heading">
              Terraform Compatibility
            </p>
            <span class="panel-block">
                <p class="control has-icons-left">
                    <input class="input" type="text" id="search-terraform-version" placeholder="Terraform Version">
                    <span class="icon is-left">
                        <i class="fas fa-filter" aria-hidden="true"></i>
                    </span>
                </p>
            </span>
            <span class="panel-block">
                <button id="search-options-update-button" class="button" onclick="updateTerraformCompatibility();">Update</button>
            </span>
        </nav>
    </div>
    <div class="column is-three-fifths">
        <section id="search-results-header">
            <span id="result-count"></span> 
        </section>
        <section id="results">
        </section>
        <section>
            <button class="button" id="prevButton" onclick="prevResults();">Prev</button>
            <button class="button" id="nextButton" onclick="nextResults();">Next</button>
        </section>

    </div>
</div>

{% endblock %}
