changeset 1469:286a3306f6bf bulkreview

Import bulk review: Cleaned up input JSON document handling. Added proper error handling.
author Sascha L. Teichmann <sascha.teichmann@intevation.de>
date Fri, 30 Nov 2018 09:15:47 +0100
parents 5e1218b5a123
children c89a18f8027d
files pkg/controllers/importqueue.go pkg/controllers/routes.go pkg/models/import.go
diffstat 3 files changed, 67 insertions(+), 27 deletions(-) [+]
line wrap: on
line diff
--- a/pkg/controllers/importqueue.go	Thu Nov 29 12:09:01 2018 +0100
+++ b/pkg/controllers/importqueue.go	Fri Nov 30 09:15:47 2018 +0100
@@ -66,15 +66,6 @@
 DELETE FROM waterway.imports WHERE id = $1`
 )
 
-type Review struct {
-	ID    int64  `json:"id"`
-	State string `json:"state"`
-}
-
-func (r Review) String() string {
-	return fmt.Sprintf("%d %s", r.ID, r.State)
-}
-
 func toTextArray(txt string, allowed []string) *pgtype.TextArray {
 	parts := strings.Split(txt, ",")
 	var accepted []string
@@ -344,17 +335,35 @@
 )
 
 func reviewImports(
-	_ interface{},
+	reviews interface{},
 	req *http.Request,
 	conn *sql.Conn,
-) (jr JSONResult, err error) {
-	decoder := json.NewDecoder(req.Body)
-	var reviews []Review
-	decoder.Decode(&reviews)
-	for _, review := range reviews {
-		updateImport(req, conn, review.ID, review.State)
+) (JSONResult, error) {
+
+	rs := reviews.([]*models.Review)
+
+	type reviewResult struct {
+		ID      int64  `json:"id"`
+		Message string `json:"message,omitempty"`
+		Error   string `json:"error,omitempty"`
 	}
-	return
+
+	results := make([]reviewResult, len(rs))
+
+	for i, rev := range rs {
+		msg, err := decideImport(req, conn, rev.ID, string(rev.State))
+		var errString string
+		if err != nil {
+			errString = err.Error()
+		}
+		results[i] = reviewResult{
+			ID:      rev.ID,
+			Message: msg,
+			Error:   errString,
+		}
+	}
+
+	return JSONResult{Result: results}, nil
 }
 
 func reviewImport(
@@ -366,15 +375,28 @@
 	vars := mux.Vars(req)
 	id, _ := strconv.ParseInt(vars["id"], 10, 64)
 	state := vars["state"]
-	return updateImport(req, conn, id, state)
+
+	var msg string
+	if msg, err = decideImport(req, conn, id, state); err != nil {
+		return
+	}
+
+	result := struct {
+		Message string `json:"message"`
+	}{
+		Message: msg,
+	}
+
+	jr = JSONResult{Result: &result}
+	return
 }
 
-func updateImport(
+func decideImport(
 	req *http.Request,
 	conn *sql.Conn,
 	id int64,
 	state string,
-) (jr JSONResult, err error) {
+) (message string, err error) {
 	ctx := req.Context()
 	var tx *sql.Tx
 	if tx, err = conn.BeginTx(ctx, nil); err != nil {
@@ -438,13 +460,8 @@
 		return
 	}
 
-	result := struct {
-		Message string `json:"message"`
-	}{
-		Message: fmt.Sprintf("Import #%d successfully changed to state '%s'.",
-			id, state),
-	}
+	message = fmt.Sprintf(
+		"Import #%d successfully changed to state '%s'.", id, state)
 
-	jr = JSONResult{Result: &result}
 	return
 }
--- a/pkg/controllers/routes.go	Thu Nov 29 12:09:01 2018 +0100
+++ b/pkg/controllers/routes.go	Fri Nov 30 09:15:47 2018 +0100
@@ -183,6 +183,7 @@
 	})).Methods(http.MethodGet)
 
 	api.Handle("/imports", waterwayAdmin(&JSONHandler{
+		Input:  func() interface{} { return []*models.Review{} },
 		Handle: reviewImports,
 	})).Methods(http.MethodPatch)
 
--- a/pkg/models/import.go	Thu Nov 29 12:09:01 2018 +0100
+++ b/pkg/models/import.go	Fri Nov 30 09:15:47 2018 +0100
@@ -15,6 +15,7 @@
 
 import (
 	"encoding/json"
+	"errors"
 	"time"
 )
 
@@ -36,8 +37,29 @@
 		Kind    string     `json:"kind"`
 		Message string     `json:"message"`
 	}
+
+	ReviewState string
+
+	Review struct {
+		ID    int64       `json:"id"`
+		State ReviewState `json:"state"`
+	}
 )
 
+var errInvalidReviewState = errors.New("state is wether 'accepted' nor 'declined'")
+
+func (rs *ReviewState) UnmarshalJSON(data []byte) error {
+	var s string
+	if err := json.Unmarshal(data, &s); err != nil {
+		return err
+	}
+	if s != "accepted" && s != "declined" {
+		return errInvalidReviewState
+	}
+	*rs = ReviewState(s)
+	return nil
+}
+
 func (it ImportTime) MarshalJSON() ([]byte, error) {
 	return json.Marshal(it.Format("2006-01-02T15:04:05"))
 }