From 703c6c038531216d7fe3ba4a59ff58f24b7ce3aa Mon Sep 17 00:00:00 2001 From: Enno Rehling Date: Sat, 7 Oct 2017 20:17:04 +0200 Subject: [PATCH] some examples for how the new orderfile logic can be used to write unit tests. --- src/CMakeLists.txt | 1 + src/orderfile.c | 54 ++++++++++++++++---------- src/orderfile.h | 6 +++ src/orderfile.test.c | 91 ++++++++++++++++++++++++++++++++++++++++++++ src/test_eressea.c | 1 + 5 files changed, 133 insertions(+), 20 deletions(-) create mode 100644 src/orderfile.test.c diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 2af57d6b7..e5ae8de7a 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -218,6 +218,7 @@ set(TESTS_SRC monsters.test.c move.test.c names.test.c + orderfile.test.c piracy.test.c prefix.test.c renumber.test.c diff --git a/src/orderfile.c b/src/orderfile.c index 90348cc17..0db6a0cba 100644 --- a/src/orderfile.c +++ b/src/orderfile.c @@ -18,8 +18,7 @@ #include #include - -static unit *unitorders(FILE * F, int enc, struct faction *f) +static unit *unitorders(input *in, faction *f) { int i; unit *u; @@ -64,7 +63,7 @@ static unit *unitorders(FILE * F, int enc, struct faction *f) * eingegeben wurde, checken wir, ob nun eine neue * Einheit oder ein neuer Spieler drankommt */ - s = getbuf(F, enc); + s = in->getbuf(in->data); if (s == NULL) break; @@ -147,23 +146,14 @@ static faction *factionorders(void) return f; } -int readorders(const char *filename) +int read_orders(input *in) { - FILE *F = NULL; const char *b; int nfactions = 0; - int enc_gamedata = ENCODING_UTF8; struct faction *f = NULL; - F = fopen(filename, "r"); - if (!F) { - perror(filename); - return -1; - } - log_info("reading orders from %s", filename); - /* TODO: recognize UTF8 BOM */ - b = getbuf(F, enc_gamedata); + b = in->getbuf(in->data); /* Auffinden der ersten Partei, und danach abarbeiten bis zur letzten * Partei */ @@ -184,7 +174,7 @@ int readorders(const char *filename) ++nfactions; } - b = getbuf(F, enc_gamedata); + b = in->getbuf(in->data); break; /* in factionorders wird nur eine zeile gelesen: @@ -193,9 +183,9 @@ int readorders(const char *filename) * vermerkt. */ case P_UNIT: - if (!f || !unitorders(F, enc_gamedata, f)) { + if (!f || !unitorders(in, f)) { do { - b = getbuf(F, enc_gamedata); + b = in->getbuf(in->data); if (!b) { break; } @@ -216,16 +206,40 @@ int readorders(const char *filename) case P_NEXT: f = NULL; - b = getbuf(F, enc_gamedata); + b = in->getbuf(in->data); break; default: - b = getbuf(F, enc_gamedata); + b = in->getbuf(in->data); break; } } - fclose(F); log_info("done reading orders for %d factions", nfactions); return 0; } + +static const char * file_getbuf(void *data) +{ + FILE *F = (FILE *)data; + return getbuf(F, ENCODING_UTF8); +} + +int readorders(const char *filename) +{ + input in; + int result; + + FILE *F = NULL; + F = fopen(filename, "r"); + if (!F) { + perror(filename); + return -1; + } + log_info("reading orders from %s", filename); + in.getbuf = file_getbuf; + in.data = F; + result = read_orders(&in); + fclose(F); + return result; +} diff --git a/src/orderfile.h b/src/orderfile.h index b36b8acae..43b86042e 100644 --- a/src/orderfile.h +++ b/src/orderfile.h @@ -7,6 +7,12 @@ extern "C" { #endif + typedef struct input { + const char *(*getbuf)(void *data); + void *data; + } input; + + int read_orders(struct input *in); int readorders(const char *filename); #ifdef __cplusplus diff --git a/src/orderfile.test.c b/src/orderfile.test.c new file mode 100644 index 000000000..87992f584 --- /dev/null +++ b/src/orderfile.test.c @@ -0,0 +1,91 @@ +#include +#include + +#include "orderfile.h" + +#include + +#include +#include + +static const char *getbuf_null(void *data) +{ + return NULL; +} + +static void test_read_orders(CuTest *tc) { + input in; + test_setup(); + in.getbuf = getbuf_null; + in.data = NULL; + CuAssertIntEquals(tc, 0, read_orders(&in)); + test_cleanup(); +} + +typedef struct order_list { + const char *orders[8]; + int next; +} order_list; + +static const char *getbuf_list(void *data) +{ + order_list * olist = (order_list *)data; + if (olist->next >= 8) { + return NULL; + } + return olist->orders[olist->next++]; +} + +static void test_faction_password_okay(CuTest *tc) { + input in; + faction *f; + order_list olist; + + test_setup(); + f = test_create_faction(NULL); + renumber_faction(f, 1); + CuAssertIntEquals(tc, 1, f->no); + faction_setpassword(f, "password"); + f->lastorders = turn - 1; + olist.orders[0] = "ERESSEA 1 password"; + olist.orders[1] = NULL; + olist.next = 0; + in.getbuf = getbuf_list; + in.data = &olist; + CuAssertIntEquals(tc, 0, read_orders(&in)); + CuAssertIntEquals(tc, 2, olist.next); + CuAssertIntEquals(tc, turn, f->lastorders); + test_cleanup(); +} + +static void test_faction_password_bad(CuTest *tc) { + input in; + faction *f; + order_list olist; + + test_setup(); + f = test_create_faction(NULL); + renumber_faction(f, 1); + CuAssertIntEquals(tc, 1, f->no); + faction_setpassword(f, "password"); + f->lastorders = turn - 1; + olist.orders[0] = "ERESSEA 1 patzword"; + olist.orders[1] = NULL; + olist.next = 0; + in.getbuf = getbuf_list; + in.data = &olist; + CuAssertIntEquals(tc, 0, read_orders(&in)); + CuAssertIntEquals(tc, 2, olist.next); + CuAssertIntEquals(tc, turn - 1, f->lastorders); + test_cleanup(); +} + +CuSuite *get_orderfile_suite(void) +{ + CuSuite *suite = CuSuiteNew(); + SUITE_ADD_TEST(suite, test_read_orders); + SUITE_ADD_TEST(suite, test_faction_password_okay); + SUITE_ADD_TEST(suite, test_faction_password_bad); + + return suite; +} diff --git a/src/test_eressea.c b/src/test_eressea.c index 215bdd2c5..38c5cf026 100644 --- a/src/test_eressea.c +++ b/src/test_eressea.c @@ -132,6 +132,7 @@ int RunAllTests(int argc, char *argv[]) ADD_SUITE(monsters); ADD_SUITE(move); ADD_SUITE(names); + ADD_SUITE(orderfile); ADD_SUITE(otherfaction); ADD_SUITE(piracy); ADD_SUITE(prefix);