diff options
author | Frédéric Guillot <fred@miniflux.net> | 2018-04-29 16:35:04 -0700 |
---|---|---|
committer | Frédéric Guillot <fred@miniflux.net> | 2018-04-29 16:35:04 -0700 |
commit | f49b42f70f902d4da1e0fa4080e99164b331b716 (patch) | |
tree | c6bdd19f11d100c44b0d30344ec37038f649e988 /http/response | |
parent | 1eba1730d1af50ed545f4fde78b22d6fb62ca11e (diff) |
Use vanilla HTTP handlers (refactoring)
Diffstat (limited to 'http/response')
-rw-r--r-- | http/response/html/html.go | 57 | ||||
-rw-r--r-- | http/response/json/json.go | 107 | ||||
-rw-r--r-- | http/response/response.go | 34 | ||||
-rw-r--r-- | http/response/xml/xml.go | 23 |
4 files changed, 221 insertions, 0 deletions
diff --git a/http/response/html/html.go b/http/response/html/html.go new file mode 100644 index 0000000..4f605e8 --- /dev/null +++ b/http/response/html/html.go @@ -0,0 +1,57 @@ +// Copyright 2018 Frédéric Guillot. All rights reserved. +// Use of this source code is governed by the Apache 2.0 +// license that can be found in the LICENSE file. + +package html + +import ( + "net/http" + + "github.com/miniflux/miniflux/logger" +) + +// OK writes a standard HTML response. +func OK(w http.ResponseWriter, b []byte) { + w.Header().Set("Content-Type", "text/html; charset=utf-8") + w.Write(b) +} + +// ServerError sends a 500 error to the browser. +func ServerError(w http.ResponseWriter, err error) { + w.Header().Set("Content-Type", "text/plain; charset=utf-8") + w.WriteHeader(http.StatusInternalServerError) + + if err != nil { + logger.Error("[Internal Server Error] %v", err) + w.Write([]byte("Internal Server Error: " + err.Error())) + } else { + w.Write([]byte("Internal Server Error")) + } +} + +// BadRequest sends a 400 error to the browser. +func BadRequest(w http.ResponseWriter, err error) { + w.Header().Set("Content-Type", "text/plain; charset=utf-8") + w.WriteHeader(http.StatusBadRequest) + + if err != nil { + logger.Error("[Bad Request] %v", err) + w.Write([]byte("Bad Request: " + err.Error())) + } else { + w.Write([]byte("Bad Request")) + } +} + +// NotFound sends a 404 error to the browser. +func NotFound(w http.ResponseWriter) { + w.Header().Set("Content-Type", "text/plain; charset=utf-8") + w.WriteHeader(http.StatusNotFound) + w.Write([]byte("Page Not Found")) +} + +// Forbidden sends a 403 error to the browser. +func Forbidden(w http.ResponseWriter) { + w.Header().Set("Content-Type", "text/plain; charset=utf-8") + w.WriteHeader(http.StatusForbidden) + w.Write([]byte("Access Forbidden")) +} diff --git a/http/response/json/json.go b/http/response/json/json.go new file mode 100644 index 0000000..ff0f06b --- /dev/null +++ b/http/response/json/json.go @@ -0,0 +1,107 @@ +// Copyright 2018 Frédéric Guillot. All rights reserved. +// Use of this source code is governed by the Apache 2.0 +// license that can be found in the LICENSE file. + +package json + +import ( + "encoding/json" + "errors" + "net/http" + + "github.com/miniflux/miniflux/logger" +) + +// OK sends a JSON response with the status code 200. +func OK(w http.ResponseWriter, v interface{}) { + commonHeaders(w) + w.WriteHeader(http.StatusOK) + w.Write(toJSON(v)) +} + +// Created sends a JSON response with the status code 201. +func Created(w http.ResponseWriter, v interface{}) { + commonHeaders(w) + w.WriteHeader(http.StatusCreated) + w.Write(toJSON(v)) +} + +// NoContent sends a JSON response with the status code 204. +func NoContent(w http.ResponseWriter) { + commonHeaders(w) + w.WriteHeader(http.StatusNoContent) +} + +// NotFound sends a JSON response with the status code 404. +func NotFound(w http.ResponseWriter, err error) { + logger.Error("[Not Found] %v", err) + commonHeaders(w) + w.WriteHeader(http.StatusNotFound) + w.Write(encodeError(err)) +} + +// ServerError sends a JSON response with the status code 500. +func ServerError(w http.ResponseWriter, err error) { + logger.Error("[Internal Server Error] %v", err) + commonHeaders(w) + w.WriteHeader(http.StatusInternalServerError) + + if err != nil { + w.Write(encodeError(err)) + } +} + +// Forbidden sends a JSON response with the status code 403. +func Forbidden(w http.ResponseWriter) { + logger.Info("[Forbidden]") + commonHeaders(w) + w.WriteHeader(http.StatusForbidden) + w.Write(encodeError(errors.New("Access Forbidden"))) +} + +// Unauthorized sends a JSON response with the status code 401. +func Unauthorized(w http.ResponseWriter) { + commonHeaders(w) + w.WriteHeader(http.StatusUnauthorized) + w.Write(encodeError(errors.New("Access Unauthorized"))) +} + +// BadRequest sends a JSON response with the status code 400. +func BadRequest(w http.ResponseWriter, err error) { + logger.Error("[Bad Request] %v", err) + commonHeaders(w) + w.WriteHeader(http.StatusBadRequest) + + if err != nil { + w.Write(encodeError(err)) + } +} + +func commonHeaders(w http.ResponseWriter) { + w.Header().Set("Accept", "application/json") + w.Header().Set("Content-Type", "application/json; charset=utf-8") +} + +func encodeError(err error) []byte { + type errorMsg struct { + ErrorMessage string `json:"error_message"` + } + + tmp := errorMsg{ErrorMessage: err.Error()} + data, err := json.Marshal(tmp) + if err != nil { + logger.Error("json encoding error: %v", err) + } + + return data +} + +func toJSON(v interface{}) []byte { + b, err := json.Marshal(v) + if err != nil { + logger.Error("json encoding error: %v", err) + return []byte("") + } + + return b +} diff --git a/http/response/response.go b/http/response/response.go new file mode 100644 index 0000000..066d061 --- /dev/null +++ b/http/response/response.go @@ -0,0 +1,34 @@ +// Copyright 2018 Frédéric Guillot. All rights reserved. +// Use of this source code is governed by the Apache 2.0 +// license that can be found in the LICENSE file. + +package response + +import ( + "net/http" + "time" +) + +// Redirect redirects the user to another location. +func Redirect(w http.ResponseWriter, r *http.Request, path string) { + http.Redirect(w, r, path, http.StatusFound) +} + +// NotModified sends a response with a 304 status code. +func NotModified(w http.ResponseWriter) { + w.WriteHeader(http.StatusNotModified) +} + +// Cache returns a response with caching headers. +func Cache(w http.ResponseWriter, r *http.Request, mimeType, etag string, content []byte, duration time.Duration) { + w.Header().Set("Content-Type", mimeType) + w.Header().Set("ETag", etag) + w.Header().Set("Cache-Control", "public") + w.Header().Set("Expires", time.Now().Add(duration).Format(time.RFC1123)) + + if etag == r.Header.Get("If-None-Match") { + w.WriteHeader(http.StatusNotModified) + } else { + w.Write(content) + } +} diff --git a/http/response/xml/xml.go b/http/response/xml/xml.go new file mode 100644 index 0000000..9e37e87 --- /dev/null +++ b/http/response/xml/xml.go @@ -0,0 +1,23 @@ +// Copyright 2018 Frédéric Guillot. All rights reserved. +// Use of this source code is governed by the Apache 2.0 +// license that can be found in the LICENSE file. + +package xml + +import ( + "fmt" + "net/http" +) + +// OK sends a XML document. +func OK(w http.ResponseWriter, data string) { + w.Header().Set("Content-Type", "text/xml") + w.Write([]byte(data)) +} + +// Attachment forces the download of a XML document. +func Attachment(w http.ResponseWriter, filename, data string) { + w.Header().Set("Content-Type", "text/xml") + w.Header().Set("Content-Disposition", fmt.Sprintf("attachment; filename=%s", filename)) + w.Write([]byte(data)) +} |