CernVM-FS  2.12.0
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
sql.h
Go to the documentation of this file.
1 
5 #ifndef CVMFS_SQL_H_
6 #define CVMFS_SQL_H_
7 
8 #include <cassert>
9 #include <string>
10 
11 #include "duplex_sqlite3.h"
12 #include "util/file_guard.h"
13 #include "util/pointer.h"
14 
15 namespace sqlite {
16 
17 struct MemStatistics {
21  , lookaside_hit(-1)
24  , page_cache_used(-1)
25  , page_cache_hit(-1)
26  , page_cache_miss(-1)
27  , schema_used(-1)
28  , stmt_used(-1)
29  { }
39  int stmt_used;
40 };
41 
42 class Sql;
43 
97 template <class DerivedT>
99  public:
100  enum OpenMode {
103  };
104 
105  static const float kSchemaEpsilon; // floats get imprecise in SQlite
106 
115  static DerivedT* Create(const std::string &filename);
116 
128  static DerivedT* Open(const std::string &filename,
129  const OpenMode open_mode);
130 
131  bool IsEqualSchema(const float value, const float compare) const {
132  return (value > compare - kSchemaEpsilon &&
133  value < compare + kSchemaEpsilon);
134  }
135 
136  bool BeginTransaction() const;
137  bool CommitTransaction() const;
138 
139  template <typename T>
140  T GetProperty(const std::string &key) const;
141  template <typename T>
142  T GetPropertyDefault(const std::string &key, const T default_value) const;
143  template <typename T>
144  bool SetProperty(const std::string &key, const T value);
145  bool HasProperty(const std::string &key) const;
146 
147  sqlite3* sqlite_db() const { return database_.database(); }
148  const std::string& filename() const { return database_.filename(); }
149  float schema_version() const { return schema_version_; }
150  unsigned schema_revision() const { return schema_revision_; }
151  bool read_write() const { return read_write_; }
152 
158  unsigned GetModifiedRowCount() const;
159 
167  double GetFreePageRatio() const;
168 
172  void GetMemStatistics(MemStatistics *stats) const;
173 
181  bool Vacuum() const;
182 
188  void PrintSqlError(const std::string &error_msg);
189 
197  std::string GetLastErrorMsg() const;
198 
199 
205  void TakeFileOwnership();
206 
212  void DropFileOwnership();
213 
221  bool OwnsFile() const { return database_.OwnsFile(); }
222 
227  void EnforceSchema(float version, unsigned revision) {
228  schema_version_ = version;
229  schema_revision_ = revision;
230  }
231 
232  protected:
237  Database(const std::string &filename,
238  const OpenMode open_mode);
239 
240  bool Initialize();
241 
242  bool CreatePropertiesTable();
243  bool PrepareCommonQueries();
244 
245  bool OpenDatabase(const int sqlite_open_flags);
246  bool Configure();
247  bool FileReadAhead();
248 
249  void ReadSchemaRevision();
250  bool StoreSchemaRevision();
251 
252  void set_schema_version(const float ver) { schema_version_ = ver; }
253  void set_schema_revision(const unsigned rev) { schema_revision_ = rev; }
254 
255  private:
262  DatabaseRaiiWrapper(const std::string &filename,
263  Database<DerivedT> *delegate)
264  : sqlite_db(NULL)
265  , lookaside_buffer(NULL)
266  , db_file_guard(filename, UnlinkGuard::kDisabled)
267  , delegate_(delegate) {}
269 
270  sqlite3* database() const { return sqlite_db; }
271  const std::string& filename() const { return db_file_guard.path(); }
272 
273  bool Close();
274 
277  bool OwnsFile() const { return db_file_guard.IsEnabled(); }
278 
279  sqlite3 *sqlite_db;
283  };
284 
285  static const char *kSchemaVersionKey;
286  static const char *kSchemaRevisionKey;
287 
288  DatabaseRaiiWrapper database_;
289 
290  const bool read_write_;
293 
296 
300 };
301 
302 
303 //
304 // # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # # #
305 //
306 
307 
329 class Sql {
330  public:
336  Sql(sqlite3 *sqlite_db, const std::string &statement);
337  virtual ~Sql();
338 
339  bool Execute();
340  bool FetchRow();
341  std::string DebugResultTable();
342  bool Reset();
343  inline int GetLastError() const { return last_error_code_; }
344 
353  std::string GetLastErrorMsg() const;
354 
355  bool BindBlob(const int index, const void* value, const unsigned size) {
356  LazyInit();
358  sqlite3_bind_blob(statement_, index, value, static_cast<int>(size),
359  SQLITE_STATIC);
360  return Successful();
361  }
362  bool BindBlobTransient(const int index, const void* value,
363  const unsigned size)
364  {
365  LazyInit();
367  sqlite3_bind_blob(statement_, index, value, static_cast<int>(size),
368  SQLITE_TRANSIENT); // NOLINT
369  return Successful();
370  }
371  bool BindDouble(const int index, const double value) {
372  LazyInit();
373  last_error_code_ = sqlite3_bind_double(statement_, index, value);
374  return Successful();
375  }
376  bool BindInt(const int index, const int value) {
377  LazyInit();
378  last_error_code_ = sqlite3_bind_int(statement_, index, value);
379  return Successful();
380  }
381  bool BindInt64(const int index, const sqlite3_int64 value) {
382  LazyInit();
383  last_error_code_ = sqlite3_bind_int64(statement_, index, value);
384  return Successful();
385  }
386  bool BindNull(const int index) {
387  LazyInit();
388  last_error_code_ = sqlite3_bind_null(statement_, index);
389  return Successful();
390  }
391  bool BindTextTransient(const int index, const std::string &value) {
392  return BindTextTransient(
393  index, value.data(), static_cast<int>(value.length()));
394  }
395  bool BindTextTransient(const int index, const char *value, const int size) {
396  // NOLINTNEXTLINE(performance-no-int-to-ptr)
397  return BindText(index, value, size, SQLITE_TRANSIENT);
398  }
399  bool BindText(const int index, const std::string &value) {
400  return BindText(index, value.data(), static_cast<int>(value.length()),
401  SQLITE_STATIC);
402  }
403  bool BindText(const int index,
404  const char* value,
405  const int size,
406  void(*dtor)(void*) = SQLITE_STATIC) {
407  LazyInit();
408  last_error_code_ = sqlite3_bind_text(statement_, index, value, size, dtor);
409  return Successful();
410  }
411 
417  template <typename T>
418  inline bool Bind(const int index, const T &value);
419 
420 
421  int RetrieveType(const int idx_column) const {
422  return sqlite3_column_type(statement_, idx_column);
423  }
424 
433  int RetrieveBytes(const int idx_column) const {
434  return sqlite3_column_bytes(statement_, idx_column);
435  }
436  const void *RetrieveBlob(const int idx_column) const {
437  return sqlite3_column_blob(statement_, idx_column);
438  }
439  double RetrieveDouble(const int idx_column) const {
440  return sqlite3_column_double(statement_, idx_column);
441  }
442  int RetrieveInt(const int idx_column) const {
443  return sqlite3_column_int(statement_, idx_column);
444  }
445  sqlite3_int64 RetrieveInt64(const int idx_column) const {
446  return sqlite3_column_int64(statement_, idx_column);
447  }
448  const unsigned char *RetrieveText(const int idx_column) const {
449  return sqlite3_column_text(statement_, idx_column);
450  }
451  std::string RetrieveString(const int idx_column) const {
452  return reinterpret_cast<const char*>(RetrieveText(idx_column));
453  }
454  template <typename T>
455  inline T Retrieve(const int index);
456 
457  protected:
458  Sql()
459  : database_(NULL)
460  , statement_(NULL)
461  , query_string_(NULL)
462  , last_error_code_(0) { }
463 
464  bool IsInitialized() const { return statement_ != NULL; }
465 
473  bool Init(const sqlite3 *database, const std::string &statement);
474 
483  void DeferredInit(const sqlite3 *database, const char *statement);
484 
489  inline bool Successful() const {
490  return SQLITE_OK == last_error_code_ ||
491  SQLITE_ROW == last_error_code_ ||
492  SQLITE_DONE == last_error_code_;
493  }
494 
495  private:
496  bool Init(const char *statement);
497  void LazyInit() {
498  if (!IsInitialized()) {
499  assert(NULL != database_);
500  assert(NULL != query_string_);
501  const bool success = Init(query_string_);
502  assert(success);
503  }
504  }
505 
506  sqlite3 *database_;
507  sqlite3_stmt *statement_;
508  const char *query_string_;
510 };
511 
512 } // namespace sqlite
513 
514 #include "sql_impl.h"
515 
516 #endif // CVMFS_SQL_H_
const char * query_string_
Definition: sql.h:508
void LazyInit()
Definition: sql.h:497
std::string GetLastErrorMsg() const
Definition: sql.cc:164
bool Bind(const int index, const T &value)
void DropFileOwnership()
Definition: sql_impl.h:350
const std::string & filename() const
Definition: sql.h:271
std::string GetLastErrorMsg() const
Definition: sql_impl.h:335
bool IsInitialized() const
Definition: sql.h:464
bool BindTextTransient(const int index, const std::string &value)
Definition: sql.h:391
bool Execute()
Definition: sql.cc:42
bool Reset()
Definition: sql.cc:126
void EnforceSchema(float version, unsigned revision)
Definition: sql.h:227
double GetFreePageRatio() const
Definition: sql_impl.h:406
int page_cache_used
Bytes used for caching pages.
Definition: sql.h:35
bool BindText(const int index, const std::string &value)
Definition: sql.h:399
bool FetchRow()
Definition: sql.cc:62
const std::string & filename() const
Definition: sql.h:148
bool Init(const sqlite3 *database, const std::string &statement)
Definition: sql.cc:132
bool PrepareCommonQueries()
Definition: sql_impl.h:234
const void * RetrieveBlob(const int idx_column) const
Definition: sql.h:436
double RetrieveDouble(const int idx_column) const
Definition: sql.h:439
bool read_write() const
Definition: sql.h:151
void TakeFileOwnership()
Definition: sql_impl.h:342
int lookaside_miss_size
Definition: sql.h:33
bool Initialize()
Definition: sql_impl.h:93
int last_error_code_
Definition: sql.h:509
float schema_version_
Definition: sql.h:291
bool BeginTransaction() const
Definition: sql_impl.h:271
void ReadSchemaRevision()
Definition: sql_impl.h:253
bool BindBlobTransient(const int index, const void *value, const unsigned size)
Definition: sql.h:362
int lookaside_slots_used
Definition: sql.h:30
Database(const std::string &filename, const OpenMode open_mode)
Definition: sql_impl.h:21
void set_schema_version(const float ver)
Definition: sql.h:252
assert((mem||(size==0))&&"Out Of Memory")
std::string DebugResultTable()
Definition: sql.cc:69
float schema_version() const
Definition: sql.h:149
int stmt_used
Bytes used for prepared statmements (lookaside + heap)
Definition: sql.h:39
void set_schema_revision(const unsigned rev)
Definition: sql.h:253
bool Configure()
Definition: sql_impl.h:184
static DerivedT * Open(const std::string &filename, const OpenMode open_mode)
Definition: sql_impl.h:73
sqlite3 * database() const
Definition: sql.h:270
bool CreatePropertiesTable()
Definition: sql_impl.h:285
Sql()
Definition: sql.h:458
T GetProperty(const std::string &key) const
Definition: sql_impl.h:305
unsigned schema_revision() const
Definition: sql.h:150
T GetPropertyDefault(const std::string &key, const T default_value) const
Definition: sql_impl.h:317
void DeferredInit(const sqlite3 *database, const char *statement)
Definition: sql.cc:158
int GetLastError() const
Definition: sql.h:343
bool BindDouble(const int index, const double value)
Definition: sql.h:371
UniquePtr< Sql > set_property_
Definition: sql.h:298
unsigned GetModifiedRowCount() const
Definition: sql_impl.h:358
static const float kSchemaEpsilon
Definition: sql.h:105
sqlite3 * database_
Definition: sql.h:506
const bool read_write_
Definition: sql.h:290
bool Vacuum() const
Definition: sql_impl.h:423
sqlite3_int64 RetrieveInt64(const int idx_column) const
Definition: sql.h:445
bool BindBlob(const int index, const void *value, const unsigned size)
Definition: sql.h:355
bool BindInt(const int index, const int value)
Definition: sql.h:376
DatabaseRaiiWrapper(const std::string &filename, Database< DerivedT > *delegate)
Definition: sql.h:262
T Retrieve(const int index)
UniquePtr< Sql > commit_transaction_
Definition: sql.h:295
UniquePtr< Sql > has_property_
Definition: sql.h:297
bool BindTextTransient(const int index, const char *value, const int size)
Definition: sql.h:395
sqlite3 * sqlite_db() const
Definition: sql.h:147
bool CommitTransaction() const
Definition: sql_impl.h:278
sqlite3_stmt * statement_
Definition: sql.h:507
int page_cache_miss
Definition: sql.h:37
bool BindInt64(const int index, const sqlite3_int64 value)
Definition: sql.h:381
bool SetProperty(const std::string &key, const T value)
Definition: sql_impl.h:325
virtual ~Sql()
Definition: sql.cc:26
bool OpenDatabase(const int sqlite_open_flags)
Definition: sql_impl.h:129
bool OwnsFile() const
Definition: sql.h:221
bool HasProperty(const std::string &key) const
Definition: sql_impl.h:293
bool IsEqualSchema(const float value, const float compare) const
Definition: sql.h:131
std::string RetrieveString(const int idx_column) const
Definition: sql.h:451
const unsigned char * RetrieveText(const int idx_column) const
Definition: sql.h:448
static const char * kSchemaRevisionKey
Definition: sql.h:286
unsigned schema_revision_
Definition: sql.h:292
bool FileReadAhead()
Definition: sql_impl.h:203
int RetrieveType(const int idx_column) const
Definition: sql.h:421
int schema_used
Bytes used to store db schema.
Definition: sql.h:38
bool BindText(const int index, const char *value, const int size, void(*dtor)(void *)=SQLITE_STATIC)
Definition: sql.h:403
int lookaside_miss_full
Definition: sql.h:34
int page_cache_hit
Definition: sql.h:36
int lookaside_slots_max
Definition: sql.h:31
Database< DerivedT > * delegate_
Definition: sql.h:282
void GetMemStatistics(MemStatistics *stats) const
Definition: sql_impl.h:368
bool Successful() const
Definition: sql.h:489
void PrintSqlError(const std::string &error_msg)
Definition: sql_impl.h:431
DatabaseRaiiWrapper database_
Definition: sql.h:288
static const char * kSchemaVersionKey
Definition: sql.h:285
int RetrieveInt(const int idx_column) const
Definition: sql.h:442
UniquePtr< Sql > get_property_
Definition: sql.h:299
bool BindNull(const int index)
Definition: sql.h:386
static void size_t size
Definition: smalloc.h:54
bool StoreSchemaRevision()
Definition: sql_impl.h:264
UniquePtr< Sql > begin_transaction_
Definition: sql.h:294
static DerivedT * Create(const std::string &filename)
Definition: sql_impl.h:30
int RetrieveBytes(const int idx_column) const
Definition: sql.h:433