1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109
|
--[[
This module implements an error object that can encapsulate the data required of an HTTP2 error.
This data is:
- the error 'name'
- the error 'code'
- the error 'description'
- an optional error message
Additionally, there is a field for a traceback.
]]
local errors = {}
local http_error_methods = {}
local http_error_mt = {
__name = "http.h2_error";
__index = http_error_methods;
}
function http_error_mt:__tostring()
local s = string.format("%s(0x%x): %s", self.name, self.code, self.description)
if self.message then
s = s .. ": " .. self.message
end
if self.traceback then
s = s .. "\n" .. self.traceback
end
return s
end
function http_error_methods:new(ob)
return setmetatable({
name = ob.name or self.name;
code = ob.code or self.code;
description = ob.description or self.description;
message = ob.message;
traceback = ob.traceback;
stream_error = ob.stream_error or false;
}, http_error_mt)
end
function http_error_methods:new_traceback(message, stream_error, lvl)
if lvl == nil then
lvl = 2
elseif lvl ~= 0 then
lvl = lvl + 1
end
local e = {
message = message;
stream_error = stream_error;
}
if lvl ~= 0 then
-- COMPAT: should be passing `nil` message (not the empty string)
-- see https://github.com/keplerproject/lua-compat-5.3/issues/16
e.traceback = debug.traceback("", lvl)
end
return self:new(e)
end
function http_error_methods:error(...)
error(self:new_traceback(...), 0)
end
http_error_mt.__call = http_error_methods.error
function http_error_methods:assert(cond, ...)
if cond then
return cond, ...
else
local message = ...
self:error(message, 2)
-- don't tail call, as error levels aren't well defined
end
end
local function is(ob)
return getmetatable(ob) == http_error_mt
end
local function add_error(name, code, description)
local e = setmetatable({
name = name;
code = code;
description = description;
}, http_error_mt)
errors[name] = e
errors[code] = e
end
-- Taken from https://http2.github.io/http2-spec/#iana-errors
add_error("NO_ERROR", 0x0, "Graceful shutdown")
add_error("PROTOCOL_ERROR", 0x1, "Protocol error detected")
add_error("INTERNAL_ERROR", 0x2, "Implementation fault")
add_error("FLOW_CONTROL_ERROR", 0x3, "Flow control limits exceeded")
add_error("SETTINGS_TIMEOUT", 0x4, "Settings not acknowledged")
add_error("STREAM_CLOSED", 0x5, "Frame received for closed stream")
add_error("FRAME_SIZE_ERROR", 0x6, "Frame size incorrect")
add_error("REFUSED_STREAM", 0x7, "Stream not processed")
add_error("CANCEL", 0x8, "Stream cancelled")
add_error("COMPRESSION_ERROR", 0x9, "Compression state not updated")
add_error("CONNECT_ERROR", 0xa, "TCP connection error for CONNECT method")
add_error("ENHANCE_YOUR_CALM", 0xb, "Processing capacity exceeded")
add_error("INADEQUATE_SECURITY", 0xc, "Negotiated TLS parameters not acceptable")
add_error("HTTP_1_1_REQUIRED", 0xd, "Use HTTP/1.1 for the request")
return {
errors = errors;
is = is;
}
|