Improve GCP error handling

This commit is contained in:
lordwelch 2020-08-07 14:43:44 -07:00
parent f63cef91d4
commit 6a43060cce
2 changed files with 24 additions and 18 deletions

View File

@ -1,6 +1,7 @@
package gcp package gcp
import ( import (
"bytes"
"crypto/rand" "crypto/rand"
"encoding/json" "encoding/json"
"fmt" "fmt"
@ -8,35 +9,36 @@ import (
"os" "os"
"github.com/stoggi/sshrimp/internal/config" "github.com/stoggi/sshrimp/internal/config"
"github.com/stoggi/sshrimp/internal/identity"
"github.com/stoggi/sshrimp/internal/signer" "github.com/stoggi/sshrimp/internal/signer"
"golang.org/x/crypto/ssh" "golang.org/x/crypto/ssh"
) )
func httpError(w http.ResponseWriter, v interface{}, statusCode int) { func httpError(w http.ResponseWriter, v interface{}, statusCode int) {
e := json.NewEncoder(w) var b bytes.Buffer
err := e.Encode(v) e := json.NewEncoder(&b)
http.Error(w, err.Error(), statusCode) _ = e.Encode(v)
http.Error(w, b.String(), statusCode)
} }
// HandleRequest handles a request to sign an SSH public key verified by an OpenIDConnect id_token // SSHrimp handles a request to sign an SSH public key verified by an OpenIDConnect id_token
func SSHrimp(w http.ResponseWriter, r *http.Request) { func SSHrimp(w http.ResponseWriter, r *http.Request) {
// Load the configuration file, if not exsits, exit. // Load the configuration file, if not exsits, exit.
c := config.NewSSHrimp() c := config.NewSSHrimp()
if err := c.Read(config.GetPath()); err != nil { if err := c.Read("./serverless_function_source_code/sshrimp.toml"); err != nil {
httpError(w, signer.SSHrimpResult{"", err.Error(), http.StatusText(http.StatusInternalServerError)}, http.StatusInternalServerError) httpError(w, signer.SSHrimpResult{Certificate: "", ErrorMessage: err.Error(), ErrorType: http.StatusText(http.StatusInternalServerError)}, http.StatusInternalServerError)
return return
} }
var event signer.SSHrimpEvent var event signer.SSHrimpEvent
if err := json.NewDecoder(r.Body).Decode(&event); err != nil { if err := json.NewDecoder(r.Body).Decode(&event); err != nil {
httpError(w, signer.SSHrimpResult{"", err.Error(), http.StatusText(http.StatusBadRequest)}, http.StatusBadRequest) httpError(w, signer.SSHrimpResult{Certificate: "", ErrorMessage: err.Error(), ErrorType: http.StatusText(http.StatusBadRequest)}, http.StatusBadRequest)
return return
} }
certificate, err := signer.ValidateRequest(event, c, r.Header.Get("Function-Execution-Id"), fmt.Sprintf("%s/%s/%s", os.Getenv("GCP_PROJECT"), os.Getenv("FUNCTION_REGION"), os.Getenv("FUNCTION_NAME"))) certificate, err := signer.ValidateRequest(event, c, r.Header.Get("Function-Execution-Id"), fmt.Sprintf("%s/%s/%s", os.Getenv("GCP_PROJECT"), os.Getenv("FUNCTION_REGION"), os.Getenv("FUNCTION_NAME")))
if err != nil { if err != nil {
httpError(w, signer.SSHrimpResult{"", err.Error(), http.StatusText(http.StatusBadRequest)}, http.StatusBadRequest) httpError(w, signer.SSHrimpResult{Certificate: "", ErrorMessage: err.Error(), ErrorType: http.StatusText(http.StatusBadRequest)}, http.StatusBadRequest)
return return
} }
@ -45,20 +47,28 @@ func SSHrimp(w http.ResponseWriter, r *http.Request) {
sshAlgorithmSigner, err := signer.NewAlgorithmSignerFromSigner(kmsSigner, ssh.SigAlgoRSASHA2256) sshAlgorithmSigner, err := signer.NewAlgorithmSignerFromSigner(kmsSigner, ssh.SigAlgoRSASHA2256)
if err != nil { if err != nil {
httpError(w, signer.SSHrimpResult{"", err.Error(), http.StatusText(http.StatusBadRequest)}, http.StatusBadRequest) httpError(w, signer.SSHrimpResult{Certificate: "", ErrorMessage: err.Error(), ErrorType: http.StatusText(http.StatusBadRequest)}, http.StatusBadRequest)
return return
} }
// Sign the certificate!! // Sign the certificate!!
if err := certificate.SignCert(rand.Reader, sshAlgorithmSigner); err != nil { if err := certificate.SignCert(rand.Reader, sshAlgorithmSigner); err != nil {
httpError(w, signer.SSHrimpResult{"", err.Error(), http.StatusText(http.StatusBadRequest)}, http.StatusBadRequest) httpError(w, signer.SSHrimpResult{Certificate: "", ErrorMessage: err.Error(), ErrorType: http.StatusText(http.StatusInternalServerError)}, http.StatusInternalServerError)
return
}
i, _ := identity.NewIdentity(c)
username, _ := i.Validate(event.Token)
cc := ssh.CertChecker{}
err = cc.CheckCert(username, &certificate)
if err != nil {
httpError(w, signer.SSHrimpResult{Certificate: "", ErrorMessage: err.Error(), ErrorType: http.StatusText(http.StatusInternalServerError)}, http.StatusBadRequest)
return return
} }
// Extract the public key (certificate) to return to the user // Extract the public key (certificate) to return to the user
pubkey, err := ssh.ParsePublicKey(certificate.Marshal()) pubkey, err := ssh.ParsePublicKey(certificate.Marshal())
if err != nil { if err != nil {
httpError(w, signer.SSHrimpResult{"", err.Error(), http.StatusText(http.StatusBadRequest)}, http.StatusBadRequest) httpError(w, signer.SSHrimpResult{Certificate: "", ErrorMessage: err.Error(), ErrorType: http.StatusText(http.StatusInternalServerError)}, http.StatusInternalServerError)
return return
} }
@ -69,9 +79,5 @@ func SSHrimp(w http.ResponseWriter, r *http.Request) {
ErrorType: "", ErrorType: "",
} }
e := json.NewEncoder(w) e := json.NewEncoder(w)
err = e.Encode(res) _ = e.Encode(res)
if err != nil {
http.Error(w, err.Error(), http.StatusBadRequest)
return
}
} }

View File

@ -52,7 +52,7 @@ func (s *GCPSigner) Public() crypto.PublicKey {
publicKey, err := x509.ParsePKIXPublicKey(pemBlock.Bytes) publicKey, err := x509.ParsePKIXPublicKey(pemBlock.Bytes)
if err != nil { if err != nil {
fmt.Printf(err.Error()) fmt.Println(err.Error())
return nil return nil
} }