public static QueryContainer GetSimpleQuery(VerejnaZakazkaSearchData searchdata)
            {
                var    query     = searchdata.Q?.Trim();
                string modifiedQ = query; // Search.Tools.FixInvalidQuery(query, queryShorcuts, queryOperators) ?? "";

                //check invalid query ( tag: missing value)

                if (searchdata.Zahajeny)
                {
                    modifiedQ = Query.ModifyQueryAND(modifiedQ, "zahajeny:1");
                }

                if (!string.IsNullOrWhiteSpace(searchdata.Oblast))
                {
                    var oblValue = NormalizeOblastValue(searchdata.Oblast);
                    if (!string.IsNullOrEmpty(oblValue))
                    {
                        modifiedQ = Query.ModifyQueryAND(modifiedQ, "oblast:" + oblValue);
                    }
                }

                var qc = SimpleQueryCreator.GetSimpleQuery <VerejnaZakazka>(modifiedQ, Rules);

                return(qc);
            }
            public static VerejnaZakazkaSearchData CachedSimpleSearch(TimeSpan expiration, VerejnaZakazkaSearchData search,
                                                                      bool logError = true, bool fixQuery = true, ElasticClient client = null, bool exactNumOfResults = false)
            {
                FullSearchQuery q = new FullSearchQuery()
                {
                    search   = search,
                    logError = logError,
                    fixQuery = fixQuery,
                    client   = client
                };

                return(cachedSearches.Get(Newtonsoft.Json.JsonConvert.SerializeObject(q), expiration));
            }
            public static VerejnaZakazkaSearchData _Search(
                VerejnaZakazkaSearchData search,
                AggregationContainerDescriptor <VerejnaZakazka> anyAggregation, ElasticClient client)
            {
                if (string.IsNullOrEmpty(search.Q) && (search.CPV == null || search.CPV.Length == 0))
                {
                    return(null);
                }

                if (client == null)
                {
                    client = HlidacStatu.Lib.ES.Manager.GetESClient_VZ();
                }

                AggregationContainerDescriptor <VerejnaZakazka> baseAggrDesc = null;

                baseAggrDesc = anyAggregation == null ?
                               null //new AggregationContainerDescriptor<VerejnaZakazka>().Sum("sumKc", m => m.Field(f => f.Castka))
                        : anyAggregation;

                Func <AggregationContainerDescriptor <VerejnaZakazka>, AggregationContainerDescriptor <VerejnaZakazka> > aggrFunc
                    = (aggr) => { return(baseAggrDesc); };

                string queryString = search.Q;

                Nest.ISearchResponse <VerejnaZakazka> res = null;
                if (search.CPV != null && search.CPV.Length > 0)
                {
                    string cpvs = search.CPV.Select(c => c + "*").Aggregate((f, s) => f + " OR " + s);
                    if (!string.IsNullOrEmpty(queryString))
                    {
                        queryString = queryString + " AND (cPV:(" + cpvs + "))";
                    }
                    else
                    {
                        queryString = "cPV:(" + cpvs + ")";
                    }
                }

                int page = search.Page - 1;

                if (page < 0)
                {
                    page = 0;
                }
                try
                {
                    res = client
                          .Search <HlidacStatu.Lib.Data.VZ.VerejnaZakazka>(a => a
                                                                           .Size(search.PageSize)
                                                                           .From(search.PageSize * page)
                                                                           .Aggregations(aggrFunc)
                                                                           .Query(qq => qq.QueryString(qs => qs
                                                                                                       .Query(queryString)
                                                                                                       .DefaultOperator(Nest.Operator.And)
                                                                                                       )
                                                                                  )
                                                                           .Sort(ss => GetSort(Convert.ToInt32(search.Order)))
                                                                           .Aggregations(aggrFunc)
                                                                           );
                }
                catch (Exception e)
                {
                    Audit.Add(Audit.Operations.Search, "", "", "VerejnaZakazka", "error", search.Q, null);
                    if (res != null && res.ServerError != null)
                    {
                        HlidacStatu.Lib.ES.Manager.LogQueryError <VerejnaZakazka>(res, "Exception, Orig query:"
                                                                                  + search.OrigQuery + "   query:"
                                                                                  + search.Q
                                                                                  + "\n\n res:" + search.Result.ToString()
                                                                                  , ex: e);
                    }
                    else
                    {
                        HlidacStatu.Util.Consts.Logger.Error("", e);
                    }
                    throw;
                }
                Audit.Add(Audit.Operations.Search, "", "", "VerejnaZakazka", res.IsValid ? "valid" : "invalid", search.Q, null);


                search.IsValid        = res.IsValid;
                search.ElasticResults = res;
                search.Total          = res.Total;


                return(search);
            }
            public static VerejnaZakazkaSearchData SimpleSearch(
                VerejnaZakazkaSearchData search,
                AggregationContainerDescriptor <VerejnaZakazka> anyAggregation = null,
                bool logError         = true, bool fixQuery = true, ElasticClient client = null,
                bool withHighlighting = false)
            {
                if (client == null)
                {
                    client = HlidacStatu.Lib.ES.Manager.GetESClient_VZ();
                }

                string query = search.Q ?? "";

                int page = search.Page - 1;

                if (page < 0)
                {
                    page = 0;
                }



                AggregationContainerDescriptor <VerejnaZakazka> baseAggrDesc = null;

                baseAggrDesc = anyAggregation == null ?
                               null //new AggregationContainerDescriptor<VerejnaZakazka>().Sum("sumKc", m => m.Field(f => f.Castka))
                        : anyAggregation;

                Func <AggregationContainerDescriptor <VerejnaZakazka>, AggregationContainerDescriptor <VerejnaZakazka> > aggrFunc
                    = (aggr) => { return(baseAggrDesc); };


                Devmasters.Core.StopWatchEx sw = new Devmasters.Core.StopWatchEx();
                sw.Start();

                if (fixQuery)
                {
                    search.OrigQuery = query;
                    query            = Lib.Searching.Tools.FixInvalidQuery(query, queryShorcuts, queryOperators);
                }
                if (logError && search.Q != search.OrigQuery)
                {
                    HlidacStatu.Util.Consts.Logger.Debug(new Devmasters.Core.Logging.LogMessage()
                                                         .SetMessage("Fixed query")
                                                         .SetCustomKeyValue("runningQuery", search.Q)
                                                         .SetCustomKeyValue("origQuery", search.OrigQuery)
                                                         );
                }


                search.Q = query;
                ISearchResponse <VerejnaZakazka> res = null;

                try
                {
                    res = client
                          .Search <VerejnaZakazka>(s => s
                                                   .Size(search.PageSize)
                                                   .Source(so => so.Excludes(ex => ex.Field("dokumenty.plainText")))
                                                   .From(page * search.PageSize)
                                                   .Query(q => GetSimpleQuery(search))
                                                   .Sort(ss => GetSort(Convert.ToInt32(search.Order)))
                                                   .Aggregations(aggrFunc)
                                                   .Highlight(h => Lib.Searching.Tools.GetHighlight <VerejnaZakazka>(withHighlighting))
                                                   .TrackTotalHits(search.ExactNumOfResults ? true : (bool?)null)
                                                   );
                    if (withHighlighting && res.Shards != null && res.Shards.Failed > 0) //if some error, do it again without highlighting
                    {
                        res = client
                              .Search <VerejnaZakazka>(s => s
                                                       .Size(search.PageSize)
                                                       .Source(so => so.Excludes(ex => ex.Field("dokumenty.plainText")))
                                                       .From(page * search.PageSize)
                                                       .Query(q => GetSimpleQuery(search))
                                                       .Sort(ss => GetSort(Convert.ToInt32(search.Order)))
                                                       .Aggregations(aggrFunc)
                                                       .Highlight(h => Lib.Searching.Tools.GetHighlight <VerejnaZakazka>(false))
                                                       .TrackTotalHits(search.ExactNumOfResults ? true : (bool?)null)
                                                       );
                    }
                }
                catch (Exception e)
                {
                    Audit.Add(Audit.Operations.Search, "", "", "VerejnaZakazka", "error", search.Q, null);
                    if (res != null && res.ServerError != null)
                    {
                        Lib.ES.Manager.LogQueryError <VerejnaZakazka>(res, "Exception, Orig query:"
                                                                      + search.OrigQuery + "   query:"
                                                                      + search.Q
                                                                      + "\n\n res:" + search.Result.ToString()
                                                                      , ex: e);
                    }
                    else
                    {
                        HlidacStatu.Util.Consts.Logger.Error("", e);
                    }
                    throw;
                }
                sw.Stop();

                Audit.Add(Audit.Operations.Search, "", "", "VerejnaZakazka", res.IsValid ? "valid" : "invalid", search.Q, null);

                if (res.IsValid == false && logError)
                {
                    Lib.ES.Manager.LogQueryError <VerejnaZakazka>(res, "Exception, Orig query:"
                                                                  + search.OrigQuery + "   query:"
                                                                  + search.Q
                                                                  + "\n\n res:" + search.Result?.ToString()
                                                                  );
                }


                search.Total          = res?.Total ?? 0;
                search.IsValid        = res?.IsValid ?? false;
                search.ElasticResults = res;
                search.ElapsedTime    = sw.Elapsed;
                return(search);
            }
            public static QueryContainer GetSimpleQuery(VerejnaZakazkaSearchData searchdata)
            {
                Lib.Searching.Rule[] rules = new Lib.Searching.Rule[] {
                    new Lib.Searching.Rule(@"osobaid:(?<q>((\w{1,} [-]{1} \w{1,})([-]{1} \d{1,3})?)) ", "ico"),
                    new Lib.Searching.Rule(@"osobaiddodavatel:(?<q>((\w{1,} [-]{1} \w{1,})([-]{1} \d{1,3})?)) ", "icododavatel"),
                    new Lib.Searching.Rule(@"osobaidzadavatel:(?<q>((\w{1,} [-]{1} \w{1,})([-]{1} \d{1,3})?)) ", "icododavatel"),

                    new Lib.Searching.Rule(@"holding:(?<q>(\d{1,8})) ", "ico"),
                    new Lib.Searching.Rule(@"holdingdodavatel:(?<q>(\d{1,8})) ", "icododavatel"),
                    new Lib.Searching.Rule(@"holdingzadavatel:(?<q>(\d{1,8})) ", "icozadavatel"),
                    new Lib.Searching.Rule(@"holdingprijemce:(?<q>(\d{1,8})) ", "icododavatel"),
                    new Lib.Searching.Rule(@"holdingplatce:(?<q>(\d{1,8})) ", "icozadavatel"),

                    new Lib.Searching.Rule("cpv:", "${cpv}"),
                    new Lib.Searching.Rule("oblast:", "${oblast}"),
                    new Lib.Searching.Rule("form:", "${form}"),
                    new Lib.Searching.Rule("zahajeny:1", "stavVZ:<=100"),
                    new Lib.Searching.Rule("ico:", "(zadavatel.iCO:${q} OR dodavatele.iCO:${q}) "),
                    new Lib.Searching.Rule("icododavatel:", "dodavatele.iCO:"),
                    new Lib.Searching.Rule("icoprijemce:", "dodavatele.iCO:"),
                    new Lib.Searching.Rule("icozadavatel:", "zadavatel.iCO:"),
                    new Lib.Searching.Rule("icoplatce:", "zadavatel.iCO:"),
                    new Lib.Searching.Rule("jmenoprijemce:", "dodavatele.jmeno:"),
                    new Lib.Searching.Rule("jmenoplatce:", "zadavatel.jmeno:"),
                    new Lib.Searching.Rule("id:", "id:"),
                    new Lib.Searching.Rule("popis:", "(nazevZakazky:${q} OR popisZakazky:${q}) "),
                    new Lib.Searching.Rule("cena:<=", "(konecnaHodnotaBezDPH:<=${q} OR odhadovanaHodnotaBezDPH:<=${q}) "),
                    new Lib.Searching.Rule("cena:>=", "(konecnaHodnotaBezDPH:>=${q} OR odhadovanaHodnotaBezDPH:>=${q}) "),
                    new Lib.Searching.Rule("cena:<", "(konecnaHodnotaBezDPH:<${q} OR odhadovanaHodnotaBezDPH:<${q}) "),
                    new Lib.Searching.Rule("cena:>", "(konecnaHodnotaBezDPH:>${q} OR odhadovanaHodnotaBezDPH:>${q}) "),
                    new Lib.Searching.Rule("cena:", "(konecnaHodnotaBezDPH:${q} OR odhadovanaHodnotaBezDPH:${q}) "),
                    new Lib.Searching.Rule("zverejneno:\\[", "datumUverejneni:["),
                    new Lib.Searching.Rule("zverejneno:(?=[<>])", "datumUverejneni:${q}"),
                    new Lib.Searching.Rule("zverejneno:(?=\\d)", "datumUverejneni:[${q} TO ${q}||+1d]"),
                    new Lib.Searching.Rule("podepsano:\\[", "datumUzavreniSmlouvy:["),
                    new Lib.Searching.Rule("podepsano:(?=[<>])", "datumUzavreniSmlouvy:${q}"),
                    new Lib.Searching.Rule("podepsano:(?=\\d)", "datumUzavreniSmlouvy:[${q} TO ${q}||+1d]"),
                    new Lib.Searching.Rule("text:", "prilohy.plainTextContent:"),
                };

                IRule[] irules = new IRule[] {
                    new OsobaId("osobaid:", "ico:"),
                    new OsobaId("osobaiddodavatel:", "icododavatel:"),
                    new OsobaId("osobaidzadavatel:", "icozadavatel:"),

                    new Holding("holding:", "ico:"),
                    new Holding("holdingdodavatel:", "icododavatel:"),
                    new Holding("holdingzadavatel:", "icozadavatel:"),
                    new Holding("holdingprijemce:", "icododavatel:"),
                    new Holding("holdingplatce:", "icozadavatel:"),

                    new VZ_CPV(),
                    new VZ_Oblast(),
                    new VZ_Form(),

                    new TransformPrefixWithValue("zahajeny:", "stavVZ:<=100", "1"),


                    new TransformPrefixWithValue("ico:", "(zadavatel.iCO:${q} OR dodavatele.iCO:${q}) ", null),
                    new TransformPrefix("icododavatel:", "dodavatele.iCO:", null),
                    new TransformPrefix("icoprijemce:", "dodavatele.iCO:", null),
                    new TransformPrefix("icozadavatel:", "zadavatel.iCO:", null),
                    new TransformPrefix("icoplatce:", "zadavatel.iCO:", null),
                    new TransformPrefix("jmenoprijemce:", "dodavatele.jmeno:", null),
                    new TransformPrefix("jmenoplatce:", "zadavatel.jmeno:", null),
                    new TransformPrefix("id:", "id:", null),

                    new TransformPrefixWithValue("popis:", "(nazevZakazky:${q} OR popisZakazky:${q})  ", null),

                    new TransformPrefixWithValue("cena:", "(konecnaHodnotaBezDPH:<=${q} OR odhadovanaHodnotaBezDPH:<=${q}) ", "<=\\d"),
                    new TransformPrefixWithValue("cena:", "(konecnaHodnotaBezDPH:>=${q} OR odhadovanaHodnotaBezDPH:>=${q}) ", ">=\\d"),
                    new TransformPrefixWithValue("cena:", "(konecnaHodnotaBezDPH:<${q} OR odhadovanaHodnotaBezDPH:<${q}) ", "<\\d"),
                    new TransformPrefixWithValue("cena:", "(konecnaHodnotaBezDPH:>${q} OR odhadovanaHodnotaBezDPH:>${q}) ", ">\\d"),
                    new TransformPrefixWithValue("cena:", "(konecnaHodnotaBezDPH:${q} OR odhadovanaHodnotaBezDPH:${q}) ", null),


                    new TransformPrefix("zverejneno:", "datumUverejneni:", "[<>]?[{\\[]+"),
                    new TransformPrefixWithValue("zverejneno:", "datumUverejneni:[${q} TO ${q}||+1d]", "\\d+"),
                    new TransformPrefix("podepsano:", "datumUzavreniSmlouvy:", "[<>]?[{\\[]+"),
                    new TransformPrefixWithValue("podepsano:", "datumUzavreniSmlouvy:[${q} TO ${q}||+1d]", "\\d+"),

                    new TransformPrefix("text:", "prilohy.plainTextContent:", null),
                };

                var    query     = searchdata.Q?.Trim();
                string modifiedQ = query; // Search.Tools.FixInvalidQuery(query, queryShorcuts, queryOperators) ?? "";

                //check invalid query ( tag: missing value)


                if (searchdata.Zahajeny)
                {
                    modifiedQ = Lib.Searching.Tools.ModifyQueryAND(modifiedQ, "zahajeny:1");
                }

                if (!string.IsNullOrWhiteSpace(searchdata.Oblast))
                {
                    var oblValue = NormalizeOblastValue(searchdata.Oblast);
                    if (!string.IsNullOrEmpty(oblValue))
                    {
                        modifiedQ = Lib.Searching.Tools.ModifyQueryAND(modifiedQ, "oblast:" + oblValue);
                    }
                }


                //var qc = Lib.Search.Tools.GetSimpleQuery<Lib.Data.VZ.VerejnaZakazka>(modifiedQ, rules); ;
                //var qc = Lib.Search.SimpleQueryCreator.GetSimpleQuery<Lib.Data.VZ.VerejnaZakazka>(query, irules);
                var qc = Lib.Searching.SimpleQueryCreator.GetSimpleQuery <Lib.Data.VZ.VerejnaZakazka>(modifiedQ, irules);

                return(qc);
            }