passed/route/password.go
2025-05-23 22:22:18 +02:00

103 lines
2.4 KiB
Go

package route
import (
"encoding/json"
"net/http"
"time"
"git.1e99.eu/1e99/passed/password"
)
func CreatePassword(storage password.Storage, maxLength int) http.HandlerFunc {
return func(res http.ResponseWriter, req *http.Request) {
var reqBody struct {
// Go automatically decodes byte arrays using Base64
Password []byte `json:"password"`
ExpiresIn time.Duration `json:"expires-in"`
}
err := json.NewDecoder(req.Body).Decode(&reqBody)
if err != nil {
http.Error(res, "Malformed JSON body", http.StatusBadRequest)
return
}
if len(reqBody.Password) > maxLength {
http.Error(res, "Password too long", http.StatusRequestEntityTooLarge)
return
}
expiresIn := reqBody.ExpiresIn * time.Second
if expiresIn <= 0 {
http.Error(res, "Too short expires-in", http.StatusBadRequest)
return
}
if expiresIn > 2*7*24*time.Hour {
http.Error(res, "Too long expires-in", http.StatusBadRequest)
return
}
id, err := storage.Create(
reqBody.Password,
time.Now().Add(expiresIn),
)
switch {
case err == password.ErrFull:
http.Error(res, "Insufficient storage", http.StatusInsufficientStorage)
return
case err != nil:
http.Error(res, "", http.StatusInternalServerError)
return
}
err = json.NewEncoder(res).Encode(&id)
if err != nil {
http.Error(res, "", http.StatusInternalServerError)
return
}
}
}
func GetPassword(storage password.Storage) http.HandlerFunc {
return func(res http.ResponseWriter, req *http.Request) {
id := req.PathValue("id")
passwd, err := storage.Get(id)
switch {
case err == password.ErrNotFound:
http.Error(res, "Password not found", http.StatusNotFound)
return
case err != nil:
http.Error(res, "", http.StatusInternalServerError)
return
}
err = storage.Delete(id)
if err != nil {
http.Error(res, "", http.StatusInternalServerError)
return
}
err = json.NewEncoder(res).Encode(&passwd)
if err != nil {
http.Error(res, "", http.StatusInternalServerError)
return
}
}
}
func HasPassword(storage password.Storage) http.HandlerFunc {
return func(res http.ResponseWriter, req *http.Request) {
id := req.PathValue("id")
_, err := storage.Get(id)
switch {
case err == password.ErrNotFound:
http.Error(res, "", http.StatusNotFound)
return
case err != nil:
http.Error(res, "", http.StatusInternalServerError)
return
}
res.WriteHeader(http.StatusNoContent)
}
}