Can you give an example of usage of this tool?
If you mean code, sure. This is all copied directly from the tool itself, just go to Tools >> Start Server to see it live.
Basics
Getting Started
– contains all the basic HTTP stuff
require(“request-http”)
– takes a host and port as arguments
local server = HTTPServer(“localhost”, 80)
– add a basic index page
server.router:get(“/”, function(request, response)
response:send_html(200, “Hello, world!”)
– let the router know the chain ended here; we already sent a response
return true
end)
– start the server
server:start()
– stop the server (once you’re done)
server:stop()
Parameterized Routing
– see Lua patterns for more information
server.router:get(“/(.*)”, function(request, response, params)
response:send_html(200, “The URL is: /” … params[1])
return true
end)
Forms
– this is our form
server.router:get(“/form”, function(request, response)
local content =
“<form method="post" action="/form">” …
“Content to POST:
” …
“<input type="text" name="message" /> <input type="submit" />” …
“”
response:send_html(200, content)
return true
end)
– and this is our processor for it
server.router:post(“/form”, function(request, response)
if request.form_data[“message”] ~= nil then
response:send_html(200, "You sent: " … request.form_data[“message”])
end
return true
end)
File Forms
– this is our form
server.router:get(“/form”, function(request, response)
local content =
“<form method="post" action="/form" enctype="multipart/form-data" >” …
“Content to POST:
” …
“<input type="file" name="files" multiple /> <input type="submit" />” …
“”
response:send_html(200, content)
return true
end)
– and this is our processor for it
server.router:post(“/form”, function(request, response)
local content = “”
for filename, contents in pairs(request.form_data[“files”]) do
local file = io.open (“uploads/” … filename, “wb”)
file:write(contents)
file:close()
content = content … filename … " uploaded!
"
end
response:send_html(200, content)
return true
end)
Middleware
Custom
server.router:use(function (request, response)
print(request.resource)
– note: it doesn’t return true, as it only does some processing
end)
– a pattern can also be specified
server.router:use(“/”, function (request, response)
print(request.resource)
end)
Packaged Middleware
– middleware is contained in the request-middleware module
require(“request-middleware”)
Static Files
– serves static files from a specific directory
– should probably be added LAST in the routing chain
– in case a matching file is not found, a callback should be specified
function file_not_found(request, response)
response:send_html(404, “No such file exists.”)
return true
end
server.router:use(static(“www”, file_not_found))
Cookies
– contains UTC timestamp() function useful for cookies
require(“request-utils”)
– parses and stores cookies in a newly-created request.cookies table
– also adds response:set_cookie(name, content, expiry)
server.router:use(cookies())
server.router:get(“/cookie”, function (request, response)
local content = “”
if request.cookies[“message”] ~= nil then
content = content … "Cookie contains: " … request.cookies[“message”] … “<br /<”
end
content = content …
“<form method="post" action="/cookie">” …
“Set cookie to:
” …
“<input type="text" name="message" /> <input type="submit" />” …
“”
response:send_html(200, content)
return true
end)
server.router:post(“/cookie”, function (request, response)
if request.form_data[“message”] ~= nil then
response:set_cookie(“message”, request.form_data[“message”], timestamp() + 60)
end
response:send_html(200, “Cookie set!”)
return true
end)
WebSockets
– adds request:websocket_requested()
– also adds response:open_websocket(handler) which returns a WebSocketClient instance
– see request-websocket-utils for more info on WebSocketClient
server.router:use(websockets())
server.router:get(“/websocket”, function(request, response)
– a basic echo server handler
local echo_server = {
[“on_open”] =
function(websocket)
print(websocket.id, “connected! :)”)
end,
[“on_message”] =
function(websocket, opcode, message)
– first argument is the FIN bit
– it indicates that this message is complete - not fragmented
websocket:send(1, opcode, message)
end,
[“on_close”] =
function(websocket)
print(websocket.id, “disconnected! :(”)
end
}
if request:websocket_requested() then
local client = response:open_websocket(echo_server)
else
response:send_html(403, “WebSocket clients only.”)
end
return true
end)
If you mean “how can this be used to make neat tools,” then here are some examples:
- You can combine it with an OSC server to send note ons and note offs from HTML5 canvas (neat procedural music).
- You can develop a protocol on top of WebSockets to allow real-time editing from multiple computers; even phones.
- That can also be used remotely for collaborative work, though there will be latency outside of your LAN.
- HTML5 isn’t restricting about what you can do, GUI wise. A formal piano roll is entirely possible with this library.
- Not limited to this library, but with Renoise’s delay column it’s likely possible to support different BPMs for each track.
You’d need a strong GUI to keep that usable though.
Just some thoughts. I’ll probably be taking on a few myself after a short break.