-
Notifications
You must be signed in to change notification settings - Fork 3
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add new plugin to call a Lua script.
- Loading branch information
Showing
10 changed files
with
264 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
: all lua clean clean-spac install |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
dependon([ fn[:-2]+'.a' for fn in glob('*=l') | ||
if fn[:3] <> 'lib']) | ||
dependon([ fn[:-2]+'.la' for fn in glob('lib*=l')]) | ||
dependon([ fn[:-3]+'.so' for fn in glob('*=so') | ||
if fn[:-3] != 'plugin-lua']) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
dependon(['plugin-lua.so']) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,153 @@ | ||
#include <lua.h> | ||
#include <lauxlib.h> | ||
#include <lualib.h> | ||
#include "mailfront.h" | ||
#include <msg/msg.h> | ||
|
||
static lua_State* L = 0; | ||
|
||
static const response* get_response(void) | ||
{ | ||
static response resp; | ||
static str msgcopy; | ||
const char* msg; | ||
|
||
resp.number = lua_tonumber(L, -2); | ||
msg = lua_tostring(L, -1); | ||
if (msg == 0 || *msg == 0) { | ||
resp.message = (resp.number < 400) ? "OK" | ||
: (resp.number < 500) ? "Deferred" | ||
: "Rejected"; | ||
} | ||
else { | ||
if (!str_copys(&msgcopy, msg)) | ||
return &resp_oom; | ||
resp.message = msgcopy.s; | ||
} | ||
lua_pop(L, 2); | ||
return (resp.number > 0) ? &resp : 0; | ||
} | ||
|
||
static int setup(const char* name) | ||
{ | ||
if (L != 0) { | ||
lua_getfield(L, LUA_GLOBALSINDEX, name); | ||
if (lua_isfunction(L, -1)) | ||
return 1; | ||
lua_pop(L, 1); | ||
} | ||
return 0; | ||
} | ||
|
||
static const response* callit(int nparams) | ||
{ | ||
int code; | ||
if ((code = lua_pcall(L, nparams, 2, 0)) != 0) { | ||
msgf("{Lua error: }d{ (}s{)}", code, lua_tostring(L, -1)); | ||
lua_pop(L, 1); | ||
return &resp_internal; | ||
} | ||
return get_response(); | ||
} | ||
|
||
static const response* init(void) | ||
{ | ||
const char* env; | ||
|
||
env = session_getenv("LUA_SCRIPT"); | ||
if (env != 0) { | ||
L = luaL_newstate(); | ||
if (L == 0) | ||
return &resp_oom; | ||
switch (luaL_loadfile(L, env)) { | ||
case LUA_ERRMEM: | ||
return &resp_oom; | ||
case 0: | ||
break; | ||
case LUA_ERRFILE: | ||
msg3("Cannot read \"", env, "\""); | ||
return &resp_internal; | ||
case LUA_ERRSYNTAX: | ||
msg3("Syntax error in \"", env, "\""); | ||
return &resp_internal; | ||
default: | ||
return &resp_internal; | ||
} | ||
return callit(0); | ||
} | ||
return 0; | ||
} | ||
|
||
static const response* reset(void) | ||
{ | ||
if (setup("reset")) | ||
return callit(0); | ||
return 0; | ||
} | ||
|
||
static const response* helo(str* hostname) | ||
{ | ||
if (setup("helo")) { | ||
lua_pushlstring(L, hostname->s, hostname->len); | ||
return callit(1); | ||
} | ||
return 0; | ||
} | ||
|
||
static const response* sender(str* address) | ||
{ | ||
if (setup("sender")) { | ||
lua_pushlstring(L, address->s, address->len); | ||
return callit(1); | ||
} | ||
return 0; | ||
} | ||
|
||
static const response* recipient(str* address) | ||
{ | ||
if (setup("recipient")) { | ||
lua_pushlstring(L, address->s, address->len); | ||
return callit(1); | ||
} | ||
return 0; | ||
} | ||
|
||
static const response* data_start(int fd) | ||
{ | ||
if (setup("data_start")) { | ||
lua_pushinteger(L, fd); | ||
return callit(1); | ||
} | ||
return 0; | ||
} | ||
|
||
static const response* data_block(const char* bytes, unsigned long len) | ||
{ | ||
if (setup("data_block")) { | ||
lua_pushlstring(L, bytes, len); | ||
return callit(1); | ||
} | ||
return 0; | ||
} | ||
|
||
static const response* message_end(int fd) | ||
{ | ||
if (setup("message_end")) { | ||
lua_pushinteger(L, fd); | ||
return callit(1); | ||
} | ||
return 0; | ||
} | ||
|
||
struct plugin plugin = { | ||
.version = PLUGIN_VERSION, | ||
.flags = 0, | ||
.init = init, | ||
.reset = reset, | ||
.helo = helo, | ||
.sender = sender, | ||
.recipient = recipient, | ||
.data_start = data_start, | ||
.data_block = data_block, | ||
.message_end = message_end, | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,32 @@ | ||
<html> | ||
<body> | ||
|
||
<h2><a href="mailfront.html">mailfront</a></h2> | ||
|
||
<h1>Plugin: lua</h1> | ||
|
||
<hr /> | ||
|
||
<p>This plugin allows for extending mailfront | ||
using <a href="http://www.lua.org/">Lua</a>. All actions in | ||
the <a href="plugin-api.html">mailfront plugin API</a> are exposed | ||
through calls to functions of the same name in the script, with the | ||
exception of the "<tt>init</tt>" function. For this function, the | ||
return from the script itself is used. The functions are passed the | ||
same parameters as described in the API. The return value from these | ||
functions is a numeric SMTP response code followed by a message. If | ||
the number is zero or <tt>nil</tt>, it is treated as an NULL response. | ||
If the message is missing, the script wrapper provides a simple one | ||
based on the response code.</p> | ||
|
||
<h2>Configuration</h2> | ||
|
||
<dl> | ||
|
||
<dt><tt>$LUA_SCRIPT</tt></dt> <dd>The file name of the Lua script to | ||
load. If not set, this plugin does nothing.</dd> | ||
|
||
</dl> | ||
|
||
</body> | ||
</html> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
-lbg | ||
-llua | ||
-lbg-sysdeps |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,64 @@ | ||
export LUA_SCRIPT=script.lua | ||
doit() { | ||
cat > script.lua | ||
echo | ||
sfecho lua <<EOF | ||
HELO helohost | ||
MAIL FROM:<sender> | ||
RCPT TO:<recip1> | ||
RCPT TO:<recip2> | ||
DATA | ||
Header: one | ||
. | ||
EOF | ||
} | ||
|
||
doit <<EOF | ||
return 555,"init failed" | ||
EOF | ||
|
||
doit <<EOF | ||
function reset() | ||
return 253,'reset' | ||
end | ||
|
||
function sender(a) | ||
return 251,'Lua sender='..a | ||
end | ||
|
||
function recipient(a) | ||
return 252,'Lua recip='..a | ||
end | ||
|
||
function data_start(fd) | ||
return 354 | ||
end | ||
EOF | ||
|
||
doit <<EOF | ||
function data_start(fd) | ||
return 421,'start fd='..fd | ||
end | ||
EOF | ||
|
||
rm -f $LUA_SCRIPT | ||
unset LUA_SCRIPT | ||
|
||
<result> | ||
|
||
555 init failed^M | ||
|
||
250 local.host^M | ||
251 Lua sender=sender^M | ||
252 Lua recip=recip1^M | ||
252 Lua recip=recip2^M | ||
354 End your message with a period on a line by itself.^M | ||
250 Received 12 bytes.^M | ||
|
||
250 local.host^M | ||
250 Sender='sender'.^M | ||
250 Recipient='recip1'.^M | ||
250 Recipient='recip2'.^M | ||
421 start fd=-1^M | ||
500 5.5.1 Not implemented.^M | ||
500 5.5.1 Not implemented.^M |