Sarah@auth.lopeos.org submitted a patch request Feb 15, 2025 22:50
- Title: Error When Rejecting Badly Formatted Patch Files / Non Patch Files
- Author: Sarah Jamie Lewis <sarah@openprivacy.ca>
repo/requests.go
@@ -24,6 +24,7 @@ type RequestList struct {
User common.AuthInfo
Repo string
Requests []*common.IssueRequest
+ Warnings []Warning
}
type RequestManager struct {
@@ -60,6 +61,11 @@ func NewRequestManager(config *common.Config, repo string, ac *auth.AuthClient)
return &RequestManager{config: config, repo: repo, ac: ac, patchHandler: *NewPatchHandler(config, repo)}
}
+func (rm *RequestManager) errorHandler(err string, w http.ResponseWriter, r *http.Request) {
+ r.AddCookie(&http.Cookie{Name: "error", Value: err})
+ rm.Serve(w, r)
+}
+
func (rm *RequestManager) ApplyPatch(w http.ResponseWriter, r *http.Request) {
authUser := rm.ac.GetAuthInfo(rm.config, r)
@@ -102,13 +108,19 @@ func (rm *RequestManager) ServePatch(w http.ResponseWriter, r *http.Request) {
func (rm *RequestManager) Serve(w http.ResponseWriter, r *http.Request) {
+ baseResponse := RequestList{Repo: rm.repo, User: rm.ac.GetAuthInfo(rm.config, r)}
+
+ if cookie, _ := r.Cookie("error"); cookie != nil {
+ baseResponse.Warnings = append(baseResponse.Warnings, Warning{Level: WARN, Message: cookie.Value})
+ }
+
if strings.HasSuffix(r.URL.Path, "/new") {
if value := r.FormValue("type"); value == "issue" {
- rm.config.Templates.ExecuteTemplate(w, "request.new.tpl.html", RequestList{Repo: rm.repo, User: rm.ac.GetAuthInfo(rm.config, r)})
+ rm.config.Templates.ExecuteTemplate(w, "request.new.tpl.html", baseResponse)
return
}
if value := r.FormValue("type"); value == "patch" {
- rm.config.Templates.ExecuteTemplate(w, "request.newpatch.tpl.html", RequestList{Repo: rm.repo, User: rm.ac.GetAuthInfo(rm.config, r)})
+ rm.config.Templates.ExecuteTemplate(w, "request.newpatch.tpl.html", baseResponse)
return
}
}
@@ -121,7 +133,7 @@ func (rm *RequestManager) Serve(w http.ResponseWriter, r *http.Request) {
// list all issues
if strings.HasSuffix(r.URL.Path, "requests/") {
authuser := rm.ac.GetAuthInfo(rm.config, r)
- rl := RequestList{Repo: rm.repo, User: authuser}
+ rl := baseResponse
// Get a list of issues in creation order...
issueList := rm.LoadIssues(rm.RequestLogPath(), func(hash string) (*common.IssueRequest, error) {
@@ -152,7 +164,7 @@ func (rm *RequestManager) Serve(w http.ResponseWriter, r *http.Request) {
// otherwise list a single issue...
authuser := rm.ac.GetAuthInfo(rm.config, r)
// otherwise...
- rt := RequestThread{Repo: rm.repo, User: rm.ac.GetAuthInfo(rm.config, r)}
+ rt := RequestThread{User: baseResponse.User, Repo: baseResponse.Repo, Warnings: baseResponse.Warnings}
issuehash := path.Base(r.URL.Path)
// Get a list of issues in creation order...
@@ -369,6 +381,7 @@ func (rm *RequestManager) updateLog(logpath string, hash string, status common.L
}
func (rm *RequestManager) handlePatch(w http.ResponseWriter, r *http.Request) {
+
// Parse our multipart form, 10 << 20 specifies a maximum
// upload of 10 MB files.
r.ParseMultipartForm(1024 * 1024 * 200)
@@ -377,20 +390,20 @@ func (rm *RequestManager) handlePatch(w http.ResponseWriter, r *http.Request) {
// the Header and the size of the file
file, _, err := r.FormFile("patchfile")
if err != nil {
- http.Error(w, err.Error(), http.StatusBadRequest)
+ rm.errorHandler("Could Not Create Patch Request", w, r)
return
}
defer file.Close()
id, err := common.RandomIdent()
if err != nil {
- http.Error(w, err.Error(), http.StatusBadRequest)
+ rm.errorHandler("Could Not Create Patch Request", w, r)
return
}
fileBytes, err := io.ReadAll(file)
if err != nil {
- http.Error(w, err.Error(), http.StatusBadRequest)
+ rm.errorHandler("Could Not Create Patch Request", w, r)
return
}
@@ -398,14 +411,18 @@ func (rm *RequestManager) handlePatch(w http.ResponseWriter, r *http.Request) {
buf := bytes.NewBuffer(fileBytes)
_, description, err := gitdiff.Parse(buf)
if err != nil {
- http.Error(w, err.Error(), http.StatusBadRequest)
+ rm.errorHandler("Could Not Create Patch Request", w, r)
+ return
+ }
+ if _, err := gitdiff.ParsePatchHeader(description); err != nil {
+ rm.errorHandler("Could Not Create Patch Request", w, r)
return
}
summary := r.FormValue("summary")
issueRequest, err := common.NewIssueRequest(summary, description, rm.ac.GetAuthInfo(rm.config, r))
if err != nil {
- http.Error(w, err.Error(), http.StatusBadRequest)
+ rm.errorHandler("Could Not Create Patch Request", w, r)
return
}
issueRequest.PatchRef = id
@@ -458,6 +475,11 @@ func (rm *RequestManager) SaveIssue(issueRequest *common.IssueRequest, w http.Re
}
func (rm *RequestManager) handleNew(w http.ResponseWriter, r *http.Request) {
+ if r.Response != nil {
+ fmt.Printf("now here....\n")
+ rm.Serve(w, r)
+ return
+ }
summary := r.FormValue("summary")
description := r.FormValue("description")
senary.go
@@ -135,6 +135,8 @@ func main() {
http.HandleFunc("POST "+path.Join("/repos/", e.Name(), "requests")+"/new", rm.Submit)
http.HandleFunc("POST "+path.Join("/repos/", e.Name(), "requests")+"/approve", rm.Submit)
http.HandleFunc("POST "+path.Join("/repos/", e.Name(), "requests")+"/tombstone", rm.Submit)
+
+ // allow downloading patches and applying them...
http.HandleFunc("GET "+path.Join("/repos/", e.Name(), "patch/{id}/{patch}")+"/{$}", rm.ServePatch)
http.HandleFunc("POST "+path.Join("/repos/", e.Name(), "apply/{id}/{patch}")+"/{$}", rm.ApplyPatch)
// allow https cloning by redirecting to git https backend
static/css/custom.css
@@ -72,4 +72,10 @@ mark.warning {
mark.info {
background-color:var(--pico-color-jade-600);color:var(--pico-color-light);
+}
+
+.error {
+ background-color:var(--pico-color-pink-600);color:var(--pico-color-light);
+ font-weight: bold;
+ text-align: center;
}
templates/request.newpatch.tpl.html
@@ -10,6 +10,12 @@
{{template "repomenu.tpl.html" .}}
<div>
+
+ {{range .Warnings}}
+ <div class="error">{{.Message}}</div>
+ <br/>
+ {{end}}
+
<h2>Submit a New Change Request</h2>
<form method="post" enctype="multipart/form-data" >
<fieldset>