Просмотр исходного кода

add message and reason for stack failures

Alexander Belanger 3 лет назад
Родитель
Сommit
51d4f3309f

+ 25 - 6
api/server/handlers/stack/create.go

@@ -3,6 +3,7 @@ package stack
 import (
 	"fmt"
 	"net/http"
+	"strings"
 
 	"github.com/porter-dev/porter/api/server/authz"
 	"github.com/porter-dev/porter/api/server/handlers"
@@ -113,6 +114,8 @@ func (p *StackCreateHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
 
 	helmReleaseMap := make(map[string]*helmrelease.Release)
 
+	deployErrs := make([]string, 0)
+
 	for _, appResource := range req.AppResources {
 		rel, err := applyAppResource(&applyAppResourceOpts{
 			config:     p.Config(),
@@ -125,9 +128,7 @@ func (p *StackCreateHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
 		})
 
 		if err != nil {
-			// TODO: mark stack with error
-			p.HandleAPIError(w, r, apierrors.NewErrInternal(err))
-			return
+			deployErrs = append(deployErrs, err.Error())
 		}
 
 		helmReleaseMap[fmt.Sprintf("%s/%s", namespace, appResource.Name)] = rel
@@ -135,7 +136,14 @@ func (p *StackCreateHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
 
 	// update stack revision status
 	revision := &stack.Revisions[0]
-	revision.Status = string(types.StackRevisionStatusDeployed)
+
+	if len(deployErrs) > 0 {
+		revision.Status = string(types.StackRevisionStatusFailed)
+		revision.Reason = "DeployError"
+		revision.Message = strings.Join(deployErrs, " , ")
+	} else {
+		revision.Status = string(types.StackRevisionStatusDeployed)
+	}
 
 	revision, err = p.Repo().Stack().UpdateStackRevision(revision)
 
@@ -144,14 +152,25 @@ func (p *StackCreateHandler) ServeHTTP(w http.ResponseWriter, r *http.Request) {
 		return
 	}
 
+	saveErrs := make([]string, 0)
+
 	for _, resource := range revision.Resources {
 		rel := helmReleaseMap[fmt.Sprintf("%s/%s", namespace, resource.Name)]
 
-		// TODO: case on addon vs application
 		_, err = release.CreateAppReleaseFromHelmRelease(p.Config(), proj.ID, cluster.ID, resource.ID, rel)
 
 		if err != nil {
-			// TODO: mark stack with error
+			saveErrs = append(saveErrs, fmt.Sprintf("the resource %s/%s could not be saved right now", namespace, resource.Name))
+		}
+	}
+
+	if len(saveErrs) > 0 {
+		revision.Reason = "SaveError"
+		revision.Message = strings.Join(saveErrs, " , ")
+
+		revision, err = p.Repo().Stack().UpdateStackRevision(revision)
+
+		if err != nil {
 			p.HandleAPIError(w, r, apierrors.NewErrInternal(err))
 			return
 		}

+ 11 - 4
api/server/handlers/stack/rollback.go

@@ -2,6 +2,7 @@ package stack
 
 import (
 	"net/http"
+	"strings"
 
 	"github.com/porter-dev/porter/api/server/authz"
 	"github.com/porter-dev/porter/api/server/handlers"
@@ -96,6 +97,8 @@ func (p *StackRollbackHandler) ServeHTTP(w http.ResponseWriter, r *http.Request)
 	}
 
 	// apply to cluster
+	rollbackErrors := make([]string, 0)
+
 	for _, resource := range revision.Resources {
 		err := rollbackAppResource(&rollbackAppResourceOpts{
 			helmAgent:      helmAgent,
@@ -104,13 +107,17 @@ func (p *StackRollbackHandler) ServeHTTP(w http.ResponseWriter, r *http.Request)
 		})
 
 		if err != nil {
-			// TODO: mark stack with error
-			p.HandleAPIError(w, r, apierrors.NewErrInternal(err))
-			return
+			rollbackErrors = append(rollbackErrors, err.Error())
 		}
 	}
 
-	revision.Status = string(types.StackRevisionStatusDeployed)
+	if len(rollbackErrors) > 0 {
+		revision.Status = string(types.StackRevisionStatusFailed)
+		revision.Reason = "RollbackError"
+		revision.Message = strings.Join(rollbackErrors, " , ")
+	} else {
+		revision.Status = string(types.StackRevisionStatusDeployed)
+	}
 
 	revision, err = p.Repo().Stack().UpdateStackRevision(revision)
 

+ 11 - 4
api/server/handlers/stack/update_source_put.go

@@ -2,6 +2,7 @@ package stack
 
 import (
 	"net/http"
+	"strings"
 
 	"github.com/porter-dev/porter/api/server/authz"
 	"github.com/porter-dev/porter/api/server/handlers"
@@ -94,6 +95,8 @@ func (p *StackPutSourceConfigHandler) ServeHTTP(w http.ResponseWriter, r *http.R
 		return
 	}
 
+	deployErrs := make([]string, 0)
+
 	for i, appResource := range clonedAppResources {
 		// get the corresponding source config tag
 		var imageTag string
@@ -118,15 +121,19 @@ func (p *StackPutSourceConfigHandler) ServeHTTP(w http.ResponseWriter, r *http.R
 		})
 
 		if err != nil {
-			// TODO: mark stack with error
-			p.HandleAPIError(w, r, apierrors.NewErrInternal(err))
-			return
+			deployErrs = append(deployErrs, err.Error())
 		}
 
 		clonedAppResources[i].HelmRevisionID++
 	}
 
-	revision.Status = string(types.StackRevisionStatusDeployed)
+	if len(deployErrs) > 0 {
+		revision.Status = string(types.StackRevisionStatusFailed)
+		revision.Reason = "DeployError"
+		revision.Message = strings.Join(deployErrs, " , ")
+	} else {
+		revision.Status = string(types.StackRevisionStatusDeployed)
+	}
 
 	revision, err = p.Repo().Stack().UpdateStackRevision(revision)
 

+ 6 - 0
api/types/stacks.go

@@ -146,6 +146,12 @@ type StackRevisionMeta struct {
 type StackRevision struct {
 	*StackRevisionMeta
 
+	// The reason for any error or status change
+	Reason string `json:"reason"`
+
+	// The message associated with an error or status change
+	Message string `json:"message"`
+
 	// The list of resources deployed in this revision
 	Resources []StackResource `json:"resources"`
 

+ 5 - 0
internal/models/stack.go

@@ -55,6 +55,9 @@ type StackRevision struct {
 
 	Status string
 
+	Reason  string
+	Message string
+
 	Resources []StackResource
 
 	SourceConfigs []StackSourceConfig
@@ -88,6 +91,8 @@ func (s StackRevision) ToStackRevisionType(stackID string) *types.StackRevision
 		StackRevisionMeta: &metaType,
 		SourceConfigs:     sourceConfigs,
 		Resources:         resources,
+		Reason:            s.Reason,
+		Message:           s.Message,
 	}
 }