From 8557e91abb8d64f81a173b4a83a46ac857b2f29d Mon Sep 17 00:00:00 2001 From: Bhanu Reddy Date: Mon, 17 Feb 2025 23:43:50 +0530 Subject: [PATCH] Migrated lifecycle commands from cli to cli-artifactory --- docs/lifecycle/create/help.go | 15 - docs/lifecycle/deletelocal/help.go | 20 -- docs/lifecycle/deleteremote/help.go | 15 - docs/lifecycle/distribute/help.go | 15 - docs/lifecycle/export/help.go | 22 -- docs/lifecycle/importbundle/help.go | 13 - docs/lifecycle/promote/help.go | 18 -- go.mod | 4 +- go.sum | 8 +- lifecycle/cli.go | 456 ---------------------------- lifecycle/cli_test.go | 131 -------- lifecycle/testdata/specfile.json | 7 - lifecycle_test.go | 4 +- main.go | 2 - utils/cliutils/commandsflags.go | 78 ----- utils/distribution/distribute.go | 52 ---- 16 files changed, 8 insertions(+), 852 deletions(-) delete mode 100644 docs/lifecycle/create/help.go delete mode 100644 docs/lifecycle/deletelocal/help.go delete mode 100644 docs/lifecycle/deleteremote/help.go delete mode 100644 docs/lifecycle/distribute/help.go delete mode 100644 docs/lifecycle/export/help.go delete mode 100644 docs/lifecycle/importbundle/help.go delete mode 100644 docs/lifecycle/promote/help.go delete mode 100644 lifecycle/cli.go delete mode 100644 lifecycle/cli_test.go delete mode 100644 lifecycle/testdata/specfile.json delete mode 100644 utils/distribution/distribute.go diff --git a/docs/lifecycle/create/help.go b/docs/lifecycle/create/help.go deleted file mode 100644 index c7079e3f2..000000000 --- a/docs/lifecycle/create/help.go +++ /dev/null @@ -1,15 +0,0 @@ -package create - -var Usage = []string{"rbc [command options] "} - -func GetDescription() string { - return "Create a release bundle from builds or from existing release bundles" -} - -func GetArguments() string { - return ` release bundle name - Name of the newly created Release Bundle. - - release bundle version - Version of the newly created Release Bundle.` -} diff --git a/docs/lifecycle/deletelocal/help.go b/docs/lifecycle/deletelocal/help.go deleted file mode 100644 index fe843fe4e..000000000 --- a/docs/lifecycle/deletelocal/help.go +++ /dev/null @@ -1,20 +0,0 @@ -package deletelocal - -var Usage = []string{"rbdell [command options] ", - "rbdell [command options] "} - -func GetDescription() string { - return "Delete all release bundle promotions to an environment or delete a release bundle locally altogether." -} - -func GetArguments() string { - return ` release bundle name - Name of the Release Bundle to delete locally. - - release bundle version - Version of the Release Bundle to delete locally. - - environment - If provided, all promotions to this environment are deleted. - Otherwise, the release bundle is deleted locally with all its promotions.` -} diff --git a/docs/lifecycle/deleteremote/help.go b/docs/lifecycle/deleteremote/help.go deleted file mode 100644 index 9d0264873..000000000 --- a/docs/lifecycle/deleteremote/help.go +++ /dev/null @@ -1,15 +0,0 @@ -package deleteremote - -var Usage = []string{"rbdelr [command options] "} - -func GetDescription() string { - return "Delete a release bundle remotely." -} - -func GetArguments() string { - return ` release bundle name - Name of the Release Bundle to delete remotely. - - release bundle version - Version of the Release Bundle to delete remotely.` -} diff --git a/docs/lifecycle/distribute/help.go b/docs/lifecycle/distribute/help.go deleted file mode 100644 index 8a3c2d47f..000000000 --- a/docs/lifecycle/distribute/help.go +++ /dev/null @@ -1,15 +0,0 @@ -package distribute - -var Usage = []string{"rbd [command options] "} - -func GetDescription() string { - return "Distribute a release bundle." -} - -func GetArguments() string { - return ` release bundle name - Name of the Release Bundle to distribute. - - release bundle version - Version of the Release Bundle to distribute.` -} diff --git a/docs/lifecycle/export/help.go b/docs/lifecycle/export/help.go deleted file mode 100644 index 2e250f941..000000000 --- a/docs/lifecycle/export/help.go +++ /dev/null @@ -1,22 +0,0 @@ -package export - -var Usage = []string{"rbe [target pattern]"} - -func GetDescription() string { - return "Triggers the Export process and downloads the Release Bundle archive" -} - -func GetArguments() string { - return ` release bundle name - Name of the Release Bundle to export. - - release bundle version - Version of the Release Bundle to export. - - target pattern - The third argument is optional and specifies the local file system target path. - If the target path ends with a slash, the path is assumed to be a directory. - For example, if you specify the target as "repo-name/a/b/", then "b" is assumed to be a directory into which files should be downloaded. - If there is no terminal slash, the target path is assumed to be a file to which the downloaded file should be renamed. - For example, if you specify the target as "a/b", the downloaded file is renamed to "b". ` -} diff --git a/docs/lifecycle/importbundle/help.go b/docs/lifecycle/importbundle/help.go deleted file mode 100644 index e12be2dc2..000000000 --- a/docs/lifecycle/importbundle/help.go +++ /dev/null @@ -1,13 +0,0 @@ -package importbundle - -var Usage = []string{"rbi [command options] "} - -func GetDescription() string { - return "Import a local release bundle archive to Artifactory" -} - -func GetArguments() string { - return ` path to archive - Path to the release bundle archive on the filesystem -` -} diff --git a/docs/lifecycle/promote/help.go b/docs/lifecycle/promote/help.go deleted file mode 100644 index b4954a8cf..000000000 --- a/docs/lifecycle/promote/help.go +++ /dev/null @@ -1,18 +0,0 @@ -package promote - -var Usage = []string{"rbp [command options] "} - -func GetDescription() string { - return "Promote a release bundle" -} - -func GetArguments() string { - return ` release bundle name - Name of the Release Bundle to promote. - - release bundle version - Version of the Release Bundle to promote. - - environment - Name of the target environment for the promotion.` -} diff --git a/go.mod b/go.mod index 6d05aa279..3b08dc254 100644 --- a/go.mod +++ b/go.mod @@ -189,9 +189,9 @@ require ( sigs.k8s.io/yaml v1.4.0 // indirect ) -replace github.com/jfrog/jfrog-cli-artifactory => github.com/jfrog/jfrog-cli-artifactory v0.1.13-0.20250212084027-746cc7ae6a63 +replace github.com/jfrog/jfrog-cli-artifactory => github.com/bhanurp/jfrog-cli-artifactory v0.1.12-0.20250217173758-8a1e2a1709f0 -replace github.com/jfrog/jfrog-cli-core/v2 => github.com/jfrog/jfrog-cli-core/v2 v2.31.1-0.20250212021126-e5223ab616af +replace github.com/jfrog/jfrog-cli-core/v2 => github.com/bhanurp/jfrog-cli-core/v2 v2.31.1-0.20250217180658-1a021e22bd12 //replace github.com/jfrog/jfrog-client-go => github.com/jfrog/jfrog-client-go v1.28.1-0.20250205140905-08198f526976 diff --git a/go.sum b/go.sum index abaeff7a1..895d58866 100644 --- a/go.sum +++ b/go.sum @@ -34,6 +34,10 @@ github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5 h1:0CwZNZbxp69SHPd github.com/armon/go-socks5 v0.0.0-20160902184237-e75332964ef5/go.mod h1:wHh0iHkYZB8zMSxRWpUBQtwG5a7fFgvEO+odwuTv2gs= github.com/beevik/etree v1.4.0 h1:oz1UedHRepuY3p4N5OjE0nK1WLCqtzHf25bxplKOHLs= github.com/beevik/etree v1.4.0/go.mod h1:cyWiXwGoasx60gHvtnEh5x8+uIjUVnjWqBvEnhnqKDA= +github.com/bhanurp/jfrog-cli-artifactory v0.1.12-0.20250217173758-8a1e2a1709f0 h1:BaGx7wODzo0ee3V4MN7Qjs5fhL1J+lOxv8kSt5Idj+A= +github.com/bhanurp/jfrog-cli-artifactory v0.1.12-0.20250217173758-8a1e2a1709f0/go.mod h1:+0NKHILvHxwbTUIvGmM5EQUVhrYOIpPo07oUl+iHfLc= +github.com/bhanurp/jfrog-cli-core/v2 v2.31.1-0.20250217180658-1a021e22bd12 h1:rZxNw3r8Qo3A/48yfFpi3w7wSlg1/8RgZry0j6xA/G0= +github.com/bhanurp/jfrog-cli-core/v2 v2.31.1-0.20250217180658-1a021e22bd12/go.mod h1:Hx2houXADsNv0eRh4w5XCS2uSsPNPn1OmiSDdwGFB7g= github.com/bradleyjkemp/cupaloy/v2 v2.8.0 h1:any4BmKE+jGIaMpnU8YgH/I2LPiLBufr6oMMlVBbn9M= github.com/bradleyjkemp/cupaloy/v2 v2.8.0/go.mod h1:bm7JXdkRd4BHJk9HpwqAI8BoAY1lps46Enkdqw6aRX0= github.com/buger/jsonparser v1.1.1 h1:2PnMjfWD7wBILjqQbt530v576A/cAbQvEW9gGIpYMUs= @@ -185,10 +189,6 @@ github.com/jfrog/gofrog v1.7.6 h1:QmfAiRzVyaI7JYGsB7cxfAJePAZTzFz0gRWZSE27c6s= github.com/jfrog/gofrog v1.7.6/go.mod h1:ntr1txqNOZtHplmaNd7rS4f8jpA5Apx8em70oYEe7+4= github.com/jfrog/jfrog-apps-config v1.0.1 h1:mtv6k7g8A8BVhlHGlSveapqf4mJfonwvXYLipdsOFMY= github.com/jfrog/jfrog-apps-config v1.0.1/go.mod h1:8AIIr1oY9JuH5dylz2S6f8Ym2MaadPLR6noCBO4C22w= -github.com/jfrog/jfrog-cli-artifactory v0.1.13-0.20250212084027-746cc7ae6a63 h1:OaDd/sz00/89jzrrTnCePnjFj0qzPUy5INXSEyR/3Zg= -github.com/jfrog/jfrog-cli-artifactory v0.1.13-0.20250212084027-746cc7ae6a63/go.mod h1:llrtIDDeRoO0MmyT9shlBA74rTlaU0aJYS9JXj72F2Q= -github.com/jfrog/jfrog-cli-core/v2 v2.31.1-0.20250212021126-e5223ab616af h1:XnyhhyARP1YCzYGdhk8ovpyZV+hSchiTGVTuejrZXsI= -github.com/jfrog/jfrog-cli-core/v2 v2.31.1-0.20250212021126-e5223ab616af/go.mod h1:Hx2houXADsNv0eRh4w5XCS2uSsPNPn1OmiSDdwGFB7g= github.com/jfrog/jfrog-cli-platform-services v1.7.0 h1:u0AOyG4JX3VT7xhEeA9gDpBgW8tYILONpQURtzR3FkI= github.com/jfrog/jfrog-cli-platform-services v1.7.0/go.mod h1:u3lMRG7XC8MeUy/OPkHkZnsgCMIi0br4sjk2/W1Pm8I= github.com/jfrog/jfrog-cli-security v1.15.0 h1:TYNIID231X/AivYtptDCF25JyH8qTQht6ISHRfwejL8= diff --git a/lifecycle/cli.go b/lifecycle/cli.go deleted file mode 100644 index 37b9d3192..000000000 --- a/lifecycle/cli.go +++ /dev/null @@ -1,456 +0,0 @@ -package lifecycle - -import ( - "errors" - "fmt" - commonCliUtils "github.com/jfrog/jfrog-cli-core/v2/common/cliutils" - "github.com/jfrog/jfrog-cli-core/v2/common/commands" - "github.com/jfrog/jfrog-cli-core/v2/common/spec" - speccore "github.com/jfrog/jfrog-cli-core/v2/common/spec" - coreCommon "github.com/jfrog/jfrog-cli-core/v2/docs/common" - "github.com/jfrog/jfrog-cli-core/v2/lifecycle" - coreConfig "github.com/jfrog/jfrog-cli-core/v2/utils/config" - "github.com/jfrog/jfrog-cli-core/v2/utils/coreutils" - "github.com/jfrog/jfrog-cli/docs/common" - rbCreate "github.com/jfrog/jfrog-cli/docs/lifecycle/create" - rbDeleteLocal "github.com/jfrog/jfrog-cli/docs/lifecycle/deletelocal" - rbDeleteRemote "github.com/jfrog/jfrog-cli/docs/lifecycle/deleteremote" - rbDistribute "github.com/jfrog/jfrog-cli/docs/lifecycle/distribute" - rbExport "github.com/jfrog/jfrog-cli/docs/lifecycle/export" - rbImport "github.com/jfrog/jfrog-cli/docs/lifecycle/importbundle" - rbPromote "github.com/jfrog/jfrog-cli/docs/lifecycle/promote" - "github.com/jfrog/jfrog-cli/utils/cliutils" - "github.com/jfrog/jfrog-cli/utils/distribution" - artClientUtils "github.com/jfrog/jfrog-client-go/artifactory/services/utils" - "github.com/jfrog/jfrog-client-go/lifecycle/services" - "github.com/jfrog/jfrog-client-go/utils" - "github.com/jfrog/jfrog-client-go/utils/errorutils" - "github.com/urfave/cli" - "os" - "strings" -) - -const lcCategory = "Lifecycle" - -func GetCommands() []cli.Command { - return cliutils.GetSortedCommands(cli.CommandsByName{ - { - Name: "release-bundle-create", - Aliases: []string{"rbc"}, - Flags: cliutils.GetCommandFlags(cliutils.ReleaseBundleCreate), - Usage: rbCreate.GetDescription(), - HelpName: coreCommon.CreateUsage("release-bundle-create", rbCreate.GetDescription(), rbCreate.Usage), - UsageText: rbCreate.GetArguments(), - ArgsUsage: common.CreateEnvVars(), - BashComplete: coreCommon.CreateBashCompletionFunc(), - Category: lcCategory, - Action: create, - }, - { - Name: "release-bundle-promote", - Aliases: []string{"rbp"}, - Flags: cliutils.GetCommandFlags(cliutils.ReleaseBundlePromote), - Usage: rbPromote.GetDescription(), - HelpName: coreCommon.CreateUsage("release-bundle-promote", rbPromote.GetDescription(), rbPromote.Usage), - UsageText: rbPromote.GetArguments(), - ArgsUsage: common.CreateEnvVars(), - BashComplete: coreCommon.CreateBashCompletionFunc(), - Category: lcCategory, - Action: promote, - }, - { - Name: "release-bundle-distribute", - Aliases: []string{"rbd"}, - Flags: cliutils.GetCommandFlags(cliutils.ReleaseBundleDistribute), - Usage: rbDistribute.GetDescription(), - HelpName: coreCommon.CreateUsage("rbd", rbDistribute.GetDescription(), rbDistribute.Usage), - UsageText: rbDistribute.GetArguments(), - ArgsUsage: common.CreateEnvVars(), - BashComplete: coreCommon.CreateBashCompletionFunc(), - Category: lcCategory, - Action: distribute, - }, - { - Name: "release-bundle-export", - Aliases: []string{"rbe"}, - Flags: cliutils.GetCommandFlags(cliutils.ReleaseBundleExport), - Usage: rbExport.GetDescription(), - HelpName: coreCommon.CreateUsage("rbe", rbExport.GetDescription(), rbExport.Usage), - UsageText: rbExport.GetArguments(), - ArgsUsage: common.CreateEnvVars(), - BashComplete: coreCommon.CreateBashCompletionFunc(), - Category: lcCategory, - Action: export, - }, - { - Name: "release-bundle-delete-local", - Aliases: []string{"rbdell"}, - Flags: cliutils.GetCommandFlags(cliutils.ReleaseBundleDeleteLocal), - Usage: rbDeleteLocal.GetDescription(), - HelpName: coreCommon.CreateUsage("rbdell", rbDeleteLocal.GetDescription(), rbDeleteLocal.Usage), - UsageText: rbDeleteLocal.GetArguments(), - ArgsUsage: common.CreateEnvVars(), - BashComplete: coreCommon.CreateBashCompletionFunc(), - Category: lcCategory, - Action: deleteLocal, - }, - { - Name: "release-bundle-delete-remote", - Aliases: []string{"rbdelr"}, - Flags: cliutils.GetCommandFlags(cliutils.ReleaseBundleDeleteRemote), - Usage: rbDeleteRemote.GetDescription(), - HelpName: coreCommon.CreateUsage("rbdelr", rbDeleteRemote.GetDescription(), rbDeleteRemote.Usage), - UsageText: rbDeleteRemote.GetArguments(), - ArgsUsage: common.CreateEnvVars(), - BashComplete: coreCommon.CreateBashCompletionFunc(), - Category: lcCategory, - Action: deleteRemote, - }, - { - Name: "release-bundle-import", - Aliases: []string{"rbi"}, - Flags: cliutils.GetCommandFlags(cliutils.ReleaseBundleImport), - Usage: rbImport.GetDescription(), - HelpName: coreCommon.CreateUsage("rbi", rbImport.GetDescription(), rbImport.Usage), - UsageText: rbImport.GetArguments(), - ArgsUsage: common.CreateEnvVars(), - BashComplete: coreCommon.CreateBashCompletionFunc(), - Category: lcCategory, - Action: releaseBundleImport, - }, - }) -} - -func validateCreateReleaseBundleContext(c *cli.Context) error { - if show, err := cliutils.ShowCmdHelpIfNeeded(c, c.Args()); show || err != nil { - return err - } - - if c.NArg() != 2 { - return cliutils.WrongNumberOfArgumentsHandler(c) - } - - return assertValidCreationMethod(c) -} - -func assertValidCreationMethod(c *cli.Context) error { - // Determine the methods provided - methods := []bool{ - c.IsSet("spec"), - c.IsSet(cliutils.Builds), - c.IsSet(cliutils.ReleaseBundles), - } - methodCount := coreutils.SumTrueValues(methods) - - // Validate that only one creation method is provided - if err := validateSingleCreationMethod(methodCount); err != nil { - return err - } - - if err := validateCreationValuesPresence(c, methodCount); err != nil { - return err - } - return nil -} - -func validateSingleCreationMethod(methodCount int) error { - if methodCount > 1 { - return errorutils.CheckErrorf( - "exactly one creation source must be supplied: --%s, --%s, or --%s.\n"+ - "Opt to use the --%s option as the --%s and --%s are deprecated", - "spec", cliutils.Builds, cliutils.ReleaseBundles, - "spec", cliutils.Builds, cliutils.ReleaseBundles, - ) - } - return nil -} - -func validateCreationValuesPresence(c *cli.Context, methodCount int) error { - if methodCount == 0 { - if !areBuildFlagsSet(c) && !areBuildEnvVarsSet() { - return errorutils.CheckErrorf("Either --build-name or JFROG_CLI_BUILD_NAME, and --build-number or JFROG_CLI_BUILD_NUMBER must be defined") - } - } - return nil -} - -// areBuildFlagsSet checks if build-name or build-number flags are set. -func areBuildFlagsSet(c *cli.Context) bool { - return c.IsSet(cliutils.BuildName) || c.IsSet(cliutils.BuildNumber) -} - -// areBuildEnvVarsSet checks if build environment variables are set. -func areBuildEnvVarsSet() bool { - return os.Getenv("JFROG_CLI_BUILD_NUMBER") != "" && os.Getenv("JFROG_CLI_BUILD_NAME") != "" -} - -func create(c *cli.Context) (err error) { - if err = validateCreateReleaseBundleContext(c); err != nil { - return err - } - - creationSpec, err := getReleaseBundleCreationSpec(c) - if err != nil { - return - } - - lcDetails, err := createLifecycleDetailsByFlags(c) - if err != nil { - return - } - - createCmd := lifecycle.NewReleaseBundleCreateCommand().SetServerDetails(lcDetails).SetReleaseBundleName(c.Args().Get(0)). - SetReleaseBundleVersion(c.Args().Get(1)).SetSigningKeyName(c.String(cliutils.SigningKey)).SetSync(c.Bool(cliutils.Sync)). - SetReleaseBundleProject(cliutils.GetProject(c)).SetSpec(creationSpec). - SetBuildsSpecPath(c.String(cliutils.Builds)).SetReleaseBundlesSpecPath(c.String(cliutils.ReleaseBundles)) - return commands.Exec(createCmd) -} - -func getReleaseBundleCreationSpec(c *cli.Context) (*spec.SpecFiles, error) { - // Checking if the "builds" or "release-bundles" flags are set - if so, the spec flag should be ignored - if c.IsSet(cliutils.Builds) || c.IsSet(cliutils.ReleaseBundles) { - return nil, nil - } - - // Check if the "spec" flag is set - if so, return the spec - if c.IsSet("spec") { - return cliutils.GetSpec(c, true, false) - } - - // Else - create a spec from the buildName and buildnumber flags or env vars - buildName := getStringFlagOrEnv(c, cliutils.BuildName, coreutils.BuildName) - buildNumber := getStringFlagOrEnv(c, cliutils.BuildNumber, coreutils.BuildNumber) - - if buildName != "" && buildNumber != "" { - return speccore.CreateSpecFromBuildNameAndNumber(buildName, buildNumber) - } - - return nil, fmt.Errorf("either the --spec flag must be provided, " + - "or both --build-name and --build-number flags (or their corresponding environment variables " + - "JFROG_CLI_BUILD_NAME and JFROG_CLI_BUILD_NUMBER) must be set") -} - -func getStringFlagOrEnv(c *cli.Context, flag string, envVar string) string { - if c.IsSet(flag) { - return c.String(flag) - } - return os.Getenv(envVar) -} - -func promote(c *cli.Context) error { - if show, err := cliutils.ShowCmdHelpIfNeeded(c, c.Args()); show || err != nil { - return err - } - - if c.NArg() != 3 { - return cliutils.WrongNumberOfArgumentsHandler(c) - } - - lcDetails, err := createLifecycleDetailsByFlags(c) - if err != nil { - return err - } - - promoteCmd := lifecycle.NewReleaseBundlePromoteCommand().SetServerDetails(lcDetails).SetReleaseBundleName(c.Args().Get(0)). - SetReleaseBundleVersion(c.Args().Get(1)).SetEnvironment(c.Args().Get(2)).SetSigningKeyName(c.String(cliutils.SigningKey)). - SetSync(c.Bool(cliutils.Sync)).SetReleaseBundleProject(cliutils.GetProject(c)). - SetIncludeReposPatterns(splitRepos(c, cliutils.IncludeRepos)).SetExcludeReposPatterns(splitRepos(c, cliutils.ExcludeRepos)) - return commands.Exec(promoteCmd) -} - -func distribute(c *cli.Context) error { - if err := validateDistributeCommand(c); err != nil { - return err - } - - lcDetails, err := createLifecycleDetailsByFlags(c) - if err != nil { - return err - } - distributionRules, maxWaitMinutes, _, err := distribution.InitReleaseBundleDistributeCmd(c) - if err != nil { - return err - } - - distributeCmd := lifecycle.NewReleaseBundleDistributeCommand() - distributeCmd.SetServerDetails(lcDetails). - SetReleaseBundleName(c.Args().Get(0)). - SetReleaseBundleVersion(c.Args().Get(1)). - SetReleaseBundleProject(cliutils.GetProject(c)). - SetDistributionRules(distributionRules). - SetDryRun(c.Bool("dry-run")). - SetAutoCreateRepo(c.Bool(cliutils.CreateRepo)). - SetPathMappingPattern(c.String(cliutils.PathMappingPattern)). - SetPathMappingTarget(c.String(cliutils.PathMappingTarget)). - SetSync(c.Bool(cliutils.Sync)). - SetMaxWaitMinutes(maxWaitMinutes) - return commands.Exec(distributeCmd) -} - -func deleteLocal(c *cli.Context) error { - if show, err := cliutils.ShowCmdHelpIfNeeded(c, c.Args()); show || err != nil { - return err - } - - if c.NArg() != 2 && c.NArg() != 3 { - return cliutils.WrongNumberOfArgumentsHandler(c) - } - - lcDetails, err := createLifecycleDetailsByFlags(c) - if err != nil { - return err - } - - environment := "" - if c.NArg() == 3 { - environment = c.Args().Get(2) - } - - deleteCmd := lifecycle.NewReleaseBundleDeleteCommand(). - SetServerDetails(lcDetails). - SetReleaseBundleName(c.Args().Get(0)). - SetReleaseBundleVersion(c.Args().Get(1)). - SetEnvironment(environment). - SetQuiet(cliutils.GetQuietValue(c)). - SetReleaseBundleProject(cliutils.GetProject(c)). - SetSync(c.Bool(cliutils.Sync)) - return commands.Exec(deleteCmd) -} - -func deleteRemote(c *cli.Context) error { - if show, err := cliutils.ShowCmdHelpIfNeeded(c, c.Args()); show || err != nil { - return err - } - - if c.NArg() != 2 { - return cliutils.WrongNumberOfArgumentsHandler(c) - } - - lcDetails, err := createLifecycleDetailsByFlags(c) - if err != nil { - return err - } - - distributionRules, maxWaitMinutes, _, err := distribution.InitReleaseBundleDistributeCmd(c) - if err != nil { - return err - } - - deleteCmd := lifecycle.NewReleaseBundleRemoteDeleteCommand(). - SetServerDetails(lcDetails). - SetReleaseBundleName(c.Args().Get(0)). - SetReleaseBundleVersion(c.Args().Get(1)). - SetDistributionRules(distributionRules). - SetDryRun(c.Bool("dry-run")). - SetMaxWaitMinutes(maxWaitMinutes). - SetQuiet(cliutils.GetQuietValue(c)). - SetReleaseBundleProject(cliutils.GetProject(c)). - SetSync(c.Bool(cliutils.Sync)) - return commands.Exec(deleteCmd) -} - -func export(c *cli.Context) error { - if show, err := cliutils.ShowCmdHelpIfNeeded(c, c.Args()); show || err != nil { - return err - } - - if c.NArg() < 2 { - return cliutils.WrongNumberOfArgumentsHandler(c) - } - lcDetails, err := createLifecycleDetailsByFlags(c) - if err != nil { - return err - } - exportCmd, modifications := initReleaseBundleExportCmd(c) - downloadConfig, err := cliutils.CreateDownloadConfiguration(c) - if err != nil { - return err - } - exportCmd. - SetServerDetails(lcDetails). - SetReleaseBundleExportModifications(modifications). - SetDownloadConfiguration(*downloadConfig) - - return commands.Exec(exportCmd) -} - -func releaseBundleImport(c *cli.Context) error { - if show, err := cliutils.ShowCmdHelpIfNeeded(c, c.Args()); show || err != nil { - return err - } - - if c.NArg() != 1 { - return cliutils.WrongNumberOfArgumentsHandler(c) - } - - rtDetails, err := createLifecycleDetailsByFlags(c) - if err != nil { - return err - } - importCmd := lifecycle.NewReleaseBundleImportCommand() - if err != nil { - return err - } - importCmd. - SetServerDetails(rtDetails). - SetFilepath(c.Args().Get(0)) - - return commands.Exec(importCmd) -} - -func validateDistributeCommand(c *cli.Context) error { - if err := distribution.ValidateReleaseBundleDistributeCmd(c); err != nil { - return err - } - - mappingPatternProvided := c.IsSet(cliutils.PathMappingPattern) - mappingTargetProvided := c.IsSet(cliutils.PathMappingTarget) - if (mappingPatternProvided && !mappingTargetProvided) || - (!mappingPatternProvided && mappingTargetProvided) { - return errorutils.CheckErrorf("the options --%s and --%s must be provided together", cliutils.PathMappingPattern, cliutils.PathMappingTarget) - } - return nil -} - -func createLifecycleDetailsByFlags(c *cli.Context) (*coreConfig.ServerDetails, error) { - lcDetails, err := cliutils.CreateServerDetailsWithConfigOffer(c, true, commonCliUtils.Platform) - if err != nil { - return nil, err - } - if lcDetails.Url == "" { - return nil, errors.New("platform URL is mandatory for lifecycle commands") - } - PlatformToLifecycleUrls(lcDetails) - return lcDetails, nil -} - -func PlatformToLifecycleUrls(lcDetails *coreConfig.ServerDetails) { - lcDetails.ArtifactoryUrl = utils.AddTrailingSlashIfNeeded(lcDetails.Url) + "artifactory/" - lcDetails.LifecycleUrl = utils.AddTrailingSlashIfNeeded(lcDetails.Url) + "lifecycle/" - lcDetails.Url = "" -} - -func splitRepos(c *cli.Context, reposOptionKey string) []string { - if c.IsSet(reposOptionKey) { - return strings.Split(c.String(reposOptionKey), ";") - } - return nil -} - -func initReleaseBundleExportCmd(c *cli.Context) (command *lifecycle.ReleaseBundleExportCommand, modifications services.Modifications) { - command = lifecycle.NewReleaseBundleExportCommand(). - SetReleaseBundleName(c.Args().Get(0)). - SetReleaseBundleVersion(c.Args().Get(1)). - SetTargetPath(c.Args().Get(2)). - SetProject(c.String(cliutils.Project)) - - modifications = services.Modifications{ - PathMappings: []artClientUtils.PathMapping{ - { - Input: c.String(cliutils.PathMappingPattern), - Output: c.String(cliutils.PathMappingTarget), - }, - }, - } - return -} diff --git a/lifecycle/cli_test.go b/lifecycle/cli_test.go deleted file mode 100644 index 5c49bcd22..000000000 --- a/lifecycle/cli_test.go +++ /dev/null @@ -1,131 +0,0 @@ -package lifecycle - -import ( - "github.com/jfrog/jfrog-cli-core/v2/utils/coreutils" - "github.com/jfrog/jfrog-cli/utils/cliutils" - "github.com/jfrog/jfrog-cli/utils/tests" - clientTestUtils "github.com/jfrog/jfrog-client-go/utils/tests" - "github.com/stretchr/testify/assert" - "path/filepath" - "testing" -) - -func TestValidateCreateReleaseBundleContext(t *testing.T) { - testRuns := []struct { - name string - args []string - flags []string - expectError bool - }{ - {"withoutArgs", []string{}, []string{}, true}, - {"oneArg", []string{"one"}, []string{}, true}, - {"twoArgs", []string{"one", "two"}, []string{}, true}, - {"extraArgs", []string{"one", "two", "three", "four"}, []string{}, true}, - {"bothSources", []string{"one", "two", "three"}, []string{cliutils.Builds + "=/path/to/file", cliutils.ReleaseBundles + "=/path/to/file"}, true}, - {"noSources", []string{"one", "two", "three"}, []string{}, true}, - {"builds without signing key", []string{"name", "version"}, []string{cliutils.Builds + "=/path/to/file"}, false}, - {"builds correct", []string{"name", "version"}, []string{ - cliutils.Builds + "=/path/to/file", cliutils.SigningKey + "=key"}, false}, - {"releaseBundles without signing key", []string{"name", "version"}, []string{cliutils.ReleaseBundles + "=/path/to/file"}, false}, - {"releaseBundles correct", []string{"name", "version"}, []string{ - cliutils.ReleaseBundles + "=/path/to/file", cliutils.SigningKey + "=key"}, false}, - {"spec without signing key", []string{"name", "version", "env"}, []string{"spec=/path/to/file"}, true}, - {"spec correct", []string{"name", "version"}, []string{ - "spec=/path/to/file", cliutils.SigningKey + "=key"}, false}, - } - - for _, test := range testRuns { - t.Run(test.name, func(t *testing.T) { - context, buffer := tests.CreateContext(t, test.flags, test.args) - err := validateCreateReleaseBundleContext(context) - if test.expectError { - assert.Error(t, err, buffer) - } else { - assert.NoError(t, err, buffer) - } - }) - } -} - -// Validates that the project option does not override the project field in the spec file. -func TestCreateReleaseBundleSpecWithProject(t *testing.T) { - projectKey := "myproj" - specFile := filepath.Join("testdata", "specfile.json") - context, _ := tests.CreateContext(t, []string{"spec=" + specFile, "project=" + projectKey}, []string{}) - creationSpec, err := getReleaseBundleCreationSpec(context) - assert.NoError(t, err) - assert.Equal(t, creationSpec.Get(0).Pattern, "path/to/file") - creationSpec.Get(0).Project = "" - assert.Equal(t, projectKey, cliutils.GetProject(context)) -} - -func TestGetReleaseBundleCreationSpec(t *testing.T) { - - t.Run("Spec Flag Set", func(t *testing.T) { - specFile := filepath.Join("testdata", "specfile.json") - ctx, _ := tests.CreateContext(t, []string{"spec=" + specFile}, []string{}) - - spec, err := getReleaseBundleCreationSpec(ctx) - - assert.NoError(t, err) - assert.NotNil(t, spec) - }) - - t.Run("Build Name and Number Set via Flags", func(t *testing.T) { - ctx, _ := tests.CreateContext(t, []string{"build-name=Common-builds", "build-number=1.0.0"}, []string{}) - - spec, err := getReleaseBundleCreationSpec(ctx) - - assert.NoError(t, err) - assert.NotNil(t, spec) - assert.Equal(t, "Common-builds/1.0.0", spec.Files[0].Build) - }) - - t.Run("Build Name and Number Set via Env Variables", func(t *testing.T) { - - setEnvBuildNameCallBack := clientTestUtils.SetEnvWithCallbackAndAssert(t, coreutils.BuildName, "Common-builds") - defer setEnvBuildNameCallBack() - setEnvBuildNumberCallBack := clientTestUtils.SetEnvWithCallbackAndAssert(t, coreutils.BuildNumber, "2.0.0") - defer setEnvBuildNumberCallBack() - - ctx, _ := tests.CreateContext(t, []string{}, []string{}) - - spec, err := getReleaseBundleCreationSpec(ctx) - - assert.NoError(t, err) - assert.NotNil(t, spec) - assert.Equal(t, "Common-builds/2.0.0", spec.Files[0].Build) - }) - - t.Run("Missing Build Name and Number", func(t *testing.T) { - ctx, _ := tests.CreateContext(t, []string{}, []string{}) - - spec, err := getReleaseBundleCreationSpec(ctx) - - assert.Error(t, err) - assert.Nil(t, spec) - assert.EqualError(t, err, "either the --spec flag must be provided, or both --build-name and --build-number flags (or their corresponding environment variables JFROG_CLI_BUILD_NAME and JFROG_CLI_BUILD_NUMBER) must be set") - }) - - t.Run("Only One Build Variable Set", func(t *testing.T) { - ctx, _ := tests.CreateContext(t, []string{"build-name=Common-builds"}, []string{}) - - spec, err := getReleaseBundleCreationSpec(ctx) - - assert.Error(t, err) - assert.Nil(t, spec) - assert.EqualError(t, err, "either the --spec flag must be provided, or both --build-name and --build-number flags (or their corresponding environment variables JFROG_CLI_BUILD_NAME and JFROG_CLI_BUILD_NUMBER) must be set") - }) - - t.Run("One Env Variable One Flag", func(t *testing.T) { - ctx, _ := tests.CreateContext(t, []string{"build-name=Common-builds"}, []string{}) - setEnvBuildNumberCallBack := clientTestUtils.SetEnvWithCallbackAndAssert(t, coreutils.BuildNumber, "2.0.0") - defer setEnvBuildNumberCallBack() - - spec, err := getReleaseBundleCreationSpec(ctx) - - assert.NoError(t, err) - assert.NotNil(t, spec) - assert.Equal(t, "Common-builds/2.0.0", spec.Files[0].Build) - }) -} diff --git a/lifecycle/testdata/specfile.json b/lifecycle/testdata/specfile.json deleted file mode 100644 index 8d28c94c9..000000000 --- a/lifecycle/testdata/specfile.json +++ /dev/null @@ -1,7 +0,0 @@ -{ - "files": [ - { - "pattern": "path/to/file" - } - ] -} \ No newline at end of file diff --git a/lifecycle_test.go b/lifecycle_test.go index 4367e8205..a6ed84a4a 100644 --- a/lifecycle_test.go +++ b/lifecycle_test.go @@ -5,11 +5,11 @@ import ( "fmt" "github.com/jfrog/gofrog/io" "github.com/jfrog/jfrog-cli-core/v2/artifactory/utils" + coreCliUtils "github.com/jfrog/jfrog-cli-core/v2/common/cliutils" configUtils "github.com/jfrog/jfrog-cli-core/v2/utils/config" "github.com/jfrog/jfrog-cli-core/v2/utils/coreutils" coreTests "github.com/jfrog/jfrog-cli-core/v2/utils/tests" "github.com/jfrog/jfrog-cli/inttestutils" - lifecycleCli "github.com/jfrog/jfrog-cli/lifecycle" "github.com/jfrog/jfrog-cli/utils/cliutils" "github.com/jfrog/jfrog-cli/utils/tests" "github.com/jfrog/jfrog-client-go/http/httpclient" @@ -321,7 +321,7 @@ func authenticateLifecycle() string { *tests.JfrogUrl = clientUtils.AddTrailingSlashIfNeeded(*tests.JfrogUrl) lcDetails = &configUtils.ServerDetails{ Url: *tests.JfrogUrl} - lifecycleCli.PlatformToLifecycleUrls(lcDetails) + coreCliUtils.PlatformToLifecycleUrls(lcDetails) cred := fmt.Sprintf("--url=%s", *tests.JfrogUrl) if *tests.JfrogAccessToken != "" { diff --git a/main.go b/main.go index 1001d880a..4e6b5911e 100644 --- a/main.go +++ b/main.go @@ -26,7 +26,6 @@ import ( "github.com/jfrog/jfrog-cli/general/login" "github.com/jfrog/jfrog-cli/general/summary" "github.com/jfrog/jfrog-cli/general/token" - "github.com/jfrog/jfrog-cli/lifecycle" "github.com/jfrog/jfrog-cli/missioncontrol" "github.com/jfrog/jfrog-cli/pipelines" "github.com/jfrog/jfrog-cli/plugins" @@ -312,7 +311,6 @@ func getCommands() ([]cli.Command, error) { allCommands = append(allCommands, platformServicesCmds...) allCommands = append(allCommands, utils.GetPlugins()...) allCommands = append(allCommands, buildtools.GetCommands()...) - allCommands = append(allCommands, lifecycle.GetCommands()...) return append(allCommands, buildtools.GetBuildToolsHelpCommands()...), nil } diff --git a/utils/cliutils/commandsflags.go b/utils/cliutils/commandsflags.go index c237ffe60..8f1f97a73 100644 --- a/utils/cliutils/commandsflags.go +++ b/utils/cliutils/commandsflags.go @@ -113,15 +113,6 @@ const ( // TransferInstall commands keys TransferInstall = "transfer-plugin-install" - // Lifecycle commands keys - ReleaseBundleCreate = "release-bundle-create" - ReleaseBundlePromote = "release-bundle-promote" - ReleaseBundleDistribute = "release-bundle-distribute" - ReleaseBundleDeleteLocal = "release-bundle-delete-local" - ReleaseBundleDeleteRemote = "release-bundle-delete-remote" - ReleaseBundleExport = "release-bundle-export" - ReleaseBundleImport = "release-bundle-import" - // Access Token Create commands keys AccessTokenCreate = "access-token-create" @@ -1629,55 +1620,11 @@ var flagsMap = map[string]cli.Flag{ Name: PreChecks, Usage: "[Default: false] Set to true to run pre-transfer checks.` `", }, - lcSync: cli.BoolTFlag{ - Name: Sync, - Usage: "[Default: true] Set to false to run asynchronously.` `", - }, - lcProject: cli.StringFlag{ - Name: Project, - Usage: "[Optional] Project key associated with the Release Bundle version.` `", - }, - lcBuilds: cli.StringFlag{ - Name: Builds, - Usage: "[Optional] Path to a JSON file containing information of the source builds from which to create a release bundle.` `", - Hidden: true, - }, - lcReleaseBundles: cli.StringFlag{ - Name: ReleaseBundles, - Usage: "[Optional] Path to a JSON file containing information of the source release bundles from which to create a release bundle.` `", - Hidden: true, - }, - lcSigningKey: cli.StringFlag{ - Name: SigningKey, - Usage: "[Optional] The GPG/RSA key-pair name given in Artifactory. If the key isn't provided, the command creates or uses the default key.` `", - }, - lcPathMappingPattern: cli.StringFlag{ - Name: PathMappingPattern, - Usage: "[Optional] Specify along with '" + PathMappingTarget + "' to distribute artifacts to a different path on the edge node. You can use wildcards to specify multiple artifacts.` `", - }, - lcPathMappingTarget: cli.StringFlag{ - Name: PathMappingTarget, - Usage: "[Optional] The target path for distributed artifacts on the edge node. If not specified, the artifacts will have the same path and name on the edge node, as on the source Artifactory server. " + - "For flexibility in specifying the distribution path, you can include placeholders in the form of {1}, {2} which are replaced by corresponding tokens in the pattern path that are enclosed in parenthesis.` `", - }, - lcDryRun: cli.BoolFlag{ - Name: dryRun, - Usage: "[Default: false] Set to true to only simulate the distribution of the release bundle.` `", - }, ThirdPartyContextualAnalysis: cli.BoolFlag{ Name: ThirdPartyContextualAnalysis, Usage: "Default: false] [npm] when set, the Contextual Analysis scan also uses the code of the project dependencies to determine the applicability of the vulnerability.", Hidden: true, }, - lcIncludeRepos: cli.StringFlag{ - Name: IncludeRepos, - Usage: "[Optional] List of semicolon-separated(;) repositories to include in the promotion. If this property is left undefined, all repositories (except those specifically excluded) are included in the promotion. " + - "If one or more repositories are specifically included, all other repositories are excluded.` `", - }, - lcExcludeRepos: cli.StringFlag{ - Name: ExcludeRepos, - Usage: "[Optional] List of semicolon-separated(;) repositories to exclude from the promotion.` `", - }, atcProject: cli.StringFlag{ Name: Project, Usage: "[Optional] The project for which this token is created. Enter the project name on which you want to apply this token.` `", @@ -1996,31 +1943,6 @@ var commandFlags = map[string][]string{ TransferInstall: { installPluginVersion, InstallPluginSrcDir, InstallPluginHomeDir, }, - ReleaseBundleCreate: { - platformUrl, user, password, accessToken, serverId, lcSigningKey, lcSync, lcProject, lcBuilds, lcReleaseBundles, - specFlag, specVars, BuildName, BuildNumber, - }, - ReleaseBundlePromote: { - platformUrl, user, password, accessToken, serverId, lcSigningKey, lcSync, lcProject, lcIncludeRepos, lcExcludeRepos, - }, - ReleaseBundleDistribute: { - platformUrl, user, password, accessToken, serverId, lcProject, DistRules, site, city, countryCodes, - lcDryRun, CreateRepo, lcPathMappingPattern, lcPathMappingTarget, lcSync, maxWaitMinutes, - }, - ReleaseBundleDeleteLocal: { - platformUrl, user, password, accessToken, serverId, deleteQuiet, lcSync, lcProject, - }, - ReleaseBundleDeleteRemote: { - platformUrl, user, password, accessToken, serverId, deleteQuiet, lcDryRun, DistRules, site, city, countryCodes, - lcSync, maxWaitMinutes, lcProject, - }, - ReleaseBundleExport: { - platformUrl, user, password, accessToken, serverId, lcPathMappingTarget, lcPathMappingPattern, Project, - downloadMinSplit, downloadSplitCount, - }, - ReleaseBundleImport: { - user, password, accessToken, serverId, platformUrl, - }, // Mission Control's commands McConfig: { mcUrl, mcAccessToken, mcInteractive, diff --git a/utils/distribution/distribute.go b/utils/distribution/distribute.go deleted file mode 100644 index bbc82bae9..000000000 --- a/utils/distribution/distribute.go +++ /dev/null @@ -1,52 +0,0 @@ -package distribution - -import ( - "github.com/jfrog/jfrog-cli-core/v2/common/spec" - "github.com/jfrog/jfrog-cli/utils/cliutils" - distributionUtils "github.com/jfrog/jfrog-client-go/utils/distribution" - "github.com/urfave/cli" -) - -func CreateDefaultDistributionRules(c *cli.Context) *spec.DistributionRules { - return &spec.DistributionRules{ - DistributionRules: []spec.DistributionRule{{ - SiteName: c.String("site"), - CityName: c.String("city"), - CountryCodes: cliutils.GetStringsArrFlagValue(c, "country-codes"), - }}, - } -} - -func ValidateReleaseBundleDistributeCmd(c *cli.Context) error { - if c.NArg() != 2 { - return cliutils.WrongNumberOfArgumentsHandler(c) - } - if c.IsSet("max-wait-minutes") && !c.IsSet("sync") { - return cliutils.PrintHelpAndReturnError("The --max-wait-minutes option can't be used without --sync", c) - } - - if c.IsSet("dist-rules") && (c.IsSet("site") || c.IsSet("city") || c.IsSet("country-code")) { - return cliutils.PrintHelpAndReturnError("The --dist-rules option can't be used with --site, --city or --country-code", c) - } - - return nil -} - -func InitReleaseBundleDistributeCmd(c *cli.Context) (distributionRules *spec.DistributionRules, maxWaitMinutes int, params distributionUtils.DistributionParams, err error) { - if c.IsSet("dist-rules") { - distributionRules, err = spec.CreateDistributionRulesFromFile(c.String("dist-rules")) - if err != nil { - return - } - } else { - distributionRules = CreateDefaultDistributionRules(c) - } - - maxWaitMinutes, err = cliutils.GetIntFlagValue(c, "max-wait-minutes", 60) - if err != nil { - return - } - - params = distributionUtils.NewDistributeReleaseBundleParams(c.Args().Get(0), c.Args().Get(1)) - return -}