|
|
#include "sqliteInt.h" |
|
|
#include "unity.h" |
|
|
#include <stdlib.h> |
|
|
#include <string.h> |
|
|
|
|
|
static sqlite3 *gDb = NULL; |
|
|
|
|
|
static FuncDef* mustFindFunc(const char *zName, int nArg){ |
|
|
FuncDef *pDef = sqlite3FindFunction(gDb, zName, nArg, SQLITE_UTF8, 0); |
|
|
TEST_ASSERT_MESSAGE(pDef != NULL, "Expected function not found"); |
|
|
TEST_ASSERT_EQUAL_INT_MESSAGE(nArg, pDef->nArg, "Function arity mismatch"); |
|
|
return pDef; |
|
|
} |
|
|
|
|
|
void setUp(void) { |
|
|
int rc; |
|
|
|
|
|
sqlite3AlterFunctions(); |
|
|
rc = sqlite3_open(":memory:", &gDb); |
|
|
TEST_ASSERT_EQUAL_INT_MESSAGE(SQLITE_OK, rc, "sqlite3_open failed"); |
|
|
} |
|
|
|
|
|
void tearDown(void) { |
|
|
if( gDb ){ |
|
|
sqlite3_close(gDb); |
|
|
gDb = NULL; |
|
|
} |
|
|
} |
|
|
|
|
|
void test_sqlite3AlterFunctions_registers_all_expected_functions(void){ |
|
|
struct { |
|
|
const char *zName; |
|
|
int nArg; |
|
|
} aFuncs[] = { |
|
|
{ "sqlite_rename_column", 9 }, |
|
|
{ "sqlite_rename_table", 7 }, |
|
|
{ "sqlite_rename_test", 7 }, |
|
|
{ "sqlite_drop_column", 3 }, |
|
|
{ "sqlite_rename_quotefix", 2 }, |
|
|
{ "sqlite_drop_constraint", 2 }, |
|
|
{ "sqlite_fail", 2 }, |
|
|
{ "sqlite_add_constraint", 3 }, |
|
|
{ "sqlite_find_constraint", 2 }, |
|
|
}; |
|
|
for(size_t i=0; i<sizeof(aFuncs)/sizeof(aFuncs[0]); i++){ |
|
|
FuncDef *pDef = mustFindFunc(aFuncs[i].zName, aFuncs[i].nArg); |
|
|
|
|
|
TEST_ASSERT_MESSAGE((pDef->funcFlags & SQLITE_FUNC_INTERNAL)!=0, |
|
|
"Function not flagged as internal"); |
|
|
TEST_ASSERT_MESSAGE(pDef->xSFunc != NULL, "xSFunc should be non-NULL for internal scalar"); |
|
|
} |
|
|
} |
|
|
|
|
|
void test_sqlite3AlterFunctions_case_insensitive_lookup(void){ |
|
|
FuncDef *p1 = sqlite3FindFunction(gDb, "SQLITE_RENAME_TABLE", 7, SQLITE_UTF8, 0); |
|
|
TEST_ASSERT_NOT_NULL(p1); |
|
|
TEST_ASSERT_EQUAL_INT(7, p1->nArg); |
|
|
TEST_ASSERT_TRUE((p1->funcFlags & SQLITE_FUNC_INTERNAL)!=0); |
|
|
} |
|
|
|
|
|
void test_sqlite3AlterFunctions_wrong_arity_returns_null(void){ |
|
|
|
|
|
FuncDef *pBad1 = sqlite3FindFunction(gDb, "sqlite_rename_table", 6, SQLITE_UTF8, 0); |
|
|
FuncDef *pBad2 = sqlite3FindFunction(gDb, "sqlite_drop_column", 2, SQLITE_UTF8, 0); |
|
|
TEST_ASSERT_NULL(pBad1); |
|
|
TEST_ASSERT_NULL(pBad2); |
|
|
} |
|
|
|
|
|
void test_sqlite3AlterFunctions_idempotent_registration(void){ |
|
|
|
|
|
sqlite3AlterFunctions(); |
|
|
|
|
|
FuncDef *p1 = sqlite3FindFunction(gDb, "sqlite_add_constraint", 3, SQLITE_UTF8, 0); |
|
|
TEST_ASSERT_NOT_NULL(p1); |
|
|
TEST_ASSERT_TRUE((p1->funcFlags & SQLITE_FUNC_INTERNAL)!=0); |
|
|
|
|
|
FuncDef *p2 = sqlite3FindFunction(gDb, "sqlite_find_constraint", 2, SQLITE_UTF8, 0); |
|
|
TEST_ASSERT_NOT_NULL(p2); |
|
|
TEST_ASSERT_TRUE((p2->funcFlags & SQLITE_FUNC_INTERNAL)!=0); |
|
|
} |
|
|
|
|
|
void test_sqlite3AlterFunctions_unknown_function_not_found(void){ |
|
|
FuncDef *p = sqlite3FindFunction(gDb, "sqlite_nonexistent", 1, SQLITE_UTF8, 0); |
|
|
TEST_ASSERT_NULL(p); |
|
|
} |
|
|
|
|
|
int main(void) { |
|
|
UNITY_BEGIN(); |
|
|
RUN_TEST(test_sqlite3AlterFunctions_registers_all_expected_functions); |
|
|
RUN_TEST(test_sqlite3AlterFunctions_case_insensitive_lookup); |
|
|
RUN_TEST(test_sqlite3AlterFunctions_wrong_arity_returns_null); |
|
|
RUN_TEST(test_sqlite3AlterFunctions_idempotent_registration); |
|
|
RUN_TEST(test_sqlite3AlterFunctions_unknown_function_not_found); |
|
|
return UNITY_END(); |
|
|
} |