lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


On 18.02.2013 18:46, Gavin Kistner wrote:
Put more simply: how would you rewrite the following suite of files so
that the user can "require 'master'" and not spam the global namespace
with "MASTER", but still have all the assertions pass?

     ### _test_usage_.lua
     require 'master'
     assert(MASTER.Simple)
     assert(MASTER.simple)
     assert(MASTER.Shared)
     assert(MASTER.Shared.go)
     assert(MASTER.Simple.ref1()==MASTER.Multi1)
     assert(pcall(MASTER.Simple.ref2))
     ### master.lua
     MASTER = {}
     require 'simple'
     require 'multi'
     require 'shared1'
     require 'shared2'
     require 'reference'
     ### simple.lua
     MASTER.Simple = {}
     function MASTER:simple() end
     ### multi.lua
     MASTER.Multi1 = {}
     MASTER.Multi2 = {}
     ### shared1.lua
     MASTER.Shared = {}
     ### shared2.lua
     function MASTER.Shared:go() end
     ### reference.lua
     function MASTER.Simple:ref1() return MASTER.Multi1 end
     function MASTER.Simple:ref2() MASTER:simple()      end


I use an "auto-require" mechanism for that. My master module contains a table which maps each public function or variable to a source file. The module table itself has a metatable with a __index function which looks up the name and then automatically calls require(file). Apart from its metatable, the master module is an empty table. After setting this up, any submodule and any application only has to require the master module explicitly. The rest is done automatically.

Here is skeleton of the master module:

------------------------------------------------
local M = {}
package.loaded[...] = M
local submodules = {
	foo = 'file1.lua',
	bar = 'file1.lua',
	baz = 'file2.lua',
	...
}
setmetatable(M, { __index = function(tbl, key)
    local v = rawget(submodules, key)
    if v then
        require(v)
        return rawget(M, key)
    end
    error(key .. ' not found!')
end })
return M
------------------------------------------------

Of course this mechanism relies on the completeness of the 'submodules' table. But I found that if you follow a certain coding discipline, the complete master module can easily be created by a little Lua program.

Hope that helps.
Regards, Bernd
--
http://sudrala.de