nitcorn :: HttpResponse :: defaultinit
# A response to send over HTTP
class HttpResponse
serialize
# HTTP protocol version
var http_version = "HTTP/1.0" is writable
# Status code of this response (200, 404, etc.)
var status_code: Int is writable
# Return the message associated to `status_code`
fun status_message: nullable String do return http_status_codes[status_code]
# Headers of this response as a `Map`
var header = new HashMap[String, String]
# Body of this response
var body: Writable = "" is writable
# Files appended after `body`
var files = new Array[String]
# Finalize this response before sending it over HTTP
fun finalize
do
# Set the content length if not already set
if not header.keys.has("Content-Length") then
# Size of the body
var len
var body = self.body
if body isa Text then
len = body.byte_length
else if body isa Bytes then
len = body.length
else
# We need the length, but there is no length in a writable.
# So just render it as a bytes then measure :/
body = body.write_to_bytes
len = body.length
# Keep the body as bytes since we have it
self.body = body
end
# Size of included files
for path in files do
# TODO handle these error cases elsewhere, an error here will result in an invalid response
if not path.file_exists then
print_error "File does not exists at '{path}'"
continue
end
var stat = path.file_stat
if stat == null then
print_error "Failed to stat file at '{path}'"
continue
end
len += stat.size
end
# Set header
header["Content-Length"] = len.to_s
end
# Set server ID
if not header.keys.has("Server") then header["Server"] = "nitcorn"
end
# Get this reponse as a string according to HTTP protocol
fun render: Writable
do
finalize
var buf = new Template
buf.add("{http_version} {status_code} {status_message or else ""}\r\n")
for key, value in header do
buf.add("{key}: {value}\r\n")
end
buf.add("\r\n")
buf.add body
return buf
end
end
lib/nitcorn/http_response.nit:25,1--107,3