#pragma once

#include <saas/library/searchserver/replier.h>

#include <saas/library/daemon_base/metrics/servicemetrics.h>
#include <saas/library/searchmap/searchmap.h>

#include <library/cpp/eventlog/eventlog.h>
#include <library/cpp/object_factory/object_factory.h>

class IRequestContext;
class ISearchContext;
class TCgiParameters;
class TRequestParams;
class TBaseServerRequestData;

class ICgiCorrector
    : public TAtomicRefCount<ICgiCorrector>
    , TNonCopyable
{
public:
    virtual ~ICgiCorrector() {}

    virtual void FormContextCgi(IRequestContext* requestContext, ISearchContext** searchContext) = 0;
    virtual void FormCgi(TCgiParameters& cgi, const TBaseServerRequestData* rd) = 0;
    virtual void SetClientCgi(const TCgiParameters& requestCgi, TCgiParameters& clientCgi, const TRequestParams& rp) = 0;
};
using ICgiCorrectorPtr = TIntrusivePtr<ICgiCorrector>;

class TServiceConfig;
class TSearchServerConfig;
class TSearchProxyConfig;

struct TSearchSource;
using TSearchSources = TVector<TSearchSource>;
using TSourcesConfig = TSearchServerConfig;

class IProxy {
public:
    using TPtr = TAtomicSharedPtr<IProxy>;
    using TFactory = NObjectFactory::TParametrizedObjectFactory<IProxy, TString>;

public:
    virtual ~IProxy() {}
    virtual ISearchReplier::TPtr BuildReplier(const TString& service, IReplyContext::TPtr context) = 0;

    virtual void Start() = 0;
    virtual void Stop() = 0;
    virtual void ReopenLogs() = 0;
    virtual TMap<TString, TString>& GetFailedSearchers() = 0;
    virtual bool IsCommonSearch() const {
        return false;
    }
    virtual TCommonSearch* GetCommonSearch(const TString& /*service*/) {
        return nullptr;
    }
    virtual void RegisterService(
        const NSearchMapParser::TSearchMapService& serviceInfo,
        const TServiceConfig& serviceConfig,
        const TSourcesConfig& sourcesConfig,
        ICgiCorrectorPtr cc,
        TServiceMetricPtr metric,
        TEventLogPtr eventlog
    ) = 0;
    virtual void RegisterMetaService(
        const NSearchMapParser::TMetaService& serviceInfo,
        const TServiceConfig& serviceConfig,
        const TSourcesConfig& sourcesConfig,
        ICgiCorrectorPtr cc,
        TServiceMetricPtr metric,
        TEventLogPtr eventlog
    ) = 0;
    virtual void RegisterUpperService(
        const TServiceConfig& serviceConfig,
        const TSourcesConfig& sourcesConfig,
        ICgiCorrectorPtr cc,
        TServiceMetricPtr metric,
        TEventLogPtr eventlog
    ) = 0;
};
