summaryrefslogtreecommitdiff
path: root/include/extension.h
blob: 701da864bf69cf1ebfe68b1a69b963df3231639f (plain)
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
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
/**
 *  Extension.h
 *
 *  The extension class is the starting point of your PHP extension. This class
 *  is instantiated the moment the PHP engine starts - for example when the
 *  apache process starts - and will be used for all subsequent requests that
 *  are handled by Apache.
 *
 *  For some environments (for example CLI scripts and FastCGI calls) only one 
 *  request is handled by an extension instance, but for others (when PHP runs
 *  as module in a webserver) many requests are handled by the same extension
 *  instance.
 * 
 *  @author Emiel Bruijntjes <emiel.bruijntjes@copernica.com>
 *  @copyright 2013 Copernica BV
 */

/**
 *  Forward declarations
 */
struct _zend_module_entry;

/**
 *  Set up namespace
 */
namespace PhpCpp {

/**
 *  Forward definitions
 */
class Functions;

/**
 *  Class definition
 */
class Extension
{
public:
    /**
     *  Extension that defines a number of functions right away
     *  @param  name        Extension name
     *  @param  version     Extension version string
     *  @param  functions   The functions that are defined
     */
    Extension(const char *name, const char *version, const std::initializer_list<Function> &functions = {});
    
    /**
     *  Destructor
     */
    virtual ~Extension();
    
    /**
     *  Initialize the extension.
     *  
     *  This method is called after the extension has been loaded, constructed 
     *  and after the compatibility has been checked, but before the requests 
     *  are handled. You can override this method to add your own initialization.
     * 
     *  The method should return true on success, and false on failure (in which
     *  case the extension will not be used)
     * 
     *  @return bool
     */
    virtual bool initialize()
    {
        return true;
    }
    
    /**
     *  Finalize the extension
     *  
     *  This method gets called after all requests were handled, and right before 
     *  the Apache module or CLI script will exit. You can override it to add
     *  your own cleanup code.
     * 
     *  @return bool
     */
    virtual bool finalize()
    {
        return true;
    }
    
    /**
     *  Create a new request
     * 
     *  You can override this method if you've created your own request class,
     *  and you'd like to use an instance of that class instead. The returned
     *  object must have been created on the heap.
     * 
     *  @return Request*
     */
    virtual Request *request()
    {
        return new Request(this);
    }
    
    /**
     *  Start a request
     * 
     *  This method is called when the zend engine is about to start a new
     *  request. Internally, it calls the request() method to instantiate
     *  a new request object, and after that it initializes the request.
     * 
     *  @return boolean
     */
    bool startRequest()
    {
        // failure if we already have a request
        if (_request) return false;
        
        // create the request
        _request = request();
    
        // and initialize it
        return _request->initialize();
    }
    
    /**
     *  End a request
     * 
     *  This method is called when the Zend engine is ready with a request.
     *  Internally, it destructs the request
     *
     *  @return boolean
     */
    bool endRequest()
    {
        // request must exist
        if (!_request) return false;
    
        // finalize the request
        bool result = _request->finalize();
        
        // destruct the request object
        delete _request;
        
        // done
        return result;
    }
    
    /**
     *  Internal method to get access to the entry
     *  @return zend_module_entry
     *  @internal
     */
    _zend_module_entry *entry();
    
private:
    /**
     *  Extension name
     *  @var char*
     */
    const char *_name;
    
    /**
     *  Extension version
     *  @var char*
     */
    const char *_version;
    
    /**
     *  The functions that are defined
     *  @var vector
     */
    Functions *_functions;

    /**
     *  The information that is passed to the Zend engine
     *  @var zend_module_entry
     */
    _zend_module_entry *_entry = NULL;

    /**
     *  The current request being processed
     *  @var Request
     */
    Request *_request = NULL;

    
};

/**
 *  End of namespace
 */
}