Skip to content

Commit c7e4958

Browse files
committed
Revert to buffered response
The http handler closes the requests body after the first response flush. Ideally it won't close the request body and after each request body line read we will write a response in a streaming fashion, thus not consuming tons of RAM. This will result in "Transfer-Encoding: chunked" instead of buffering the response and sending "Content-Length: XXX".
1 parent 93342dc commit c7e4958

File tree

1 file changed

+34
-33
lines changed

1 file changed

+34
-33
lines changed

main.go

Lines changed: 34 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,7 @@ func main() {
7575

7676
func query(w http.ResponseWriter, r *http.Request) {
7777
w.Header().Set("Server", "SQLiteQueryServer v"+version)
78+
// w.Header().Set("X-Content-Type-Options", "nosniff") // prevent browsers from doing MIME-type sniffing
7879

7980
if r.URL.Path != "/query" {
8081
http.Error(w, helpMessage, http.StatusNotFound)
@@ -85,18 +86,18 @@ func query(w http.ResponseWriter, r *http.Request) {
8586
return
8687
}
8788

88-
wFlusher, ok := w.(http.Flusher)
89-
if !ok {
90-
http.Error(w,
91-
fmt.Sprintf("Error creating a stream writer.\n\n%s", helpMessage), http.StatusInternalServerError)
92-
return
93-
}
89+
// wFlusher, ok := w.(http.Flusher)
90+
// if !ok {
91+
// http.Error(w,
92+
// fmt.Sprintf("Error creating a stream writer.\n\n%s", helpMessage), http.StatusInternalServerError)
93+
// return
94+
// }
9495

9596
w.Header().Set("Content-Type", "application/json")
9697
outpoutEncoder := json.NewEncoder(w)
9798
// start printing the outer array
9899
fmt.Fprintf(w, "[")
99-
wFlusher.Flush()
100+
// wFlusher.Flush()
100101

101102
reqCsvReader := csv.NewReader(r.Body)
102103
reqCsvReader.ReuseRecord = true
@@ -116,7 +117,7 @@ func query(w http.ResponseWriter, r *http.Request) {
116117
if !isFirstQuery {
117118
// print comma between queries results
118119
fmt.Fprintf(w, ",")
119-
wFlusher.Flush()
120+
// wFlusher.Flush()
120121
}
121122
isFirstQuery = false
122123

@@ -147,14 +148,14 @@ func query(w http.ResponseWriter, r *http.Request) {
147148
fmt.Fprintf(w, `"headers":`)
148149
outpoutEncoder.Encode(cols)
149150
fmt.Fprintf(w, `,"out":[`) // start printing the out rows array
150-
wFlusher.Flush()
151+
// wFlusher.Flush()
151152

152153
isFirstRow := true
153154
for rows.Next() {
154155
if !isFirstRow {
155156
// print comma between rows
156157
fmt.Fprintf(w, ",")
157-
wFlusher.Flush()
158+
// wFlusher.Flush()
158159
}
159160
isFirstRow = false
160161

@@ -184,33 +185,12 @@ func query(w http.ResponseWriter, r *http.Request) {
184185

185186
// finish printing a query result
186187
fmt.Fprintf(w, "]}")
187-
wFlusher.Flush()
188+
// wFlusher.Flush()
188189
}
189190

190191
// finish printing the outer array
191192
fmt.Fprintf(w, "]\n")
192-
wFlusher.Flush()
193-
}
194-
195-
func countParams() int {
196-
rows, err := queryStmt.Query()
197-
if err != nil {
198-
regex := regexp.MustCompile(`sql: expected (\d+) arguments, got 0`)
199-
regexSubmatches := regex.FindAllStringSubmatch(err.Error(), 1)
200-
if len(regexSubmatches) != 1 || len(regexSubmatches[0]) != 2 {
201-
// this is weird, return best guess
202-
return strings.Count(queryString, "?")
203-
}
204-
count, err := strconv.Atoi(regexSubmatches[0][1])
205-
if err != nil {
206-
// this is weirder because the regex is \d+
207-
// return best guess
208-
return strings.Count(queryString, "?")
209-
}
210-
return count
211-
}
212-
rows.Close()
213-
return 0
193+
// wFlusher.Flush()
214194
}
215195

216196
func buildHelpMessage() {
@@ -273,3 +253,24 @@ func buildHelpMessage() {
273253
- Element #1 is the result of query #1, Element #2 is the result of query #2, and so forth.
274254
`, serverPort)
275255
}
256+
257+
func countParams() int {
258+
rows, err := queryStmt.Query()
259+
if err != nil {
260+
regex := regexp.MustCompile(`sql: expected (\d+) arguments, got 0`)
261+
regexSubmatches := regex.FindAllStringSubmatch(err.Error(), 1)
262+
if len(regexSubmatches) != 1 || len(regexSubmatches[0]) != 2 {
263+
// this is weird, return best guess
264+
return strings.Count(queryString, "?")
265+
}
266+
count, err := strconv.Atoi(regexSubmatches[0][1])
267+
if err != nil {
268+
// this is weirder because the regex is \d+
269+
// return best guess
270+
return strings.Count(queryString, "?")
271+
}
272+
return count
273+
}
274+
rows.Close()
275+
return 0
276+
}

0 commit comments

Comments
 (0)