src/echo.bend
emerging-ezhttp@0.21.0.0 · 141 lines · 17 definitions
1
2
3
4
5
6import Base
7import emerging-ezhttp@0.21.0.0/src/http.bend as Http
8import emerging-ezhttp@0.21.0.0/src/qs.bend as Qs
9
10
11def wsp(+c: Char) -> Bool:
12 Bool.or(Char.is_eq(c, ' '), Char.is_eq(c, '\t'))
13
14
15
16def wsp.lead.if(t: String, +h: Char, space: Bool, rest: Unit -> String)
17 -> String:
18 match space:
19 case True{}:
20 rest(Unit{})
21 case False{}:
22 SCon{h, t}
23
24
25def wsp.lead(s: String) -> String:
26 match s:
27 case SNil{}:
28 SNil{}
29 case SCon{+h, +t}:
30 wsp.lead.if(t, h, wsp(h), _u => wsp.lead(t))
31
32
33def wsp.trim(s: String) -> String:
34 String.reverse(wsp.lead(String.reverse(wsp.lead(s))))
35
36
37def pair.named(+name: String, value: String, empty: Bool) -> Maybe<&2, Qs.Kv()>:
38 match empty:
39 case True{}:
40 None{}
41 case False{}:
42 Some{(name, value)}
43
44
45
46
47def pair.cut(m: Maybe<&2, Qs.Kv()>) -> Maybe<&2, Qs.Kv()>:
48 match m:
49 case None{}:
50 None{}
51 case Some{(before, after)}:
52 +name = wsp.trim(before)
53 pair.named(name, wsp.trim(after), String.is_empty(name))
54
55
56
57def pair(line: String) -> Maybe<&2, Qs.Kv()>:
58 pair.cut(Qs.cut(Http.first(String.split(line, ';'))))
59
60
61
62
63def put.at(key: String, old: String, value: String, t: List<&2, Qs.Kv()>,
64 hit: Bool, rest: Unit -> List<&2, Qs.Kv()>) -> List<&2, Qs.Kv()>:
65 match hit:
66 case True{}:
67 (key, value) <> t
68 case False{}:
69 (key, old) <> rest(Unit{})
70
71
72
73
74def put(jar: List<&2, Qs.Kv()>, +name: String, +value: String)
75 -> List<&2, Qs.Kv()>:
76 match jar:
77 case []:
78 [(name, value)]
79 case (+key, old) <> +t:
80 put.at(key, old, value, t, String.eq(key, name),
81 _u => put(t, name, value))
82
83
84def add(jar: List<&2, Qs.Kv()>, m: Maybe<&2, Qs.Kv()>) -> List<&2, Qs.Kv()>:
85 match m:
86 case None{}:
87 jar
88 case Some{(name, value)}:
89 put(jar, name, value)
90
91
92def store(lines: List<&2, String>, jar: List<&2, Qs.Kv()>)
93 -> List<&2, Qs.Kv()>:
94 match lines:
95 case []:
96 jar
97 case l <> t:
98 store(t, add(jar, pair(l)))
99
100
101def one(name: String, value: String) -> String:
102 name ++ "=" ++ value
103
104
105def more(jar: List<&2, Qs.Kv()>) -> String:
106 match jar:
107 case []:
108 ""
109 case (name, value) <> t:
110 "; " ++ one(name, value) ++ more(t)
111
112
113def line(jar: List<&2, Qs.Kv()>) -> String:
114 match jar:
115 case []:
116 ""
117 case (name, value) <> t:
118 one(name, value) ++ more(t)
119
120
121def echo(lines: List<&2, String>) -> String:
122 line(store(lines, []))
123
124
125def values.put(value: String, rest: List<&2, String>, hit: Bool)
126 -> List<&2, String>:
127 match hit:
128 case True{}:
129 value <> rest
130 case False{}:
131 rest
132
133
134
135def values(hs: List<&2, Http.Header>) -> List<&2, String>:
136 match hs:
137 case []:
138 []
139 case Http.H{name, value} <> t:
140 values.put(value, values(t), String.eq(String.to_lower(name),
141 "set-cookie"))