Consolidate unit testing code
This commit is contained in:
@@ -4,11 +4,8 @@ Modules are listed in dependency order — each module's dependencies
|
|||||||
all appear earlier in the list. Where a dependency comes only from
|
all appear earlier in the list. Where a dependency comes only from
|
||||||
the `.cpp` file (not the `.hpp`), it is marked **(cpp-only)**.
|
the `.cpp` file (not the `.hpp`), it is marked **(cpp-only)**.
|
||||||
|
|
||||||
- **bytell-hash-map** — third-party hash map (header-only)
|
|
||||||
- **eng-malloc** — custom deterministic memory allocator
|
- **eng-malloc** — custom deterministic memory allocator
|
||||||
- **enginewrapper** — pure C interface for driver/driven boundary
|
- **enginewrapper** — pure C interface for driver/driven boundary
|
||||||
- **fast-float** — third-party float parser (header-only)
|
|
||||||
- **flat-hash-map** — third-party hash map (header-only)
|
|
||||||
- **spookyv2** — hash function
|
- **spookyv2** — hash function
|
||||||
- **util** → spookyv2
|
- **util** → spookyv2
|
||||||
- **luastack** → util
|
- **luastack** → util
|
||||||
|
|||||||
@@ -29,7 +29,7 @@ ifeq "$(OS)" "Linux"
|
|||||||
LUPREX_EXE:=luprex
|
LUPREX_EXE:=luprex
|
||||||
LUPREXLIB_DLL:=luprexlib.so
|
LUPREXLIB_DLL:=luprexlib.so
|
||||||
LUPREXSTATIC_EXE:=luprexstatic
|
LUPREXSTATIC_EXE:=luprexstatic
|
||||||
COMPILE:=g++ -Wall $(OPT) -std=c++20 -fvisibility=hidden -c -MMD -fPIC -o
|
COMPILE:=g++ -Wall $(OPT) -std=c++20 -fvisibility=hidden -c -MMD -MP -fPIC -o
|
||||||
LINKDLL:=g++ -Wall $(OPT) -std=c++20 -export-dynamic -Wl,--no-allow-shlib-undefined -Wl,-z,defs -shared -o
|
LINKDLL:=g++ -Wall $(OPT) -std=c++20 -export-dynamic -Wl,--no-allow-shlib-undefined -Wl,-z,defs -shared -o
|
||||||
LINKEXE:=g++ -Wall $(OPT) -std=c++20 -export-dynamic -o
|
LINKEXE:=g++ -Wall $(OPT) -std=c++20 -export-dynamic -o
|
||||||
MAKEDEPS:=true
|
MAKEDEPS:=true
|
||||||
@@ -84,7 +84,7 @@ BASE_CORE := \
|
|||||||
traceback planemap pprint luavector idalloc sched http \
|
traceback planemap pprint luavector idalloc sched http \
|
||||||
json table luasnap animqueue streambuffer source world-core world-accessor \
|
json table luasnap animqueue streambuffer source world-core world-accessor \
|
||||||
world-difftab world-diffxmit world-pairtab world-testing lpxserver lpxclient \
|
world-difftab world-diffxmit world-pairtab world-testing lpxserver lpxclient \
|
||||||
eng-tests printbuffer serializelua
|
unit-testing printbuffer serializelua
|
||||||
|
|
||||||
BASE_DRV := driver drvutil sslutil readline
|
BASE_DRV := driver drvutil sslutil readline
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +0,0 @@
|
|||||||
#ifndef DRIVERTESTS_HPP
|
|
||||||
#define DRIVERTESTS_HPP
|
|
||||||
|
|
||||||
#endif // DRIVERTESTS_HPP
|
|
||||||
|
|
||||||
@@ -433,43 +433,6 @@ eng::string SourceDB::rebuild_module(const eng::string &mod) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void SourceDB::run_unittests() {
|
|
||||||
lua_State *L = lua_state_;
|
|
||||||
LuaVar unittests, name, func, err, globtab;
|
|
||||||
LuaExtStack LS(L, unittests, name, func, err, globtab);
|
|
||||||
|
|
||||||
LS.getglobaltable(globtab);
|
|
||||||
LS.rawget(unittests, globtab, "unittests");
|
|
||||||
|
|
||||||
// Sort the unit test names.
|
|
||||||
eng::set<eng::string> names;
|
|
||||||
LS.set(name, LuaNil);
|
|
||||||
while (LS.next(unittests, name, func) != 0) {
|
|
||||||
if (LS.isfunction(func) && LS.isstring(name)) {
|
|
||||||
names.insert(LS.ckstring(name));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Run the functions in order
|
|
||||||
bool any = false;
|
|
||||||
for (const eng::string &name : names) {
|
|
||||||
util::dprint("Running unittests: ", name);
|
|
||||||
LS.rawget(func, unittests, name);
|
|
||||||
|
|
||||||
lua_pushvalue(L, func.index());
|
|
||||||
eng::string msg = traceback_pcall(L, 0, 0);
|
|
||||||
if (!msg.empty()) {
|
|
||||||
LS.set(err, msg);
|
|
||||||
util::dprint(msg);
|
|
||||||
any = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (any) {
|
|
||||||
exit(1);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void SourceDB::init(lua_State *L) {
|
void SourceDB::init(lua_State *L) {
|
||||||
lua_state_ = L;
|
lua_state_ = L;
|
||||||
LuaVar globtab, persist, unpersist, classname, classtab, funcname, funcp, rawfunc, nullstring;
|
LuaVar globtab, persist, unpersist, classname, classtab, funcname, funcp, rawfunc, nullstring;
|
||||||
|
|||||||
@@ -181,13 +181,6 @@ public:
|
|||||||
void diff(const SourceDB &auth, StreamBuffer *sb);
|
void diff(const SourceDB &auth, StreamBuffer *sb);
|
||||||
bool patch(StreamBuffer *sb, DebugCollector *dbc);
|
bool patch(StreamBuffer *sb, DebugCollector *dbc);
|
||||||
|
|
||||||
// run_unittests
|
|
||||||
//
|
|
||||||
// Run all the lua unit tests. Print any errors to console. If there
|
|
||||||
// are any errors, exits the program.
|
|
||||||
//
|
|
||||||
void run_unittests();
|
|
||||||
|
|
||||||
// Get/Set code (for unit testing).
|
// Get/Set code (for unit testing).
|
||||||
//
|
//
|
||||||
// These functions are direct getters/setters for values in the source
|
// These functions are direct getters/setters for values in the source
|
||||||
|
|||||||
@@ -3,9 +3,80 @@
|
|||||||
#include "drivenengine.hpp"
|
#include "drivenengine.hpp"
|
||||||
#include "streambuffer.hpp"
|
#include "streambuffer.hpp"
|
||||||
#include "world.hpp"
|
#include "world.hpp"
|
||||||
|
#include "traceback.hpp"
|
||||||
|
|
||||||
#include <iomanip>
|
#include <iomanip>
|
||||||
|
|
||||||
|
static void run_unittests(lua_State *L) {
|
||||||
|
LuaVar unittests, name, func, err, globtab;
|
||||||
|
LuaExtStack LS(L, unittests, name, func, err, globtab);
|
||||||
|
|
||||||
|
LS.getglobaltable(globtab);
|
||||||
|
LS.rawget(unittests, globtab, "unittests");
|
||||||
|
|
||||||
|
// Sort the unit test names.
|
||||||
|
eng::set<eng::string> names;
|
||||||
|
LS.set(name, LuaNil);
|
||||||
|
while (LS.next(unittests, name, func) != 0) {
|
||||||
|
if (LS.isfunction(func) && LS.isstring(name)) {
|
||||||
|
names.insert(LS.ckstring(name));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Run the functions in order
|
||||||
|
bool any = false;
|
||||||
|
for (const eng::string &name : names) {
|
||||||
|
util::dprint("Running unittests: ", name);
|
||||||
|
LS.rawget(func, unittests, name);
|
||||||
|
|
||||||
|
lua_pushvalue(L, func.index());
|
||||||
|
eng::string msg = traceback_pcall(L, 0, 0);
|
||||||
|
if (!msg.empty()) {
|
||||||
|
LS.set(err, msg);
|
||||||
|
util::dprint(msg);
|
||||||
|
any = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (any) {
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
class RunUnitTests : public DrivenEngine {
|
||||||
|
public:
|
||||||
|
UniqueWorld world_;
|
||||||
|
|
||||||
|
RunUnitTests(EngineWrapper *) {
|
||||||
|
world_.reset(new World(WORLD_TYPE_MASTER));
|
||||||
|
rescan_lua_source(true);
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual void event_access(AccessKind kind, int64_t place_id, std::string_view datapk, StreamBuffer *retpk) override {
|
||||||
|
switch (kind) {
|
||||||
|
case AccessKind::INVOKE_LUA_SOURCE: {
|
||||||
|
world_->update_source(datapk);
|
||||||
|
run_unittests(world_->state());
|
||||||
|
stop_driver();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
default: break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void event_update() override {}
|
||||||
|
};
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// Driver tests.
|
||||||
|
//
|
||||||
|
// These tests can't go through the unit testing framework,
|
||||||
|
// because they're tests of the driver-engine interface
|
||||||
|
// and the driver.
|
||||||
|
//
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
static void write_closed_message(Channel *ch) {
|
static void write_closed_message(Channel *ch) {
|
||||||
util::dprint("Chan ", ch->chid(), " closed [", ch->error(), "]\n");
|
util::dprint("Chan ", ch->chid(), " closed [", ch->error(), "]\n");
|
||||||
}
|
}
|
||||||
@@ -89,30 +160,6 @@ public:
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
class RunUnitTests : public DrivenEngine {
|
|
||||||
public:
|
|
||||||
UniqueWorld world_;
|
|
||||||
|
|
||||||
RunUnitTests(EngineWrapper *) {
|
|
||||||
world_.reset(new World(WORLD_TYPE_MASTER));
|
|
||||||
rescan_lua_source(true);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual void event_access(AccessKind kind, int64_t place_id, std::string_view datapk, StreamBuffer *retpk) override {
|
|
||||||
switch (kind) {
|
|
||||||
case AccessKind::INVOKE_LUA_SOURCE: {
|
|
||||||
world_->update_source(datapk);
|
|
||||||
world_->run_unittests();
|
|
||||||
stop_driver();
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
default: break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void event_update() override {}
|
|
||||||
};
|
|
||||||
|
|
||||||
DrivenEngineDefine("driverwebservertest", DriverWebServerTest);
|
DrivenEngineDefine("driverwebservertest", DriverWebServerTest);
|
||||||
DrivenEngineDefine("driverdnsfailtest", DriverDNSFailTest);
|
DrivenEngineDefine("driverdnsfailtest", DriverDNSFailTest);
|
||||||
DrivenEngineDefine("driverprintclocktest", DriverPrintClockTest);
|
DrivenEngineDefine("driverprintclocktest", DriverPrintClockTest);
|
||||||
1
luprex/cpp/core/unit-testing.hpp
Normal file
1
luprex/cpp/core/unit-testing.hpp
Normal file
@@ -0,0 +1 @@
|
|||||||
|
#pragma once
|
||||||
@@ -713,12 +713,6 @@ HttpServerResponse World::http_serve(const HttpParser &request) {
|
|||||||
return response;
|
return response;
|
||||||
}
|
}
|
||||||
|
|
||||||
void World::run_unittests() {
|
|
||||||
assert(stack_is_clear());
|
|
||||||
source_db_.run_unittests();
|
|
||||||
assert(stack_is_clear());
|
|
||||||
}
|
|
||||||
|
|
||||||
void World::invoke(const Invocation &inv) {
|
void World::invoke(const Invocation &inv) {
|
||||||
switch (inv.kind()) {
|
switch (inv.kind()) {
|
||||||
case AccessKind::INVOKE_LUA_CALL:
|
case AccessKind::INVOKE_LUA_CALL:
|
||||||
|
|||||||
@@ -317,10 +317,6 @@ public:
|
|||||||
//
|
//
|
||||||
HttpServerResponse http_serve(const HttpParser &request);
|
HttpServerResponse http_serve(const HttpParser &request);
|
||||||
|
|
||||||
// Run all unit tests.
|
|
||||||
//
|
|
||||||
void run_unittests();
|
|
||||||
|
|
||||||
// Install this world into an EngineWrapper's function pointers.
|
// Install this world into an EngineWrapper's function pointers.
|
||||||
//
|
//
|
||||||
void expose_world_to_driver(EngineWrapper *w);
|
void expose_world_to_driver(EngineWrapper *w);
|
||||||
|
|||||||
Reference in New Issue
Block a user