diff options
Diffstat (limited to 'tests/unit/unittest/sqlitestatement-test.cpp')
-rw-r--r-- | tests/unit/unittest/sqlitestatement-test.cpp | 388 |
1 files changed, 283 insertions, 105 deletions
diff --git a/tests/unit/unittest/sqlitestatement-test.cpp b/tests/unit/unittest/sqlitestatement-test.cpp index cb8206d875..cc264bf90f 100644 --- a/tests/unit/unittest/sqlitestatement-test.cpp +++ b/tests/unit/unittest/sqlitestatement-test.cpp @@ -38,13 +38,22 @@ #include <vector> +namespace Sqlite { +bool operator==(Utils::span<const byte> first, Utils::span<const byte> second) +{ + return first.size() == second.size() + && std::memcmp(first.data(), second.data(), first.size()) == 0; +} +} // namespace Sqlite + namespace { -using Sqlite::JournalMode; -using Sqlite::Exception; using Sqlite::Database; +using Sqlite::Exception; +using Sqlite::JournalMode; using Sqlite::ReadStatement; using Sqlite::ReadWriteStatement; +using Sqlite::Value; using Sqlite::WriteStatement; MATCHER_P3(HasValues, value1, value2, rowid, @@ -65,11 +74,33 @@ MATCHER_P3(HasValues, value1, value2, rowid, && statement.fetchSmallStringViewValue(1) == value2; } +MATCHER_P(HasNullValues, rowid, std::string(negation ? "isn't null" : "is null")) +{ + Database &database = arg.database(); + + SqliteTestStatement statement("SELECT name, number FROM test WHERE rowid=?", database); + statement.bind(1, rowid); + + statement.next(); + + return statement.fetchValueView(0).isNull() && statement.fetchValueView(1).isNull(); +} + class SqliteStatement : public ::testing::Test { protected: - void SetUp() override; - void TearDown() override; + void SetUp() override + { + database.execute("CREATE TABLE test(name TEXT UNIQUE, number NUMERIC, value NUMERIC)"); + database.execute("INSERT INTO test VALUES ('bar', 'blah', 1)"); + database.execute("INSERT INTO test VALUES ('foo', 23.3, 2)"); + database.execute("INSERT INTO test VALUES ('poo', 40, 3)"); + } + void TearDown() override + { + if (database.isOpen()) + database.close(); + } protected: Database database{":memory:", Sqlite::JournalMode::Memory}; @@ -125,7 +156,7 @@ TEST_F(SqliteStatement, CountRows) TEST_F(SqliteStatement, Value) { - SqliteTestStatement statement("SELECT name, number FROM test ORDER BY name", database); + SqliteTestStatement statement("SELECT name, number, value FROM test ORDER BY name", database); statement.next(); statement.next(); @@ -142,47 +173,19 @@ TEST_F(SqliteStatement, Value) ASSERT_THAT(statement.fetchValue<Utils::SmallString>(1), "23.3"); ASSERT_THAT(statement.fetchValue<Utils::PathString>(1), "23.3"); ASSERT_THAT(statement.fetchSmallStringViewValue(1), "23.3"); + ASSERT_THAT(statement.fetchValueView(0), Eq("foo")); + ASSERT_THAT(statement.fetchValueView(1), Eq(23.3)); + ASSERT_THAT(statement.fetchValueView(2), Eq(2)); } -TEST_F(SqliteStatement, ThrowNoValuesToFetchForNotSteppedStatement) -{ - SqliteTestStatement statement("SELECT name, number FROM test", database); - - ASSERT_THROW(statement.fetchValue<int>(0), Sqlite::NoValuesToFetch); -} - -TEST_F(SqliteStatement, ThrowNoValuesToFetchForDoneStatement) -{ - SqliteTestStatement statement("SELECT name, number FROM test", database); - while (statement.next()) {} - - ASSERT_THROW(statement.fetchValue<int>(0), Sqlite::NoValuesToFetch); -} - -TEST_F(SqliteStatement, ThrowInvalidColumnFetchedForNegativeColumn) -{ - SqliteTestStatement statement("SELECT name, number FROM test", database); - statement.next(); - - ASSERT_THROW(statement.fetchValue<int>(-1), Sqlite::InvalidColumnFetched); -} - -TEST_F(SqliteStatement, ThrowInvalidColumnFetchedForNotExistingColumn) -{ - SqliteTestStatement statement("SELECT name, number FROM test", database); - statement.next(); - - ASSERT_THROW(statement.fetchValue<int>(2), Sqlite::InvalidColumnFetched); -} - -TEST_F(SqliteStatement, ToIntergerValue) +TEST_F(SqliteStatement, ToIntegerValue) { auto value = ReadStatement::toValue<int>("SELECT number FROM test WHERE name='foo'", database); ASSERT_THAT(value, 23); } -TEST_F(SqliteStatement, ToLongIntergerValue) +TEST_F(SqliteStatement, ToLongIntegerValue) { ASSERT_THAT(ReadStatement::toValue<qint64>("SELECT number FROM test WHERE name='foo'", database), Eq(23)); } @@ -197,13 +200,16 @@ TEST_F(SqliteStatement, ToStringValue) ASSERT_THAT(ReadStatement::toValue<Utils::SmallString>("SELECT name FROM test WHERE name='foo'", database), "foo"); } -TEST_F(SqliteStatement, ColumnNames) +TEST_F(SqliteStatement, BindNull) { - SqliteTestStatement statement("SELECT name, number FROM test", database); + database.execute("INSERT INTO test VALUES (NULL, 323, 344)"); + SqliteTestStatement statement("SELECT name, number FROM test WHERE name IS ?", database); - auto columnNames = statement.columnNames(); + statement.bind(1, Sqlite::NullValue{}); + statement.next(); - ASSERT_THAT(columnNames, ElementsAre("name", "number")); + ASSERT_TRUE(statement.fetchValueView(0).isNull()); + ASSERT_THAT(statement.fetchValue<int>(1), 323); } TEST_F(SqliteStatement, BindString) @@ -212,7 +218,6 @@ TEST_F(SqliteStatement, BindString) SqliteTestStatement statement("SELECT name, number FROM test WHERE name=?", database); statement.bind(1, "foo"); - statement.next(); ASSERT_THAT(statement.fetchSmallStringViewValue(0), "foo"); @@ -249,55 +254,96 @@ TEST_F(SqliteStatement, BindDouble) ASSERT_THAT(statement.fetchSmallStringViewValue(0), "foo"); } -TEST_F(SqliteStatement, BindIntegerByParameter) +TEST_F(SqliteStatement, BindPointer) { - SqliteTestStatement statement("SELECT name, number FROM test WHERE number=@number", database); + SqliteTestStatement statement("SELECT value FROM carray(?, 5, 'int64')", database); + std::vector<long long> values{1, 1, 2, 3, 5}; - statement.bind("@number", 40); + statement.bind(1, values.data()); statement.next(); - ASSERT_THAT(statement.fetchSmallStringViewValue(0), "poo"); + ASSERT_THAT(statement.fetchIntValue(0), 1); } -TEST_F(SqliteStatement, BindLongIntegerByParameter) +TEST_F(SqliteStatement, BindBlob) { - SqliteTestStatement statement("SELECT name, number FROM test WHERE number=@number", database); + SqliteTestStatement statement("WITH T(blob) AS (VALUES (?)) SELECT blob FROM T", database); + const unsigned char chars[] = "aaafdfdlll"; + auto bytePointer = reinterpret_cast<const Sqlite::byte *>(chars); + Utils::span<const Sqlite::byte> bytes{bytePointer, sizeof(chars) - 1}; - statement.bind("@number", int64_t(40)); + statement.bind(1, bytes); statement.next(); - ASSERT_THAT(statement.fetchSmallStringViewValue(0), "poo"); + ASSERT_THAT(statement.fetchBlobValue(0), Eq(bytes)); } -TEST_F(SqliteStatement, BindDoubleByIndex) +TEST_F(SqliteStatement, BindEmptyBlob) { - SqliteTestStatement statement("SELECT name, number FROM test WHERE number=@number", database); + SqliteTestStatement statement("WITH T(blob) AS (VALUES (?)) SELECT blob FROM T", database); + Utils::span<const Sqlite::byte> bytes; - statement.bind(statement.bindingIndexForName("@number"), 23.3); + statement.bind(1, bytes); statement.next(); - ASSERT_THAT(statement.fetchSmallStringViewValue(0), "foo"); + ASSERT_THAT(statement.fetchBlobValue(0), IsEmpty()); } -TEST_F(SqliteStatement, BindIndexIsZeroIsThrowingBindingIndexIsOutOfBound) +TEST_F(SqliteStatement, BindIndexIsZeroIsThrowingBindingIndexIsOutOfBoundInt) { SqliteTestStatement statement("SELECT name, number FROM test WHERE number=$1", database); ASSERT_THROW(statement.bind(0, 40), Sqlite::BindingIndexIsOutOfRange); } -TEST_F(SqliteStatement, BindIndexIsTpLargeIsThrowingBindingIndexIsOutOfBound) +TEST_F(SqliteStatement, BindIndexIsZeroIsThrowingBindingIndexIsOutOfBoundNull) +{ + SqliteTestStatement statement("SELECT name, number FROM test WHERE number=$1", database); + + ASSERT_THROW(statement.bind(0, Sqlite::NullValue{}), Sqlite::BindingIndexIsOutOfRange); +} + +TEST_F(SqliteStatement, BindIndexIsToLargeIsThrowingBindingIndexIsOutOfBoundLongLong) +{ + SqliteTestStatement statement("SELECT name, number FROM test WHERE number=$1", database); + + ASSERT_THROW(statement.bind(2, 40LL), Sqlite::BindingIndexIsOutOfRange); +} + +TEST_F(SqliteStatement, BindIndexIsToLargeIsThrowingBindingIndexIsOutOfBoundStringView) +{ + SqliteTestStatement statement("SELECT name, number FROM test WHERE number=$1", database); + + ASSERT_THROW(statement.bind(2, "foo"), Sqlite::BindingIndexIsOutOfRange); +} + +TEST_F(SqliteStatement, BindIndexIsToLargeIsThrowingBindingIndexIsOutOfBoundStringFloat) +{ + SqliteTestStatement statement("SELECT name, number FROM test WHERE number=$1", database); + + ASSERT_THROW(statement.bind(2, 2.), Sqlite::BindingIndexIsOutOfRange); +} + +TEST_F(SqliteStatement, BindIndexIsToLargeIsThrowingBindingIndexIsOutOfBoundPointer) +{ + SqliteTestStatement statement("SELECT name, number FROM test WHERE number=$1", database); + + ASSERT_THROW(statement.bind(2, nullptr), Sqlite::BindingIndexIsOutOfRange); +} + +TEST_F(SqliteStatement, BindIndexIsToLargeIsThrowingBindingIndexIsOutOfBoundValue) { SqliteTestStatement statement("SELECT name, number FROM test WHERE number=$1", database); - ASSERT_THROW(statement.bind(2, 40), Sqlite::BindingIndexIsOutOfRange); + ASSERT_THROW(statement.bind(2, Sqlite::Value{1}), Sqlite::BindingIndexIsOutOfRange); } -TEST_F(SqliteStatement, WrongBindingNameThrowingBindingIndexIsOutOfBound) +TEST_F(SqliteStatement, BindIndexIsToLargeIsThrowingBindingIndexIsOutOfBoundBlob) { - SqliteTestStatement statement("SELECT name, number FROM test WHERE number=@name", database); + SqliteTestStatement statement("WITH T(blob) AS (VALUES (?)) SELECT blob FROM T", database); + Utils::span<const Sqlite::byte> bytes; - ASSERT_THROW(statement.bind("@name2", 40), Sqlite::WrongBindingName); + ASSERT_THROW(statement.bind(2, bytes), Sqlite::BindingIndexIsOutOfRange); } TEST_F(SqliteStatement, BindValues) @@ -310,6 +356,16 @@ TEST_F(SqliteStatement, BindValues) ASSERT_THAT(statement, HasValues("see", "7.23", 1)); } +TEST_F(SqliteStatement, BindNullValues) +{ + SqliteTestStatement statement("UPDATE test SET name=?, number=? WHERE rowid=?", database); + + statement.bindValues(Sqlite::NullValue{}, Sqlite::Value{}, 1); + statement.execute(); + + ASSERT_THAT(statement, HasNullValues(1)); +} + TEST_F(SqliteStatement, WriteValues) { WriteStatement statement("UPDATE test SET name=?, number=? WHERE rowid=?", database); @@ -319,25 +375,69 @@ TEST_F(SqliteStatement, WriteValues) ASSERT_THAT(statement, HasValues("see", "7.23", 1)); } -TEST_F(SqliteStatement, BindNamedValues) +TEST_F(SqliteStatement, WritePointerValues) { - SqliteTestStatement statement("UPDATE test SET name=@name, number=@number WHERE rowid=@id", database); + SqliteTestStatement statement("SELECT value FROM carray(?, ?, 'int64')", database); + std::vector<long long> values{1, 1, 2, 3, 5}; - statement.bindNameValues("@name", "see", "@number", 7.23, "@id", 1); - statement.execute(); + statement.write(values.data(), int(values.size())); - ASSERT_THAT(statement, HasValues("see", "7.23", 1)); + ASSERT_THAT(statement.template values<int>(5), ElementsAre(1, 1, 2, 3, 5)); } -TEST_F(SqliteStatement, WriteNamedValues) +TEST_F(SqliteStatement, WriteNullValues) { - WriteStatement statement("UPDATE test SET name=@name, number=@number WHERE rowid=@id", database); + WriteStatement statement("UPDATE test SET name=?, number=? WHERE rowid=?", database); + statement.write(1, 1, 1); - statement.writeNamed("@name", "see", "@number", 7.23, "@id", 1); + statement.write(Sqlite::NullValue{}, Sqlite::Value{}, 1); + + ASSERT_THAT(statement, HasNullValues(1)); +} + +TEST_F(SqliteStatement, WriteSqliteValues) +{ + WriteStatement statement("UPDATE test SET name=?, number=? WHERE rowid=?", database); + + statement.write(Value{"see"}, Value{7.23}, Value{1}); ASSERT_THAT(statement, HasValues("see", "7.23", 1)); } +TEST_F(SqliteStatement, WriteEmptyBlobs) +{ + SqliteTestStatement statement("WITH T(blob) AS (VALUES (?)) SELECT blob FROM T", database); + + Utils::span<const Sqlite::byte> bytes; + + statement.write(bytes); + + ASSERT_THAT(statement.fetchBlobValue(0), IsEmpty()); +} + +class Blob +{ +public: + Blob(Utils::span<const Sqlite::byte> bytes) + : bytes(bytes.begin(), bytes.end()) + {} + + std::vector<Sqlite::byte> bytes; +}; + +TEST_F(SqliteStatement, WriteBlobs) +{ + SqliteTestStatement statement("INSERT INTO test VALUES ('blob', 40, ?)", database); + SqliteTestStatement readStatement("SELECT value FROM test WHERE name = 'blob'", database); + const unsigned char chars[] = "aaafdfdlll"; + auto bytePointer = reinterpret_cast<const Sqlite::byte *>(chars); + Utils::span<const Sqlite::byte> bytes{bytePointer, sizeof(chars) - 1}; + + statement.write(bytes); + + ASSERT_THAT(readStatement.template value<Blob>(), Optional(Field(&Blob::bytes, Eq(bytes)))); +} + TEST_F(SqliteStatement, CannotWriteToClosedDatabase) { database.close(); @@ -361,9 +461,8 @@ TEST_F(SqliteStatement, GetTupleValuesWithoutArguments) auto values = statement.values<Tuple, 3>(3); - ASSERT_THAT(values, ElementsAre(Tuple{"bar", 0, 1}, - Tuple{"foo", 23.3, 2}, - Tuple{"poo", 40.0, 3})); + ASSERT_THAT(values, + UnorderedElementsAre(Tuple{"bar", 0, 1}, Tuple{"foo", 23.3, 2}, Tuple{"poo", 40.0, 3})); } TEST_F(SqliteStatement, GetSingleValuesWithoutArguments) @@ -372,7 +471,33 @@ TEST_F(SqliteStatement, GetSingleValuesWithoutArguments) std::vector<Utils::SmallString> values = statement.values<Utils::SmallString>(3); - ASSERT_THAT(values, ElementsAre("bar", "foo", "poo")); + ASSERT_THAT(values, UnorderedElementsAre("bar", "foo", "poo")); +} + +class FooValue +{ +public: + FooValue(Sqlite::ValueView value) + : value(value) + {} + + Sqlite::Value value; + + template<typename Type> + friend bool operator==(const FooValue &value, const Type &other) + { + return value.value == other; + } +}; + +TEST_F(SqliteStatement, GetSingleSqliteValuesWithoutArguments) +{ + ReadStatement statement("SELECT number FROM test", database); + database.execute("INSERT INTO test VALUES (NULL, NULL, NULL)"); + + std::vector<FooValue> values = statement.values<FooValue>(3); + + ASSERT_THAT(values, UnorderedElementsAre(Eq("blah"), Eq(23.3), Eq(40), IsNull())); } TEST_F(SqliteStatement, GetStructValuesWithoutArguments) @@ -381,9 +506,10 @@ TEST_F(SqliteStatement, GetStructValuesWithoutArguments) auto values = statement.values<Output, 3>(3); - ASSERT_THAT(values, ElementsAre(Output{"bar", "blah", 1}, - Output{"foo", "23.3", 2}, - Output{"poo", "40", 3})); + ASSERT_THAT(values, + UnorderedElementsAre(Output{"bar", "blah", 1}, + Output{"foo", "23.3", 2}, + Output{"poo", "40", 3})); } TEST_F(SqliteStatement, GetValuesForSingleOutputWithBindingMultipleTimes) @@ -404,18 +530,17 @@ TEST_F(SqliteStatement, GetValuesForMultipleOutputValuesAndContainerQueryValues) auto values = statement.values<Tuple, 3>(3, queryValues); - ASSERT_THAT(values, ElementsAre(Tuple{"poo", 40, 3.}, - Tuple{"foo", 23.3, 2.})); + ASSERT_THAT(values, UnorderedElementsAre(Tuple{"poo", 40, 3.}, Tuple{"foo", 23.3, 2.})); } TEST_F(SqliteStatement, GetValuesForSingleOutputValuesAndContainerQueryValues) { std::vector<double> queryValues = {40, 23.3}; - ReadStatement statement("SELECT name, number FROM test WHERE number=?", database); + ReadStatement statement("SELECT name FROM test WHERE number=?", database); std::vector<Utils::SmallString> values = statement.values<Utils::SmallString>(3, queryValues); - ASSERT_THAT(values, ElementsAre("poo", "foo")); + ASSERT_THAT(values, UnorderedElementsAre("poo", "foo")); } TEST_F(SqliteStatement, GetValuesForMultipleOutputValuesAndContainerQueryTupleValues) @@ -427,19 +552,18 @@ TEST_F(SqliteStatement, GetValuesForMultipleOutputValuesAndContainerQueryTupleVa auto values = statement.values<ResultTuple, 3>(3, queryValues); - ASSERT_THAT(values, ElementsAre(ResultTuple{"poo", 40, 3}, - ResultTuple{"bar", 0, 1})); + ASSERT_THAT(values, UnorderedElementsAre(ResultTuple{"poo", 40, 3}, ResultTuple{"bar", 0, 1})); } TEST_F(SqliteStatement, GetValuesForSingleOutputValuesAndContainerQueryTupleValues) { using Tuple = std::tuple<Utils::SmallString, Utils::SmallString>; std::vector<Tuple> queryValues = {{"poo", "40"}, {"bar", "blah"}}; - ReadStatement statement("SELECT name, number FROM test WHERE name= ? AND number=?", database); + ReadStatement statement("SELECT name FROM test WHERE name= ? AND number=?", database); std::vector<Utils::SmallString> values = statement.values<Utils::SmallString>(3, queryValues); - ASSERT_THAT(values, ElementsAre("poo", "bar")); + ASSERT_THAT(values, UnorderedElementsAre("poo", "bar")); } TEST_F(SqliteStatement, GetValuesForMultipleOutputValuesAndMultipleQueryValue) @@ -491,8 +615,47 @@ TEST_F(SqliteStatement, GetStructOutputValuesAndContainerQueryTupleValues) auto values = statement.values<Output, 3>(3, queryValues); - ASSERT_THAT(values, ElementsAre(Output{"poo", "40", 3}, - Output{"bar", "blah", 1})); + ASSERT_THAT(values, UnorderedElementsAre(Output{"poo", "40", 3}, Output{"bar", "blah", 1})); +} + +TEST_F(SqliteStatement, GetBlobValues) +{ + database.execute("INSERT INTO test VALUES ('blob', 40, x'AABBCCDD')"); + ReadStatement statement("SELECT value FROM test WHERE name='blob'", database); + const int value = 0xDDCCBBAA; + auto bytePointer = reinterpret_cast<const Sqlite::byte *>(&value); + Utils::span<const Sqlite::byte> bytes{bytePointer, 4}; + + auto values = statement.values<Blob>(1); + + ASSERT_THAT(values, ElementsAre(Field(&Blob::bytes, Eq(bytes)))); +} + +TEST_F(SqliteStatement, GetEmptyBlobValueForInteger) +{ + ReadStatement statement("SELECT value FROM test WHERE name='poo'", database); + + auto value = statement.value<Blob>(); + + ASSERT_THAT(value, Optional(Field(&Blob::bytes, IsEmpty()))); +} + +TEST_F(SqliteStatement, GetEmptyBlobValueForFloat) +{ + ReadStatement statement("SELECT number FROM test WHERE name='foo'", database); + + auto value = statement.value<Blob>(); + + ASSERT_THAT(value, Optional(Field(&Blob::bytes, IsEmpty()))); +} + +TEST_F(SqliteStatement, GetEmptyBlobValueForText) +{ + ReadStatement statement("SELECT number FROM test WHERE name='bar'", database); + + auto value = statement.value<Blob>(); + + ASSERT_THAT(value, Optional(Field(&Blob::bytes, IsEmpty()))); } TEST_F(SqliteStatement, GetOptionalSingleValueAndMultipleQueryValue) @@ -650,41 +813,56 @@ TEST_F(SqliteStatement, ResetIfWriteIsThrowingException) ASSERT_ANY_THROW(mockStatement.write("bar")); } -TEST_F(SqliteStatement, ResetIfWriteNamedIsThrowingException) +TEST_F(SqliteStatement, ResetIfExecuteThrowsException) { MockSqliteStatement mockStatement; - EXPECT_CALL(mockStatement, bindingIndexForName(TypedEq<Utils::SmallStringView>("@foo"))) - .WillOnce(Return(1)); - EXPECT_CALL(mockStatement, bind(1, TypedEq<Utils::SmallStringView>("bar"))) - .WillOnce(Throw(Sqlite::StatementIsBusy(""))); + EXPECT_CALL(mockStatement, next()).WillOnce(Throw(Sqlite::StatementIsBusy(""))); EXPECT_CALL(mockStatement, reset()); - ASSERT_ANY_THROW(mockStatement.writeNamed("@foo", "bar")); + ASSERT_ANY_THROW(mockStatement.execute()); } -TEST_F(SqliteStatement, ResetIfExecuteThrowsException) +TEST_F(SqliteStatement, ThrowInvalidColumnFetchedForToManyArgumentsForValue) { - MockSqliteStatement mockStatement; + SqliteTestStatement statement("SELECT name, number FROM test", database); - EXPECT_CALL(mockStatement, next()).WillOnce(Throw(Sqlite::StatementIsBusy(""))); - EXPECT_CALL(mockStatement, reset()); + ASSERT_THROW(statement.value<int>(), Sqlite::ColumnCountDoesNotMatch); +} - ASSERT_ANY_THROW(mockStatement.execute()); +TEST_F(SqliteStatement, ThrowInvalidColumnFetchedForToManyArgumentsForValues) +{ + SqliteTestStatement statement("SELECT name, number FROM test", database); + + ASSERT_THROW(statement.values<int>(1), Sqlite::ColumnCountDoesNotMatch); +} + +TEST_F(SqliteStatement, ThrowInvalidColumnFetchedForToManyArgumentsForValuesWithArguments) +{ + SqliteTestStatement statement("SELECT name, number FROM test WHERE name=?", database); + + ASSERT_THROW(statement.values<int>(1, 2), Sqlite::ColumnCountDoesNotMatch); } -void SqliteStatement::SetUp() +TEST_F(SqliteStatement, ThrowInvalidColumnFetchedForToManyArgumentsForValuesWithVectorArguments) { - database.execute("CREATE TABLE test(name TEXT UNIQUE, number NUMERIC, value NUMERIC)"); - database.execute("INSERT INTO test VALUES ('bar', 'blah', 1)"); - database.execute("INSERT INTO test VALUES ('foo', 23.3, 2)"); - database.execute("INSERT INTO test VALUES ('poo', 40, 3)"); + SqliteTestStatement statement("SELECT name, number FROM test", database); + + ASSERT_THROW(statement.values<int>(1, std::vector<int>{}), Sqlite::ColumnCountDoesNotMatch); } -void SqliteStatement::TearDown() +TEST_F(SqliteStatement, ThrowInvalidColumnFetchedForToManyArgumentsForValuesWithTupleArguments) { - if (database.isOpen()) - database.close(); + SqliteTestStatement statement("SELECT name, number FROM test", database); + + ASSERT_THROW(statement.values<int>(1, std::vector<std::tuple<int>>{}), + Sqlite::ColumnCountDoesNotMatch); } +TEST_F(SqliteStatement, ThrowInvalidColumnFetchedForToManyArgumentsForToValues) +{ + ASSERT_THROW(SqliteTestStatement::toValue<int>("SELECT name, number FROM test", database), + Sqlite::ColumnCountDoesNotMatch); } + +} // namespace |