[erlang-questions] [ANN] erlualib 0.1 - seamlessly implement *any* Erlang behaviour in Lua

Motiejus Jakštys <>
Fri Jul 27 14:40:48 CEST 2012


Hi,

I am excited to announce erlualib 0.1, which enables us to implement
arbitrary Erlang behavious in Lua. This library allows to embed Lua code
to Erlang codebase very easily and transparently.

Why do we do it? In Spil games, we have game developers, who are
wonderful flash programmers. We want to create some server-side game
processing actions, and want game devs to create these. They are also
not really much into Erlang. So they write the game rules in Lua,
adhering to an Erlang behaviour, and we easily plug the module in.
Because of transparency of this library, we (backend) will not even be
aware if the game is written in Lua or Erlang.

How to do it:

1. Create an Erlang module which you want to implement in Lua
2. Add 4 lines:
    1. `-module(my_mod).`
    2. `-behaviour(abitrary_behaviour).`
    3. `-implemented_in({priv, "/module_impl.lua"}). % where to forward calls`
    4. `-compile({parse_transform, lua_behaviour}). % this does the hard work`
3. Compile and use `my_mod` as if it was written in pure Erlang.

Below is an example of simple key-value name server. It has 2 operations:

* `{add_name, Key :: binary(), Value :: binary()} -> ok.`
* `{get_addr, Key :: binary()} -> 'error' | Value :: binary().`

==== `name_server.erl` ====

-module(name_server).
-behaviour(gen_server).
-implemented_in({priv, "/name_server.lua"}).
-compile({parse_transform, lua_behaviour}).

==== `priv/name_server.lua` ====

function init()
    return erlang.atom("ok"), {} -- This empty table will be our state
end

-- Forwards the call to function which is specified in req[1]. Returns
-- {reply, Return, NewTable}. Return and NewTable are values from the
-- forwarded module.
function handle_call(req, from, tbl)
    return erlang.atom("reply"), call(tbl, req)
end

-- Adds name to State. Returns {ok, Table}.
function add_name(tbl, name, address)
    tbl[name] = address
    return erlang.atom("ok"), tbl
end

-- Gets name table and current name. Returns: { 'error' | Value, Table}
function get_addr(tbl, name)
    return tbl[name] or erlang.atom("error"), tbl
end

-- Call req[1](tbl, req[2], req[3], ...)
function call(tbl, req) return _G[req[1]](tbl, unpack(req, 2)) end

That's it! Compile `name_server.erl` and call it. Alternatively, download the
[example][erlualib_examples] and `make test`.

Performance
===========
`luam:one_call/3` (the "do all" function) consists of 3 parts:

1. `lua:new_state/0`, takes ~220-250µs.
2. `luam:call/4`, takes ~12-15µs.
3. `lua:close/1`, negligible.

For `lua_behaviour`, new Lua state is created on every request, which
adds significant overhead. In `gen_(server|fsm)` case (as well as many
others), it will be possible to reuse the state, and performance will be
much, much better. I just need to create `gen_(server|fsm)` specific
`parse_transform` for it, which is planned for near future.

Type conversions Lua -> Erlang
==============================
As you already noticed in the Lua example, "erlang" lua library is
available! Now it has only one method `atom`, which takes a string and
returns atom. Analogue `tuple` method is planned (now, when you return
an indexed table in Lua, it is treated as a proplist with numeric
indices, so there is no way to return nested tuples).

Some words about erlualib
=========================
erlualib is a library for embedding Lua into Erlang. It provides a
simple interface that is very similar to the Lua C API, as well as some
very useful high-level functions.

This is a fork of Ray Morgan's Erl-Lua library with the following
changes:

* High test coverage (and PropEr tests)
* New low-level commands
* Strings in Lua are Binaries in Erlang (instead of lists of numbers)
* Many bugfixes
* Dialyzer is happy about this project
* Rebarized
* `luam:call/4`.
* arbitrary erlang behaviours in Lua

Erlualib is a nice example how and when to PropErly test things. Tests
for `parse_transforms` are coming soon.

Library is very fresh, and in heavy development. Bug reports, patches,
and comments are very welcome.

[erlualib_examples]: https://github.com/Motiejus/erlualib_examples
[erlualib]: https://github.com/Motiejus/erlualib

Motiejus
-------------- next part --------------
A non-text attachment was scrubbed...
Name: signature.asc
Type: application/pgp-signature
Size: 836 bytes
Desc: Digital signature
URL: <http://erlang.org/pipermail/erlang-questions/attachments/20120727/c064b811/attachment.bin>


More information about the erlang-questions mailing list