From 441f0258572a2fa1a4bbd706fe5aaa6e0250c1eb Mon Sep 17 00:00:00 2001 From: Weston Haught Date: Wed, 26 Aug 2020 15:58:11 -0700 Subject: [PATCH 1/7] add form --- cmd/server/assets/codestatus/show.html | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/cmd/server/assets/codestatus/show.html b/cmd/server/assets/codestatus/show.html index f12dcf477..cf20fa940 100644 --- a/cmd/server/assets/codestatus/show.html +++ b/cmd/server/assets/codestatus/show.html @@ -42,6 +42,10 @@
Status
Expiry
+
+ + +
From 2fee331aa0c6f4386909c1eae8013e437ebfe028 Mon Sep 17 00:00:00 2001 From: Weston Haught Date: Wed, 26 Aug 2020 17:41:40 -0700 Subject: [PATCH 2/7] submit form, not ajax for invalidate code --- cmd/adminapi/main.go | 2 +- .../assets/codestatus/_codescripts.html | 22 +++++---- cmd/server/assets/codestatus/show.html | 24 +++++---- cmd/server/main.go | 1 + pkg/controller/codestatus/expire.go | 46 ++++++++++++++++- pkg/controller/codestatus/show.go | 49 ++++++++++--------- 6 files changed, 100 insertions(+), 44 deletions(-) diff --git a/cmd/adminapi/main.go b/cmd/adminapi/main.go index 6928b3a84..7e02753ba 100644 --- a/cmd/adminapi/main.go +++ b/cmd/adminapi/main.go @@ -142,7 +142,7 @@ func realMain(ctx context.Context) error { codeStatusController := codestatus.NewAPI(ctx, config, db, h) r.Handle("/api/checkcodestatus", codeStatusController.HandleCheckCodeStatus()).Methods("POST") - r.Handle("/api/expirecode", codeStatusController.HandleExpire()).Methods("POST") + r.Handle("/api/expirecode", codeStatusController.HandleExpireAPI()).Methods("POST") srv, err := server.New(config.Port) if err != nil { diff --git a/cmd/server/assets/codestatus/_codescripts.html b/cmd/server/assets/codestatus/_codescripts.html index 526a776bd..2b30327bb 100644 --- a/cmd/server/assets/codestatus/_codescripts.html +++ b/cmd/server/assets/codestatus/_codescripts.html @@ -2,7 +2,7 @@ {{end}} diff --git a/cmd/server/assets/codestatus/show.html b/cmd/server/assets/codestatus/show.html index 3dbde6744..a0f7cd182 100644 --- a/cmd/server/assets/codestatus/show.html +++ b/cmd/server/assets/codestatus/show.html @@ -42,28 +42,32 @@
Status
Expiry
-
- - -
+
+
+ {{ .csrfField }} + + +
+
-
- ← Enter another code -
+ ← Enter another code {{template "scripts" .}} {{template "codescripts" .}} diff --git a/cmd/server/main.go b/cmd/server/main.go index 3ba6b36b8..ae70303d8 100644 --- a/cmd/server/main.go +++ b/cmd/server/main.go @@ -242,6 +242,7 @@ func realMain(ctx context.Context) error { codeStatusController := codestatus.NewServer(ctx, config, db, h) sub.Handle("/status", codeStatusController.HandleIndex()).Methods("GET") sub.Handle("/show", codeStatusController.HandleShow()).Methods("POST") + sub.Handle("/expire", codeStatusController.HandleExpirePage()).Methods("POST") } // apikeys diff --git a/pkg/controller/codestatus/expire.go b/pkg/controller/codestatus/expire.go index 3f61a5a74..cc706c114 100644 --- a/pkg/controller/codestatus/expire.go +++ b/pkg/controller/codestatus/expire.go @@ -21,9 +21,10 @@ import ( "github.com/google/exposure-notifications-verification-server/pkg/api" "github.com/google/exposure-notifications-verification-server/pkg/controller" + "github.com/google/exposure-notifications-verification-server/pkg/database" ) -func (c *Controller) HandleExpire() http.Handler { +func (c *Controller) HandleExpireAPI() http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { var request api.ExpireCodeRequest if err := controller.BindJSON(w, r, &request); err != nil { @@ -51,3 +52,46 @@ func (c *Controller) HandleExpire() http.Handler { }) }) } + +func (c *Controller) HandleExpirePage() http.Handler { + return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + ctx := r.Context() + var code *database.VerificationCode + + session := controller.SessionFromContext(ctx) + if session == nil { + controller.MissingSession(w, r, c.h) + return + } + flash := controller.Flash(session) + + retCode := Code{} + + var form FormData + if err := controller.BindForm(w, r, &form); err != nil { + flash.Error("Failed to process form: %v.", err) + c.renderStatus(ctx, w, code) + return + } + + // Retrieve once to check permissions. + + code, _, apiErr := c.CheckCodeStatus(r, form.UUID) + if apiErr != nil { + flash.Error("failed to expire code", apiErr.Error) + c.renderStatus(ctx, w, code) + return + } + + expiredCode, err := c.db.ExpireCode(form.UUID) + if err != nil { + flash.Error("Failed to process form: %v.", err) + expiredCode = code + } else { + flash.Alert("Expired code.") + } + + c.responseCode(ctx, r, expiredCode, &retCode) + c.renderShow(ctx, w, retCode) + }) +} diff --git a/pkg/controller/codestatus/show.go b/pkg/controller/codestatus/show.go index cf0b1d243..b1b70a3a9 100644 --- a/pkg/controller/codestatus/show.go +++ b/pkg/controller/codestatus/show.go @@ -25,11 +25,11 @@ import ( "github.com/google/exposure-notifications-verification-server/pkg/database" ) -func (c *Controller) HandleShow() http.Handler { - type FormData struct { - UUID string `form:"uuid"` - } +type FormData struct { + UUID string `form:"uuid"` +} +func (c *Controller) HandleShow() http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() @@ -56,7 +56,6 @@ func (c *Controller) HandleShow() http.Handler { c.renderStatus(ctx, w, &code) return } - retCode.UUID = form.UUID code, _, apiErr := c.CheckCodeStatus(r, form.UUID) if apiErr != nil { @@ -67,28 +66,34 @@ func (c *Controller) HandleShow() http.Handler { c.renderStatus(ctx, w, &code) return } - retCode.TestType = strings.Title(code.TestType) - - if code.IssuingUserID != 0 { - retCode.IssuerType = "Issuing user" - retCode.Issuer = c.getUserName(ctx, r, code.IssuingUserID) - } else if code.IssuingAppID != 0 { - retCode.IssuerType = "Issuing app" - retCode.Issuer = c.getAuthAppName(ctx, r, code.IssuingAppID) - } - if code.Claimed { - retCode.Status = "Claimed by user" - } else { - retCode.Status = "Not yet claimed" - } - if !code.IsExpired() { - retCode.Expires = code.ExpiresAt.UTC().Unix() - } + c.responseCode(ctx, r, code, &retCode) c.renderShow(ctx, w, retCode) }) } +func (c *Controller) responseCode(ctx context.Context, r *http.Request, code *database.VerificationCode, retCode *Code) { + retCode.UUID = code.UUID + retCode.TestType = strings.Title(code.TestType) + + if code.IssuingUserID != 0 { + retCode.IssuerType = "Issuing user" + retCode.Issuer = c.getUserName(ctx, r, code.IssuingUserID) + } else if code.IssuingAppID != 0 { + retCode.IssuerType = "Issuing app" + retCode.Issuer = c.getAuthAppName(ctx, r, code.IssuingAppID) + } + + if code.Claimed { + retCode.Status = "Claimed by user" + } else { + retCode.Status = "Not yet claimed" + } + if !code.IsExpired() { + retCode.Expires = code.ExpiresAt.UTC().Unix() + } +} + func (c *Controller) getUserName(ctx context.Context, r *http.Request, id uint) (userName string) { userName = "Unknown user" _, user, err := c.getAuthorizationFromContext(r) From 57df7b140f231093c95935b550181d1d70d35a69 Mon Sep 17 00:00:00 2001 From: Weston Haught Date: Wed, 26 Aug 2020 17:56:00 -0700 Subject: [PATCH 3/7] switch pointer around --- pkg/controller/codestatus/expire.go | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/pkg/controller/codestatus/expire.go b/pkg/controller/codestatus/expire.go index cc706c114..246837b5c 100644 --- a/pkg/controller/codestatus/expire.go +++ b/pkg/controller/codestatus/expire.go @@ -56,7 +56,7 @@ func (c *Controller) HandleExpireAPI() http.Handler { func (c *Controller) HandleExpirePage() http.Handler { return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() - var code *database.VerificationCode + var code database.VerificationCode session := controller.SessionFromContext(ctx) if session == nil { @@ -70,7 +70,7 @@ func (c *Controller) HandleExpirePage() http.Handler { var form FormData if err := controller.BindForm(w, r, &form); err != nil { flash.Error("Failed to process form: %v.", err) - c.renderStatus(ctx, w, code) + c.renderStatus(ctx, w, &code) return } @@ -79,14 +79,14 @@ func (c *Controller) HandleExpirePage() http.Handler { code, _, apiErr := c.CheckCodeStatus(r, form.UUID) if apiErr != nil { flash.Error("failed to expire code", apiErr.Error) - c.renderStatus(ctx, w, code) + c.renderStatus(ctx, w, &code) return } expiredCode, err := c.db.ExpireCode(form.UUID) if err != nil { flash.Error("Failed to process form: %v.", err) - expiredCode = code + expiredCode = &code } else { flash.Alert("Expired code.") } From 31bf60d97c622d99323fc772aa5f13408455a303 Mon Sep 17 00:00:00 2001 From: Weston Haught Date: Wed, 26 Aug 2020 17:58:36 -0700 Subject: [PATCH 4/7] form data --- pkg/controller/codestatus/expire.go | 12 ++++++++---- pkg/controller/codestatus/show.go | 8 ++++---- 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/pkg/controller/codestatus/expire.go b/pkg/controller/codestatus/expire.go index 246837b5c..444db6f39 100644 --- a/pkg/controller/codestatus/expire.go +++ b/pkg/controller/codestatus/expire.go @@ -54,9 +54,13 @@ func (c *Controller) HandleExpireAPI() http.Handler { } func (c *Controller) HandleExpirePage() http.Handler { + type FormData struct { + UUID string `form:"uuid"` + } + return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() - var code database.VerificationCode + var code *database.VerificationCode = &database.VerificationCode{} session := controller.SessionFromContext(ctx) if session == nil { @@ -70,7 +74,7 @@ func (c *Controller) HandleExpirePage() http.Handler { var form FormData if err := controller.BindForm(w, r, &form); err != nil { flash.Error("Failed to process form: %v.", err) - c.renderStatus(ctx, w, &code) + c.renderStatus(ctx, w, code) return } @@ -79,14 +83,14 @@ func (c *Controller) HandleExpirePage() http.Handler { code, _, apiErr := c.CheckCodeStatus(r, form.UUID) if apiErr != nil { flash.Error("failed to expire code", apiErr.Error) - c.renderStatus(ctx, w, &code) + c.renderStatus(ctx, w, code) return } expiredCode, err := c.db.ExpireCode(form.UUID) if err != nil { flash.Error("Failed to process form: %v.", err) - expiredCode = &code + expiredCode = code } else { flash.Alert("Expired code.") } diff --git a/pkg/controller/codestatus/show.go b/pkg/controller/codestatus/show.go index b1b70a3a9..5a34555d6 100644 --- a/pkg/controller/codestatus/show.go +++ b/pkg/controller/codestatus/show.go @@ -25,11 +25,11 @@ import ( "github.com/google/exposure-notifications-verification-server/pkg/database" ) -type FormData struct { - UUID string `form:"uuid"` -} - func (c *Controller) HandleShow() http.Handler { + type FormData struct { + UUID string `form:"uuid"` + } + return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() From 6127bd1e39edc1b6573c7ad0feda537601140d11 Mon Sep 17 00:00:00 2001 From: Weston Haught Date: Thu, 27 Aug 2020 14:49:32 -0700 Subject: [PATCH 5/7] patch / mux.vars --- cmd/server/assets/codestatus/show.html | 4 ++-- cmd/server/main.go | 2 +- pkg/controller/codestatus/expire.go | 19 +++++-------------- 3 files changed, 8 insertions(+), 17 deletions(-) diff --git a/cmd/server/assets/codestatus/show.html b/cmd/server/assets/codestatus/show.html index a0f7cd182..be2fdf201 100644 --- a/cmd/server/assets/codestatus/show.html +++ b/cmd/server/assets/codestatus/show.html @@ -43,9 +43,9 @@
Expiry
-
+ + {{ .csrfField }} -
diff --git a/cmd/server/main.go b/cmd/server/main.go index ae70303d8..5a4dc02dd 100644 --- a/cmd/server/main.go +++ b/cmd/server/main.go @@ -242,7 +242,7 @@ func realMain(ctx context.Context) error { codeStatusController := codestatus.NewServer(ctx, config, db, h) sub.Handle("/status", codeStatusController.HandleIndex()).Methods("GET") sub.Handle("/show", codeStatusController.HandleShow()).Methods("POST") - sub.Handle("/expire", codeStatusController.HandleExpirePage()).Methods("POST") + sub.Handle("/{uuid}/expire", codeStatusController.HandleExpirePage()).Methods("PATCH") } // apikeys diff --git a/pkg/controller/codestatus/expire.go b/pkg/controller/codestatus/expire.go index 444db6f39..3ac017c21 100644 --- a/pkg/controller/codestatus/expire.go +++ b/pkg/controller/codestatus/expire.go @@ -22,6 +22,7 @@ import ( "github.com/google/exposure-notifications-verification-server/pkg/api" "github.com/google/exposure-notifications-verification-server/pkg/controller" "github.com/google/exposure-notifications-verification-server/pkg/database" + "github.com/gorilla/mux" ) func (c *Controller) HandleExpireAPI() http.Handler { @@ -54,13 +55,9 @@ func (c *Controller) HandleExpireAPI() http.Handler { } func (c *Controller) HandleExpirePage() http.Handler { - type FormData struct { - UUID string `form:"uuid"` - } - return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() - var code *database.VerificationCode = &database.VerificationCode{} + vars := mux.Vars(r) session := controller.SessionFromContext(ctx) if session == nil { @@ -69,25 +66,19 @@ func (c *Controller) HandleExpirePage() http.Handler { } flash := controller.Flash(session) + code := &database.VerificationCode{} retCode := Code{} - var form FormData - if err := controller.BindForm(w, r, &form); err != nil { - flash.Error("Failed to process form: %v.", err) - c.renderStatus(ctx, w, code) - return - } - // Retrieve once to check permissions. - code, _, apiErr := c.CheckCodeStatus(r, form.UUID) + code, _, apiErr := c.CheckCodeStatus(r, vars["uuid"]) if apiErr != nil { flash.Error("failed to expire code", apiErr.Error) c.renderStatus(ctx, w, code) return } - expiredCode, err := c.db.ExpireCode(form.UUID) + expiredCode, err := c.db.ExpireCode(vars["uuid"]) if err != nil { flash.Error("Failed to process form: %v.", err) expiredCode = code From 56b7252a9396d0d26d45d625d28c7d1532df983e Mon Sep 17 00:00:00 2001 From: Weston Haught Date: Thu, 27 Aug 2020 14:54:43 -0700 Subject: [PATCH 6/7] fix build --- pkg/controller/codestatus/expire.go | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/pkg/controller/codestatus/expire.go b/pkg/controller/codestatus/expire.go index 3ac017c21..c85d47bdd 100644 --- a/pkg/controller/codestatus/expire.go +++ b/pkg/controller/codestatus/expire.go @@ -21,7 +21,6 @@ import ( "github.com/google/exposure-notifications-verification-server/pkg/api" "github.com/google/exposure-notifications-verification-server/pkg/controller" - "github.com/google/exposure-notifications-verification-server/pkg/database" "github.com/gorilla/mux" ) @@ -66,11 +65,7 @@ func (c *Controller) HandleExpirePage() http.Handler { } flash := controller.Flash(session) - code := &database.VerificationCode{} - retCode := Code{} - // Retrieve once to check permissions. - code, _, apiErr := c.CheckCodeStatus(r, vars["uuid"]) if apiErr != nil { flash.Error("failed to expire code", apiErr.Error) @@ -86,6 +81,7 @@ func (c *Controller) HandleExpirePage() http.Handler { flash.Alert("Expired code.") } + retCode := Code{} c.responseCode(ctx, r, expiredCode, &retCode) c.renderShow(ctx, w, retCode) }) From c8e1485e1b0c377d54c5b5cd8471887252ef6a62 Mon Sep 17 00:00:00 2001 From: Weston Haught Date: Thu, 27 Aug 2020 15:00:39 -0700 Subject: [PATCH 7/7] format error --- pkg/controller/codestatus/expire.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pkg/controller/codestatus/expire.go b/pkg/controller/codestatus/expire.go index c85d47bdd..4518dfab8 100644 --- a/pkg/controller/codestatus/expire.go +++ b/pkg/controller/codestatus/expire.go @@ -68,7 +68,7 @@ func (c *Controller) HandleExpirePage() http.Handler { // Retrieve once to check permissions. code, _, apiErr := c.CheckCodeStatus(r, vars["uuid"]) if apiErr != nil { - flash.Error("failed to expire code", apiErr.Error) + flash.Error("Failed to expire code: %v.", apiErr.Error) c.renderStatus(ctx, w, code) return }