diff options
Diffstat (limited to 'test/lbaselib.test.js')
-rw-r--r-- | test/lbaselib.test.js | 436 |
1 files changed, 436 insertions, 0 deletions
diff --git a/test/lbaselib.test.js b/test/lbaselib.test.js new file mode 100644 index 0000000..259de36 --- /dev/null +++ b/test/lbaselib.test.js @@ -0,0 +1,436 @@ +"use strict"; + +const lua = require('../src/lua.js'); +const lauxlib = require('../src/lauxlib.js'); +const lualib = require('../src/lualib.js'); +const {to_luastring} = require("../src/fengaricore.js"); + + +test('print', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + print("hello", "world", 123) + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } +}); + + +test('setmetatable, getmetatable', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + local mt = { + __index = function () + print("hello") + return "hello" + end + } + + local t = {} + + setmetatable(t, mt); + + return t[1], getmetatable(t) + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tojsstring(L, -2)) + .toBe("hello"); + + expect(lua.lua_istable(L, -1)).toBe(true); +}); + + +test('rawequal', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + local mt = { + __eq = function () + return true + end + } + + local t1 = {} + local t2 = {} + + setmetatable(t1, mt); + + return rawequal(t1, t2), t1 == t2 + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_toboolean(L, -2)).toBe(false); + + expect(lua.lua_toboolean(L, -1)).toBe(true); +}); + + +test('rawset, rawget', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + local mt = { + __newindex = function (table, key, value) + rawset(table, key, "hello") + end + } + + local t = {} + + setmetatable(t, mt); + + t["yo"] = "bye" + rawset(t, "yoyo", "bye") + + return rawget(t, "yo"), t["yo"], rawget(t, "yoyo"), t["yoyo"] + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tojsstring(L, -4)) + .toBe("hello"); + + expect(lua.lua_tojsstring(L, -3)) + .toBe("hello"); + + expect(lua.lua_tojsstring(L, -2)) + .toBe("bye"); + + expect(lua.lua_tojsstring(L, -1)) + .toBe("bye"); +}); + + +test('type', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + return type(1), type(true), type("hello"), type({}), type(nil) + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tojsstring(L, -5)) + .toBe("number"); + + expect(lua.lua_tojsstring(L, -4)) + .toBe("boolean"); + + expect(lua.lua_tojsstring(L, -3)) + .toBe("string"); + + expect(lua.lua_tojsstring(L, -2)) + .toBe("table"); + + expect(lua.lua_tojsstring(L, -1)) + .toBe("nil"); +}); + + +test('error', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + error("you fucked up") + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + expect(() => { + lua.lua_call(L, 0, -1); + }).toThrow(/you fucked up/); + } +}); + + +test('error, protected', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + error("you fucked up") + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_pcall(L, 0, -1, 0); + } + + expect(lua.lua_tojsstring(L, -1)).toMatch(/you fucked up/); +}); + + +test('pcall', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + local willFail = function () + error("you fucked up") + end + + return pcall(willFail) + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tojsstring(L, -1)).toMatch(/you fucked up/); +}); + + +test('xpcall', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + local willFail = function () + error("you fucked up") + end + + local msgh = function (err) + return "Something's wrong: " .. err + end + + return xpcall(willFail, msgh) + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tojsstring(L, -1)).toMatch(/Something's wrong: .*you fucked up/); +}); + + +test('ipairs', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + local t = {1, 2, 3, 4, 5, ['yo'] = 'lo'} + + local sum = 0 + for i, v in ipairs(t) do + sum = sum + v + end + + return sum + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tointeger(L, -1)).toBe(15); +}); + + +test('select', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + return {select('#', 1, 2, 3)}, {select(2, 1, 2, 3)}, {select(-2, 1, 2, 3)} + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect([...lua.lua_topointer(L, -3).strong.entries()].map(e => e[1].value.value)) + .toEqual([3]); + + expect([...lua.lua_topointer(L, -2).strong.entries()].map(e => e[1].value.value).sort()) + .toEqual([2, 3]); + + expect([...lua.lua_topointer(L, -1).strong.entries()].map(e => e[1].value.value).sort()) + .toEqual([2, 3]); +}); + + +test('tonumber', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + return tonumber('foo'), + tonumber('123'), + tonumber('12.3'), + tonumber('az', 36), + tonumber('10', 2) + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_isnil(L, -5)).toBe(true); + expect(lua.lua_tonumber(L, -4)).toBe(123); + expect(lua.lua_tonumber(L, -3)).toBe(12.3); + expect(lua.lua_tonumber(L, -2)).toBe(395); + expect(lua.lua_tonumber(L, -1)).toBe(2); +}); + + +test('assert', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + assert(1 < 0, "this doesn't makes sense") + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_pcall(L, 0, -1, 0); + } + + expect(lua.lua_tojsstring(L, -1)).toMatch(/this doesn't makes sense/); +}); + + +test('rawlen', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + return rawlen({1, 2, 3}), rawlen('hello') + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tonumber(L, -2)).toBe(3); + expect(lua.lua_tonumber(L, -1)).toBe(5); +}); + + +test('next', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + local total = 0 + local t = { + 1, + two = 2, + 3, + four = 4 + } + + for k,v in next, t, nil do + total = total + v + end + + return total + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tonumber(L, -1)).toBe(10); +}); + + +test('pairs', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + local total = 0 + local t = { + 1, + two = 2, + 3, + four = 4 + } + + for k,v in pairs(t) do + total = total + v + end + + return total + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tonumber(L, -1)).toBe(10); +}); + + +test('pairs with __pairs', () => { + let L = lauxlib.luaL_newstate(); + if (!L) throw Error("failed to create lua state"); + + let luaCode = ` + local total = 0 + + local mt = { + __pairs = function(t) + return next, {5, 6, 7, 8}, nil + end + } + + local t = { + 1, + two = 2, + 3, + four = 4 + } + + setmetatable(t, mt) + + for k,v in pairs(t) do + total = total + v + end + + return total + `; + { + lualib.luaL_openlibs(L); + expect(lauxlib.luaL_loadstring(L, to_luastring(luaCode))).toBe(lua.LUA_OK); + lua.lua_call(L, 0, -1); + } + + expect(lua.lua_tonumber(L, -1)).toBe(26); +}); |