working test
This commit is contained in:
		
							
								
								
									
										119
									
								
								thirdparty/SQLiteCpp/tests/Backup_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										119
									
								
								thirdparty/SQLiteCpp/tests/Backup_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@@ -0,0 +1,119 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @file    Backup_test.cpp
 | 
			
		||||
 * @ingroup tests
 | 
			
		||||
 * @brief   Test of a SQLite Backup.
 | 
			
		||||
 *
 | 
			
		||||
 * Copyright (c) 2015 Shibao HONG (shibaohong@outlook.com)
 | 
			
		||||
 * Copyright (c) 2015-2019 Sebastien Rombauts (sebastien.rombauts@gmail.com)
 | 
			
		||||
 *
 | 
			
		||||
 * Distributed under the MIT License (MIT) (See accompanying file LICENSE.txt
 | 
			
		||||
 * or copy at http://opensource.org/licenses/MIT)
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include <SQLiteCpp/Backup.h>
 | 
			
		||||
#include <SQLiteCpp/Database.h>
 | 
			
		||||
#include <SQLiteCpp/Statement.h>
 | 
			
		||||
#include <SQLiteCpp/Exception.h>
 | 
			
		||||
 | 
			
		||||
#include <sqlite3.h> // for SQLITE_ERROR, SQLITE_RANGE and SQLITE_DONE
 | 
			
		||||
 | 
			
		||||
#include <gtest/gtest.h>
 | 
			
		||||
 | 
			
		||||
#include <cstdio>
 | 
			
		||||
 | 
			
		||||
TEST(Backup, initException)
 | 
			
		||||
{
 | 
			
		||||
    remove("backup_test.db3");
 | 
			
		||||
    SQLite::Database srcDB("backup_test.db3", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    srcDB.exec("CREATE TABLE backup_test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
    ASSERT_EQ(1, srcDB.exec("INSERT INTO backup_test VALUES (1, \"first\")"));
 | 
			
		||||
    ASSERT_EQ(1, srcDB.exec("INSERT INTO backup_test VALUES (2, \"second\")"));
 | 
			
		||||
    EXPECT_THROW(SQLite::Backup backup(srcDB, srcDB), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(SQLite::Backup backup(srcDB, "main", srcDB, "main"), SQLite::Exception);
 | 
			
		||||
    const std::string name("main");
 | 
			
		||||
    EXPECT_THROW(SQLite::Backup backup(srcDB, name, srcDB, name), SQLite::Exception);
 | 
			
		||||
    remove("backup_test.db3");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Backup, executeStepOne)
 | 
			
		||||
{
 | 
			
		||||
    remove("backup_test.db3");
 | 
			
		||||
    remove("backup_test.db3.backup");
 | 
			
		||||
    SQLite::Database srcDB("backup_test.db3", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    srcDB.exec("CREATE TABLE backup_test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
    ASSERT_EQ(1, srcDB.exec("INSERT INTO backup_test VALUES (1, \"first\")"));
 | 
			
		||||
    ASSERT_EQ(1, srcDB.exec("INSERT INTO backup_test VALUES (2, \"second\")"));
 | 
			
		||||
 | 
			
		||||
    SQLite::Database destDB("backup_test.db3.backup", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    SQLite::Backup backup(destDB, "main", srcDB, "main");
 | 
			
		||||
    int res = backup.executeStep(1); // backup only one page at a time
 | 
			
		||||
    ASSERT_EQ(SQLite::OK, res);
 | 
			
		||||
    const int total = backup.getTotalPageCount();
 | 
			
		||||
    ASSERT_EQ(2, total);
 | 
			
		||||
    int remaining = backup.getRemainingPageCount();
 | 
			
		||||
    ASSERT_EQ(1, remaining);
 | 
			
		||||
    res = backup.executeStep(1); // backup the second and last page
 | 
			
		||||
    ASSERT_EQ(SQLITE_DONE, res);
 | 
			
		||||
    remaining = backup.getRemainingPageCount();
 | 
			
		||||
    ASSERT_EQ(0, remaining);
 | 
			
		||||
 | 
			
		||||
    SQLite::Statement query(destDB, "SELECT * FROM backup_test ORDER BY id ASC");
 | 
			
		||||
    ASSERT_TRUE(query.executeStep());
 | 
			
		||||
    EXPECT_EQ(1, query.getColumn(0).getInt());
 | 
			
		||||
    EXPECT_STREQ("first", query.getColumn(1));
 | 
			
		||||
    ASSERT_TRUE(query.executeStep());
 | 
			
		||||
    EXPECT_EQ(2, query.getColumn(0).getInt());
 | 
			
		||||
    EXPECT_STREQ("second", query.getColumn(1));
 | 
			
		||||
    remove("backup_test.db3");
 | 
			
		||||
    remove("backup_test.db3.backup");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Backup, executeStepAll)
 | 
			
		||||
{
 | 
			
		||||
    remove("backup_test.db3");
 | 
			
		||||
    remove("backup_test.db3.backup");
 | 
			
		||||
    SQLite::Database srcDB("backup_test.db3", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    srcDB.exec("CREATE TABLE backup_test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
    ASSERT_EQ(1, srcDB.exec("INSERT INTO backup_test VALUES (1, \"first\")"));
 | 
			
		||||
    ASSERT_EQ(1, srcDB.exec("INSERT INTO backup_test VALUES (2, \"second\")"));
 | 
			
		||||
 | 
			
		||||
    SQLite::Database destDB("backup_test.db3.backup", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    SQLite::Backup backup(destDB, srcDB);
 | 
			
		||||
    const int res = backup.executeStep(); // uses default argument "-1" => execute all steps at once
 | 
			
		||||
    ASSERT_EQ(res, SQLITE_DONE);
 | 
			
		||||
    const int total = backup.getTotalPageCount();
 | 
			
		||||
    ASSERT_EQ(2, total);
 | 
			
		||||
    const int remaining = backup.getRemainingPageCount();
 | 
			
		||||
    ASSERT_EQ(0, remaining);
 | 
			
		||||
 | 
			
		||||
    SQLite::Statement query(destDB, "SELECT * FROM backup_test ORDER BY id ASC");
 | 
			
		||||
    ASSERT_TRUE(query.executeStep());
 | 
			
		||||
    EXPECT_EQ(1, query.getColumn(0).getInt());
 | 
			
		||||
    EXPECT_STREQ("first", query.getColumn(1));
 | 
			
		||||
    ASSERT_TRUE(query.executeStep());
 | 
			
		||||
    EXPECT_EQ(2, query.getColumn(0).getInt());
 | 
			
		||||
    EXPECT_STREQ("second", query.getColumn(1));
 | 
			
		||||
    remove("backup_test.db3");
 | 
			
		||||
    remove("backup_test.db3.backup");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Backup, executeStepException)
 | 
			
		||||
{
 | 
			
		||||
    remove("backup_test.db3");
 | 
			
		||||
    remove("backup_test.db3.backup");
 | 
			
		||||
    SQLite::Database srcDB("backup_test.db3", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    srcDB.exec("CREATE TABLE backup_test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
    ASSERT_EQ(1, srcDB.exec("INSERT INTO backup_test VALUES (1, \"first\")"));
 | 
			
		||||
    ASSERT_EQ(1, srcDB.exec("INSERT INTO backup_test VALUES (2, \"second\")"));
 | 
			
		||||
    {
 | 
			
		||||
        SQLite::Database destDB("backup_test.db3.backup", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
        (void)destDB;
 | 
			
		||||
    }
 | 
			
		||||
    {
 | 
			
		||||
        SQLite::Database destDB("backup_test.db3.backup", SQLite::OPEN_READONLY);
 | 
			
		||||
        SQLite::Backup backup(destDB, srcDB);
 | 
			
		||||
        EXPECT_THROW(backup.executeStep(), SQLite::Exception);
 | 
			
		||||
    }
 | 
			
		||||
    remove("backup_test.db3");
 | 
			
		||||
    remove("backup_test.db3.backup");
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										241
									
								
								thirdparty/SQLiteCpp/tests/Column_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										241
									
								
								thirdparty/SQLiteCpp/tests/Column_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@@ -0,0 +1,241 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @file    Column_test.cpp
 | 
			
		||||
 * @ingroup tests
 | 
			
		||||
 * @brief   Test of a SQLiteCpp Column.
 | 
			
		||||
 *
 | 
			
		||||
 * Copyright (c) 2012-2019 Sebastien Rombauts (sebastien.rombauts@gmail.com)
 | 
			
		||||
 *
 | 
			
		||||
 * Distributed under the MIT License (MIT) (See accompanying file LICENSE.txt
 | 
			
		||||
 * or copy at http://opensource.org/licenses/MIT)
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include <SQLiteCpp/Database.h>
 | 
			
		||||
#include <SQLiteCpp/Statement.h>
 | 
			
		||||
#include <SQLiteCpp/Column.h>
 | 
			
		||||
 | 
			
		||||
#include <sqlite3.h> // for sqlite3_int64
 | 
			
		||||
 | 
			
		||||
#include <gtest/gtest.h>
 | 
			
		||||
 | 
			
		||||
#include <cstdio>
 | 
			
		||||
#include <stdint.h>
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
TEST(Column, basis)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT, int INTEGER, double REAL, binary BLOB, empty TEXT)"));
 | 
			
		||||
    EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
    EXPECT_TRUE(db.tableExists(std::string("test")));
 | 
			
		||||
    EXPECT_EQ(0, db.getLastInsertRowid());
 | 
			
		||||
 | 
			
		||||
    // Create a first row (autoid: 1) with all kind of data and a null value
 | 
			
		||||
    SQLite::Statement   insert(db, "INSERT INTO test VALUES (NULL, \"first\", -123, 0.123, ?, NULL)");
 | 
			
		||||
    // Bind the blob value to the first parameter of the SQL query
 | 
			
		||||
    const char  buffer[] = {'b', 'l', '\0', 'b'}; // "bl\0b" : 4 char, with a null byte inside
 | 
			
		||||
    const int   size = sizeof(buffer); // size = 4
 | 
			
		||||
    const void* blob = &buffer;
 | 
			
		||||
    insert.bind(1, blob, size);
 | 
			
		||||
    // Execute the one-step query to insert the row
 | 
			
		||||
    EXPECT_EQ(1, insert.exec());
 | 
			
		||||
    EXPECT_EQ(1, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(1, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    EXPECT_THROW(insert.exec(), SQLite::Exception); // exec() shall throw as it needs to be reseted
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query
 | 
			
		||||
    SQLite::Statement   query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(6, query.getColumnCount ());
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
 | 
			
		||||
    // validates every variant of cast operators, and conversions of types
 | 
			
		||||
    {
 | 
			
		||||
        const sqlite3_int64 id1     = query.getColumn(0); // operator long long()
 | 
			
		||||
        const int64_t       id2     = query.getColumn(0); // operator long long()
 | 
			
		||||
        const long long     id3     = query.getColumn(0); // operator long long()
 | 
			
		||||
        const long          id4     = query.getColumn(0); // operator long long() or long() depending on compiler/architecture
 | 
			
		||||
        const char          id5     = query.getColumn(0); // operator char()
 | 
			
		||||
        const short         id6     = query.getColumn(0); // operator short()
 | 
			
		||||
        const unsigned int  uint1   = query.getColumn(0); // operator unsigned int()
 | 
			
		||||
        const uint32_t      uint2   = query.getColumn(0); // operator unsigned int()
 | 
			
		||||
        const unsigned char uint3   = query.getColumn(0); // operator unsigned char()
 | 
			
		||||
        const unsigned short uint4  = query.getColumn(0); // operator unsigned short()
 | 
			
		||||
        const char*         ptxt    = query.getColumn(1); // operator const char*()
 | 
			
		||||
        const std::string   msg     = query.getColumn(1); // operator std::string() (or const char* with MSVC)
 | 
			
		||||
        const int           integer = query.getColumn(2); // operator int()
 | 
			
		||||
        const double        real    = query.getColumn(3); // operator double()
 | 
			
		||||
        const void*         pblob   = query.getColumn(4); // operator void*()
 | 
			
		||||
#if !defined(_MSC_VER) || _MSC_VER >= 1900
 | 
			
		||||
        // This implicit cast should use operator std::string()
 | 
			
		||||
        // but would fallback to const char* with MSVC 2010-2013 (witch does not work with the NULL char in the middle)
 | 
			
		||||
        const std::string   sblob   = query.getColumn(4); // operator std::string()
 | 
			
		||||
#endif
 | 
			
		||||
        const void*         pempty  = query.getColumn(5); // operator void*()
 | 
			
		||||
        EXPECT_EQ(1,            id1);
 | 
			
		||||
        EXPECT_EQ(1,            id2);
 | 
			
		||||
        EXPECT_EQ(1,            id3);
 | 
			
		||||
        EXPECT_EQ(1,            id4);
 | 
			
		||||
        EXPECT_EQ(1,            id5);
 | 
			
		||||
        EXPECT_EQ(1,            id6);
 | 
			
		||||
        EXPECT_EQ(1U,           uint1);
 | 
			
		||||
        EXPECT_EQ(1U,           uint2);
 | 
			
		||||
        EXPECT_EQ(1U,           uint3);
 | 
			
		||||
        EXPECT_EQ(1U,           uint4);
 | 
			
		||||
        EXPECT_STREQ("first",   ptxt);
 | 
			
		||||
        EXPECT_EQ("first",      msg);
 | 
			
		||||
        EXPECT_EQ(-123,         integer);
 | 
			
		||||
        EXPECT_EQ(0.123,        real);
 | 
			
		||||
        EXPECT_EQ(0,            memcmp("bl\0b", pblob, size));
 | 
			
		||||
#if !defined(_MSC_VER) || _MSC_VER >= 1900
 | 
			
		||||
        EXPECT_EQ((size_t)size, sblob.size());
 | 
			
		||||
        EXPECT_EQ(0,            memcmp("bl\0b", &sblob[0], size));
 | 
			
		||||
#endif
 | 
			
		||||
        EXPECT_EQ(NULL,         pempty);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // validates every variant of explicit getters
 | 
			
		||||
    {
 | 
			
		||||
        int64_t             id      = query.getColumn(0).getInt64();
 | 
			
		||||
        const unsigned int  uint1   = query.getColumn(0).getUInt();
 | 
			
		||||
        const uint32_t      uint2   = query.getColumn(0).getUInt();
 | 
			
		||||
        const char*         ptxt    = query.getColumn(1).getText();
 | 
			
		||||
        const std::string   msg1    = query.getColumn(1).getText();
 | 
			
		||||
        const std::string   msg2    = query.getColumn(1).getString();
 | 
			
		||||
        const int           integer = query.getColumn(2).getInt();
 | 
			
		||||
        const double        real    = query.getColumn(3).getDouble();
 | 
			
		||||
        const void*         pblob   = query.getColumn(4).getBlob();
 | 
			
		||||
        const std::string   sblob   = query.getColumn(4).getString();
 | 
			
		||||
        EXPECT_EQ(1,            id);
 | 
			
		||||
        EXPECT_EQ(1U,           uint1);
 | 
			
		||||
        EXPECT_EQ(1U,           uint2);
 | 
			
		||||
        EXPECT_STREQ("first",   ptxt);
 | 
			
		||||
        EXPECT_EQ("first",      msg1);
 | 
			
		||||
        EXPECT_EQ("first",      msg2);
 | 
			
		||||
        EXPECT_EQ(-123,         integer);
 | 
			
		||||
        EXPECT_EQ(0.123,        real);
 | 
			
		||||
        EXPECT_EQ(0,            memcmp("bl\0b", pblob, 4));
 | 
			
		||||
        EXPECT_EQ(0,            memcmp("bl\0b", &sblob[0], 4));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Validate getBytes(), getType(), isInteger(), isNull()...
 | 
			
		||||
    EXPECT_EQ(SQLite::INTEGER,  query.getColumn(0).getType());
 | 
			
		||||
    EXPECT_EQ(true,             query.getColumn(0).isInteger());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(0).isFloat());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(0).isText());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(0).isBlob());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(0).isNull());
 | 
			
		||||
    EXPECT_STREQ("1",           query.getColumn(0).getText());  // convert to string
 | 
			
		||||
    EXPECT_EQ(1,                query.getColumn(0).getBytes()); // size of the string "1" without the null terminator
 | 
			
		||||
    EXPECT_EQ(SQLite::TEXT,     query.getColumn(1).getType());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(1).isInteger());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(1).isFloat());
 | 
			
		||||
    EXPECT_EQ(true,             query.getColumn(1).isText());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(1).isBlob());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(1).isNull());
 | 
			
		||||
    EXPECT_STREQ("first",       query.getColumn(1).getText());  // convert to string
 | 
			
		||||
    EXPECT_EQ(5,                query.getColumn(1).getBytes()); // size of the string "first"
 | 
			
		||||
    EXPECT_EQ(SQLite::INTEGER,  query.getColumn(2).getType());
 | 
			
		||||
    EXPECT_EQ(true,             query.getColumn(2).isInteger());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(2).isFloat());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(2).isText());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(2).isBlob());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(2).isNull());
 | 
			
		||||
    EXPECT_STREQ("-123",        query.getColumn(2).getText());  // convert to string
 | 
			
		||||
    EXPECT_EQ(4,                query.getColumn(2).getBytes()); // size of the string "-123"
 | 
			
		||||
    EXPECT_EQ(SQLite::FLOAT,    query.getColumn(3).getType());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(3).isInteger());
 | 
			
		||||
    EXPECT_EQ(true,             query.getColumn(3).isFloat());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(3).isText());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(3).isBlob());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(3).isNull());
 | 
			
		||||
    EXPECT_STREQ("0.123",       query.getColumn(3).getText());  // convert to string
 | 
			
		||||
    EXPECT_EQ(5,                query.getColumn(3).getBytes()); // size of the string "0.123"
 | 
			
		||||
    EXPECT_EQ(SQLite::BLOB,     query.getColumn(4).getType());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(4).isInteger());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(4).isFloat());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(4).isText());
 | 
			
		||||
    EXPECT_EQ(true,             query.getColumn(4).isBlob());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(4).isNull());
 | 
			
		||||
    EXPECT_STREQ("bl\0b",       query.getColumn(4).getText());  // convert to string
 | 
			
		||||
    EXPECT_EQ(4,                query.getColumn(4).getBytes()); // size of the blob "bl\0b" with the null char
 | 
			
		||||
    EXPECT_EQ(SQLite::Null,     query.getColumn(5).getType());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(5).isInteger());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(5).isFloat());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(5).isText());
 | 
			
		||||
    EXPECT_EQ(false,            query.getColumn(5).isBlob());
 | 
			
		||||
    EXPECT_EQ(true,             query.getColumn(5).isNull());
 | 
			
		||||
    EXPECT_STREQ("",            query.getColumn(5).getText());  // convert to string
 | 
			
		||||
    EXPECT_EQ(0,                query.getColumn(5).getBytes()); // size of the string "" without the null terminator
 | 
			
		||||
 | 
			
		||||
    // Use intermediate Column objects (this is not the recommended way to use the API)
 | 
			
		||||
    {
 | 
			
		||||
        const SQLite::Column id = query.getColumn(0);
 | 
			
		||||
        EXPECT_EQ(1, id.getInt64());
 | 
			
		||||
        const SQLite::Column msg = query.getColumn(1);
 | 
			
		||||
        EXPECT_EQ("first", msg.getString());
 | 
			
		||||
        const SQLite::Column integer = query.getColumn(2);
 | 
			
		||||
        EXPECT_EQ(-123, integer.getInt());
 | 
			
		||||
        const SQLite::Column dbl = query.getColumn(3);
 | 
			
		||||
        EXPECT_EQ(0.123, dbl.getDouble());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Column, getName)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT)"));
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\")"));
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query, using the "id" column name as-is, but aliasing the "msg" column with new name "value"
 | 
			
		||||
    SQLite::Statement   query(db, "SELECT id, msg as value FROM test");
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
 | 
			
		||||
    // Show how to get the aliased names of the result columns.
 | 
			
		||||
    const std::string name0 = query.getColumn(0).getName();
 | 
			
		||||
    const std::string name1 = query.getColumn(1).getName();
 | 
			
		||||
    EXPECT_EQ("id",     name0);
 | 
			
		||||
    EXPECT_EQ("value",  name1);
 | 
			
		||||
 | 
			
		||||
