Added a EditorSocial.
[UnsignedByte.git] / src / DAL / SavableManager.h
blobac11918d0e54527cfc6e3ad1aa7ea2187b1e0718
1 /***************************************************************************
2 * Copyright (C) 2008 by Sverre Rabbelier *
3 * sverre@rabbelier.nl *
4 * *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 3 of the License, or *
8 * (at your option) any later version. *
9 * *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
14 * *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
20 #pragma once
22 /**
23 * @file SavableManager.h
24 * This file container the SavableManager class.
26 * @see SavableManager.
27 */
29 #include "Types.h"
31 /** The type used to cache integer type field values. */
32 typedef std::map<KeyImpl*, value_type> KeyFieldMap;
34 /** The type used to cache text type field values. */
35 typedef std::pair<FieldImpl*, std::string> TextFieldPair;
37 /** The type used to cache SavableManagers by their keys in. */
38 typedef std::map<KeyFieldMap, SavableManagerPtr> ByKeyCache;
40 /** The type used to cache SavableManagers by their value in. */
41 typedef std::map<TextFieldPair, SavableManagerPtr> ByValueCache;
43 /**
44 * This class represents one row in the database.
46 * It may be used to perform CRUD operations on the database.
47 * (Create, Retreive, Update, Delete)
49 * Trivial locking is implemented through <code>lock</code> and <code>unlock</code>.
50 * That is, it is asserted that a lock was aquired when performing a write operation.
51 * However, it is not checked that it was the called that aquired the lock.
52 * It is therefore the responsibility of the caller not to use write operation unless it previously aquired a lock.
54 * @see lock
55 * @see unlock
56 */
57 class SavableManager : public boost::enable_shared_from_this<SavableManager>
59 public:
60 /**
61 * Select multiple entries from the database restricting on the specified values.
63 * This method wraps the creation of the SelectionMask and the call to the database.
64 * This is the preferred method of selection multiple rows from the database.
66 * @param values The values to filter on.
67 * @return A SavableManagers bucket containing the retreived data.
68 * @see SelectionMask
70 static SavableManagersPtr getmulti(FieldValuesPtr values);
72 /**
73 * Select multiple entries from the database restricting on the specified values.
75 * This method wraps the creation of the SelectionMask and the call to the database.
76 * This is the preferred method of selection multiple rows from the database.
78 * @param values The values to filter on.
79 * @param joins The joins to extend the selection with.
80 * @return A SavableManagers bucket containing the retreived data.
81 * @see SelectionMask
83 static SavableManagersPtr getmulti(FieldValuesPtr values, const Joins& joins);
85 /**
86 * Select multiple entries from the database restricting with the specified mask.
88 * This method uses the specified mask to make the call to the database.
89 * This is the preferred method of selection multiple rows from the database.
91 * @param mask The mask to use.
92 * @return A SavableManagers bucket containing the retreived data.
93 * @see SelectionMask
94 */
95 static SavableManagersPtr getmulti(SelectionMaskPtr mask);
97 /** Returns a new manager for the specified table, it is not yet stored in the database. */
98 static SavableManagerPtr getnew(TableImplPtr table);
100 /** Returns a manager for the specified table using the specified key. */
101 static SavableManagerPtr bykey(KeyValuePtr key);
103 /** Returns a manager using the specified keys, these are asserted to be all the keys for this table.*/
104 static SavableManagerPtr bykeys(KeysPtr keys);
106 /** Returns a manager using the specified value, this value should uniquely identify an entry. */
107 static SavableManagerPtr byvalue(ValuePtr value);
109 /** Wrapper that looks up a manager by the specified value and returns the keys. */
110 static KeysPtr lookupvalue(ValuePtr value);
112 /** Count how many entries there are that satisfy this mask. */
113 static size_t count(SelectionMaskPtr mask);
115 /** Count how many entries there are for the given keys set. */
116 static size_t count(KeysPtr keys);
119 /** Remove the row this manager represents from the databse. */
120 void erase();
122 /** Save the row this manager represents to the database. */
123 void save();
125 /** Discards any changes made to this manager. */
126 void discard();
128 /** Wether the manager has been saved to the database or not. */
129 bool exists() const;
131 /** Whether a write lock could be aquired for this manager. */
132 bool lock();
134 /** Releases the lock, it is asserted at run-time that a lock was previously aquired. */
135 void unlock();
138 /** Binds the keys of this manager to the specified statement. */
139 void bindKeys(sqlite3* db, sqlite3_stmt* stmt, const int startpos = 1) const;
141 /** Binds the fields of this manager to the specified statement. */
142 void bindFields(sqlite3* db, sqlite3_stmt* stmt, const int startpos = 1) const;
144 /** First binds the keys and then the fields of this manager to the specified statement. */
145 void bindUpdate(sqlite3* db, sqlite3_stmt* stmt) const;
147 /** Binds the lookup field of this manager to the specified statement. */
148 void bindLookup(sqlite3* db, sqlite3_stmt* stmt) const;
151 /**
152 * Parse an insertion from the database.
154 * Only valid on a table with a singular primary key.
155 * That is, sqlite3_last_insert_rowid must return the id of the inserted row.
157 void parseInsert(sqlite3* db);
159 /** Read in this managers fields from a selection from the database. */
160 void parseSelect(sqlite3_stmt* stmt, const int startpos = 0);
162 /** Read in the keys and the fields for this manager from a lookup from the database. */
163 void parseLookup(sqlite3_stmt* stmt);
166 /** Returns the table this manager belongs to. */
167 TableImplPtr getTable() const;
169 /** Returns the value of the specified field of the row this manager represents . */
170 ValuePtr getValue(FieldImplPtr field) const;
172 /** Returns the keys in this manager. */
173 KeysPtr getKeys() const;
175 /** Returns the size of the primary keys for this manager. */
176 size_t primaryKeySize() const;
179 /** Returns a string representation of this manager. */
180 std::string toString();
182 /** Returns an array of strings, one for each field in this row. */
183 Strings fieldList() const;
185 /** Returns a string representation of the valueus of this manager compared to the database. */
186 std::string getDiff() const;
188 /** Wether any changes been made to this manager that have not been saved to the databse yet. */
189 bool isDirty() const;
192 /** Sets this managers keys to the specified values, it is asserted at runtime that a lock has been aquired. */
193 void setKeys(KeysPtr keys);
195 /** Sets the specified field of this manager to the specified value, it is asserted at runtime that a lock has been aquired. */
196 void setValue(ValuePtr value);
198 /** Sets the specified field of this manager to the specified value, it is asserted at runtime that a lock has been aquired. */
199 void setValue(FieldImplPtr field, cstring value);
201 /** Sets the specified field of this manager to the specified value, it is asserted at runtime that a lock has been aquired. */
202 void setValue(FieldImplPtr field, value_type value);
204 /** Sets the specified field of this manager to the specified value, it is asserted at runtime that a lock has been aquired. */
205 void setValue(KeyImplPtr field, value_type value);
207 private:
208 /** This is a managed class, use the factory methods insteaed of this constructor to create a new instance. */
209 SavableManager(TableImplPtr table);
211 /** Destructor, a noop. */
212 ~SavableManager();
215 /** Unsets the dirty field and all the dirty fields of all keys and fields. */
216 void cleanup();
219 /** Cache the specified manager. */
220 static void doFullCache(SavableManagerPtr manager);
222 /** Uncache the specified manager. */
223 static void doUncache(SavableManagerPtr manager);
225 /** Recache the specified manager. */
226 static void doRecache(SavableManagerPtr manager);
228 /** Construct a map from the specified manager. */
229 static KeyFieldMap constructMap(SavableManagerPtr keys);
231 /** Construct a map from the specified keys bucket. */
232 static KeyFieldMap constructMap(KeysPtr keys);
234 /** Construct a pair from a value object. */
235 static TextFieldPair constructPair(FieldValuePtr value);
237 /** Returns a string presentation of a KeyField map. */
238 static std::string fromMap(const KeyFieldMap& map);
241 static ByKeyCache ms_byKeyCache; /**< Lookup to retreive managers by the keys. */
242 static ByValueCache ms_byValueCache; /**< Lookup to retreive managers by value. */
245 friend SmartPtrDelete(SavableManager);
246 friend class SelectionMask;
248 TableImplPtr m_table; /**< The table this manager belongs to. */
249 ValuePtr m_lookupvalue; /**< The value the lookup will use. */
251 FieldValueMap m_fields; /**< The value of this manager. */
252 FieldValueMap m_orig; /**< The values of this manager as they currently are in the database. */
254 bool m_newentry; /**< Whether this manager is saved to the database yet. */
255 bool m_locked; /**< Whether this manager is locked for writing. */