summaryrefslogtreecommitdiffstats
path: root/searchcore/src/vespa/searchcore/proton/common/cachedselect.h
blob: cdda29ec301b2be95ce8e2b594660b430ecae15f (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root.
#pragma once

#include <vespa/document/select/resultset.h>
#include <vespa/vespalib/stllike/string.h>
#include <memory>
#include <vector>

namespace document {
    class DocumentTypeRepo;
    class Document;
    namespace select { class Node; }
}
namespace search {
    class AttributeVector;
    class IAttributeManager;
}

namespace search::attribute { class ReadableAttributeVector; }

namespace proton {

class SelectContext;
class SelectPruner;

/**
 * Cached selection expression, to avoid pruning expression for each
 * new bucket.
 */
class CachedSelect
{
public:
    typedef std::shared_ptr<CachedSelect> SP;

    class Session {
    private:
        std::unique_ptr<document::select::Node> _docSelect;
        std::unique_ptr<document::select::Node> _preDocOnlySelect;
        std::unique_ptr<document::select::Node> _preDocSelect;

    public:
        Session(std::unique_ptr<document::select::Node> docSelect,
                std::unique_ptr<document::select::Node> preDocOnlySelect,
                std::unique_ptr<document::select::Node> preDocSelect);
        bool contains(const SelectContext &context) const;
        bool contains(const document::Document &doc) const;
        const document::select::Node &selectNode() const;
    };

    using AttributeVectors = std::vector<std::shared_ptr<search::attribute::ReadableAttributeVector>>;

private:
    // Single value attributes referenced from selection expression
    AttributeVectors _attributes;

    // Pruned selection expression, specific for a document type
    std::unique_ptr<document::select::Node> _docSelect;
    uint32_t _fieldNodes;
    uint32_t _attrFieldNodes;
    uint32_t _svAttrFieldNodes;
    bool _allFalse;
    bool _allTrue;
    bool _allInvalid;

    /**
     * If expression doesn't reference multi value attributes or
     * non-attribute fields then this selection expression can be used
     * without retrieving document from document store (must use
     * SelectContext class and populate _docId instead).
     */
    std::unique_ptr<document::select::Node> _preDocOnlySelect;

    /**
     * If expression references at least one single value attribute field
     * then this selection expression can be used to disqualify a
     * document without retrieving it from document store if it evaluates to false.
     */
    std::unique_ptr<document::select::Node> _preDocSelect;

    void setDocumentSelect(SelectPruner &docsPruner);
    void setPreDocumentSelect(const search::IAttributeManager &amgr,
                              SelectPruner &noDocsPruner);

public:
    CachedSelect();
    ~CachedSelect();

    const AttributeVectors &attributes() const { return _attributes; }
    uint32_t fieldNodes() const { return _fieldNodes; }
    uint32_t attrFieldNodes() const { return _attrFieldNodes; }
    uint32_t svAttrFieldNodes() const { return _svAttrFieldNodes; }
    bool allFalse() const { return _allFalse; }
    bool allTrue() const { return _allTrue; }
    bool allInvalid() const { return _allInvalid; }

    // Should only be used for unit testing
    const std::unique_ptr<document::select::Node> &docSelect() const { return _docSelect; }
    const std::unique_ptr<document::select::Node> &preDocOnlySelect() const { return _preDocOnlySelect; }
    const std::unique_ptr<document::select::Node> &preDocSelect() const { return _preDocSelect; }

    void set(const vespalib::string &selection,
             const document::DocumentTypeRepo &repo);
                  
    void set(const vespalib::string &selection,
             const vespalib::string &docTypeName,
             const document::Document &emptyDoc,
             const document::DocumentTypeRepo &repo,
             const search::IAttributeManager *amgr,
             bool hasFields);

    std::unique_ptr<Session> createSession() const;

};

}