github.com/mook-as/cf-cli@v7.0.0-beta.28.0.20200120190804-b91c115fae48+incompatible/command/v6/create_buildpack_command_test.go (about)

     1  package v6_test
     2  
     3  import (
     4  	"errors"
     5  
     6  	. "github.com/onsi/ginkgo"
     7  	. "github.com/onsi/gomega"
     8  	. "github.com/onsi/gomega/gbytes"
     9  
    10  	"code.cloudfoundry.org/cli/actor/actionerror"
    11  	"code.cloudfoundry.org/cli/actor/v2action"
    12  	"code.cloudfoundry.org/cli/api/cloudcontroller/ccerror"
    13  	"code.cloudfoundry.org/cli/command/commandfakes"
    14  	"code.cloudfoundry.org/cli/command/translatableerror"
    15  	. "code.cloudfoundry.org/cli/command/v6"
    16  	"code.cloudfoundry.org/cli/command/v6/v6fakes"
    17  	"code.cloudfoundry.org/cli/util/configv3"
    18  	"code.cloudfoundry.org/cli/util/ui"
    19  )
    20  
    21  var _ = Describe("CreateBuildpackCommand", func() {
    22  	var (
    23  		cmd             CreateBuildpackCommand
    24  		testUI          *ui.UI
    25  		fakeConfig      *commandfakes.FakeConfig
    26  		fakeSharedActor *commandfakes.FakeSharedActor
    27  		fakeActor       *v6fakes.FakeCreateBuildpackActor
    28  		input           *Buffer
    29  		binaryName      string
    30  
    31  		executeErr error
    32  	)
    33  
    34  	BeforeEach(func() {
    35  		input = NewBuffer()
    36  		testUI = ui.NewTestUI(input, NewBuffer(), NewBuffer())
    37  		fakeConfig = new(commandfakes.FakeConfig)
    38  		fakeSharedActor = new(commandfakes.FakeSharedActor)
    39  		fakeActor = new(v6fakes.FakeCreateBuildpackActor)
    40  
    41  		cmd = CreateBuildpackCommand{
    42  			UI:          testUI,
    43  			Config:      fakeConfig,
    44  			SharedActor: fakeSharedActor,
    45  			Actor:       fakeActor,
    46  		}
    47  
    48  		cmd.RequiredArgs.Buildpack = "bp-name"
    49  		cmd.RequiredArgs.Position = 3
    50  
    51  		binaryName = "faceman"
    52  		fakeConfig.BinaryNameReturns(binaryName)
    53  	})
    54  
    55  	JustBeforeEach(func() {
    56  		executeErr = cmd.Execute(nil)
    57  	})
    58  
    59  	When("an error is encountered checking if the environment is setup correctly", func() {
    60  		BeforeEach(func() {
    61  			fakeSharedActor.CheckTargetReturns(actionerror.NotLoggedInError{BinaryName: binaryName})
    62  		})
    63  
    64  		It("returns an error", func() {
    65  			Expect(executeErr).To(MatchError(actionerror.NotLoggedInError{BinaryName: binaryName}))
    66  			Expect(fakeSharedActor.CheckTargetCallCount()).To(Equal(1))
    67  			checkTargetedOrgArg, checkTargetedSpaceArg := fakeSharedActor.CheckTargetArgsForCall(0)
    68  			Expect(checkTargetedOrgArg).To(BeFalse())
    69  			Expect(checkTargetedSpaceArg).To(BeFalse())
    70  		})
    71  	})
    72  
    73  	When("the user is logged in", func() {
    74  		When("getting the current user fails", func() {
    75  			var expectedErr error
    76  
    77  			BeforeEach(func() {
    78  				expectedErr = errors.New("some-error that happened")
    79  				fakeConfig.CurrentUserReturns(configv3.User{}, expectedErr)
    80  			})
    81  
    82  			It("returns the error", func() {
    83  				Expect(executeErr).To(MatchError(expectedErr))
    84  				Expect(fakeConfig.CurrentUserCallCount()).To(Equal(1))
    85  			})
    86  		})
    87  
    88  		When("getting the current user succeeds", func() {
    89  			var fakeUser configv3.User
    90  
    91  			BeforeEach(func() {
    92  				fakeUser = configv3.User{Name: "some-user"}
    93  				fakeConfig.CurrentUserReturns(fakeUser, nil)
    94  			})
    95  
    96  			When("creating the buildpack fails because a buildpack already exists", func() {
    97  				BeforeEach(func() {
    98  					fakeActor.CreateBuildpackReturns(v2action.Buildpack{}, v2action.Warnings{"some-create-bp-warning"}, actionerror.BuildpackNameTakenError{Name: "bp-name"})
    99  				})
   100  
   101  				It("prints the error message as a warning but does not return it", func() {
   102  					Expect(executeErr).ToNot(HaveOccurred())
   103  					Expect(testUI.Err).To(Say("some-create-bp-warning"))
   104  					Expect(testUI.Err).To(Say("Buildpack bp-name already exists"))
   105  					Expect(testUI.Out).To(Say("TIP: use 'faceman update-buildpack' to update this buildpack"))
   106  				})
   107  			})
   108  
   109  			When("creating the buildpack fails with a buildpack-invalid error", func() {
   110  				When("the buildpack has an invalid name", func() {
   111  					BeforeEach(func() {
   112  						fakeActor.CreateBuildpackReturns(v2action.Buildpack{}, v2action.Warnings{"some-create-bp-warning"}, actionerror.BuildpackInvalidError{Message: "Buildpack is invalid: name can only contain alphanumeric characters"})
   113  						cmd.RequiredArgs.Buildpack = "bp.name.oops.periods"
   114  					})
   115  
   116  					It("prints the error message as a warning but does not return it", func() {
   117  						Expect(executeErr).ToNot(HaveOccurred())
   118  						Expect(testUI.Err).To(Say("some-create-bp-warning"))
   119  						Expect(testUI.Err).To(Say("Buildpack is invalid: name can only contain alphanumeric characters"))
   120  						Expect(testUI.Out).ToNot(Say("TIP:"))
   121  					})
   122  				})
   123  
   124  				When("the buildpack with the nil stack already exists", func() {
   125  					BeforeEach(func() {
   126  						fakeActor.CreateBuildpackReturns(v2action.Buildpack{}, v2action.Warnings{"some-create-bp-warning"}, actionerror.BuildpackInvalidError{Message: "Buildpack is invalid: stack unique"})
   127  						cmd.RequiredArgs.Buildpack = "bp-name"
   128  					})
   129  
   130  					It("prints the error message as a warning but does not return it", func() {
   131  						Expect(executeErr).ToNot(HaveOccurred())
   132  						Expect(testUI.Err).To(Say("some-create-bp-warning"))
   133  						Expect(testUI.Err).To(Say("Buildpack bp-name already exists without a stack"))
   134  						Expect(testUI.Out).To(Say("TIP: use 'faceman buildpacks' and 'faceman delete-buildpack' to delete buildpack bp-name without a stack"))
   135  					})
   136  				})
   137  			})
   138  
   139  			When("the path specified is an empty directory", func() {
   140  				var emptyDirectoryError error
   141  				BeforeEach(func() {
   142  					emptyDirectoryError = actionerror.EmptyBuildpackDirectoryError{Path: "some-directory"}
   143  					fakeActor.PrepareBuildpackBitsReturns("", emptyDirectoryError)
   144  					cmd.RequiredArgs.Path = "some empty directory"
   145  				})
   146  
   147  				It("exits without updating if the path points to an empty directory", func() {
   148  					Expect(executeErr).To(MatchError(emptyDirectoryError))
   149  					Expect(fakeActor.CreateBuildpackCallCount()).To(Equal(0))
   150  				})
   151  			})
   152  
   153  			When("creating the buildpack fails with a generic error", func() {
   154  				BeforeEach(func() {
   155  					fakeActor.CreateBuildpackReturns(v2action.Buildpack{}, v2action.Warnings{"some-create-bp-warning"}, errors.New("some-create-bp-error"))
   156  				})
   157  
   158  				It("returns an error and warnings", func() {
   159  					Expect(executeErr).To(MatchError("some-create-bp-error"))
   160  					Expect(testUI.Err).To(Say("some-create-bp-warning"))
   161  				})
   162  			})
   163  
   164  			When("creating the buildpack succeeds", func() {
   165  				BeforeEach(func() {
   166  					fakeActor.CreateBuildpackReturns(v2action.Buildpack{GUID: "some-guid"}, v2action.Warnings{"some-create-bp-warning"}, nil)
   167  					cmd.RequiredArgs.Path = "some-path/to/buildpack.zip"
   168  				})
   169  
   170  				It("displays that the buildpack was created successfully", func() {
   171  					Expect(executeErr).ToNot(HaveOccurred())
   172  					Expect(testUI.Out).To(Say("OK"))
   173  
   174  					Expect(fakeActor.CreateBuildpackCallCount()).To(Equal(1))
   175  					bpName, bpPosition, enabled := fakeActor.CreateBuildpackArgsForCall(0)
   176  					Expect(bpName).To(Equal("bp-name"))
   177  					Expect(bpPosition).To(Equal(3))
   178  					Expect(enabled).To(Equal(true))
   179  				})
   180  
   181  				When("preparing the buildpack bits fails", func() {
   182  					BeforeEach(func() {
   183  						fakeActor.PrepareBuildpackBitsReturns("some/invalid/path", errors.New("some-prepare-bp-error"))
   184  					})
   185  
   186  					It("returns an error", func() {
   187  						Expect(executeErr).To(MatchError("some-prepare-bp-error"))
   188  						Expect(fakeActor.PrepareBuildpackBitsCallCount()).To(Equal(1))
   189  					})
   190  				})
   191  
   192  				When("preparing the buildpack bits succeeds", func() {
   193  					BeforeEach(func() {
   194  						fakeActor.PrepareBuildpackBitsReturns("buildpack.zip", nil)
   195  					})
   196  
   197  					It("displays that upload is starting", func() {
   198  						Expect(executeErr).ToNot(HaveOccurred())
   199  						Expect(testUI.Out).To(Say("Uploading buildpack bp-name as some-user"))
   200  
   201  						Expect(fakeActor.PrepareBuildpackBitsCallCount()).To(Equal(1))
   202  						path, _, _ := fakeActor.PrepareBuildpackBitsArgsForCall(0)
   203  						Expect(path).To(Equal("some-path/to/buildpack.zip"))
   204  					})
   205  
   206  					When("uploading the buildpack fails because a buildpack with that stack already exists", func() {
   207  						BeforeEach(func() {
   208  							fakeActor.UploadBuildpackReturns(v2action.Warnings{"some-upload-bp-warning"}, actionerror.BuildpackAlreadyExistsForStackError{Message: "The buildpack name bp-name is already in use with stack stack-name"})
   209  						})
   210  
   211  						It("prints the error message as a warning but does not return it", func() {
   212  							Expect(executeErr).ToNot(HaveOccurred())
   213  							Expect(testUI.Err).To(Say("some-upload-bp-warning"))
   214  							Expect(testUI.Err).To(Say("The buildpack name bp-name is already in use with stack stack-name"))
   215  							Expect(testUI.Out).To(Say("TIP: use 'faceman update-buildpack' to update this buildpack"))
   216  						})
   217  					})
   218  
   219  					When("uploading the buildpack fails with a generic error", func() {
   220  						BeforeEach(func() {
   221  							fakeActor.UploadBuildpackReturns(v2action.Warnings{"some-upload-bp-warning"}, errors.New("some-upload-bp-error"))
   222  						})
   223  
   224  						It("returns an error and warnings", func() {
   225  							Expect(executeErr).To(MatchError("some-upload-bp-error"))
   226  							Expect(testUI.Err).To(Say("some-create-bp-warning"))
   227  							Expect(testUI.Err).To(Say("some-upload-bp-warning"))
   228  						})
   229  
   230  					})
   231  
   232  					When("the client returns invalid auth token", func() {
   233  						BeforeEach(func() {
   234  							fakeActor.UploadBuildpackReturns(v2action.Warnings{"some-create-bp-with-auth-warning"}, ccerror.InvalidAuthTokenError{Message: "token expired"})
   235  						})
   236  
   237  						It("alerts the user and retries the upload", func() {
   238  							Expect(testUI.Err).To(Say("Failed to upload buildpack due to auth token expiration, retrying..."))
   239  							Expect(fakeActor.UploadBuildpackCallCount()).To(Equal(2))
   240  						})
   241  					})
   242  
   243  					When("uploading the buildpack succeeds", func() {
   244  						BeforeEach(func() {
   245  							fakeActor.UploadBuildpackReturns(v2action.Warnings{"some-upload-bp-warning"}, nil)
   246  						})
   247  
   248  						It("displays that the buildpack was uploaded successfully", func() {
   249  							Expect(executeErr).ToNot(HaveOccurred())
   250  							Expect(testUI.Out).To(Say("Done uploading"))
   251  							Expect(testUI.Out).To(Say("OK"))
   252  							Expect(testUI.Err).To(Say("some-upload-bp-warning"))
   253  
   254  							Expect(fakeActor.UploadBuildpackCallCount()).To(Equal(1))
   255  							guid, path, _ := fakeActor.UploadBuildpackArgsForCall(0)
   256  							Expect(guid).To(Equal("some-guid"))
   257  							Expect(path).To(Equal("buildpack.zip"))
   258  
   259  						})
   260  					})
   261  				})
   262  			})
   263  
   264  			When("both --enable and --disable are provided", func() {
   265  				BeforeEach(func() {
   266  					cmd.Enable = true
   267  					cmd.Disable = true
   268  				})
   269  
   270  				It("returns an argument combination error", func() {
   271  					argumentCombinationError := translatableerror.ArgumentCombinationError{
   272  						Args: []string{"--enable", "--disable"},
   273  					}
   274  					Expect(executeErr).To(MatchError(argumentCombinationError))
   275  				})
   276  			})
   277  
   278  			When("--enable is provided", func() {
   279  				BeforeEach(func() {
   280  					cmd.Enable = true
   281  					fakeActor.CreateBuildpackReturns(v2action.Buildpack{GUID: "some-guid"}, v2action.Warnings{"some-create-bp-warning"}, nil)
   282  				})
   283  
   284  				It("successfully creates a buildpack with enabled set to true", func() {
   285  					Expect(executeErr).ToNot(HaveOccurred())
   286  					Expect(testUI.Out).To(Say("OK"))
   287  					Expect(testUI.Out).To(Say("Uploading buildpack bp-name as some-user"))
   288  					Expect(testUI.Out).To(Say("Done uploading"))
   289  					Expect(testUI.Out).To(Say("OK"))
   290  
   291  					Expect(fakeActor.CreateBuildpackCallCount()).To(Equal(1))
   292  					_, _, enabled := fakeActor.CreateBuildpackArgsForCall(0)
   293  					Expect(enabled).To(BeTrue())
   294  				})
   295  			})
   296  
   297  			When("--disable is provided", func() {
   298  				BeforeEach(func() {
   299  					cmd.Disable = true
   300  					fakeActor.CreateBuildpackReturns(v2action.Buildpack{GUID: "some-guid"}, v2action.Warnings{"some-create-bp-warning"}, nil)
   301  				})
   302  
   303  				It("successfully creates a buildpack with enabled set to false", func() {
   304  					Expect(executeErr).ToNot(HaveOccurred())
   305  					Expect(testUI.Out).To(Say("OK"))
   306  					Expect(testUI.Out).To(Say("Uploading buildpack bp-name as some-user"))
   307  					Expect(testUI.Out).To(Say("Done uploading"))
   308  					Expect(testUI.Out).To(Say("OK"))
   309  
   310  					Expect(fakeActor.CreateBuildpackCallCount()).To(Equal(1))
   311  					_, _, enabled := fakeActor.CreateBuildpackArgsForCall(0)
   312  					Expect(enabled).To(BeFalse())
   313  				})
   314  			})
   315  
   316  		})
   317  	})
   318  })