6 ms·
While a module system in JavaScript will be useful, this seems overly complicated. I like Lua's approach to modules. In Lua, a file is basically equivalent to
by russellsprouts 12y ago
While a module system in JavaScript will be useful, this seems overly complicated.
I like Lua's approach to modules. In Lua, a file is basically equivalent to a function body. It accepts arguments and can return values. In JavaScript, this is not allowed.
In Lua, a function can accept multiple arguments in a tuple called `...`. Every file is implicitly a vararg function, so we can unpack the `...` to get arguments.
> add.lua
local a,b = ...
return a + b
> file.lua
local add = load 'add.lua'
print(add(1,2)) --> 3
load takes a file path and returns that source file as a function.
Most files ignore arguments, but they do return values.
> add2.lua
return function(a,b) return a + b end
> file2.lua
local add = require 'add'
print(add(1,2))
`require` loads a source file, executes it, and returns the value that it returns. It is similar to `return load(fileName)()`, but it also has a search mechanism, and caches the result. So, the Lua equivalent of export default is simply returning a value at the end of a source file.
The named exports are also easy to replicate. You simply return an object with the keys you want.
> math.lua
return {
add = function(a,b) return a + b end,
sub = function(a,b) return a - b end
}
> other.lua
local math = require 'math'
local add, sub = math.add, math.sub
You can also have something similar to the `export function name(){}` declaration.
> hello.lua
local exports = {}
function exports.hello()
print "Hello World"
end
exports.VERSION = '0.0.1'
return exports
> file3.lua
local hello = require'hello'.hello
local version = require'hello'.VERSION
hello() --> Hello World
In all, I think the Lua's require is a much cleaner way to implement modules. Unfortunately, it cannot handle circular references. It may be possible to add this feature using Lua's coroutines, however. I will have to research how it is handled in JavaScript to be sure.
- pcwalton 12y ago> In all, I think the Lua's require is a much cleaner way to implement modules. The idea behind ES6 modules is to add static name resolution to JavaScript. Because of the incredibly dynamic nature of JS, you can never know what any global name resolves to, as it could change at a moment's notice. The same is true in Lua's module system: `_G` is completely mutable and it (or its metatable!) can change at any time, altering the bindings in the program. I personally feel that, given how JavaScript is getting used in larger and larger codebases, some measure of static checking was long overdue.
- oblio 12y ago> Unfortunately, it cannot handle circular references. Wouldn't this be bad design in 99% of circumstances anyway? I say 99% because I don't want to be categorical, personally I think circular references/dependencies are always bad on some level.