/* exprfilter.cc
 * This file belongs to Worker, a file manager for UN*X/X11.
 * Copyright (C) 2014-2025 Ralf Hoffmann.
 * You can contact me at: ralf@boomerangsworld.de
 *   or http://www.boomerangsworld.de/worker
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 */

#include "exprfilter.hh"
#include "exprfilter_parser.hh"
#include "exprfilter_evalatoms.hh"

ExprFilter::ExprFilter( const std::string &filter,
                        const ExprFilterOptions &options ) :
    m_filter_string( filter )
{
    std::list< ExprToken > tokens;

    exprfilter_scan_expr( filter.c_str(), tokens );

    ExprFilterParser efp( tokens, options );

    efp.parse( &m_efe );

    m_valid_reconstructed_filter = efp.getValidReconstructedFilter();
    m_valid = efp.valid();
    m_expected_tokens = efp.getListOfExpectedTokens();

    // ignore errors on purpose here, whatever is reasonable ok will be used
}

ExprFilter::~ExprFilter()
{
}

bool ExprFilter::check( NWCEntrySelectionState &e )
{
    try {
        m_check_result = m_efe.eval( e );
    } catch ( int ) {
        // default value in case of errors is true, match any entry
        m_check_result = { true, {} };
    }

    return m_check_result.result;
}

const ExprFilterEval::result_item &ExprFilter::get_results() const
{
    return m_check_result;
}

std::string ExprFilter::getValidReconstructedFilter() const
{
    return m_valid_reconstructed_filter;
}

std::list< std::string > ExprFilter::getListOfExpectedStrings() const
{
    std::list< std::string > res;

    for ( auto &e : m_expected_tokens ) {
        res.push_back( e.description );
    }

    return res;
}

std::list< ExprFilterParser::token_help > ExprFilter::getListOfExpectedTokens() const
{
    return m_expected_tokens;
}

bool ExprFilter::containsTypeExpression() const
{
    return m_efe.contains<ExprAtomTypeCmp>();
}

void ExprFilter::setCheckInterrupt( std::function< bool () > interrupt_cb )
{
    m_efe.setCheckInterrupt( interrupt_cb );
}

void ExprFilter::setFeedbackCallback( std::function< void ( const std::string & ) > feedback_cb )
{
    m_efe.setFeedbackCallback( feedback_cb );
}

bool ExprFilter::valid() const
{
    return m_valid;
}
