moonbridge

diff moonbridge_http.lua @ 203:a1907691f740

Fixes to timeout system in HTTP module
author jbe
date Sun Jun 21 02:42:27 2015 +0200 (2015-06-21)
parents 2ed3d94a0eb7
children 7d1cda1ed530
line diff
     1.1 --- a/moonbridge_http.lua	Sun Jun 21 02:05:24 2015 +0200
     1.2 +++ b/moonbridge_http.lua	Sun Jun 21 02:42:27 2015 +0200
     1.3 @@ -231,21 +231,6 @@
     1.4          end
     1.5        end
     1.6      end
     1.7 -    -- function that enforces consumption of all input:
     1.8 -    local function consume_all(timeout)
     1.9 -      local starttime = timeout and moonbridge_io.timeref()
    1.10 -      while consume do
    1.11 -        if timeout then
    1.12 -          if not poll(socket_set, nil, timeout-moonbridge_io.timeref(starttime)) then
    1.13 -            return false
    1.14 -          end
    1.15 -        else
    1.16 -          poll(socket_set, nil)
    1.17 -        end
    1.18 -        consume()
    1.19 -        return true
    1.20 -      end
    1.21 -    end
    1.22      -- handle requests in a loop:
    1.23      repeat
    1.24        -- table for caching nil values:
    1.25 @@ -375,6 +360,60 @@
    1.26        local chunk_bytes = 0          -- sum of lengths of chunks to send
    1.27        local streamed_post_params         = {}  -- mapping from POST field name to stream function
    1.28        local streamed_post_param_patterns = {}  -- list of POST field pattern and stream function pairs
    1.29 +      -- function to report an error:
    1.30 +      local function request_error(throw_error, status, text)
    1.31 +        if
    1.32 +          state == "init" or
    1.33 +          state == "no_status_sent" or
    1.34 +          state == "info_status_sent"
    1.35 +        then
    1.36 +          local error_response_status, errmsg = pcall(function()
    1.37 +            request:monologue()
    1.38 +            request:send_status(status)
    1.39 +            request:send_header("Content-Type", "text/plain")
    1.40 +            request:send_data(status, "\n")
    1.41 +            if text then
    1.42 +              request:send_data("\n", text, "\n")
    1.43 +            end
    1.44 +            request:finish()
    1.45 +          end)
    1.46 +          if not error_response_status then
    1.47 +            if text then
    1.48 +              error("Error while sending error response (" .. status .. " / " .. text .. "): " .. errmsg)
    1.49 +            else
    1.50 +              error("Error while sending error response (" .. status .. "): " .. errmsg)
    1.51 +            end
    1.52 +          end
    1.53 +        end
    1.54 +        if throw_error then
    1.55 +          local errmsg = "Error while reading request from client. Error response: " .. status
    1.56 +          if text then
    1.57 +            errmsg = errmsg .. " (" .. text .. ")"
    1.58 +          end
    1.59 +          error(errmsg)
    1.60 +        else
    1.61 +          return survive
    1.62 +        end
    1.63 +      end
    1.64 +      -- function that enforces consumption of all input:
    1.65 +      local function consume_all(timeout)
    1.66 +        local starttime = timeout and moonbridge_io.timeref()
    1.67 +        while consume do
    1.68 +          if timeout then
    1.69 +            -- passed timeout does not get reset but refers to starttime
    1.70 +            if not poll(socket_set, nil, timeout-moonbridge_io.timeref(starttime)) then
    1.71 +              return false
    1.72 +            end
    1.73 +          else
    1.74 +            -- stall_timeout gets reset for every poll
    1.75 +            if not poll(socket_set, nil, stall_timeout) then
    1.76 +              request_error(true, "408 Request Timeout", "Timeout while waiting for request body")
    1.77 +            end
    1.78 +          end
    1.79 +          consume()
    1.80 +        end
    1.81 +        return true
    1.82 +      end
    1.83        -- function to assert non-faulty handle:
    1.84        local function assert_not_faulty()
    1.85          assert(state ~= "faulty", "Tried to use faulty request handle")
    1.86 @@ -439,41 +478,6 @@
    1.87            state = old_state
    1.88          end
    1.89        end
    1.90 -      -- function to report an error:
    1.91 -      local function request_error(throw_error, status, text)
    1.92 -        if
    1.93 -          state == "init" or
    1.94 -          state == "no_status_sent" or
    1.95 -          state == "info_status_sent"
    1.96 -        then
    1.97 -          local error_response_status, errmsg = pcall(function()
    1.98 -            request:monologue()
    1.99 -            request:send_status(status)
   1.100 -            request:send_header("Content-Type", "text/plain")
   1.101 -            request:send_data(status, "\n")
   1.102 -            if text then
   1.103 -              request:send_data("\n", text, "\n")
   1.104 -            end
   1.105 -            request:finish()
   1.106 -          end)
   1.107 -          if not error_response_status then
   1.108 -            if text then
   1.109 -              error("Error while sending error response (" .. status .. " / " .. text .. "): " .. errmsg)
   1.110 -            else
   1.111 -              error("Error while sending error response (" .. status .. "): " .. errmsg)
   1.112 -            end
   1.113 -          end
   1.114 -        end
   1.115 -        if throw_error then
   1.116 -          local errmsg = "Error while reading request from client. Error response: " .. status
   1.117 -          if text then
   1.118 -            errmsg = errmsg .. " (" .. text .. ")"
   1.119 -          end
   1.120 -          error(errmsg)
   1.121 -        else
   1.122 -          return survive
   1.123 -        end
   1.124 -      end
   1.125        -- read functions
   1.126        local function read(...)
   1.127          local data, status = socket:read_yield(...)

Impressum / About Us