#ifdef SQLITE_ENABLE_COLUMN_METADATA
 | 
			
		||||
    // Show how to get origin names of the table columns from which theses result columns come from.
 | 
			
		||||
    // Requires the SQLITE_ENABLE_COLUMN_METADATA preprocessor macro to be
 | 
			
		||||
    // also defined at compile times of the SQLite library itself.
 | 
			
		||||
    const std::string oname0 = query.getColumn(0).getOriginName();
 | 
			
		||||
    const std::string oname1 = query.getColumn(1).getOriginName();
 | 
			
		||||
    EXPECT_EQ("id",     oname0);
 | 
			
		||||
    EXPECT_EQ("msg",    oname1);
 | 
			
		||||
#endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Column, stream)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (msg TEXT)"));
 | 
			
		||||
    SQLite::Statement insert(db, "INSERT INTO test VALUES (?)");
 | 
			
		||||
 | 
			
		||||
    // content to test
 | 
			
		||||
    const char str_[] = "stringwith\0embedded";
 | 
			
		||||
    std::string str(str_, sizeof(str_)-1);
 | 
			
		||||
 | 
			
		||||
    insert.bind(1, str);
 | 
			
		||||
    // Execute the one-step query to insert the row
 | 
			
		||||
    EXPECT_EQ(1, insert.exec());
 | 
			
		||||
    EXPECT_EQ(1, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    std::stringstream ss;
 | 
			
		||||
    ss << query.getColumn(0);
 | 
			
		||||
    std::string content = ss.str();
 | 
			
		||||
    EXPECT_EQ(content, str);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										364
									
								
								thirdparty/SQLiteCpp/tests/Database_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										364
									
								
								thirdparty/SQLiteCpp/tests/Database_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@@ -0,0 +1,364 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @file    Database_test.cpp
 | 
			
		||||
 * @ingroup tests
 | 
			
		||||
 * @brief   Test of a SQLiteCpp Database.
 | 
			
		||||
 *
 | 
			
		||||
 * Copyright (c) 2012-2019 Sebastien Rombauts (sebastien.rombauts@gmail.com)
 | 
			
		||||
 *
 | 
			
		||||
 * Distributed under the MIT License (MIT) (See accompanying file LICENSE.txt
 | 
			
		||||
 * or copy at http://opensource.org/licenses/MIT)
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include <SQLiteCpp/Database.h>
 | 
			
		||||
 | 
			
		||||
#include <sqlite3.h> // for SQLITE_ERROR and SQLITE_VERSION_NUMBER
 | 
			
		||||
 | 
			
		||||
#include <gtest/gtest.h>
 | 
			
		||||
 | 
			
		||||
#include <cstdio>
 | 
			
		||||
 | 
			
		||||
#ifdef SQLITECPP_ENABLE_ASSERT_HANDLER
 | 
			
		||||
namespace SQLite
 | 
			
		||||
{
 | 
			
		||||
/// definition of the assertion handler enabled when SQLITECPP_ENABLE_ASSERT_HANDLER is defined in the project (CMakeList.txt)
 | 
			
		||||
void assertion_failed(const char* apFile, const long apLine, const char* apFunc, const char* apExpr, const char* apMsg)
 | 
			
		||||
{
 | 
			
		||||
    // TODO: unit test that this assertion callback get called (already tested manually)
 | 
			
		||||
    std::cout << "assertion_failed(" << apFile << ", " << apLine << ", " << apFunc << ", " << apExpr << ", " << apMsg << ")\n";
 | 
			
		||||
}
 | 
			
		||||
}
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
TEST(SQLiteCpp, version)
 | 
			
		||||
{
 | 
			
		||||
    EXPECT_STREQ(SQLITE_VERSION,        SQLite::VERSION);
 | 
			
		||||
    EXPECT_EQ   (SQLITE_VERSION_NUMBER, SQLite::VERSION_NUMBER);
 | 
			
		||||
    EXPECT_STREQ(SQLITE_VERSION,        SQLite::getLibVersion());
 | 
			
		||||
    EXPECT_EQ   (SQLITE_VERSION_NUMBER, SQLite::getLibVersionNumber());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Database, ctorExecCreateDropExist)
 | 
			
		||||
{
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
    {
 | 
			
		||||
        // Try to open a non-existing database
 | 
			
		||||
        std::string filename = "test.db3";
 | 
			
		||||
        EXPECT_THROW(SQLite::Database not_found(filename), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
        // Create a new database
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
        EXPECT_STREQ("test.db3", db.getFilename().c_str());
 | 
			
		||||
        EXPECT_FALSE(db.tableExists("test"));
 | 
			
		||||
        EXPECT_FALSE(db.tableExists(std::string("test")));
 | 
			
		||||
        EXPECT_EQ(0, db.getLastInsertRowid());
 | 
			
		||||
 | 
			
		||||
        EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)"));
 | 
			
		||||
        EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
        EXPECT_TRUE(db.tableExists(std::string("test")));
 | 
			
		||||
        EXPECT_EQ(0, db.getLastInsertRowid());
 | 
			
		||||
        
 | 
			
		||||
        EXPECT_EQ(0, db.exec("DROP TABLE IF EXISTS test"));
 | 
			
		||||
        EXPECT_FALSE(db.tableExists("test"));
 | 
			
		||||
        EXPECT_FALSE(db.tableExists(std::string("test")));
 | 
			
		||||
        EXPECT_EQ(0, db.getLastInsertRowid());
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#if __cplusplus >= 201103L || (defined(_MSC_VER) && _MSC_VER >= 1600)
 | 
			
		||||
 | 
			
		||||
SQLite::Database DatabaseBuilder(const char* apName)
 | 
			
		||||
{
 | 
			
		||||
    return SQLite::Database(apName, SQLite::OPEN_READWRITE | SQLite::OPEN_CREATE);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Database, moveConstructor)
 | 
			
		||||
{
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
    {
 | 
			
		||||
        // Create a new database, using the move constructor
 | 
			
		||||
        SQLite::Database db = DatabaseBuilder("test.db3");
 | 
			
		||||
        EXPECT_FALSE(db.tableExists("test"));
 | 
			
		||||
        EXPECT_TRUE(db.getHandle() != NULL);
 | 
			
		||||
        SQLite::Database moved = std::move(db);
 | 
			
		||||
        EXPECT_TRUE(db.getHandle() == NULL);
 | 
			
		||||
        EXPECT_TRUE(moved.getHandle() != NULL);
 | 
			
		||||
        EXPECT_FALSE(moved.tableExists("test"));
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#endif 
 | 
			
		||||
 | 
			
		||||
TEST(Database, createCloseReopen)
 | 
			
		||||
{
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
    {
 | 
			
		||||
        // Try to open the non-existing database
 | 
			
		||||
        EXPECT_THROW(SQLite::Database not_found("test.db3"), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
        // Create a new database
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
        EXPECT_FALSE(db.tableExists("test"));
 | 
			
		||||
        db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
        EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    {
 | 
			
		||||
        // Reopen the database file
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
        EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Database, inMemory)
 | 
			
		||||
{
 | 
			
		||||
    {
 | 
			
		||||
        // Create a new database
 | 
			
		||||
        SQLite::Database db(":memory:", SQLite::OPEN_READWRITE);
 | 
			
		||||
        EXPECT_FALSE(db.tableExists("test"));
 | 
			
		||||
        db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
        EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
        // Create a new database: not shared with the above db
 | 
			
		||||
        SQLite::Database db2(":memory:");
 | 
			
		||||
        EXPECT_FALSE(db2.tableExists("test"));
 | 
			
		||||
    } // Close an destroy DBs
 | 
			
		||||
    {
 | 
			
		||||
        // Create a new database: no more "test" table
 | 
			
		||||
        SQLite::Database db(":memory:");
 | 
			
		||||
        EXPECT_FALSE(db.tableExists("test"));
 | 
			
		||||
    } // Close an destroy DB
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#if SQLITE_VERSION_NUMBER >= 3007015 // SQLite v3.7.15 is first version with PRAGMA busy_timeout
 | 
			
		||||
TEST(Database, busyTimeout)
 | 
			
		||||
{
 | 
			
		||||
    {
 | 
			
		||||
        // Create a new database with default timeout of 0ms
 | 
			
		||||
        SQLite::Database db(":memory:");
 | 
			
		||||
        // Busy timeout default to 0ms: any contention between threads or process leads to SQLITE_BUSY error
 | 
			
		||||
        EXPECT_EQ(0, db.execAndGet("PRAGMA busy_timeout").getInt());
 | 
			
		||||
 | 
			
		||||
        // Set a non null busy timeout: any contention between threads will leads to as much retry as possible during the time
 | 
			
		||||
        db.setBusyTimeout(5000);
 | 
			
		||||
        EXPECT_EQ(5000, db.execAndGet("PRAGMA busy_timeout").getInt());
 | 
			
		||||
 | 
			
		||||
        // Reset timeout to 0
 | 
			
		||||
        db.setBusyTimeout(0);
 | 
			
		||||
        EXPECT_EQ(0, db.execAndGet("PRAGMA busy_timeout").getInt());
 | 
			
		||||
    }
 | 
			
		||||
    {
 | 
			
		||||
        // Create a new database with a non null busy timeout
 | 
			
		||||
        SQLite::Database db(":memory:", SQLite::OPEN_READWRITE, 5000);
 | 
			
		||||
        EXPECT_EQ(5000, db.execAndGet("PRAGMA busy_timeout").getInt());
 | 
			
		||||
 | 
			
		||||
        // Reset timeout to null
 | 
			
		||||
        db.setBusyTimeout(0);
 | 
			
		||||
        EXPECT_EQ(0, db.execAndGet("PRAGMA busy_timeout").getInt());
 | 
			
		||||
    }
 | 
			
		||||
    {
 | 
			
		||||
        // Create a new database with a non null busy timeout
 | 
			
		||||
        const std::string memory = ":memory:";
 | 
			
		||||
        SQLite::Database db(memory, SQLite::OPEN_READWRITE, 5000);
 | 
			
		||||
        EXPECT_EQ(5000, db.execAndGet("PRAGMA busy_timeout").getInt());
 | 
			
		||||
 | 
			
		||||
        // Reset timeout to null
 | 
			
		||||
        db.setBusyTimeout(0);
 | 
			
		||||
        EXPECT_EQ(0, db.execAndGet("PRAGMA busy_timeout").getInt());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
#endif // SQLITE_VERSION_NUMBER >= 3007015
 | 
			
		||||
 | 
			
		||||
TEST(Database, exec)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE);
 | 
			
		||||
 | 
			
		||||
    // Create a new table with an explicit "id" column aliasing the underlying rowid
 | 
			
		||||
    // NOTE: here exec() returns 0 only because it is the first statements since database connexion,
 | 
			
		||||
    //       but its return is an undefined value for "CREATE TABLE" statements.
 | 
			
		||||
    db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
    EXPECT_EQ(0, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(0, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // first row : insert the "first" text value into new row of id 1
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\")"));
 | 
			
		||||
    EXPECT_EQ(1, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(1, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // second row : insert the "second" text value into new row of id 2
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"second\")"));
 | 
			
		||||
    EXPECT_EQ(2, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(2, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // third row : insert the "third" text value into new row of id 3
 | 
			
		||||
    const std::string insert("INSERT INTO test VALUES (NULL, \"third\")");
 | 
			
		||||
    EXPECT_EQ(1, db.exec(insert));
 | 
			
		||||
    EXPECT_EQ(3, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(3, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // update the second row : update text value to "second_updated"
 | 
			
		||||
    EXPECT_EQ(1, db.exec("UPDATE test SET value=\"second-updated\" WHERE id='2'"));
 | 
			
		||||
    EXPECT_EQ(3, db.getLastInsertRowid()); // last inserted row ID is still 3
 | 
			
		||||
    EXPECT_EQ(4, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // delete the third row
 | 
			
		||||
    EXPECT_EQ(1, db.exec("DELETE FROM test WHERE id='3'"));
 | 
			
		||||
    EXPECT_EQ(3, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(5, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // drop the whole table, ie the two remaining columns
 | 
			
		||||
    // NOTE: here exec() returns 1, like the last time, as it is an undefined value for "DROP TABLE" statements
 | 
			
		||||
    db.exec("DROP TABLE IF EXISTS test");
 | 
			
		||||
    EXPECT_FALSE(db.tableExists("test"));
 | 
			
		||||
    EXPECT_EQ(5, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // Re-Create the same table
 | 
			
		||||
    // NOTE: here exec() returns 1, like the last time, as it is an undefined value for "CREATE TABLE" statements
 | 
			
		||||
    db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
    EXPECT_EQ(5, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // insert two rows with two *different* statements => returns only 1, ie. for the second INSERT statement
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\");INSERT INTO test VALUES (NULL, \"second\");"));
 | 
			
		||||
    EXPECT_EQ(2, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(7, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
#if (SQLITE_VERSION_NUMBER >= 3007011)
 | 
			
		||||
    // insert two rows with only one statement (starting with SQLite 3.7.11) => returns 2
 | 
			
		||||
    EXPECT_EQ(2, db.exec("INSERT INTO test VALUES (NULL, \"third\"), (NULL, \"fourth\");"));
 | 
			
		||||
    EXPECT_EQ(4, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(9, db.getTotalChanges());
 | 
			
		||||
#endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Database, execAndGet)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE);
 | 
			
		||||
 | 
			
		||||
    // Create a new table with an explicit "id" column aliasing the underlying rowid
 | 
			
		||||
    db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT, weight INTEGER)");
 | 
			
		||||
 | 
			
		||||
    // insert a few rows
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\",  3)"));
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"second\", 5)"));
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"third\",  7)"));
 | 
			
		||||
 | 
			
		||||
    // Get a single value result with an easy to use shortcut
 | 
			
		||||
    EXPECT_STREQ("second",  db.execAndGet("SELECT value FROM test WHERE id=2"));
 | 
			
		||||
    EXPECT_STREQ("third",   db.execAndGet("SELECT value FROM test WHERE weight=7"));
 | 
			
		||||
    EXPECT_EQ(3,            db.execAndGet("SELECT weight FROM test WHERE value=\"first\"").getInt());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Database, execException)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    // exception with SQL error: "no such table"
 | 
			
		||||
    EXPECT_THROW(db.exec("INSERT INTO test VALUES (NULL, \"first\",  3)"), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(SQLITE_ERROR, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLITE_ERROR, db.getExtendedErrorCode());
 | 
			
		||||
    EXPECT_STREQ("no such table: test", db.getErrorMsg());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT, weight INTEGER)");
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
    EXPECT_STREQ("not an error", db.getErrorMsg());
 | 
			
		||||
 | 
			
		||||
    // exception with SQL error: "table test has 3 columns but 2 values were supplied"
 | 
			
		||||
    EXPECT_THROW(db.exec("INSERT INTO test VALUES (NULL,  3)"), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(SQLITE_ERROR, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLITE_ERROR, db.getExtendedErrorCode());
 | 
			
		||||
    EXPECT_STREQ("table test has 3 columns but 2 values were supplied", db.getErrorMsg());
 | 
			
		||||
 | 
			
		||||
    // exception with SQL error: "No row to get a column from"
 | 
			
		||||
    EXPECT_THROW(db.execAndGet("SELECT weight FROM test WHERE value=\"first\""), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\",  3)"));
 | 
			
		||||
    // exception with SQL error: "No row to get a column from"
 | 
			
		||||
    EXPECT_THROW(db.execAndGet("SELECT weight FROM test WHERE value=\"second\""), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    // Add a row with more values than columns in the table: "table test has 3 columns but 4 values were supplied"
 | 
			
		||||
    EXPECT_THROW(db.exec("INSERT INTO test VALUES (NULL, \"first\", 123, 0.123)"), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(SQLITE_ERROR, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLITE_ERROR, db.getExtendedErrorCode());
 | 
			
		||||
    EXPECT_STREQ("table test has 3 columns but 4 values were supplied", db.getErrorMsg());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// TODO: test Database::createFunction()
 | 
			
		||||
// TODO: test Database::loadExtension()
 | 
			
		||||
 | 
			
		||||
#ifdef SQLITE_HAS_CODEC
 | 
			
		||||
TEST(Database, encryptAndDecrypt)
 | 
			
		||||
{
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
    {
 | 
			
		||||
        // Try to open the non-existing database
 | 
			
		||||
        EXPECT_THROW(SQLite::Database not_found("test.db3"), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
        // Create a new database
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READWRITE | SQLite::OPEN_CREATE);
 | 
			
		||||
        EXPECT_FALSE(db.tableExists("test"));
 | 
			
		||||
        db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
        EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    {
 | 
			
		||||
        // Reopen the database file and encrypt it
 | 
			
		||||
        EXPECT_TRUE(SQLite::Database::isUnencrypted("test.db3"));
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READWRITE);
 | 
			
		||||
        // Encrypt the database
 | 
			
		||||
        db.rekey("123secret");
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    {
 | 
			
		||||
        // Reopen the database file and try to use it
 | 
			
		||||
        EXPECT_FALSE(SQLite::Database::isUnencrypted("test.db3"));
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READONLY);
 | 
			
		||||
        EXPECT_THROW(db.tableExists("test"), SQLite::Exception);
 | 
			
		||||
        db.key("123secret");
 | 
			
		||||
        EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    {
 | 
			
		||||
        // Reopen the database file and decrypt it
 | 
			
		||||
        EXPECT_FALSE(SQLite::Database::isUnencrypted("test.db3"));
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READWRITE);
 | 
			
		||||
        // Decrypt the database
 | 
			
		||||
        db.key("123secret");
 | 
			
		||||
        db.rekey("");
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    {
 | 
			
		||||
        // Reopen the database file and use it
 | 
			
		||||
        EXPECT_TRUE(SQLite::Database::isUnencrypted("test.db3"));
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READWRITE);
 | 
			
		||||
        EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
}
 | 
			
		||||
#else // SQLITE_HAS_CODEC
 | 
			
		||||
TEST(Database, encryptAndDecrypt)
 | 
			
		||||
{
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
    {
 | 
			
		||||
        // Try to open the non-existing database
 | 
			
		||||
        EXPECT_THROW(SQLite::Database not_found("test.db3"), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
        // Create a new database
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READWRITE | SQLite::OPEN_CREATE);
 | 
			
		||||
        EXPECT_FALSE(db.tableExists("test"));
 | 
			
		||||
        db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)");
 | 
			
		||||
        EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    {
 | 
			
		||||
        // Reopen the database file and encrypt it
 | 
			
		||||
        EXPECT_TRUE(SQLite::Database::isUnencrypted("test.db3"));
 | 
			
		||||
        SQLite::Database db("test.db3", SQLite::OPEN_READWRITE);
 | 
			
		||||
        // Encrypt the database
 | 
			
		||||
        EXPECT_THROW(db.key("123secret"), SQLite::Exception);
 | 
			
		||||
        EXPECT_THROW(db.rekey("123secret"), SQLite::Exception);
 | 
			
		||||
    } // Close DB test.db3
 | 
			
		||||
    remove("test.db3");
 | 
			
		||||
}
 | 
			
		||||
#endif // SQLITE_HAS_CODEC
 | 
			
		||||
							
								
								
									
										73
									
								
								thirdparty/SQLiteCpp/tests/Exception_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										73
									
								
								thirdparty/SQLiteCpp/tests/Exception_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@@ -0,0 +1,73 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @file    Transaction_test.cpp
 | 
			
		||||
 * @ingroup tests
 | 
			
		||||
 * @brief   Test of a SQLite Transaction.
 | 
			
		||||
 *
 | 
			
		||||
 * Copyright (c) 2012-2019 Sebastien Rombauts (sebastien.rombauts@gmail.com)
 | 
			
		||||
 *
 | 
			
		||||
 * Distributed under the MIT License (MIT) (See accompanying file LICENSE.txt
 | 
			
		||||
 * or copy at http://opensource.org/licenses/MIT)
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include <SQLiteCpp/Exception.h>
 | 
			
		||||
 | 
			
		||||
#include <gtest/gtest.h>
 | 
			
		||||
 | 
			
		||||
#include <string>
 | 
			
		||||
 | 
			
		||||
TEST(Exception, copy)
 | 
			
		||||
{
 | 
			
		||||
    const SQLite::Exception ex1("some error", 2);
 | 
			
		||||
    const SQLite::Exception ex2 = ex1;
 | 
			
		||||
    EXPECT_STREQ(ex1.what(), ex2.what());
 | 
			
		||||
    EXPECT_EQ(ex1.getErrorCode(), ex2.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(ex1.getExtendedErrorCode(), ex2.getExtendedErrorCode());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// see http://eel.is/c++draft/exception#2 or http://www.cplusplus.com/reference/exception/exception/operator=/
 | 
			
		||||
// an assignment operator is expected to be avaiable
 | 
			
		||||
TEST(Exception, assignment)
 | 
			
		||||
{
 | 
			
		||||
    const SQLite::Exception ex1("some error", 2);
 | 
			
		||||
    SQLite::Exception ex2("some error2", 3);
 | 
			
		||||
 | 
			
		||||
    ex2 = ex1;
 | 
			
		||||
 | 
			
		||||
    EXPECT_STREQ(ex1.what(), ex2.what());
 | 
			
		||||
    EXPECT_EQ(ex1.getErrorCode(), ex2.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(ex1.getExtendedErrorCode(), ex2.getExtendedErrorCode());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Exception, throw_catch)
 | 
			
		||||
{
 | 
			
		||||
    const char message[] = "some error";
 | 
			
		||||
    try
 | 
			
		||||
    {
 | 
			
		||||
        throw SQLite::Exception(message);
 | 
			
		||||
    }
 | 
			
		||||
    catch (const std::runtime_error& ex)
 | 
			
		||||
    {
 | 
			
		||||
        EXPECT_STREQ(ex.what(), message);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
TEST(Exception, constructor)
 | 
			
		||||
{
 | 
			
		||||
    const char msg1[] = "error msg";
 | 
			
		||||
    std::string msg2 = msg1;
 | 
			
		||||
    {
 | 
			
		||||
        const SQLite::Exception ex1(msg1);
 | 
			
		||||
        const SQLite::Exception ex2(msg2);
 | 
			
		||||
        EXPECT_STREQ(ex1.what(), ex2.what());
 | 
			
		||||
        EXPECT_EQ(ex1.getErrorCode(), ex2.getErrorCode());
 | 
			
		||||
        EXPECT_EQ(ex1.getExtendedErrorCode(), ex2.getExtendedErrorCode());
 | 
			
		||||
    }
 | 
			
		||||
    {
 | 
			
		||||
        const SQLite::Exception ex1(msg1, 1);
 | 
			
		||||
        const SQLite::Exception ex2(msg2, 1);
 | 
			
		||||
        EXPECT_STREQ(ex1.what(), ex2.what());
 | 
			
		||||
        EXPECT_EQ(ex1.getErrorCode(), ex2.getErrorCode());
 | 
			
		||||
        EXPECT_EQ(ex1.getExtendedErrorCode(), ex2.getExtendedErrorCode());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										54
									
								
								thirdparty/SQLiteCpp/tests/ExecuteMany_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										54
									
								
								thirdparty/SQLiteCpp/tests/ExecuteMany_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@@ -0,0 +1,54 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @file    VariadicBind_test.cpp
 | 
			
		||||
 * @ingroup tests
 | 
			
		||||
 * @brief   Test of variadic bind
 | 
			
		||||
 *
 | 
			
		||||
 * Copyright (c) 2019 Maximilian Bachmann (github@maxbachmann)
 | 
			
		||||
 * Copyright (c) 2019 Sebastien Rombauts (sebastien.rombauts@gmail.com)
 | 
			
		||||
 *
 | 
			
		||||
 * Distributed under the MIT License (MIT) (See accompanying file LICENSE.txt
 | 
			
		||||
 * or copy at http://opensource.org/licenses/MIT)
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include <SQLiteCpp/Database.h>
 | 
			
		||||
#include <SQLiteCpp/Statement.h>
 | 
			
		||||
#include <SQLiteCpp/ExecuteMany.h>
 | 
			
		||||
 | 
			
		||||
#include <gtest/gtest.h>
 | 
			
		||||
 | 
			
		||||
#include <cstdio>
 | 
			
		||||
 | 
			
		||||
#if (__cplusplus >= 201402L) || ( defined(_MSC_VER) && (_MSC_VER >= 1900) ) // c++14: Visual Studio 2015
 | 
			
		||||
TEST(ExecuteMany, invalid)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
 | 
			
		||||
    EXPECT_EQ(0, db.exec("DROP TABLE IF EXISTS test"));
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT DEFAULT 'default')"));
 | 
			
		||||
    EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
    {
 | 
			
		||||
        execute_many(db, "INSERT INTO test VALUES (?, ?)",
 | 
			
		||||
            std::make_tuple(1),
 | 
			
		||||
            std::make_tuple(2, "two"),
 | 
			
		||||
            std::make_tuple(3, "three")
 | 
			
		||||
        );
 | 
			
		||||
    }
 | 
			
		||||
    // make sure the content is as expected
 | 
			
		||||
    {
 | 
			
		||||
        SQLite::Statement query(db, std::string{"SELECT id, value FROM test ORDER BY id"});
 | 
			
		||||
        std::vector<std::pair<int, std::string> > results;
 | 
			
		||||
        while (query.executeStep())
 | 
			
		||||
        {
 | 
			
		||||
            const int id = query.getColumn(0);
 | 
			
		||||
            std::string value = query.getColumn(1);
 | 
			
		||||
            results.emplace_back( id, std::move(value) );
 | 
			
		||||
        }
 | 
			
		||||
        EXPECT_EQ(std::size_t(3), results.size());
 | 
			
		||||
 | 
			
		||||
        EXPECT_EQ(std::make_pair(1,std::string{""}), results.at(0));
 | 
			
		||||
        EXPECT_EQ(std::make_pair(2,std::string{"two"}), results.at(1));
 | 
			
		||||
        EXPECT_EQ(std::make_pair(3,std::string{"three"}), results.at(2));
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
#endif // c++14
 | 
			
		||||
							
								
								
									
										864
									
								
								thirdparty/SQLiteCpp/tests/Statement_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										864
									
								
								thirdparty/SQLiteCpp/tests/Statement_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@@ -0,0 +1,864 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @file    Statement_test.cpp
 | 
			
		||||
 * @ingroup tests
 | 
			
		||||
 * @brief   Test of a SQLiteCpp Statement.
 | 
			
		||||
 *
 | 
			
		||||
 * Copyright (c) 2012-2019 Sebastien Rombauts (sebastien.rombauts@gmail.com)
 | 
			
		||||
 *
 | 
			
		||||
 * Distributed under the MIT License (MIT) (See accompanying file LICENSE.txt
 | 
			
		||||
 * or copy at http://opensource.org/licenses/MIT)
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include <SQLiteCpp/Database.h>
 | 
			
		||||
#include <SQLiteCpp/Statement.h>
 | 
			
		||||
 | 
			
		||||
#include <sqlite3.h> // for SQLITE_DONE
 | 
			
		||||
 | 
			
		||||
#include <gtest/gtest.h>
 | 
			
		||||
 | 
			
		||||
#include <cstdio>
 | 
			
		||||
#include <stdint.h>
 | 
			
		||||
 | 
			
		||||
#include <climits> // For INT_MAX
 | 
			
		||||
 | 
			
		||||
TEST(Statement, invalid)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query, but without any table in the database
 | 
			
		||||
    EXPECT_THROW(SQLite::Statement query(db, "SELECT * FROM test"), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(SQLITE_ERROR, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLITE_ERROR, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)"));
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query with no parameter
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(2, query.getColumnCount ());
 | 
			
		||||
    EXPECT_FALSE(query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, query.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, query.getExtendedErrorCode());
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(-1), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(0), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(1), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(2), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.getColumn(-1), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.getColumn(0), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.getColumn(1), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.getColumn(2), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    query.reset();
 | 
			
		||||
    EXPECT_FALSE(query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_FALSE(query.hasRow());
 | 
			
		||||
    EXPECT_TRUE( query.isDone());
 | 
			
		||||
    query.reset();
 | 
			
		||||
    EXPECT_FALSE(query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
 | 
			
		||||
    query.reset();
 | 
			
		||||
    EXPECT_THROW(query.bind(-1, 123), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.bind(0, 123), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.bind(1, 123), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.bind(2, 123), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.bind(0, "abc"), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.bind(0), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(SQLITE_RANGE, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLITE_RANGE, db.getExtendedErrorCode());
 | 
			
		||||
    EXPECT_STREQ("column index out of range", db.getErrorMsg());
 | 
			
		||||
    EXPECT_EQ(SQLITE_RANGE, query.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLITE_RANGE, query.getExtendedErrorCode());
 | 
			
		||||
    EXPECT_STREQ("column index out of range", query.getErrorMsg());
 | 
			
		||||
 | 
			
		||||
    query.exec(); // exec() instead of executeStep() as there is no result
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(0), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.getColumn(0), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    EXPECT_THROW(query.exec(), SQLite::Exception); // exec() shall throw as it needs to be reseted
 | 
			
		||||
 | 
			
		||||
    // Add a first row
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\")"));
 | 
			
		||||
    EXPECT_EQ(1, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(1, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    query.reset();
 | 
			
		||||
    EXPECT_FALSE(query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
 | 
			
		||||
    EXPECT_THROW(query.exec(), SQLite::Exception); // exec() shall throw as it does not expect a result
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#if __cplusplus >= 201103L || (defined(_MSC_VER) && _MSC_VER >= 1600)
 | 
			
		||||
 | 
			
		||||
SQLite::Statement StatementBuilder(SQLite::Database& aDb, const char* apQuery)
 | 
			
		||||
{
 | 
			
		||||
    return SQLite::Statement(aDb, apQuery);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, moveConstructor)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE | SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)"));
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\")"));
 | 
			
		||||
    EXPECT_EQ(1, db.getLastInsertRowid());
 | 
			
		||||
 | 
			
		||||
    SQLite::Statement query = StatementBuilder(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_FALSE(query.getQuery().empty());
 | 
			
		||||
    EXPECT_FALSE(query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_EQ(2, query.getColumnCount());
 | 
			
		||||
    SQLite::Statement moved = std::move(query);
 | 
			
		||||
    EXPECT_TRUE(query.getQuery().empty());
 | 
			
		||||
    EXPECT_EQ(0, query.getColumnCount());
 | 
			
		||||
    EXPECT_FALSE(moved.getQuery().empty());
 | 
			
		||||
    EXPECT_EQ(2, moved.getColumnCount());
 | 
			
		||||
    // Execute
 | 
			
		||||
    moved.executeStep();
 | 
			
		||||
    EXPECT_TRUE(moved.hasRow());
 | 
			
		||||
    EXPECT_FALSE(moved.isDone());
 | 
			
		||||
    EXPECT_FALSE(query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
TEST(Statement, executeStep)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT, int INTEGER, double REAL)"));
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a first row
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\", 123, 0.123)"));
 | 
			
		||||
    EXPECT_EQ(1, db.getLastInsertRowid());
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(4, query.getColumnCount());
 | 
			
		||||
 | 
			
		||||
    // Get the first row
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    const int64_t       id      = query.getColumn(0);
 | 
			
		||||
    const std::string   msg     = query.getColumn(1);
 | 
			
		||||
    const int           integer = query.getColumn(2);
 | 
			
		||||
    const long          integer2= query.getColumn(2);
 | 
			
		||||
    const double        real    = query.getColumn(3);
 | 
			
		||||
    EXPECT_EQ(1,        id);
 | 
			
		||||
    EXPECT_EQ("first",  msg);
 | 
			
		||||
    EXPECT_EQ(123,      integer);
 | 
			
		||||
    EXPECT_EQ(123,      integer2);
 | 
			
		||||
    EXPECT_EQ(0.123,    real);
 | 
			
		||||
 | 
			
		||||
    // Step one more time to discover there is nothing more
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_FALSE(query.hasRow());
 | 
			
		||||
    EXPECT_TRUE (query.isDone()); // "done" is "the end"
 | 
			
		||||
 | 
			
		||||
    // Step after "the end" throw an exception
 | 
			
		||||
    EXPECT_THROW(query.executeStep(), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    // Try to insert a new row with the same PRIMARY KEY: "UNIQUE constraint failed: test.id"
 | 
			
		||||
    SQLite::Statement insert(db, "INSERT INTO test VALUES (1, \"impossible\", 456, 0.456)");
 | 
			
		||||
    EXPECT_THROW(insert.executeStep(), SQLite::Exception);
 | 
			
		||||
    // in this case, reset() do throw again the same error
 | 
			
		||||
    EXPECT_THROW(insert.reset(), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    // Try again to insert a new row with the same PRIMARY KEY (with an alternative method): "UNIQUE constraint failed: test.id"
 | 
			
		||||
    SQLite::Statement insert2(db, "INSERT INTO test VALUES (1, \"impossible\", 456, 0.456)");
 | 
			
		||||
    EXPECT_THROW(insert2.exec(), SQLite::Exception);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, tryExecuteStep)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT, int INTEGER, double REAL)"));
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a first row
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\", 123, 0.123)"));
 | 
			
		||||
    EXPECT_EQ(1, db.getLastInsertRowid());
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(4, query.getColumnCount());
 | 
			
		||||
 | 
			
		||||
    // Get the first row
 | 
			
		||||
    EXPECT_EQ(query.tryExecuteStep(), SQLITE_ROW);
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    const int64_t       id      = query.getColumn(0);
 | 
			
		||||
    const std::string   msg     = query.getColumn(1);
 | 
			
		||||
    const int           integer = query.getColumn(2);
 | 
			
		||||
    const long          integer2= query.getColumn(2);
 | 
			
		||||
    const double        real    = query.getColumn(3);
 | 
			
		||||
    EXPECT_EQ(1,        id);
 | 
			
		||||
    EXPECT_EQ("first",  msg);
 | 
			
		||||
    EXPECT_EQ(123,      integer);
 | 
			
		||||
    EXPECT_EQ(123,      integer2);
 | 
			
		||||
    EXPECT_EQ(0.123,    real);
 | 
			
		||||
 | 
			
		||||
    // Step one more time to discover there is nothing more
 | 
			
		||||
    EXPECT_EQ(query.tryExecuteStep(), SQLITE_DONE);
 | 
			
		||||
    EXPECT_FALSE(query.hasRow());
 | 
			
		||||
    EXPECT_TRUE (query.isDone()); // "done" is "the end"
 | 
			
		||||
 | 
			
		||||
    // Try to insert a new row with the same PRIMARY KEY: "UNIQUE constraint failed: test.id"
 | 
			
		||||
    SQLite::Statement insert(db, "INSERT INTO test VALUES (1, \"impossible\", 456, 0.456)");
 | 
			
		||||
    EXPECT_EQ(insert.tryExecuteStep(), SQLITE_CONSTRAINT);
 | 
			
		||||
    // in this case, reset() do throw again the same error
 | 
			
		||||
    EXPECT_EQ(insert.tryReset(), SQLITE_CONSTRAINT);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, bindings)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT, int INTEGER, double REAL)"));
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Insertion with bindable parameters
 | 
			
		||||
    SQLite::Statement insert(db, "INSERT INTO test VALUES (NULL, ?, ?, ?)");
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query to check the results
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(4, query.getColumnCount());
 | 
			
		||||
 | 
			
		||||
    // First row with text/int/double
 | 
			
		||||
    {
 | 
			
		||||
        const char* text = "first";
 | 
			
		||||
        const int integer = -123;
 | 
			
		||||
        const double dbl = 0.123;
 | 
			
		||||
        insert.bind(1, text);
 | 
			
		||||
        insert.bind(2, integer);
 | 
			
		||||
        insert.bind(3, dbl);
 | 
			
		||||
        EXPECT_EQ(insert.getExpandedSQL(), "INSERT INTO test VALUES (NULL, 'first', -123, 0.123)");
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE (query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ   (1,         query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_STREQ("first",   query.getColumn(1).getText());
 | 
			
		||||
        EXPECT_EQ   (-123,      query.getColumn(2).getInt());
 | 
			
		||||
        EXPECT_EQ   (0.123,     query.getColumn(3).getDouble());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // reset() without clearbindings()
 | 
			
		||||
    insert.reset();
 | 
			
		||||
 | 
			
		||||
    // Second row with the same exact values because clearbindings() was not called
 | 
			
		||||
    {
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE (query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ   (2,         query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_STREQ("first",   query.getColumn(1).getText());
 | 
			
		||||
        EXPECT_EQ   (-123,      query.getColumn(2).getInt());
 | 
			
		||||
        EXPECT_EQ   (0.123,     query.getColumn(3).getDouble());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // reset() with clearbindings() and no more bindings
 | 
			
		||||
    insert.reset();
 | 
			
		||||
    insert.clearBindings();
 | 
			
		||||
 | 
			
		||||
    // Third row with the all null values because clearbindings() was called
 | 
			
		||||
    {
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the resultw
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE (query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ   (3,     query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_TRUE (query.isColumnNull(1));
 | 
			
		||||
        EXPECT_STREQ("",    query.getColumn(1).getText());
 | 
			
		||||
        EXPECT_TRUE (query.isColumnNull(2));
 | 
			
		||||
        EXPECT_EQ   (0,     query.getColumn(2).getInt());
 | 
			
		||||
        EXPECT_TRUE (query.isColumnNull(3));
 | 
			
		||||
        EXPECT_EQ   (0.0,   query.getColumn(3).getDouble());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // reset() with clearbindings() and new bindings
 | 
			
		||||
    insert.reset();
 | 
			
		||||
    insert.clearBindings();
 | 
			
		||||
 | 
			
		||||
    // Fourth row with string/int64/float
 | 
			
		||||
    {
 | 
			
		||||
        const std::string   fourth("fourth");
 | 
			
		||||
        const long long     int64 = 12345678900000LL;
 | 
			
		||||
        const float         float32 = 0.234f;
 | 
			
		||||
        insert.bind(1, fourth);
 | 
			
		||||
        insert.bind(2, int64);
 | 
			
		||||
        insert.bind(3, float32);
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE (query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ(4,                query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_EQ(fourth,           query.getColumn(1).getText());
 | 
			
		||||
        EXPECT_EQ(12345678900000LL, query.getColumn(2).getInt64());
 | 
			
		||||
        EXPECT_EQ(0.234f,           query.getColumn(3).getDouble());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // reset() without clearbindings()
 | 
			
		||||
    insert.reset();
 | 
			
		||||
 | 
			
		||||
    // Fifth row with binary buffer and a null parameter
 | 
			
		||||
    {
 | 
			
		||||
        const char buffer[] = "binary";
 | 
			
		||||
        insert.bind(1, buffer, sizeof(buffer));
 | 
			
		||||
        insert.bind(2);
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE (query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ(5,                query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_STREQ(buffer,        query.getColumn(1).getText());
 | 
			
		||||
        EXPECT_TRUE (query.isColumnNull(2));
 | 
			
		||||
        EXPECT_EQ(0,                query.getColumn(2).getInt());
 | 
			
		||||
        EXPECT_EQ(0.234f,           query.getColumn(3).getDouble());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    // reset() without clearbindings()
 | 
			
		||||
    insert.reset();
 | 
			
		||||
 | 
			
		||||
    // Sixth row with uint32_t unsigned value and a long value (which is either a 32b int or a 64b long long)
 | 
			
		||||
    {
 | 
			
		||||
        const uint32_t  uint32 = 4294967295U;
 | 
			
		||||
        const long      integer = -123;
 | 
			
		||||
        insert.bind(2, uint32);
 | 
			
		||||
        insert.bind(3, integer);
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE(query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ(6, query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_EQ(4294967295U, query.getColumn(2).getUInt());
 | 
			
		||||
        EXPECT_EQ(-123, query.getColumn(3).getInt());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    // reset() without clearbindings()
 | 
			
		||||
    insert.reset();
 | 
			
		||||
 | 
			
		||||
    // Seventh row using another variant of int64 type
 | 
			
		||||
    {
 | 
			
		||||
        const int64_t   int64 = 12345678900000LL;
 | 
			
		||||
        insert.bind(2, int64);
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE(query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ(7, query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_EQ(12345678900000LL, query.getColumn(2).getInt64());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, bindNoCopy)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, txt1 TEXT, txt2 TEXT, binary BLOB)"));
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Insertion with bindable parameters
 | 
			
		||||
    SQLite::Statement insert(db, "INSERT INTO test VALUES (NULL, ?, ?, ?)");
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query to check the results
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(4, query.getColumnCount());
 | 
			
		||||
 | 
			
		||||
    // Insert one row with all variants of bindNoCopy()
 | 
			
		||||
    {
 | 
			
		||||
        const char*         txt1   = "first";
 | 
			
		||||
        const std::string   txt2   = "sec\0nd";
 | 
			
		||||
        const char          blob[] = {'b','l','\0','b'};
 | 
			
		||||
        insert.bindNoCopy(1, txt1);
 | 
			
		||||
        insert.bindNoCopy(2, txt2);
 | 
			
		||||
        insert.bindNoCopy(3, blob, sizeof(blob));
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE(query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ(1, query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_STREQ(txt1, query.getColumn(1).getText());
 | 
			
		||||
        EXPECT_EQ(0, memcmp(&txt2[0], &query.getColumn(2).getString()[0], txt2.size()));
 | 
			
		||||
        EXPECT_EQ(0, memcmp(blob, &query.getColumn(3).getString()[0], sizeof(blob)));
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, bindByName)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT, int INTEGER, double REAL, long INTEGER)"));
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Insertion with bindable parameters
 | 
			
		||||
    SQLite::Statement insert(db, "INSERT INTO test VALUES (NULL, @msg, @int, @double, @long)");
 | 
			
		||||
 | 
			
		||||
    // First row with text/int/double
 | 
			
		||||
    insert.bind("@msg",      "first");
 | 
			
		||||
    insert.bind("@int",      123);
 | 
			
		||||
    insert.bind("@long",      -123);
 | 
			
		||||
    insert.bind("@double",   0.123);
 | 
			
		||||
    EXPECT_EQ(1, insert.exec());
 | 
			
		||||
    EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query to check the result
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(5, query.getColumnCount());
 | 
			
		||||
 | 
			
		||||
    // Check the result
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_EQ   (1,         query.getColumn(0).getInt64());
 | 
			
		||||
    EXPECT_STREQ("first",   query.getColumn(1).getText());
 | 
			
		||||
    EXPECT_EQ   (123,       query.getColumn(2).getInt());
 | 
			
		||||
    EXPECT_EQ   (0.123,     query.getColumn(3).getDouble());
 | 
			
		||||
    EXPECT_EQ   (-123,      query.getColumn(4).getInt());
 | 
			
		||||
 | 
			
		||||
    // reset() with clearbindings() and new bindings
 | 
			
		||||
    insert.reset();
 | 
			
		||||
    insert.clearBindings();
 | 
			
		||||
 | 
			
		||||
    // Second row with string/int64/float
 | 
			
		||||
    {
 | 
			
		||||
        const std::string   second("second");
 | 
			
		||||
        const long long     int64 = 12345678900000LL;
 | 
			
		||||
        const long          integer = -123;
 | 
			
		||||
        const float         float32 = 0.234f;
 | 
			
		||||
        insert.bind("@msg",      second);
 | 
			
		||||
        insert.bind("@int",      int64);
 | 
			
		||||
        insert.bind("@double",   float32);
 | 
			
		||||
        insert.bind("@long",     integer);
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE (query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ(2,                query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_EQ(second,           query.getColumn(1).getText());
 | 
			
		||||
        EXPECT_EQ(12345678900000LL, query.getColumn(2).getInt64());
 | 
			
		||||
        EXPECT_EQ(0.234f,           query.getColumn(3).getDouble());
 | 
			
		||||
        EXPECT_EQ(-123,             query.getColumn(4).getInt());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // reset() without clearbindings()
 | 
			
		||||
    insert.reset();
 | 
			
		||||
 | 
			
		||||
    // Third row with binary buffer and a null parameter
 | 
			
		||||
    {
 | 
			
		||||
        const char buffer[] = "binary";
 | 
			
		||||
        insert.bind("@msg", buffer, sizeof(buffer));
 | 
			
		||||
        insert.bind("@int");
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE (query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ(3,                query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_STREQ(buffer,        query.getColumn(1).getText());
 | 
			
		||||
        EXPECT_TRUE (query.isColumnNull(2));
 | 
			
		||||
        EXPECT_EQ(0,                query.getColumn(2).getInt());
 | 
			
		||||
        EXPECT_EQ(0.234f,           query.getColumn(3).getDouble());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // reset() without clearbindings()
 | 
			
		||||
    insert.reset();
 | 
			
		||||
 | 
			
		||||
    // Fourth row with uint32_t unsigned value and int64_t 64bits value
 | 
			
		||||
    {
 | 
			
		||||
        const uint32_t  uint32 = 4294967295U;
 | 
			
		||||
        const int64_t   int64 = 12345678900000LL;
 | 
			
		||||
        insert.bind("@int", uint32);
 | 
			
		||||
        insert.bind("@long", int64);
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE(query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ(4, query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_EQ(4294967295U, query.getColumn(2).getUInt());
 | 
			
		||||
        EXPECT_EQ(12345678900000LL, query.getColumn(4).getInt64());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, bindNoCopyByName)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, txt1 TEXT, txt2 TEXT, binary BLOB)"));
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Insertion with bindable parameters
 | 
			
		||||
    SQLite::Statement insert(db, "INSERT INTO test VALUES (NULL, @txt1, @txt2, @blob)");
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query to check the results
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(4, query.getColumnCount());
 | 
			
		||||
 | 
			
		||||
    // Insert one row with all variants of bindNoCopy()
 | 
			
		||||
    {
 | 
			
		||||
        const char*         txt1 = "first";
 | 
			
		||||
        const std::string   txt2 = "sec\0nd";
 | 
			
		||||
        const char          blob[] = { 'b','l','\0','b' };
 | 
			
		||||
        insert.bindNoCopy("@txt1", txt1);
 | 
			
		||||
        insert.bindNoCopy("@txt2", txt2);
 | 
			
		||||
        insert.bindNoCopy("@blob", blob, sizeof(blob));
 | 
			
		||||
        EXPECT_EQ(1, insert.exec());
 | 
			
		||||
        EXPECT_EQ(SQLITE_DONE, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Check the result
 | 
			
		||||
        query.executeStep();
 | 
			
		||||
        EXPECT_TRUE(query.hasRow());
 | 
			
		||||
        EXPECT_FALSE(query.isDone());
 | 
			
		||||
        EXPECT_EQ(1, query.getColumn(0).getInt64());
 | 
			
		||||
        EXPECT_STREQ(txt1, query.getColumn(1).getText());
 | 
			
		||||
        EXPECT_EQ(0, memcmp(&txt2[0], &query.getColumn(2).getString()[0], txt2.size()));
 | 
			
		||||
        EXPECT_EQ(0, memcmp(blob, &query.getColumn(3).getString()[0], sizeof(blob)));
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, isColumnNull)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    ASSERT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (msg TEXT, int INTEGER, double REAL)"));
 | 
			
		||||
    ASSERT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a first row with no null values, then other rows with each time a NULL value
 | 
			
		||||
    ASSERT_EQ(1, db.exec("INSERT INTO test VALUES (\"first\", 123,  0.123)"));
 | 
			
		||||
    ASSERT_EQ(1, db.exec("INSERT INTO test VALUES (NULL,      123,  0.123)"));
 | 
			
		||||
    ASSERT_EQ(1, db.exec("INSERT INTO test VALUES (\"first\", NULL, 0.123)"));
 | 
			
		||||
    ASSERT_EQ(1, db.exec("INSERT INTO test VALUES (\"first\", 123,  NULL)"));
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query
 | 
			
		||||
    const std::string select("SELECT * FROM test");
 | 
			
		||||
    SQLite::Statement query(db, select);
 | 
			
		||||
    EXPECT_EQ(select, query.getQuery());
 | 
			
		||||
    EXPECT_EQ(3, query.getColumnCount());
 | 
			
		||||
 | 
			
		||||
    // Get the first non-null row
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(-1), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(0));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(1));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(2));
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(3), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    // Get the second row with null text
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(-1), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(true, query.isColumnNull(0));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(1));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(2));
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(3), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    // Get the second row with null integer
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(-1), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(0));
 | 
			
		||||
    EXPECT_EQ(true, query.isColumnNull(1));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(2));
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(3), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    // Get the third row with null float
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(-1), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(0));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(1));
 | 
			
		||||
    EXPECT_EQ(true, query.isColumnNull(2));
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(3), SQLite::Exception);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, isColumnNullByName)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLITE_OPEN_READWRITE | SQLITE_OPEN_CREATE);
 | 
			
		||||
    ASSERT_EQ(SQLITE_OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (msg TEXT, int INTEGER, double REAL)"));
 | 
			
		||||
    ASSERT_EQ(SQLITE_OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a first row with no null values, then other rows with each time a NULL value
 | 
			
		||||
    ASSERT_EQ(1, db.exec("INSERT INTO test VALUES (\"first\", 123,  0.123)"));
 | 
			
		||||
    ASSERT_EQ(1, db.exec("INSERT INTO test VALUES (NULL,      123,  0.123)"));
 | 
			
		||||
    ASSERT_EQ(1, db.exec("INSERT INTO test VALUES (\"first\", NULL, 0.123)"));
 | 
			
		||||
    ASSERT_EQ(1, db.exec("INSERT INTO test VALUES (\"first\", 123,  NULL)"));
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query
 | 
			
		||||
    const std::string select("SELECT * FROM test");
 | 
			
		||||
    SQLite::Statement query(db, select);
 | 
			
		||||
    EXPECT_EQ(select, query.getQuery());
 | 
			
		||||
    EXPECT_EQ(3, query.getColumnCount());
 | 
			
		||||
 | 
			
		||||
    // Get the first non-null row
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(""), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull("msg"));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull("int"));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull("double"));
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(3), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    // Get the second row with null text
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(""), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(true, query.isColumnNull("msg"));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull(1));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull("double"));
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(3), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    // Get the second row with null integer
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(""), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull("msg"));
 | 
			
		||||
    EXPECT_EQ(true, query.isColumnNull("int"));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull("double"));
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(3), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    // Get the third row with null float
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(""), SQLite::Exception);
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull("msg"));
 | 
			
		||||
    EXPECT_EQ(false, query.isColumnNull("int"));
 | 
			
		||||
    EXPECT_EQ(true, query.isColumnNull("double"));
 | 
			
		||||
    EXPECT_THROW(query.isColumnNull(3), SQLite::Exception);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, getColumnByName)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT, int INTEGER, double REAL)"));
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a first row
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\", 123, 0.123)"));
 | 
			
		||||
    EXPECT_EQ(1, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(1, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(4, query.getColumnCount());
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE (query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
 | 
			
		||||
    // Look for non-existing columns
 | 
			
		||||
    EXPECT_THROW(query.getColumn("unknown"), SQLite::Exception);
 | 
			
		||||
    EXPECT_THROW(query.getColumn(""), SQLite::Exception);
 | 
			
		||||
 | 
			
		||||
    const std::string   msg     = query.getColumn("msg");
 | 
			
		||||
    const int           integer = query.getColumn("int");
 | 
			
		||||
    const double        real    = query.getColumn("double");
 | 
			
		||||
    EXPECT_EQ("first",  msg);
 | 
			
		||||
    EXPECT_EQ(123,      integer);
 | 
			
		||||
    EXPECT_EQ(0.123,    real);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
TEST(Statement, getName)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT)"));
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query, using the "id" column name as-is, but aliasing the "msg" column with new name "value"
 | 
			
		||||
    SQLite::Statement query(db, "SELECT id, msg as value FROM test");
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
 | 
			
		||||
    const std::string name0 = query.getColumnName(0);
 | 
			
		||||
    const std::string name1 = query.getColumnName(1);
 | 
			
		||||
    EXPECT_EQ("id", name0);
 | 
			
		||||
    EXPECT_EQ("value", name1);
 | 
			
		||||
 | 
			
		||||
#ifdef SQLITE_ENABLE_COLUMN_METADATA
 | 
			
		||||
    // Show how to get origin names of the table columns from which theses result columns come from.
 | 
			
		||||
    // Requires the SQLITE_ENABLE_COLUMN_METADATA preprocessor macro to be
 | 
			
		||||
    // also defined at compile times of the SQLite library itself.
 | 
			
		||||
    const std::string oname0 = query.getColumnOriginName(0);
 | 
			
		||||
    const std::string oname1 = query.getColumnOriginName(1);
 | 
			
		||||
    EXPECT_EQ("id", oname0);
 | 
			
		||||
    EXPECT_EQ("msg", oname1);
 | 
			
		||||
#endif
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#if __cplusplus >= 201402L || (defined(_MSC_VER) && _MSC_VER >= 1900)
 | 
			
		||||
TEST(Statement, getColumns)
 | 
			
		||||
{
 | 
			
		||||
    struct GetRowTestStruct
 | 
			
		||||
    {
 | 
			
		||||
        int id;
 | 
			
		||||
        std::string msg;
 | 
			
		||||
        int integer;
 | 
			
		||||
        double real;
 | 
			
		||||
        GetRowTestStruct(int _id, std::string _msg, int _integer, double _real)
 | 
			
		||||
        : id(_id), msg(_msg), integer(_integer), real(_real)
 | 
			
		||||
        {}
 | 
			
		||||
 | 
			
		||||
        GetRowTestStruct(int _id, const std::string& _msg)
 | 
			
		||||
        : id(_id), msg(_msg), integer(-1), real(0.0)
 | 
			
		||||
        {}
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE | SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a new table
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT, int INTEGER, double REAL)"));
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    // Create a first row
 | 
			
		||||
    EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\", 123, 0.123)"));
 | 
			
		||||
    EXPECT_EQ(1, db.getLastInsertRowid());
 | 
			
		||||
    EXPECT_EQ(1, db.getTotalChanges());
 | 
			
		||||
 | 
			
		||||
    // Compile a SQL query
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    EXPECT_STREQ("SELECT * FROM test", query.getQuery().c_str());
 | 
			
		||||
    EXPECT_EQ(4, query.getColumnCount());
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_TRUE(query.hasRow());
 | 
			
		||||
    EXPECT_FALSE(query.isDone());
 | 
			
		||||
 | 
			
		||||
    // Get all columns
 | 
			
		||||
    auto testStruct = query.getColumns<GetRowTestStruct, 4>();
 | 
			
		||||
    EXPECT_EQ(1, testStruct.id);
 | 
			
		||||
    EXPECT_EQ("first", testStruct.msg);
 | 
			
		||||
    EXPECT_EQ(123, testStruct.integer);
 | 
			
		||||
    EXPECT_EQ(0.123, testStruct.real);
 | 
			
		||||
 | 
			
		||||
    // Get only the first 2 columns
 | 
			
		||||
    auto testStruct2 = query.getColumns<GetRowTestStruct, 2>();
 | 
			
		||||
    EXPECT_EQ(1, testStruct2.id);
 | 
			
		||||
    EXPECT_EQ("first", testStruct2.msg);
 | 
			
		||||
    EXPECT_EQ(-1, testStruct2.integer);
 | 
			
		||||
    EXPECT_EQ(0.0, testStruct2.real);
 | 
			
		||||
}
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
#if (LONG_MAX > INT_MAX) // sizeof(long)==8 means the data model of the system is LP64 (64bits Linux)
 | 
			
		||||
TEST(Statement, bind64bitsLong)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getExtendedErrorCode());
 | 
			
		||||
 | 
			
		||||
    SQLite::Statement query(db, "SELECT ?");
 | 
			
		||||
    query.bind(1, 4294967297L);
 | 
			
		||||
    query.executeStep();
 | 
			
		||||
    EXPECT_EQ(4294967297L, query.getColumn(0).getInt64());
 | 
			
		||||
}
 | 
			
		||||
#endif
 | 
			
		||||
 | 
			
		||||
TEST(Statement, getBindParameterCount)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE | SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, msg TEXT)"));
 | 
			
		||||
 | 
			
		||||
    SQLite::Statement query(db, "SELECT id, msg FROM test where id = ?");
 | 
			
		||||
    EXPECT_EQ(1, query.getBindParameterCount());
 | 
			
		||||
 | 
			
		||||
    SQLite::Statement query2(db, "SELECT id, msg FROM test where id = ? and msg = ?");
 | 
			
		||||
    EXPECT_EQ(2, query2.getBindParameterCount());
 | 
			
		||||
 | 
			
		||||
    SQLite::Statement query3(db, "SELECT id, msg FROM test");
 | 
			
		||||
    EXPECT_EQ(0, query3.getBindParameterCount());
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										104
									
								
								thirdparty/SQLiteCpp/tests/Transaction_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										104
									
								
								thirdparty/SQLiteCpp/tests/Transaction_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@@ -0,0 +1,104 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @file    Transaction_test.cpp
 | 
			
		||||
 * @ingroup tests
 | 
			
		||||
 * @brief   Test of a SQLite Transaction.
 | 
			
		||||
 *
 | 
			
		||||
 * Copyright (c) 2012-2019 Sebastien Rombauts (sebastien.rombauts@gmail.com)
 | 
			
		||||
 *
 | 
			
		||||
 * Distributed under the MIT License (MIT) (See accompanying file LICENSE.txt
 | 
			
		||||
 * or copy at http://opensource.org/licenses/MIT)
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include <SQLiteCpp/Transaction.h>
 | 
			
		||||
#include <SQLiteCpp/Database.h>
 | 
			
		||||
#include <SQLiteCpp/Statement.h>
 | 
			
		||||
#include <SQLiteCpp/Exception.h>
 | 
			
		||||
 | 
			
		||||
#include <gtest/gtest.h>
 | 
			
		||||
 | 
			
		||||
#include <cstdio>
 | 
			
		||||
 | 
			
		||||
TEST(Transaction, commitRollback)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
    EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
        // Begin transaction
 | 
			
		||||
        SQLite::Transaction transaction(db);
 | 
			
		||||
 | 
			
		||||
        EXPECT_EQ(0, db.exec("CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT)"));
 | 
			
		||||
        EXPECT_EQ(SQLite::OK, db.getErrorCode());
 | 
			
		||||
 | 
			
		||||
        // Insert a first value
 | 
			
		||||
        EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"first\")"));
 | 
			
		||||
        EXPECT_EQ(1, db.getLastInsertRowid());
 | 
			
		||||
 | 
			
		||||
        // Commit transaction
 | 
			
		||||
        transaction.commit();
 | 
			
		||||
 | 
			
		||||
        // Commit again throw an exception
 | 
			
		||||
        EXPECT_THROW(transaction.commit(), SQLite::Exception);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Auto rollback if no commit() before the end of scope
 | 
			
		||||
    {
 | 
			
		||||
        // Begin transaction
 | 
			
		||||
        SQLite::Transaction transaction(db);
 | 
			
		||||
 | 
			
		||||
        // Insert a second value (that will be rollbacked)
 | 
			
		||||
        EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"third\")"));
 | 
			
		||||
        EXPECT_EQ(2, db.getLastInsertRowid());
 | 
			
		||||
 | 
			
		||||
        // end of scope: automatic rollback
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Auto rollback of a transaction on error/exception
 | 
			
		||||
    try
 | 
			
		||||
    {
 | 
			
		||||
        // Begin transaction
 | 
			
		||||
        SQLite::Transaction transaction(db);
 | 
			
		||||
 | 
			
		||||
        // Insert a second value (that will be rollbacked)
 | 
			
		||||
        EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"second\")"));
 | 
			
		||||
        EXPECT_EQ(2, db.getLastInsertRowid());
 | 
			
		||||
 | 
			
		||||
        // Execute with an error => exception with auto-rollback
 | 
			
		||||
        db.exec("DesiredSyntaxError to raise an exception to rollback the transaction");
 | 
			
		||||
 | 
			
		||||
        GTEST_FATAL_FAILURE_("we should never get there");
 | 
			
		||||
        transaction.commit(); // We should never get there
 | 
			
		||||
    }
 | 
			
		||||
    catch (std::exception& e)
 | 
			
		||||
    {
 | 
			
		||||
        std::cout << "SQLite exception: " << e.what() << std::endl;
 | 
			
		||||
        // expected error, see above
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Double rollback with a manual command before the end of scope
 | 
			
		||||
    {
 | 
			
		||||
        // Begin transaction
 | 
			
		||||
        SQLite::Transaction transaction(db);
 | 
			
		||||
 | 
			
		||||
        // Insert a second value (that will be rollbacked)
 | 
			
		||||
        EXPECT_EQ(1, db.exec("INSERT INTO test VALUES (NULL, \"third\")"));
 | 
			
		||||
        EXPECT_EQ(2, db.getLastInsertRowid());
 | 
			
		||||
 | 
			
		||||
        // Execute a manual rollback (no real use case I can think of, so no rollback() method)
 | 
			
		||||
        db.exec("ROLLBACK");
 | 
			
		||||
 | 
			
		||||
        // end of scope: the automatic rollback should not raise an error because it is harmless
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Check the results (expect only one row of result, as all other one have been rollbacked)
 | 
			
		||||
    SQLite::Statement query(db, "SELECT * FROM test");
 | 
			
		||||
    int nbRows = 0;
 | 
			
		||||
    while (query.executeStep())
 | 
			
		||||
    {
 | 
			
		||||
        nbRows++;
 | 
			
		||||
        EXPECT_EQ(1, query.getColumn(0).getInt());
 | 
			
		||||
        EXPECT_STREQ("first", query.getColumn(1).getText());
 | 
			
		||||
    }
 | 
			
		||||
    EXPECT_EQ(1, nbRows);
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										109
									
								
								thirdparty/SQLiteCpp/tests/VariadicBind_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										109
									
								
								thirdparty/SQLiteCpp/tests/VariadicBind_test.cpp
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@@ -0,0 +1,109 @@
 | 
			
		||||
/**
 | 
			
		||||
 * @file    VariadicBind_test.cpp
 | 
			
		||||
 * @ingroup tests
 | 
			
		||||
 * @brief   Test of variadic bind
 | 
			
		||||
 *
 | 
			
		||||
 * Copyright (c) 2016 Paul Dreik (github@pauldreik.se)
 | 
			
		||||
 * Copyright (c) 2016-2019 Sebastien Rombauts (sebastien.rombauts@gmail.com)
 | 
			
		||||
 * Copyright (c) 2019 Maximilian Bachmann (github@maxbachmann)
 | 
			
		||||
 *
 | 
			
		||||
 * Distributed under the MIT License (MIT) (See accompanying file LICENSE.txt
 | 
			
		||||
 * or copy at http://opensource.org/licenses/MIT)
 | 
			
		||||
 */
 | 
			
		||||
 | 
			
		||||
#include <SQLiteCpp/Database.h>
 | 
			
		||||
#include <SQLiteCpp/Statement.h>
 | 
			
		||||
#include <SQLiteCpp/VariadicBind.h>
 | 
			
		||||
 | 
			
		||||
#include <gtest/gtest.h>
 | 
			
		||||
 | 
			
		||||
#include <cstdio>
 | 
			
		||||
 | 
			
		||||
#if (__cplusplus >= 201103L) || ( defined(_MSC_VER) && (_MSC_VER >= 1800) ) // c++11: Visual Studio 2013
 | 
			
		||||
TEST(VariadicBind, invalid)
 | 
			
		||||
{
 | 
			
		||||
    // Create a new database
 | 
			
		||||
    SQLite::Database db(":memory:", SQLite::OPEN_READWRITE|SQLite::OPEN_CREATE);
 | 
			
		||||
 | 
			
		||||
    EXPECT_EQ(0, db.exec("DROP TABLE IF EXISTS test"));
 | 
			
		||||
    EXPECT_EQ(0,
 | 
			
		||||
            db.exec(
 | 
			
		||||
                    "CREATE TABLE test (id INTEGER PRIMARY KEY, value TEXT DEFAULT 'default') "));
 | 
			
		||||
    EXPECT_EQ(0,
 | 
			
		||||
            db.exec(
 | 
			
		||||
                    "CREATE TABLE test2 (id INTEGER PRIMARY KEY, value TEXT DEFAULT 'default') "));
 | 
			
		||||
    EXPECT_TRUE(db.tableExists("test"));
 | 
			
		||||
    EXPECT_TRUE(db.tableExists("test2"));
 | 
			
		||||
 | 
			
		||||
    {
 | 
			
		||||
        SQLite::Statement query(db, "INSERT INTO test VALUES (?, ?)");
 | 
			
		||||
 | 
			
		||||
        // bind one argument less than expected - should be fine.
 | 
			
		||||
        // the unspecified argument should be set to null, not the default.
 | 
			
		||||
        SQLite::bind(query, 1);
 | 
			
		||||
        EXPECT_EQ(1, query.exec());
 | 
			
		||||
        query.reset();
 | 
			
		||||
 | 
			
		||||
        // bind all arguments - should work just fine
 | 
			
		||||
        SQLite::bind(query, 2, "two");
 | 
			
		||||
        EXPECT_EQ(1, query.exec());
 | 
			
		||||
        query.reset();
 | 
			
		||||
 | 
			
		||||
        // bind too many arguments - should throw.
 | 
			
		||||
        EXPECT_THROW(SQLite::bind(query, 3, "three", 0), SQLite::Exception);
 | 
			
		||||
        EXPECT_EQ(1, query.exec());
 | 
			
		||||
    }
 | 
			
		||||
    // make sure the content is as expected
 | 
			
		||||
    {
 | 
			
		||||
        SQLite::Statement query(db, std::string{"SELECT id, value FROM test ORDER BY id"});
 | 
			
		||||
        std::vector<std::pair<int, std::string> > results;
 | 
			
		||||
        while (query.executeStep())
 | 
			
		||||
        {
 | 
			
		||||
            const int id = query.getColumn(0);
 | 
			
		||||
            std::string value = query.getColumn(1);
 | 
			
		||||
            results.emplace_back( id, std::move(value) );
 | 
			
		||||
        }
 | 
			
		||||
        EXPECT_EQ(std::size_t(3), results.size());
 | 
			
		||||
 | 
			
		||||
        EXPECT_EQ(std::make_pair(1,std::string{""}), results.at(0));
 | 
			
		||||
        EXPECT_EQ(std::make_pair(2,std::string{"two"}), results.at(1));
 | 
			
		||||
        EXPECT_EQ(std::make_pair(3,std::string{"three"}), results.at(2));
 | 
			
		||||
    }
 | 
			
		||||
    #if (__cplusplus >= 201402L) || ( defined(_MSC_VER) && (_MSC_VER >= 1900) ) // c++14: Visual Studio 2015
 | 
			
		||||
    {
 | 
			
		||||
        SQLite::Statement query(db, "INSERT INTO test2 VALUES (?, ?)");
 | 
			
		||||
 | 
			
		||||
        // bind one argument less than expected - should be fine.
 | 
			
		||||
        // the unspecified argument should be set to null, not the default.
 | 
			
		||||
        SQLite::bind(query, std::make_tuple(1));
 | 
			
		||||
        EXPECT_EQ(1, query.exec());
 | 
			
		||||
        query.reset();
 | 
			
		||||
 | 
			
		||||
        // bind all arguments - should work just fine
 | 
			
		||||
        SQLite::bind(query, std::make_tuple(2, "two"));
 | 
			
		||||
        EXPECT_EQ(1, query.exec());
 | 
			
		||||
        query.reset();
 | 
			
		||||
 | 
			
		||||
        // bind too many arguments - should throw.
 | 
			
		||||
        EXPECT_THROW(SQLite::bind(query, std::make_tuple(3, "three", 0)), SQLite::Exception);
 | 
			
		||||
        EXPECT_EQ(1, query.exec());
 | 
			
		||||
    }
 | 
			
		||||
    // make sure the content is as expected
 | 
			
		||||
    {
 | 
			
		||||
        SQLite::Statement query(db, std::string{"SELECT id, value FROM test2 ORDER BY id"});
 | 
			
		||||
        std::vector<std::pair<int, std::string> > results;
 | 
			
		||||
        while (query.executeStep())
 | 
			
		||||
        {
 | 
			
		||||
            const int id = query.getColumn(0);
 | 
			
		||||
            std::string value = query.getColumn(1);
 | 
			
		||||
            results.emplace_back( id, std::move(value) );
 | 
			
		||||
        }
 | 
			
		||||
        EXPECT_EQ(std::size_t(3), results.size());
 | 
			
		||||
 | 
			
		||||
        EXPECT_EQ(std::make_pair(1,std::string{""}), results.at(0));
 | 
			
		||||
        EXPECT_EQ(std::make_pair(2,std::string{"two"}), results.at(1));
 | 
			
		||||
        EXPECT_EQ(std::make_pair(3,std::string{"three"}), results.at(2));
 | 
			
		||||
    }
 | 
			
		||||
    #endif // c++14
 | 
			
		||||
}
 | 
			
		||||
#endif // c++11
 | 
			
		||||
		Reference in New Issue
	
	Block a user