Software /
code /
prosody
Annotate
net/http/parser.lua @ 9340:368b092bf4bf
mod_storage_memory: Fix saving of remaining items during deletion
All data is compiled into functions that return new copies in order to
prevent mutation of stored data.
This has downsides.
Also an ugly hack.
author | Kim Alvefur <zash@zash.se> |
---|---|
date | Sat, 22 Sep 2018 16:03:50 +0200 |
parent | 8045:55a56dc935f2 |
child | 10540:375d31225d53 |
rev | line source |
---|---|
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
1 local tonumber = tonumber; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
2 local assert = assert; |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
3 local t_insert, t_concat = table.insert, table.concat; |
4866
d54999db3aa1
net.http.parser: Do full URL decoding and parsing (e.g. adds request.url.query when present)
Matthew Wild <mwild1@gmail.com>
parents:
4716
diff
changeset
|
4 local url_parse = require "socket.url".parse; |
5460
274c10668fe8
net.http.parser: Depend on util.http instead of net.http for urlencode
Matthew Wild <mwild1@gmail.com>
parents:
5323
diff
changeset
|
5 local urldecode = require "util.http".urldecode; |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
6 |
4716
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
7 local function preprocess_path(path) |
5222
61c47d26481d
net.http.parser: Fix syntax error introduced in c5edb08fc7cb.
Waqas Hussain <waqas20@gmail.com>
parents:
5207
diff
changeset
|
8 path = urldecode((path:gsub("//+", "/"))); |
4716
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
9 if path:sub(1,1) ~= "/" then |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
10 path = "/"..path; |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
11 end |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
12 local level = 0; |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
13 for component in path:gmatch("([^/]+)/") do |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
14 if component == ".." then |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
15 level = level - 1; |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
16 elseif component ~= "." then |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
17 level = level + 1; |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
18 end |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
19 if level < 0 then |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
20 return nil; |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
21 end |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
22 end |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
23 return path; |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
24 end |
6eeb142a8073
mod_http_files, net.http.parser: Move path normalization to net.http.parser so that all modules can benefit
Matthew Wild <mwild1@gmail.com>
parents:
4712
diff
changeset
|
25 |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
26 local httpstream = {}; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
27 |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
28 function httpstream.new(success_cb, error_cb, parser_type, options_cb) |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
29 local client = true; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
30 if not parser_type or parser_type == "server" then client = false; else assert(parser_type == "client", "Invalid parser type"); end |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
31 local buf, buflen, buftable = {}, 0, true; |
7578
65bf55fdf971
net.http.parser: Allow limits to be configurable via options callback
Kim Alvefur <zash@zash.se>
parents:
7577
diff
changeset
|
32 local bodylimit = tonumber(options_cb and options_cb().body_size_limit) or 10*1024*1024; |
65bf55fdf971
net.http.parser: Allow limits to be configurable via options callback
Kim Alvefur <zash@zash.se>
parents:
7577
diff
changeset
|
33 local buflimit = tonumber(options_cb and options_cb().buffer_size_limit) or bodylimit * 2; |
5463
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
34 local chunked, chunk_size, chunk_start; |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
35 local state = nil; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
36 local packet; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
37 local len; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
38 local have_body; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
39 local error; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
40 return { |
7569
a15ce0014ac9
net.http.parser: Remove unused argument [luacheck]
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
41 feed = function(_, data) |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
42 if error then return nil, "parse has failed"; end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
43 if not data then -- EOF |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
44 if buftable then buf, buftable = t_concat(buf), false; end |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
45 if state and client and not len then -- reading client body until EOF |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
46 packet.body = buf; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
47 success_cb(packet); |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
48 elseif buf ~= "" then -- unexpected EOF |
8045
55a56dc935f2
net.http: Pass error all the way to callback
Kim Alvefur <zash@zash.se>
parents:
7635
diff
changeset
|
49 error = true; return error_cb("unexpected-eof"); |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
50 end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
51 return; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
52 end |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
53 if buftable then |
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
54 t_insert(buf, data); |
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
55 else |
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
56 buf = { buf, data }; |
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
57 buftable = true; |
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
58 end |
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
59 buflen = buflen + #data; |
7577
3dc52f1778db
net.http.parser: Add a limit on maximum buffer size, default to 20M
Kim Alvefur <zash@zash.se>
parents:
7576
diff
changeset
|
60 if buflen > buflimit then error = true; return error_cb("max-buffer-size-exceeded"); end |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
61 while buflen > 0 do |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
62 if state == nil then -- read request |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
63 if buftable then buf, buftable = t_concat(buf), false; end |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
64 local index = buf:find("\r\n\r\n", nil, true); |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
65 if not index then return; end -- not enough data |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
66 local method, path, httpversion, status_code, reason_phrase; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
67 local first_line; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
68 local headers = {}; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
69 for line in buf:sub(1,index+1):gmatch("([^\r\n]+)\r\n") do -- parse request |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
70 if first_line then |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
71 local key, val = line:match("^([^%s:]+): *(.*)$"); |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
72 if not key then error = true; return error_cb("invalid-header-line"); end -- TODO handle multi-line and invalid headers |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
73 key = key:lower(); |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
74 headers[key] = headers[key] and headers[key]..","..val or val; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
75 else |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
76 first_line = line; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
77 if client then |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
78 httpversion, status_code, reason_phrase = line:match("^HTTP/(1%.[01]) (%d%d%d) (.*)$"); |
5462
3ecae471d9dd
net.http.parser: Convert status_code to a number before trying to compare it to numbers
Matthew Wild <mwild1@gmail.com>
parents:
5461
diff
changeset
|
79 status_code = tonumber(status_code); |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
80 if not status_code then error = true; return error_cb("invalid-status-line"); end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
81 have_body = not |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
82 ( (options_cb and options_cb().method == "HEAD") |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
83 or (status_code == 204 or status_code == 304 or status_code == 301) |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
84 or (status_code >= 100 and status_code < 200) ); |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
85 else |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
86 method, path, httpversion = line:match("^(%w+) (%S+) HTTP/(1%.[01])$"); |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
87 if not method then error = true; return error_cb("invalid-status-line"); end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
88 end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
89 end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
90 end |
5291
01f7522049fb
net.http.parser: Abort if no status line is received.
Kim Alvefur <zash@zash.se>
parents:
5259
diff
changeset
|
91 if not first_line then error = true; return error_cb("invalid-status-line"); end |
5463
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
92 chunked = have_body and headers["transfer-encoding"] == "chunked"; |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
93 len = tonumber(headers["content-length"]); -- TODO check for invalid len |
7576
d3646443a02e
net.http.parser: Add a limit on content length, default to 10M
Kim Alvefur <zash@zash.se>
parents:
7575
diff
changeset
|
94 if len and len > bodylimit then error = true; return error_cb("content-length-limit-exceeded"); end |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
95 if client then |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
96 -- FIXME handle '100 Continue' response (by skipping it) |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
97 if not have_body then len = 0; end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
98 packet = { |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
99 code = status_code; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
100 httpversion = httpversion; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
101 headers = headers; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
102 body = have_body and "" or nil; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
103 -- COMPAT the properties below are deprecated |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
104 responseversion = httpversion; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
105 responseheaders = headers; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
106 }; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
107 else |
5259
c85c348253bd
net.http.parser: Skip url.parse when we don't have a full URL (also fixes traceback on paths starting with '//').
Waqas Hussain <waqas20@gmail.com>
parents:
5222
diff
changeset
|
108 local parsed_url; |
c85c348253bd
net.http.parser: Skip url.parse when we don't have a full URL (also fixes traceback on paths starting with '//').
Waqas Hussain <waqas20@gmail.com>
parents:
5222
diff
changeset
|
109 if path:byte() == 47 then -- starts with / |
c85c348253bd
net.http.parser: Skip url.parse when we don't have a full URL (also fixes traceback on paths starting with '//').
Waqas Hussain <waqas20@gmail.com>
parents:
5222
diff
changeset
|
110 local _path, _query = path:match("([^?]*).?(.*)"); |
c85c348253bd
net.http.parser: Skip url.parse when we don't have a full URL (also fixes traceback on paths starting with '//').
Waqas Hussain <waqas20@gmail.com>
parents:
5222
diff
changeset
|
111 if _query == "" then _query = nil; end |
c85c348253bd
net.http.parser: Skip url.parse when we don't have a full URL (also fixes traceback on paths starting with '//').
Waqas Hussain <waqas20@gmail.com>
parents:
5222
diff
changeset
|
112 parsed_url = { path = _path, query = _query }; |
c85c348253bd
net.http.parser: Skip url.parse when we don't have a full URL (also fixes traceback on paths starting with '//').
Waqas Hussain <waqas20@gmail.com>
parents:
5222
diff
changeset
|
113 else |
c85c348253bd
net.http.parser: Skip url.parse when we don't have a full URL (also fixes traceback on paths starting with '//').
Waqas Hussain <waqas20@gmail.com>
parents:
5222
diff
changeset
|
114 parsed_url = url_parse(path); |
5323
4c30f638ff55
net.http.parser: Ensure full URL in status line contains a path.
Waqas Hussain <waqas20@gmail.com>
parents:
5322
diff
changeset
|
115 if not(parsed_url and parsed_url.path) then error = true; return error_cb("invalid-url"); end |
5259
c85c348253bd
net.http.parser: Skip url.parse when we don't have a full URL (also fixes traceback on paths starting with '//').
Waqas Hussain <waqas20@gmail.com>
parents:
5222
diff
changeset
|
116 end |
4866
d54999db3aa1
net.http.parser: Do full URL decoding and parsing (e.g. adds request.url.query when present)
Matthew Wild <mwild1@gmail.com>
parents:
4716
diff
changeset
|
117 path = preprocess_path(parsed_url.path); |
4879
45bb378a4a98
net.http.parser: Keep the Host header no host is present in the URI
Kim Alvefur <zash@zash.se>
parents:
4866
diff
changeset
|
118 headers.host = parsed_url.host or headers.host; |
4712
4fc99f1b7570
net.http.parser: Handle full URLs in status line.
Waqas Hussain <waqas20@gmail.com>
parents:
4631
diff
changeset
|
119 |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
120 len = len or 0; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
121 packet = { |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
122 method = method; |
4866
d54999db3aa1
net.http.parser: Do full URL decoding and parsing (e.g. adds request.url.query when present)
Matthew Wild <mwild1@gmail.com>
parents:
4716
diff
changeset
|
123 url = parsed_url; |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
124 path = path; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
125 httpversion = httpversion; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
126 headers = headers; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
127 body = nil; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
128 }; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
129 end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
130 buf = buf:sub(index + 4); |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
131 buflen = #buf; |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
132 state = true; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
133 end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
134 if state then -- read body |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
135 if client then |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
136 if chunked then |
7635
6879a220917b
net.http.parser: Don't collapse buffer when expecting a chunk and not enough data has been received
Kim Alvefur <zash@zash.se>
parents:
7634
diff
changeset
|
137 if chunk_start and buflen - chunk_start - 2 < chunk_size then |
6879a220917b
net.http.parser: Don't collapse buffer when expecting a chunk and not enough data has been received
Kim Alvefur <zash@zash.se>
parents:
7634
diff
changeset
|
138 return; |
6879a220917b
net.http.parser: Don't collapse buffer when expecting a chunk and not enough data has been received
Kim Alvefur <zash@zash.se>
parents:
7634
diff
changeset
|
139 end -- not enough data |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
140 if buftable then buf, buftable = t_concat(buf), false; end |
5463
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
141 if not buf:find("\r\n", nil, true) then |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
142 return; |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
143 end -- not enough data |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
144 if not chunk_size then |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
145 chunk_size, chunk_start = buf:match("^(%x+)[^\r\n]*\r\n()"); |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
146 chunk_size = chunk_size and tonumber(chunk_size, 16); |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
147 if not chunk_size then error = true; return error_cb("invalid-chunk-size"); end |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
148 end |
5463
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
149 if chunk_size == 0 and buf:find("\r\n\r\n", chunk_start-2, true) then |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
150 state, chunk_size = nil, nil; |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
151 buf = buf:gsub("^.-\r\n\r\n", ""); -- This ensure extensions and trailers are stripped |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
152 success_cb(packet); |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
153 elseif buflen - chunk_start - 2 >= chunk_size then -- we have a chunk |
5475
c2c9f07c5d6a
net.http.parser: Fix off-by-one error in chunked encoding parser
Matthew Wild <mwild1@gmail.com>
parents:
5463
diff
changeset
|
154 packet.body = packet.body..buf:sub(chunk_start, chunk_start + (chunk_size-1)); |
5463
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
155 buf = buf:sub(chunk_start + chunk_size + 2); |
7634
b1132d74f54c
net.http.parser: Fix missing buffer length adjustment when parsing chunked streams
Kim Alvefur <zash@zash.se>
parents:
7581
diff
changeset
|
156 buflen = buflen - (chunk_start + chunk_size + 2 - 1); |
5463
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
157 chunk_size, chunk_start = nil, nil; |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
158 else -- Partial chunk remaining |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
159 break; |
111953bfe767
net.http.parser: Fix chunked encoding response parsing, and make it more robust
Matthew Wild <mwild1@gmail.com>
parents:
5462
diff
changeset
|
160 end |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
161 elseif len and buflen >= len then |
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
162 if buftable then buf, buftable = t_concat(buf), false; end |
6523
63d3126b75f1
net.http.parser: Fix whitespace/indentation
Matthew Wild <mwild1@gmail.com>
parents:
6522
diff
changeset
|
163 if packet.code == 101 then |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
164 packet.body, buf, buflen, buftable = buf, {}, 0, true; |
6523
63d3126b75f1
net.http.parser: Fix whitespace/indentation
Matthew Wild <mwild1@gmail.com>
parents:
6522
diff
changeset
|
165 else |
63d3126b75f1
net.http.parser: Fix whitespace/indentation
Matthew Wild <mwild1@gmail.com>
parents:
6522
diff
changeset
|
166 packet.body, buf = buf:sub(1, len), buf:sub(len + 1); |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
167 buflen = #buf; |
6523
63d3126b75f1
net.http.parser: Fix whitespace/indentation
Matthew Wild <mwild1@gmail.com>
parents:
6522
diff
changeset
|
168 end |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
169 state = nil; success_cb(packet); |
5461
67b674f6a299
net.http.parser: Break when no more usable data in buffer (client part of e5ec60dfb202)
Matthew Wild <mwild1@gmail.com>
parents:
5460
diff
changeset
|
170 else |
67b674f6a299
net.http.parser: Break when no more usable data in buffer (client part of e5ec60dfb202)
Matthew Wild <mwild1@gmail.com>
parents:
5460
diff
changeset
|
171 break; |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
172 end |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
173 elseif buflen >= len then |
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
174 if buftable then buf, buftable = t_concat(buf), false; end |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
175 packet.body, buf = buf:sub(1, len), buf:sub(len + 1); |
7575
3ae247af68f4
net.http.parser: Buffer into a table to reduce GC pressure, collapse to string when needed (fixes #603)
Kim Alvefur <zash@zash.se>
parents:
6523
diff
changeset
|
176 buflen = #buf; |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
177 state = nil; success_cb(packet); |
4910
e5ec60dfb202
net.http.parser: Break loop when no more usable data in buffer
Matthew Wild <mwild1@gmail.com>
parents:
4879
diff
changeset
|
178 else |
e5ec60dfb202
net.http.parser: Break loop when no more usable data in buffer
Matthew Wild <mwild1@gmail.com>
parents:
4879
diff
changeset
|
179 break; |
4631
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
180 end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
181 end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
182 end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
183 end; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
184 }; |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
185 end |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
186 |
fc5d3b053454
net.http.{server|codes|parser}: Initial commit.
Waqas Hussain <waqas20@gmail.com>
parents:
diff
changeset
|
187 return httpstream; |