jbe@0: -- Moonbridge example application jbe@0: -- invoke with ./moonbridge example_application.lua jbe@0: jbe@4: local http = require "moonbridge_http" jbe@0: jbe@0: local documents = {"example_webpage.html", "example_webpage.css"} jbe@0: jbe@0: listen{ jbe@0: -- listen to a tcp version 4 socket jbe@0: { proto = "tcp4", port = 8080, localhost = true }, jbe@0: jbe@0: -- listen to a tcp version 6 socket jbe@0: { proto = "tcp6", port = 8080, localhost = true }, jbe@0: jbe@0: -- listen to a unix domain socket jbe@0: --{ proto = "local", path = 'socket' }, jbe@0: jbe@0: -- execute the listener regularly (without incoming connection) jbe@0: --{ proto = "interval", name = "myint", delay = 10, strict = false }, jbe@0: jbe@0: -- desired number of spare (idle) processes jbe@0: pre_fork = 1, -- number of forks jbe@0: jbe@0: -- minimum number of processes jbe@0: min_fork = 2, -- number of forks jbe@0: jbe@0: -- maximum number of processes (hard limit) jbe@0: max_fork = 16, -- number of forks jbe@0: jbe@0: -- delay between creation of spare processes jbe@0: fork_delay = 1, -- seconds jbe@0: jbe@0: -- delay before retry of failed process creation jbe@0: fork_error_delay = 2, -- seconds jbe@0: jbe@0: -- delay between destruction of excessive spare processes jbe@0: exit_delay = 60, -- seconds jbe@0: jbe@0: -- idle time after a fork gets terminated jbe@0: idle_timeout = 0, -- seconds (0 for no timeout) jbe@0: jbe@0: -- maximum memory consumption before process gets terminated jbe@0: memory_limit = 1024*1024, -- bytes jbe@0: jbe@0: -- preparation of process (executed before fork) jbe@0: prepare = function() jbe@0: for i, document in ipairs(documents) do jbe@0: local file = assert(io.open(document)) jbe@0: documents[document] = file:read("*a") jbe@0: file:close() jbe@0: end jbe@0: end, jbe@0: jbe@0: -- connection handler jbe@0: connect = http.generate_handler( jbe@0: { jbe@0: static_headers = {"Server: Moonbridge Example Server"}, jbe@0: request_body_size_limit = 16*1024*1024*1024 -- allow big file uploads jbe@0: }, jbe@0: function(request) jbe@0: jbe@0: if request.method == "GET" or request.method == "HEAD" then jbe@0: jbe@0: if request.path == "/" then jbe@0: request:send_status("303 See Other") jbe@0: request:send_header("Location", "http://" .. request.headers_value.host .. "/example_webpage.html") jbe@0: jbe@0: else jbe@0: local document_name = string.match(request.path, "^/(.*)$") jbe@0: local document_extension = string.match(document_name, "%.([^.])$") jbe@0: local document = documents[string.match(request.path, "^/(.*)$")] jbe@0: if document then jbe@0: request:send_status("200 OK") jbe@0: jbe@0: if document_extension == "html" then jbe@0: request:send_header("Content-Type", "text/html; charset=UTF-8") jbe@0: elseif document_extension == "css" then jbe@0: request:send_header("Content-Type", "text/css; charset=UTF-8") jbe@0: end jbe@0: request:send_data(document) jbe@0: else jbe@0: request:send_status("404 Not Found") jbe@0: request:send_header("Content-Type", "text/html; chatset=UTF-8") jbe@0: request:send_data("404 Not Found

404 Not Found

") jbe@0: end jbe@0: jbe@0: end jbe@0: jbe@0: elseif request.method == "POST" then jbe@0: jbe@0: if request.path == "/post_example" then jbe@0: local files = {} jbe@0: do jbe@0: local file jbe@0: request:stream_post_param("files", function(chunk, field_name, meta) jbe@0: if meta then jbe@0: file = { jbe@0: file_name = meta.file_name, jbe@0: content_type = meta.content_type, jbe@0: length = 0 jbe@0: } jbe@0: end jbe@0: if chunk then jbe@0: file.length = file.length + #chunk jbe@0: else jbe@0: files[#files+1] = file jbe@0: end jbe@0: end) jbe@0: end jbe@0: jbe@0: request:send_status("200 OK") jbe@0: request:send_header("Content-Type", "text/html; chatset=UTF-8") jbe@0: request:send_data("\n\n") jbe@0: request:send_data('\n') jbe@0: request:send_data("Moonbridge Network Server for Lua Applications – Example Application\n") jbe@0: request:send_data("\n\n") jbe@0: request:send_data("

Moonbridge Network Server for Lua – Example Application

\n") jbe@0: request:send_data("

POST request successful

\n") jbe@0: request:send_data('\n\n\n') jbe@0: for i, file in ipairs(files) do jbe@0: request:send_data("") jbe@0: request:send_data("") jbe@0: request:send_data("") jbe@0: request:send_data('") jbe@0: request:send_data("\n") jbe@0: end jbe@0: request:send_data("\n
File nameContent typeBytes received
", http.encode_html(file.file_name or "(unknown)"), "", http.encode_html(file.content_type or "(unknown)"), "', http.encode_html(tostring(file.length)), "
\n") jbe@0: request:send_data("

Submitted comment: ", http.encode_html(request.post_params.comment), "

\n") jbe@0: request:send_data("\n\n") jbe@0: jbe@0: else jbe@0: request:send_status("404 Not Found") jbe@0: request:send_data("404 Not Found

404 Not Found

") jbe@0: jbe@0: end jbe@0: jbe@0: else jbe@0: request:send_status("405 Method not allowed") jbe@0: jbe@0: end jbe@0: jbe@0: -- returning false causes termination of current process (and re-forking) jbe@0: return true jbe@0: end), jbe@0: jbe@0: -- executed on process termination jbe@0: finish = function() jbe@0: end jbe@0: } jbe@0: