func (s ShellDeploymentStrategy) Rollback() error { log.Info("Shell Rolling back") for _, c := range s.RollbackCommands { s.runCommand(c) } log.Info("Shell Rollback complete!") return nil }
func (s ShellDeploymentStrategy) Deploy() error { log.Info("Shell Deploying") for _, c := range s.Commands { s.runCommand(c) } if rand.Intn(2) == 1 { log.Info("Shell Deployment complete with errors, rolling back!") return errors.New("Shit, something went wrong!") } else { log.Info("Shell Deployment complete!") return nil } }
func (s ShellDeploymentStrategy) runCommand(c string) error { // Create command string cmd := s.createCommand(c) log.Info(" --> Running command: %s", c) // Create command string out, err := cmd.Output() if err != nil { log.Fatal(fmt.Sprintf("Script '%s' with args '%v' not found or is not executable: %v", cmd.Path, cmd.Args, err)) return err } log.Info(log.Colorize(log.CYAN, fmt.Sprintf("%s", out))) return nil }
func (s *ECSDeploymentStrategy) registerTask(taskJson string) { definitions := make([]*ecs.ContainerDefinition, len(s.Containers)) for i, d := range s.Containers { definitions[i] = &ecs.ContainerDefinition{ Essential: aws.Bool(d.Essential), Image: aws.String(d.Image), Name: aws.String(d.Name), Memory: aws.Int64(int64(d.Memory)), PortMappings: []*ecs.PortMapping{ { ContainerPort: aws.Int64(80), HostPort: aws.Int64(80), Protocol: aws.String("tcp"), }, }, } } params := &ecs.RegisterTaskDefinitionInput{ ContainerDefinitions: definitions, Family: aws.String(s.Application), } resp, err := s.ecs.RegisterTaskDefinition(params) if err != nil { log.Fatalf("%v", err) } s.taskDefinitionARN = *resp.TaskDefinition.TaskDefinitionArn log.Info("Task %s created", s.taskDefinitionARN) }
func (pc *DeployCommand) Run(args []string) int { cmdFlags := flag.NewFlagSet("proxy", flag.ContinueOnError) cmdFlags.Usage = func() { pc.Meta.Ui.Output(pc.Help()) } c := &godspeed.GodspeedConfig{} cmdFlags.StringVar(&c.ConfigFile, "config", "", "Path to a YAML configuration file") // Validate if err := cmdFlags.Parse(args); err != nil { return 1 } godspeed := godspeed.New(c) godspeed.Setup() log.Info("Performing Deployment...") for _, d := range godspeed.DeploymentStrategies { res := d.Deploy() if res != nil { d.Rollback() } } godspeed.Shutdown() return 0 }
func (s *ECSDeploymentStrategy) Deploy() error { log.Info("Deploying to ECS") s.checkCluster(s.ClusterName) s.registerTask(s.TaskDefinition) s.createOrUpdateService() return nil }
func (s *ECSDeploymentStrategy) createOrUpdateService() { exists := s.serviceExists(s.Service.Name) // If service does not exist... if !exists { log.Info(fmt.Sprintf("Service %s not created, creating...", s.Service.Name)) params := &ecs.CreateServiceInput{ DesiredCount: aws.Int64(1), // Required ServiceName: aws.String(s.Service.Name), // Required TaskDefinition: aws.String(s.taskDefinitionARN), Cluster: aws.String(s.ClusterName), LoadBalancers: []*ecs.LoadBalancer{ { // Required ContainerName: aws.String(s.Service.Application), ContainerPort: aws.Int64(80), LoadBalancerName: aws.String(s.ElbId), }, }, Role: aws.String("ecsServiceRole"), } _, err := s.ecs.CreateService(params) if err != nil { log.Fatal(err.Error()) return } } else { log.Info(fmt.Sprintf("Service %s already created, updating...", s.Service.Name)) params := &ecs.UpdateServiceInput{ DesiredCount: aws.Int64(1), // Required Service: aws.String(s.Service.Name), // Required TaskDefinition: aws.String(s.taskDefinitionARN), Cluster: aws.String(s.ClusterName), } _, err := s.ecs.UpdateService(params) if err != nil { log.Fatal(err.Error()) return } } }
func (s *ECSDeploymentStrategy) checkCluster(cluster string) { params := &ecs.DescribeClustersInput{ Clusters: []*string{ aws.String(cluster), }, } resp, err := s.ecs.DescribeClusters(params) if err != nil { log.Fatalf("%v", err) return } if len(resp.Clusters) == 0 { log.Fatalf("Cluster '%s' does not exist", cluster) } if *resp.Clusters[0].Status != "ACTIVE" { log.Info("Cluster not yet active, waiting...") } }
func (s *ECSDeploymentStrategy) Rollback() error { log.Info("ECS Rolling back") return nil }