func()

in internal/pkg/cli/pipeline_deploy.go [247:372]


func (o *deployPipelineOpts) Execute() error {
	if !o.allowDowngrade {
		isLegacy, err := o.isLegacy(o.name)
		if err != nil {
			return err
		}
		pipelineVersionGetter, err := o.pipelineVersionGetter(o.appName, o.name, isLegacy)
		if err != nil {
			return err
		}
		if err := validatePipelineVersion(pipelineVersionGetter, o.name, o.templateVersion); err != nil {
			return err
		}
	}

	// Read pipeline manifest.
	pipeline, err := o.getPipelineMft()
	if err != nil {
		return err
	}

	// If the source has an existing connection, get the correlating ConnectionARN.
	connection, ok := pipeline.Source.Properties["connection_name"]
	if ok {
		arn, err := o.codestar.GetConnectionARN((connection).(string))
		if err != nil {
			return fmt.Errorf("get connection ARN: %w", err)
		}
		pipeline.Source.Properties["connection_arn"] = arn
	}

	source, shouldPrompt, err := deploy.PipelineSourceFromManifest(pipeline.Source)
	if err != nil {
		return fmt.Errorf("read source from manifest: %w", err)
	}
	o.shouldPromptUpdateConnection = shouldPrompt

	// Convert full manifest path to relative path from workspace root.
	relPath, err := o.ws.Rel(o.pipeline.Path)
	if err != nil {
		return err
	}

	// Convert environments to deployment stages.
	stages, err := o.convertStages(pipeline.Stages)
	if err != nil {
		return fmt.Errorf("convert environments to deployment stage: %w", err)
	}

	// Get cross-regional resources.
	artifactBuckets, err := o.getArtifactBuckets()
	if err != nil {
		return fmt.Errorf("get cross-regional resources: %w", err)
	}

	isLegacy, err := o.isLegacy(pipeline.Name)
	if err != nil {
		return err
	}
	var build deploy.Build
	if err = build.Init(pipeline.Build, filepath.Dir(relPath)); err != nil {
		return err
	}

	deployPipelineInput := &deploy.CreatePipelineInput{
		AppName:             o.appName,
		Name:                pipeline.Name,
		IsLegacy:            isLegacy,
		Source:              source,
		Build:               &build,
		Stages:              stages,
		ArtifactBuckets:     artifactBuckets,
		AdditionalTags:      o.app.Tags,
		Version:             o.templateVersion,
		PermissionsBoundary: o.app.PermissionsBoundary,
	}

	overrideOpts := newOverrideOpts{
		path:       o.ws.PipelineOverridesPath(o.pipeline.Name),
		appName:    o.appName,
		fileSystem: afero.NewOsFs(),
		sess:       o.sessProvider,
	}

	overrider, err := clideploy.NewOverrider(overrideOpts.path, overrideOpts.appName, overrideOpts.envName, overrideOpts.fileSystem, overrideOpts.sess)
	if err != nil {
		return err
	}
	stackConfig := deploycfn.WrapWithTemplateOverrider(o.pipelineStackConfig(deployPipelineInput), overrider)

	if o.showDiff {
		tpl, err := stackConfig.Template()
		if err != nil {
			return fmt.Errorf("generate the new template for diff: %w", err)
		}
		if err = diff(o, tpl, o.diffWriter); err != nil {
			var errHasDiff *errHasDiff
			if !errors.As(err, &errHasDiff) {
				return err
			}
		}
		if !o.skipConfirmation {
			contd, err := o.prompt.Confirm(continueDeploymentPrompt, "")
			if err != nil {
				return fmt.Errorf("ask whether to continue with the deployment: %w", err)
			}
			if !contd {
				return nil
			}
		}
	}

	// bootstrap pipeline resources
	o.prog.Start(fmt.Sprintf(fmtPipelineDeployResourcesStart, color.HighlightUserInput(o.appName)))
	err = o.pipelineDeployer.AddPipelineResourcesToApp(o.app, o.region)
	if err != nil {
		o.prog.Stop(log.Serrorf(fmtPipelineDeployResourcesFailed, color.HighlightUserInput(o.appName)))
		return fmt.Errorf("add pipeline resources to application %s in %s: %w", o.appName, o.region, err)
	}
	o.prog.Stop(log.Ssuccessf(fmtPipelineDeployResourcesComplete, color.HighlightUserInput(o.appName)))

	if err := o.deployPipeline(deployPipelineInput, stackConfig); err != nil {
		return err
	}
	return nil
}