Подтвердить что ты не робот

Целесообразно ли (далее) ограничить размер форм при использовании golang?

Я искал вокруг и, насколько я могу судить, запросы формы POST уже ограничены 10 МБ (http://golang.org/src/net/http/request.go#L721).

Если бы мне пришлось уменьшить это в моем методе ServeHTTP, я не уверен, как правильно это сделать. Я бы попробовал что-то вроде этого:

r.Body = http.MaxBytesReader(w, r.Body, MaxFileSize) 
err := r.ParseForm()
if err != nil {
     //redirect to some error page
     return
}

Но вернется ли ошибка при закрытии соединения? Как я мог бы запретить читать все? Я нашел это: qaru.site/info/414738/..., но что, если длина контента не установлена ​​и в середине чтения я понимаю, что файл слишком большой.

Я использую это как меру безопасности, чтобы не допустить, чтобы кто-то задерживал мои серверные ресурсы.

4b9b3361

Ответ 1

Правильный способ ограничить размер тела запроса заключается в том, чтобы сделать то, что вы предложили:

r.Body = http.MaxBytesReader(w, r.Body, MaxFileSize) 
err := r.ParseForm()
if err != nil {
 // redirect or set error status code.
 return
}

MaxBytesReader устанавливает флаг в ответе, когда предел достигнут. Когда этот флаг установлен, сервер не считывает оставшуюся часть тела запроса, и сервер закрывает соединение при возврате из обработчика.

Если вас беспокоят вредоносные клиенты, вы также должны установить Server.ReadTimeout, Server.WriteTimeout и, возможно, Server.MaxHeaderBytes.

Если вы хотите установить ограничение тела запроса для всех ваших обработчиков, тогда оберните обработчик root обработчиком, который устанавливает предел перед делегированием корневому обработчику:

 type maxBytesHandler struct {
     h http.Handler
     n int64
 }

 func (h *maxBytesHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
     r.Body = http.MaxBytesReader(w, r.Body, h.n) 
     h.h.ServeHTTP(w, r)
 }

Оберните обработчик root при вызове ListenAndServe:

log.Fatal(http.ListenAndServe(":8080", &maxBytesHandler{h:mux, n:4096))

или при настройке сервера:

s := http.Server{
    Addr: ":8080",
    Handler: &maxBytesReader{h:mux, n:4096},
}
log.Fatal(s.ListenAndServe())

В другом ответе нет необходимости в патче. MaxBytesReader является официальным способом ограничения размера тела запроса.

Ответ 2

Изменить: как указывали другие, MaxByteReader поддерживается. Интересно, что вместо этого используется читатель по умолчанию, limitreader после утверждения типа для максимального байтового считывателя.

Добавить патч к исходному коду Go и настроить его! В конце концов, вы работаете с проектом с открытым исходным кодом. Добавление сеттера в http.Request и некоторые модульные тесты для него - это, вероятно, всего 20 минут работы. Имея твердое значение здесь немного неудобно, верните его и исправьте:).

Вы можете, конечно, реализовать свой собственный метод ParseForm(r *http.Request), если вам действительно нужно переопределить это. Go - это, по сути, BSD, поэтому вы можете скопировать вставку библиотеки ParseForm и изменить предел, но это немного уродливое нет?