11package weblink ;
22
3- import haxe .ds .StringMap ;
43import haxe .http .HttpMethod ;
54import haxe .io .Bytes ;
65import weblink ._internal .Server ;
6+ import weblink .http .HeaderMap ;
7+ import weblink .http .HeaderName ;
8+ import weblink .http .HeaderValue ;
9+
10+ using StringTools ;
711
812class Request {
913 public var cookies : List <Cookie >;
1014 public var path : String ;
1115 public var basePath : String ;
16+
1217 /** Contains values for parameters declared in the route matched, if there are any. **/
1318 public var routeParams : Map <String , String >;
19+
1420 public var ip : String ;
1521 public var baseUrl : String ;
16- public var headers : StringMap < String > ;
22+ public final headers : HeaderMap ;
1723 public var text : String ;
1824 public var method : HttpMethod ;
1925 public var data : Bytes ;
@@ -22,15 +28,13 @@ class Request {
2228
2329 var chunkSize : Null <Int >;
2430
25- public var encoding : Array <String > = [] ;
31+ public final encoding : Array <String >;
2632
2733 var pos : Int ;
2834
2935 private function new (lines : Array <String >) {
30- headers = new StringMap <String >();
3136 data = null ;
32- // for (line in lines)
33- // Sys.println(line);
37+
3438 if (lines .length == 0 )
3539 return ;
3640 var index = 0 ;
@@ -42,39 +46,70 @@ class Request {
4246 if (index2 == - 1 )
4347 index2 = index3 ;
4448 if (index2 != - 1 ) {
45- basePath = path .substr (0 ,index2 );
46- }else {
49+ basePath = path .substr (0 , index2 );
50+ } else {
4751 basePath = path ;
4852 }
49- // trace(basePath);
50- // trace(path);
51- // trace(first.substring(0, index - 1).toUpperCase());
53+
5254 method = first .substring (0 , index - 1 ).toUpperCase ();
55+
56+ final headers = this .headers = new HeaderMap ();
5357 for (i in 0 ... lines .length - 1 ) {
5458 if (lines [i ] == " " ) {
5559 lines = lines .slice (i + 1 );
5660 break ;
5761 }
5862 index = lines [i ].indexOf (" :" );
59- headers .set (lines [i ].substring (0 , index ), lines [i ].substring (index + 2 ));
63+
64+ final left = lines [i ].substring (0 , index );
65+ switch (HeaderName .tryNormalizeString (left )) {
66+ case Valid (name ):
67+ final right = lines [i ].substring (index + 2 ).trim ();
68+ switch (HeaderValue .validateString (right , false )) {
69+ case Valid (value ):
70+ if (name .allowsRawCommaSeparatedValues ()) {
71+ for (subvalue in value .split (" ," ).map (v -> v .trim ())) {
72+ headers .add (name , cast subvalue );
73+ }
74+ } else if (name .allowsRawSemicolonSeparatedValues ()) {
75+ for (subvalue in value .split (" ;" ).map (v -> v .trim ())) {
76+ headers .add (name , cast subvalue );
77+ }
78+ } else if (name .doesNotAllowRepeats () && headers .exists (name )) {
79+ // Idea: respond with 400 Bad Request
80+ headers .set (name , value );
81+ } else {
82+ headers .add (name , value );
83+ }
84+ case _ :
85+ // Silently ignore that the header value is invalid
86+ // Idea: respond with 400 Bad Request immediately
87+ }
88+ case _ :
89+ // Silently ignore that the header name is invalid
90+ // Idea: respond with 400 Bad Request immediately
91+ }
6092 }
61- baseUrl = headers .get (" Host" );
6293
63- if (headers .exists (" Cookie" )) {
64- cookies = new List <Cookie >();
65- var string = headers .get (" Cookie" );
94+ this .baseUrl = headers .get (Host );
6695
67- for (sub in string .split (" ;" )) {
68- string = StringTools .trim (sub );
69- // Split into the component Keyvalue pair for the cookie.
70- var keyVal = string .split (" =" );
71- cookies .add (new Cookie (keyVal [0 ], keyVal [1 ]));
96+ this .cookies = new List <Cookie >();
97+ final cookieValues = headers .getAll (Cookie );
98+ if (cookieValues != null ) {
99+ for (value in cookieValues ) {
100+ final parts = value .split (" =" );
101+ this .cookies .add (new Cookie (parts [0 ], parts [1 ]));
72102 }
73103 }
74104
75- if (headers .exists (" Transfer-Encoding" )) {
76- encoding = headers .get (" Transfer-Encoding" ).split (" ," );
105+ this .encoding = [];
106+ final encodingValues = headers .getAll (TransferEncoding );
107+ if (encodingValues != null ) {
108+ for (value in encodingValues ) {
109+ this .encoding .push (value );
110+ }
77111 }
112+
78113 if (method == Post || method == Put ) {
79114 chunked = false ;
80115 if (encoding .indexOf (" chunked" ) > - 1 ) {
0 commit comments