1 // Copyright (C) 2012-2020 Internet Systems Consortium, Inc. ("ISC")
2 //
3 // This Source Code Form is subject to the terms of the Mozilla Public
4 // License, v. 2.0. If a copy of the MPL was not distributed with this
5 // file, You can obtain one at http://mozilla.org/MPL/2.0/.
6 
7 #ifndef LEASE_MGR_FACTORY_H
8 #define LEASE_MGR_FACTORY_H
9 
10 #include <database/database_connection.h>
11 #include <dhcpsrv/lease_mgr.h>
12 #include <exceptions/exceptions.h>
13 
14 #include <boost/scoped_ptr.hpp>
15 
16 #include <string>
17 
18 namespace isc {
19 namespace dhcp {
20 
21 
22 /// @brief No lease manager exception
23 ///
24 /// Thrown if an attempt is made to get a reference to the current lease
25 /// manager and none is currently available.
26 class NoLeaseManager : public Exception {
27 public:
NoLeaseManager(const char * file,size_t line,const char * what)28     NoLeaseManager(const char* file, size_t line, const char* what) :
29         isc::Exception(file, line, what) {}
30 };
31 
32 /// @brief Lease Manager Factory
33 ///
34 /// This class comprises nothing but static methods used to create a lease
35 /// manager.  It analyzes the database information passed to the creation
36 /// function and instantiates an appropriate lease manager based on the type
37 /// requested.
38 ///
39 /// Strictly speaking these functions could be stand-alone functions.  However,
40 /// it is convenient to encapsulate them in a class for naming purposes.
41 ///
42 /// @todo: Will need to develop some form of registration mechanism for
43 ///        user-supplied backends (so that there is no need to modify the code).
44 class LeaseMgrFactory {
45 public:
46     /// @brief Create an instance of a lease manager.
47     ///
48     /// Each database backend has its own lease manager type.  This static
49     /// method sets the "current" lease manager to be a manager of the
50     /// appropriate type.  The actual lease manager is returned by the
51     /// "instance" method.
52     ///
53     /// @note When called, the current lease manager is <b>always</b> destroyed
54     ///       and a new one created - even if the parameters are the same.
55     ///
56     /// dbaccess is a generic way of passing parameters. Parameters are passed
57     /// in the "name=value" format, separated by spaces.  The data MUST include
58     /// a keyword/value pair of the form "type=dbtype" giving the database
59     /// type, e.q. "mysql" or "sqlite3".
60     ///
61     /// @param dbaccess Database access parameters.  These are in the form of
62     ///        "keyword=value" pairs, separated by spaces. They are backend-
63     ///        -end specific, although must include the "type" keyword which
64     ///        gives the backend in use.
65     ///
66     /// @throw isc::InvalidParameter dbaccess string does not contain the "type"
67     ///        keyword.
68     /// @throw isc::dhcp::InvalidType The "type" keyword in dbaccess does not
69     ///        identify a supported backend.
70     static void create(const std::string& dbaccess);
71 
72     /// @brief Destroy lease manager
73     ///
74     /// Destroys the current lease manager object.  This should have the effect
75     /// of closing the database connection.  The method is a no-op if no
76     /// lease manager is available.
77     static void destroy();
78 
79     /// @brief Return current lease manager
80     ///
81     /// Returns an instance of the "current" lease manager.  An exception
82     /// will be thrown if none is available.
83     ///
84     /// @throw isc::dhcp::NoLeaseManager No lease manager is available: use
85     ///        create() to create one before calling this method.
86     static LeaseMgr& instance();
87 
88     /// @brief Indicates if the lease manager has been instantiated.
89     ///
90     /// @return True if the lease manager instance exists, false otherwise.
91     static bool haveInstance();
92 
93 private:
94     /// @brief Hold pointer to lease manager
95     ///
96     /// Holds a pointer to the singleton lease manager.  The singleton
97     /// is encapsulated in this method to avoid a "static initialization
98     /// fiasco" if defined in an external static variable.
99     static boost::scoped_ptr<LeaseMgr>& getLeaseMgrPtr();
100 
101 };
102 
103 } // end of isc::dhcp namespace
104 } // end of isc namespace
105 
106 #endif // LEASE_MGR_FACTORY_H
107