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
|
#ifndef CERT_TRANS_LOG_SQLITE_STATEMENT_H_
#define CERT_TRANS_LOG_SQLITE_STATEMENT_H_
#include <glog/logging.h>
#include <sqlite3.h>
#include <string>
#include "base/macros.h"
namespace sqlite {
// Reduce the ugliness of the sqlite3 API.
class Statement {
public:
Statement(sqlite3* db, const char* sql) : stmt_(NULL) {
int ret = sqlite3_prepare_v2(db, sql, -1, &stmt_, NULL);
if (ret != SQLITE_OK)
LOG(ERROR) << "ret = " << ret << ", err = " << sqlite3_errmsg(db)
<< ", sql = " << sql << std::endl;
CHECK_EQ(SQLITE_OK, ret);
}
~Statement() {
int ret = sqlite3_finalize(stmt_);
// can get SQLITE_CONSTRAINT if an insert failed due to a duplicate key.
CHECK(ret == SQLITE_OK || ret == SQLITE_CONSTRAINT);
}
// Fields start at 0! |value| must have lifetime that covers its
// use, which is up until the SQL statement finishes executing
// (i.e. after the last Step()).
void BindBlob(unsigned field, const std::string& value) {
CHECK_EQ(SQLITE_OK, sqlite3_bind_blob(stmt_, field + 1, value.data(),
value.length(), NULL));
}
void BindUInt64(unsigned field, sqlite3_uint64 value) {
CHECK_EQ(SQLITE_OK, sqlite3_bind_int64(stmt_, field + 1, value));
}
void GetBlob(unsigned column, std::string* value) {
const void* data = sqlite3_column_blob(stmt_, column);
CHECK_NOTNULL(data);
value->assign(static_cast<const char*>(data),
sqlite3_column_bytes(stmt_, column));
}
sqlite3_uint64 GetUInt64(unsigned column) {
return sqlite3_column_int64(stmt_, column);
}
int GetType(unsigned column) {
return sqlite3_column_type(stmt_, column);
}
int Step() {
return sqlite3_step(stmt_);
}
private:
sqlite3_stmt* stmt_;
DISALLOW_COPY_AND_ASSIGN(Statement);
};
} // namespace sqlite
#endif // CERT_TRANS_LOG_SQLITE_STATEMENT_H_
|