Mongoose(SHTTP)+LUA

前端时间需要一个嵌入式的webserver,但最终没有一个比较满意的。

最近就在想是否自己写一个支持lua脚本的服务器版本,可以嵌入到各种webserver中,且是与webserver集成在一起,而非单独进程方式(类似cgi)。

想到那么就开始动手写,由于之前利用的是cgilua,那么就做一个cgilua的子集吧,尽量兼容。

需求

  1. 兼容cgilua,其网页格式仍然以.lp为后缀
  2. lp文件格式通cgilua
  3. 尽量做到少依赖其他库或者文件(比如说SAPI,expact等)
  4. 文件尽量少,可以方便的在linux,windows,uclinux,vxworks下移植和使用
  5. 不创建新的进程/Task来处理lp
  6. 暂不支持sajax

基本思路

  1. 读取lp文件,并解释成LUA语法。将HTML语句转换cgilua.put语句,去掉LUA语句前后的转义字符
  2. 调用LUA虚拟机执行lua语句,将结果通过webserver发送出去
  3. webserver在适配代码中需要将POST信息,环境变量等信息传递给lua虚拟机,传递方式就是创建相应的POST和env数组

代码结构

代码主要分为两部分,一部分为实现lp文件解析,另一部分为与webserver之间的适配代码。

  • sluacgi.c、lua.c为lp解析文件
  • mongoose.c为webserver代码和适配代码(可与mongoose源码比较,新增代码为适配代码)
  • main.c

选择mongoose的缘故是因为mongoose可以在windows下运行,方便调试

 

接口

对外接口

  • lp_load: 加载文件,并解释成lua语法。对应与lp_load_free,释放lp_load所申请的资源
  • lp_parse:启动LUA虚拟机,执行lua脚本,最后得到所需的html语句。对应与lp_parse_free,释放lp_load所申请的资源

webserver需要实现接口

  • sluacgi_make_env: html需要的环境变量,实现类似cgilua的servervariable接口
  • sluacgi_make_args: 生成POST信息
  • sluacgi_post_savefile: POST文件保存接口(针对post文件,为了减少内存消耗,与cgilua实现不一样)

兼容cgilua接口列表

  • print
  • put
  • servervariable
  • header
  • httpstatus
  • lp.include
  • mkurlpath
  • mkabsoluteurl
  • splitonlast
  • splitonfirst

可优化

  • 如果是用于嵌入式系统上,建议采用thttpd,因为其完全是用单线程做处理,效率和资源使用更高效
  • 如果是单线程处理,则对lp_load和lp_parse可做下优化处理,不需要频繁申请/释放内存
  • 如果不需要支持 #!/usr/bin/env cgilua.cgi ,建议将lp_load中对lp_check_exec调用去掉,更高效一些
  • 目前暂不支持sajax,如果需要可直接加入

代码

http://download.csdn.net/source/2662100

 

lp文件格式

普通

请参考附件中的例子

文件

为了兼容cgilua,故写成如下格式

<html>
<% cgilua.lp.include ("header.lp")%>

<tr align="center" bgcolor="#CCCCCC">
<td width="472" height="44" colspan="2"><div align="center">
    <p><font color="#0" size="4" face="Geneva, Arial, Helvetica, sans-serif"><strong>demo</strong></font></p>
  </div></td>
</tr>

<form method="POST" enctype="multipart/form-data" action="admin_soft_update.lp">
<tr bgcolor="#888888">
    <td>file</td>
    <td>
    <input type="file" name="file">
    </td>
</tr>

<tr bgcolor="#CCCCCC">
<td height="20" colspan="2" align="center"><div align="right">
    <input type="submit" value="put">
</div></td>
</tr>
</form>
<%
local fs_dir = 'www/uploads/'
local msg = nil

local function xavante_save()
    local f = cgilua.POST.file
    if f and next(f) then
        local _, name = cgilua.splitonlast(f.filename)
        local file1 = f.file
        os.execute('rm -rf '..fs_dir..'*')
        os.execute('mkdir '..fs_dir)
        local dest = io.open(fs_dir..name, "wb")
        if dest then
            local bytes = file1:read("*a")
            dest:write(bytes)
            dest:close()
        end
        return true, name
    end
    return false
end

local function sluacgi_save()
    local filename = cgilua.POST.filename
    if filename then
        local _, name = cgilua.splitonlast(filename)
        os.execute('rm -rf '..fs_dir..'*')
        os.execute('mkdir '..fs_dir)
        cgilua.savefile(fs_dir..name)
        return true, name
    end
    return false
end

function save_file()
    if cgilua.sluacgi_ver then
        return sluacgi_save()
    else
        return xavante_save()
    end
end

    local ret, name = save_file()
    if ret then
            msg = 'success'
    else
            msg = 'failure'
    end
%>

    </table>
<p>this is a demo</p>
<% cgilua.lp.include ("buttom.lp")%>

</table>
</form>
</center>

<script language="javascript">
<%
    if( msg ) then
    cgilua.put("alert('"..msg.."')")
    end
%>
</script>
</body>
</html>


工程文件说明

源码中用到了lua和tolua++的第三方库,下载地址为:

lua:  http://www.lua.org/download.html

tolua++: http://www.codenix.com/~tolua/

下载下来后解压放入sluacgi目录, 然后修改mongoose项目属性的中的addtational include Directories 中的包含路径,编译即可


评论 9
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值