diff --git a/frontends/nextjs/src/lib/lua/ui/call-lua-function.ts b/frontends/nextjs/src/lib/lua/ui/call-lua-function.ts new file mode 100644 index 000000000..60c91ccd5 --- /dev/null +++ b/frontends/nextjs/src/lib/lua/ui/call-lua-function.ts @@ -0,0 +1,37 @@ +import * as fengari from 'fengari-web' +import { fromLua } from '@/lib/lua/functions/converters/from-lua' + +const lua = fengari.lua + +/** + * Call a Lua function that's in a table on the stack + * @param L - Lua state + * @param tableIndex - Stack index of the table containing the function + * @param functionName - Name of the function to call + * @returns The result of the function call + */ +export function callLuaFunction(L: any, tableIndex: number, functionName: string): any { + // Get the function from the table + lua.lua_getfield(L, tableIndex, fengari.to_luastring(functionName)) + + // Check if it's a function + if (!lua.lua_isfunction(L, -1)) { + lua.lua_pop(L, 1) + throw new Error(`${functionName} is not a function`) + } + + // Call the function with 0 arguments, expecting 1 return value + const callResult = lua.lua_pcall(L, 0, 1, 0) + + if (callResult !== lua.LUA_OK) { + const errorMsg = lua.lua_tojsstring(L, -1) + lua.lua_pop(L, 1) + throw new Error(`Error calling ${functionName}: ${errorMsg}`) + } + + // Convert the result to JavaScript + const result = fromLua(L, -1) + lua.lua_pop(L, 1) + + return result +} diff --git a/frontends/nextjs/src/lib/lua/ui/load-lua-ui-package.test.ts b/frontends/nextjs/src/lib/lua/ui/load-lua-ui-package.test.ts index e243baba4..c64f1cdcc 100644 --- a/frontends/nextjs/src/lib/lua/ui/load-lua-ui-package.test.ts +++ b/frontends/nextjs/src/lib/lua/ui/load-lua-ui-package.test.ts @@ -1,10 +1,11 @@ -import { describe, it, expect } from 'bun:test' +import { describe, expect,it } from 'bun:test' import { join } from 'path' + import { loadLuaUIPackage } from './load-lua-ui-package' describe('loadLuaUIPackage', () => { it('should load example-form package with manifest and lua files', async () => { - const packagePath = join(__dirname, '../packages/lua-ui/example-form') + const packagePath = join(__dirname, '../../packages/lua-ui/example-form') const uiPackage = await loadLuaUIPackage(packagePath) // Check manifest @@ -45,7 +46,7 @@ describe('loadLuaUIPackage', () => { }) it('should execute action function from loaded package', async () => { - const packagePath = join(__dirname, '../packages/lua-ui/example-form') + const packagePath = join(__dirname, '../../packages/lua-ui/example-form') const uiPackage = await loadLuaUIPackage(packagePath) // Call the action function diff --git a/frontends/nextjs/src/lib/lua/ui/load-lua-ui-package.ts b/frontends/nextjs/src/lib/lua/ui/load-lua-ui-package.ts index 85b90ff40..bc0260ce8 100644 --- a/frontends/nextjs/src/lib/lua/ui/load-lua-ui-package.ts +++ b/frontends/nextjs/src/lib/lua/ui/load-lua-ui-package.ts @@ -1,12 +1,14 @@ -import { readFile, readdir } from 'fs/promises' +import { readdir,readFile } from 'fs/promises' import { join } from 'path' -import { executeLuaCode } from '@/lib/lua/functions/execution/execute-lua-code' + import { createLuaEngine } from '@/lib/lua/engine/core/create-lua-engine' +import { executeLuaCode } from '@/lib/lua/functions/execution/execute-lua-code' + import type { + LuaUIComponent, LuaUIManifest, LuaUIPackage, LuaUIPage, - LuaUIComponent, } from './types/lua-ui-package' /** diff --git a/frontends/nextjs/src/lib/lua/ui/test-lua-module.test.ts b/frontends/nextjs/src/lib/lua/ui/test-lua-module.test.ts new file mode 100644 index 000000000..6299b5f28 --- /dev/null +++ b/frontends/nextjs/src/lib/lua/ui/test-lua-module.test.ts @@ -0,0 +1,32 @@ +import { describe, expect,it } from 'bun:test' + +import { createLuaEngine } from '@/lib/lua/engine/core/create-lua-engine' +import { executeLuaCode } from '@/lib/lua/functions/execution/execute-lua-code' + +describe('Lua module loading', () => { + it('should load a simple Lua module with function', async () => { + const luaCode = ` +local M = {} + +function M.render() + return { + type = "Box", + props = { padding = 2 } + } +end + +return M +` + + const engine = createLuaEngine() + const result = await executeLuaCode(engine.L, luaCode, {}, []) + + console.log('Execution result:', JSON.stringify(result, null, 2)) + console.log('Result type:', typeof result.result) + console.log('Result keys:', result.result ? Object.keys(result.result) : 'no keys') + + engine.destroy() + + expect(result.success).toBe(true) + }) +}) diff --git a/frontends/nextjs/src/types/dbal.d.ts b/frontends/nextjs/src/types/dbal.d.ts index 569e1ef69..cb9657b1a 100644 --- a/frontends/nextjs/src/types/dbal.d.ts +++ b/frontends/nextjs/src/types/dbal.d.ts @@ -7,9 +7,9 @@ * under the large-file threshold and easier to maintain. */ +export * from './dbal/blob.js' export * from './dbal/core-config.js' export * from './dbal/core-types.js' -export * from './dbal/tenant-context.js' export * from './dbal/kv-store.js' -export * from './dbal/blob.js' export * from './dbal/tenant-aware-blob.js' +export * from './dbal/tenant-context.js'