github.com/cloudfoundry-attic/cli-with-i18n@v6.32.1-0.20171002233121-7401370d3b85+incompatible/cf/commands/route/map_route_test.go (about)

     1  package route_test
     2  
     3  import (
     4  	"errors"
     5  
     6  	"code.cloudfoundry.org/cli/cf/commandregistry"
     7  	"code.cloudfoundry.org/cli/cf/commands/route"
     8  	"code.cloudfoundry.org/cli/cf/commands/route/routefakes"
     9  	"code.cloudfoundry.org/cli/cf/configuration/coreconfig"
    10  	"code.cloudfoundry.org/cli/cf/flags"
    11  	"code.cloudfoundry.org/cli/cf/models"
    12  	"code.cloudfoundry.org/cli/cf/requirements"
    13  	"code.cloudfoundry.org/cli/cf/requirements/requirementsfakes"
    14  	"github.com/blang/semver"
    15  
    16  	"code.cloudfoundry.org/cli/cf/api/apifakes"
    17  
    18  	testconfig "code.cloudfoundry.org/cli/util/testhelpers/configuration"
    19  	testterm "code.cloudfoundry.org/cli/util/testhelpers/terminal"
    20  
    21  	"strings"
    22  
    23  	. "code.cloudfoundry.org/cli/util/testhelpers/matchers"
    24  	. "github.com/onsi/ginkgo"
    25  	. "github.com/onsi/gomega"
    26  )
    27  
    28  var _ = Describe("MapRoute", func() {
    29  	var (
    30  		ui         *testterm.FakeUI
    31  		configRepo coreconfig.Repository
    32  		routeRepo  *apifakes.FakeRouteRepository
    33  
    34  		cmd         commandregistry.Command
    35  		deps        commandregistry.Dependency
    36  		factory     *requirementsfakes.FakeFactory
    37  		flagContext flags.FlagContext
    38  
    39  		loginRequirement            requirements.Requirement
    40  		applicationRequirement      *requirementsfakes.FakeApplicationRequirement
    41  		domainRequirement           *requirementsfakes.FakeDomainRequirement
    42  		minAPIVersionRequirement    requirements.Requirement
    43  		diegoApplicationRequirement *requirementsfakes.FakeDiegoApplicationRequirement
    44  
    45  		originalCreateRouteCmd commandregistry.Command
    46  		fakeCreateRouteCmd     commandregistry.Command
    47  
    48  		fakeDomain models.DomainFields
    49  	)
    50  
    51  	BeforeEach(func() {
    52  		ui = &testterm.FakeUI{}
    53  		configRepo = testconfig.NewRepositoryWithDefaults()
    54  		routeRepo = new(apifakes.FakeRouteRepository)
    55  		repoLocator := deps.RepoLocator.SetRouteRepository(routeRepo)
    56  
    57  		deps = commandregistry.Dependency{
    58  			UI:          ui,
    59  			Config:      configRepo,
    60  			RepoLocator: repoLocator,
    61  		}
    62  
    63  		originalCreateRouteCmd = commandregistry.Commands.FindCommand("create-route")
    64  		fakeCreateRouteCmd = new(routefakes.OldFakeRouteCreator)
    65  		commandregistry.Register(fakeCreateRouteCmd)
    66  
    67  		cmd = &route.MapRoute{}
    68  		cmd.SetDependency(deps, false)
    69  
    70  		flagContext = flags.NewFlagContext(cmd.MetaData().Flags)
    71  
    72  		factory = new(requirementsfakes.FakeFactory)
    73  
    74  		loginRequirement = &passingRequirement{Name: "login-requirement"}
    75  		factory.NewLoginRequirementReturns(loginRequirement)
    76  
    77  		applicationRequirement = new(requirementsfakes.FakeApplicationRequirement)
    78  		factory.NewApplicationRequirementReturns(applicationRequirement)
    79  
    80  		fakeApplication := models.Application{}
    81  		fakeApplication.GUID = "fake-app-guid"
    82  		applicationRequirement.GetApplicationReturns(fakeApplication)
    83  
    84  		domainRequirement = new(requirementsfakes.FakeDomainRequirement)
    85  		factory.NewDomainRequirementReturns(domainRequirement)
    86  
    87  		fakeDomain = models.DomainFields{
    88  			GUID: "fake-domain-guid",
    89  			Name: "fake-domain-name",
    90  		}
    91  		domainRequirement.GetDomainReturns(fakeDomain)
    92  
    93  		minAPIVersionRequirement = &passingRequirement{Name: "min-api-version-requirement"}
    94  		factory.NewMinAPIVersionRequirementReturns(minAPIVersionRequirement)
    95  
    96  		diegoApplicationRequirement = new(requirementsfakes.FakeDiegoApplicationRequirement)
    97  		factory.NewDiegoApplicationRequirementReturns(diegoApplicationRequirement)
    98  	})
    99  
   100  	AfterEach(func() {
   101  		commandregistry.Register(originalCreateRouteCmd)
   102  	})
   103  
   104  	Describe("Help text", func() {
   105  		var usage []string
   106  
   107  		BeforeEach(func() {
   108  			cmd := &route.MapRoute{}
   109  			up := commandregistry.CLICommandUsagePresenter(cmd)
   110  
   111  			usage = strings.Split(up.Usage(), "\n")
   112  		})
   113  
   114  		It("contains an example", func() {
   115  			Expect(usage).To(ContainElement("   cf map-route my-app example.com --port 50000                 # example.com:50000"))
   116  		})
   117  
   118  		It("contains the options", func() {
   119  			Expect(usage).To(ContainElement("   --hostname, -n      Hostname for the HTTP route (required for shared domains)"))
   120  			Expect(usage).To(ContainElement("   --path              Path for the HTTP route"))
   121  			Expect(usage).To(ContainElement("   --port              Port for the TCP route"))
   122  			Expect(usage).To(ContainElement("   --random-port       Create a random port for the TCP route"))
   123  		})
   124  
   125  		It("shows the usage", func() {
   126  			Expect(usage).To(ContainElement("   Map an HTTP route:"))
   127  			Expect(usage).To(ContainElement("      cf map-route APP_NAME DOMAIN [--hostname HOSTNAME] [--path PATH]"))
   128  
   129  			Expect(usage).To(ContainElement("   Map a TCP route:"))
   130  			Expect(usage).To(ContainElement("      cf map-route APP_NAME DOMAIN (--port PORT | --random-port)"))
   131  		})
   132  	})
   133  
   134  	Describe("Requirements", func() {
   135  		Context("when not provided exactly two args", func() {
   136  			BeforeEach(func() {
   137  				flagContext.Parse("app-name")
   138  			})
   139  
   140  			It("fails with usage", func() {
   141  				_, err := cmd.Requirements(factory, flagContext)
   142  				Expect(err).To(HaveOccurred())
   143  				Expect(ui.Outputs()).To(ContainSubstrings(
   144  					[]string{"Incorrect Usage. Requires APP_NAME and DOMAIN as arguments"},
   145  					[]string{"NAME"},
   146  					[]string{"USAGE"},
   147  				))
   148  			})
   149  		})
   150  
   151  		Context("when provided exactly two args", func() {
   152  			BeforeEach(func() {
   153  				flagContext.Parse("app-name", "domain-name")
   154  			})
   155  
   156  			It("returns a LoginRequirement", func() {
   157  				actualRequirements, err := cmd.Requirements(factory, flagContext)
   158  				Expect(err).NotTo(HaveOccurred())
   159  				Expect(factory.NewLoginRequirementCallCount()).To(Equal(1))
   160  
   161  				Expect(actualRequirements).To(ContainElement(loginRequirement))
   162  			})
   163  
   164  			It("returns an ApplicationRequirement", func() {
   165  				actualRequirements, err := cmd.Requirements(factory, flagContext)
   166  				Expect(err).NotTo(HaveOccurred())
   167  				Expect(factory.NewApplicationRequirementCallCount()).To(Equal(1))
   168  
   169  				Expect(factory.NewApplicationRequirementArgsForCall(0)).To(Equal("app-name"))
   170  				Expect(actualRequirements).To(ContainElement(applicationRequirement))
   171  			})
   172  
   173  			It("returns a DomainRequirement", func() {
   174  				actualRequirements, err := cmd.Requirements(factory, flagContext)
   175  				Expect(err).NotTo(HaveOccurred())
   176  				Expect(factory.NewDomainRequirementCallCount()).To(Equal(1))
   177  
   178  				Expect(factory.NewDomainRequirementArgsForCall(0)).To(Equal("domain-name"))
   179  				Expect(actualRequirements).To(ContainElement(domainRequirement))
   180  			})
   181  
   182  			Context("when a path is passed", func() {
   183  				BeforeEach(func() {
   184  					flagContext.Parse("app-name", "domain-name", "--path", "the-path")
   185  				})
   186  
   187  				It("returns a MinAPIVersionRequirement as the first requirement", func() {
   188  					actualRequirements, err := cmd.Requirements(factory, flagContext)
   189  					Expect(err).NotTo(HaveOccurred())
   190  
   191  					expectedVersion, err := semver.Make("2.36.0")
   192  					Expect(err).NotTo(HaveOccurred())
   193  
   194  					Expect(factory.NewMinAPIVersionRequirementCallCount()).To(Equal(1))
   195  					feature, requiredVersion := factory.NewMinAPIVersionRequirementArgsForCall(0)
   196  					Expect(feature).To(Equal("Option '--path'"))
   197  					Expect(requiredVersion).To(Equal(expectedVersion))
   198  					Expect(actualRequirements[0]).To(Equal(minAPIVersionRequirement))
   199  				})
   200  			})
   201  
   202  			Context("when a path is not passed", func() {
   203  				BeforeEach(func() {
   204  					flagContext.Parse("app-name", "domain-name")
   205  				})
   206  
   207  				It("does not return a MinAPIVersionRequirement", func() {
   208  					actualRequirements, err := cmd.Requirements(factory, flagContext)
   209  					Expect(err).NotTo(HaveOccurred())
   210  					Expect(factory.NewMinAPIVersionRequirementCallCount()).To(Equal(0))
   211  					Expect(actualRequirements).NotTo(ContainElement(minAPIVersionRequirement))
   212  				})
   213  			})
   214  
   215  			Context("when a port is passed", func() {
   216  				appName := "app-name"
   217  
   218  				BeforeEach(func() {
   219  					flagContext.Parse(appName, "domain-name", "--port", "1234")
   220  				})
   221  
   222  				It("returns a MinAPIVersionRequirement as the first requirement", func() {
   223  					actualRequirements, err := cmd.Requirements(factory, flagContext)
   224  					Expect(err).NotTo(HaveOccurred())
   225  
   226  					expectedVersion, err := semver.Make("2.53.0")
   227  					Expect(err).NotTo(HaveOccurred())
   228  
   229  					Expect(factory.NewMinAPIVersionRequirementCallCount()).To(Equal(1))
   230  					feature, requiredVersion := factory.NewMinAPIVersionRequirementArgsForCall(0)
   231  					Expect(feature).To(Equal("Option '--port'"))
   232  					Expect(requiredVersion).To(Equal(expectedVersion))
   233  					Expect(actualRequirements[0]).To(Equal(minAPIVersionRequirement))
   234  				})
   235  
   236  				It("returns a DiegoApplicationRequirement", func() {
   237  					actualRequirements, err := cmd.Requirements(factory, flagContext)
   238  					Expect(err).NotTo(HaveOccurred())
   239  
   240  					Expect(factory.NewDiegoApplicationRequirementCallCount()).To(Equal(1))
   241  					actualAppName := factory.NewDiegoApplicationRequirementArgsForCall(0)
   242  					Expect(appName).To(Equal(actualAppName))
   243  					Expect(actualRequirements).NotTo(BeEmpty())
   244  				})
   245  			})
   246  
   247  			Context("when the --random-port option is given", func() {
   248  				appName := "app-name"
   249  
   250  				BeforeEach(func() {
   251  					err := flagContext.Parse(appName, "domain-name", "--random-port")
   252  					Expect(err).NotTo(HaveOccurred())
   253  				})
   254  
   255  				It("returns a MinAPIVersionRequirement", func() {
   256  					expectedVersion, err := semver.Make("2.53.0")
   257  					Expect(err).NotTo(HaveOccurred())
   258  
   259  					actualRequirements, err := cmd.Requirements(factory, flagContext)
   260  					Expect(err).NotTo(HaveOccurred())
   261  
   262  					Expect(factory.NewMinAPIVersionRequirementCallCount()).To(Equal(1))
   263  					feature, requiredVersion := factory.NewMinAPIVersionRequirementArgsForCall(0)
   264  					Expect(feature).To(Equal("Option '--random-port'"))
   265  					Expect(requiredVersion).To(Equal(expectedVersion))
   266  					Expect(actualRequirements).To(ContainElement(minAPIVersionRequirement))
   267  				})
   268  
   269  				It("returns a DiegoApplicationRequirement", func() {
   270  					actualRequirements, err := cmd.Requirements(factory, flagContext)
   271  					Expect(err).NotTo(HaveOccurred())
   272  
   273  					Expect(factory.NewDiegoApplicationRequirementCallCount()).To(Equal(1))
   274  					actualAppName := factory.NewDiegoApplicationRequirementArgsForCall(0)
   275  					Expect(appName).To(Equal(actualAppName))
   276  					Expect(actualRequirements).NotTo(BeEmpty())
   277  				})
   278  			})
   279  
   280  			Context("when passing port with a hostname", func() {
   281  				BeforeEach(func() {
   282  					flagContext.Parse("app-name", "example.com", "--port", "8080", "--hostname", "something-else")
   283  				})
   284  
   285  				It("fails", func() {
   286  					_, err := cmd.Requirements(factory, flagContext)
   287  					Expect(err).To(HaveOccurred())
   288  					Expect(ui.Outputs()).To(ContainSubstrings(
   289  						[]string{"FAILED"},
   290  						[]string{"Cannot specify port together with hostname and/or path."},
   291  					))
   292  				})
   293  			})
   294  
   295  			Context("when passing port with a path", func() {
   296  				BeforeEach(func() {
   297  					flagContext.Parse("app-name", "example.com", "--port", "8080", "--path", "something-else")
   298  				})
   299  
   300  				It("fails", func() {
   301  					_, err := cmd.Requirements(factory, flagContext)
   302  					Expect(err).To(HaveOccurred())
   303  					Expect(ui.Outputs()).To(ContainSubstrings(
   304  						[]string{"FAILED"},
   305  						[]string{"Cannot specify port together with hostname and/or path."},
   306  					))
   307  				})
   308  			})
   309  
   310  			Context("when both --port and --random-port are given", func() {
   311  				BeforeEach(func() {
   312  					err := flagContext.Parse("app-name", "domain-name", "--port", "9090", "--random-port")
   313  					Expect(err).NotTo(HaveOccurred())
   314  				})
   315  
   316  				It("fails with error", func() {
   317  					_, err := cmd.Requirements(factory, flagContext)
   318  					Expect(err).To(HaveOccurred())
   319  					Expect(ui.Outputs()).To(ContainSubstrings(
   320  						[]string{"FAILED"},
   321  						[]string{"Cannot specify random-port together with port, hostname and/or path."},
   322  					))
   323  				})
   324  			})
   325  
   326  			Context("when both --random-port and --hostname are given", func() {
   327  				BeforeEach(func() {
   328  					err := flagContext.Parse("app-name", "domain-name", "--hostname", "host", "--random-port")
   329  					Expect(err).NotTo(HaveOccurred())
   330  				})
   331  
   332  				It("fails with error", func() {
   333  					_, err := cmd.Requirements(factory, flagContext)
   334  					Expect(err).To(HaveOccurred())
   335  					Expect(ui.Outputs()).To(ContainSubstrings(
   336  						[]string{"FAILED"},
   337  						[]string{"Cannot specify random-port together with port, hostname and/or path."},
   338  					))
   339  				})
   340  			})
   341  
   342  			Context("when --random-port and --path are given", func() {
   343  				BeforeEach(func() {
   344  					err := flagContext.Parse("app-name", "domain-name", "--path", "path", "--random-port")
   345  					Expect(err).NotTo(HaveOccurred())
   346  				})
   347  
   348  				It("fails with error", func() {
   349  					_, err := cmd.Requirements(factory, flagContext)
   350  					Expect(err).To(HaveOccurred())
   351  					Expect(ui.Outputs()).To(ContainSubstrings(
   352  						[]string{"FAILED"},
   353  						[]string{"Cannot specify random-port together with port, hostname and/or path."},
   354  					))
   355  				})
   356  			})
   357  		})
   358  	})
   359  
   360  	Describe("Execute", func() {
   361  		var err error
   362  
   363  		BeforeEach(func() {
   364  			err := flagContext.Parse("app-name", "domain-name")
   365  			Expect(err).NotTo(HaveOccurred())
   366  			cmd.Requirements(factory, flagContext)
   367  		})
   368  
   369  		JustBeforeEach(func() {
   370  			err = cmd.Execute(flagContext)
   371  		})
   372  
   373  		It("tries to create the route", func() {
   374  			Expect(err).ToNot(HaveOccurred())
   375  			fakeRouteCreator, ok := fakeCreateRouteCmd.(*routefakes.OldFakeRouteCreator)
   376  			Expect(ok).To(BeTrue())
   377  
   378  			Expect(fakeRouteCreator.CreateRouteCallCount()).To(Equal(1))
   379  			host, path, port, randomPort, domain, space := fakeRouteCreator.CreateRouteArgsForCall(0)
   380  			Expect(host).To(Equal(""))
   381  			Expect(path).To(Equal(""))
   382  			Expect(port).To(Equal(0))
   383  			Expect(randomPort).To(BeFalse())
   384  			Expect(domain).To(Equal(fakeDomain))
   385  			Expect(space).To(Equal(models.SpaceFields{
   386  				Name: "my-space",
   387  				GUID: "my-space-guid",
   388  			}))
   389  		})
   390  
   391  		Context("when a port is passed", func() {
   392  			BeforeEach(func() {
   393  				err := flagContext.Parse("app-name", "domain-name", "--port", "60000")
   394  				Expect(err).NotTo(HaveOccurred())
   395  				cmd.Requirements(factory, flagContext)
   396  			})
   397  
   398  			It("tries to create the route with the port", func() {
   399  				fakeRouteCreator, ok := fakeCreateRouteCmd.(*routefakes.OldFakeRouteCreator)
   400  				Expect(ok).To(BeTrue())
   401  
   402  				Expect(err).ToNot(HaveOccurred())
   403  				Expect(fakeRouteCreator.CreateRouteCallCount()).To(Equal(1))
   404  				_, _, port, _, _, _ := fakeRouteCreator.CreateRouteArgsForCall(0)
   405  				Expect(port).To(Equal(60000))
   406  			})
   407  		})
   408  
   409  		Context("when a random-port is passed", func() {
   410  			BeforeEach(func() {
   411  				err := flagContext.Parse("app-name", "domain-name", "--random-port")
   412  				Expect(err).NotTo(HaveOccurred())
   413  				cmd.Requirements(factory, flagContext)
   414  			})
   415  
   416  			It("tries to create the route with a random port", func() {
   417  				fakeRouteCreator, ok := fakeCreateRouteCmd.(*routefakes.OldFakeRouteCreator)
   418  				Expect(ok).To(BeTrue())
   419  
   420  				Expect(err).ToNot(HaveOccurred())
   421  				Expect(fakeRouteCreator.CreateRouteCallCount()).To(Equal(1))
   422  				_, _, _, randomPort, _, _ := fakeRouteCreator.CreateRouteArgsForCall(0)
   423  				Expect(randomPort).To(BeTrue())
   424  			})
   425  		})
   426  
   427  		Context("when creating the route fails", func() {
   428  			BeforeEach(func() {
   429  				fakeRouteCreator, ok := fakeCreateRouteCmd.(*routefakes.OldFakeRouteCreator)
   430  				Expect(ok).To(BeTrue())
   431  				fakeRouteCreator.CreateRouteReturns(models.Route{}, errors.New("create-route-err"))
   432  			})
   433  
   434  			It("returns an error", func() {
   435  				Expect(err).To(HaveOccurred())
   436  				Expect(err.Error()).To(ContainSubstring("create-route-err"))
   437  			})
   438  		})
   439  
   440  		Context("when creating the route succeeds", func() {
   441  			BeforeEach(func() {
   442  				fakeRouteCreator, ok := fakeCreateRouteCmd.(*routefakes.OldFakeRouteCreator)
   443  				Expect(ok).To(BeTrue())
   444  				fakeRouteCreator.CreateRouteReturns(models.Route{GUID: "fake-route-guid"}, nil)
   445  			})
   446  
   447  			It("tells the user that it is adding the route", func() {
   448  				Expect(err).ToNot(HaveOccurred())
   449  				Expect(ui.Outputs()).To(ContainSubstrings(
   450  					[]string{"Adding route", "to app", "in org"},
   451  				))
   452  			})
   453  
   454  			It("tries to bind the route", func() {
   455  				Expect(err).ToNot(HaveOccurred())
   456  				Expect(routeRepo.BindCallCount()).To(Equal(1))
   457  				routeGUID, appGUID := routeRepo.BindArgsForCall(0)
   458  				Expect(routeGUID).To(Equal("fake-route-guid"))
   459  				Expect(appGUID).To(Equal("fake-app-guid"))
   460  			})
   461  
   462  			Context("when binding the route succeeds", func() {
   463  				BeforeEach(func() {
   464  					routeRepo.BindReturns(nil)
   465  				})
   466  
   467  				It("tells the user that it succeeded", func() {
   468  					Expect(err).ToNot(HaveOccurred())
   469  					Expect(ui.Outputs()).To(ContainSubstrings(
   470  						[]string{"OK"},
   471  					))
   472  				})
   473  			})
   474  
   475  			Context("when binding the route fails", func() {
   476  				BeforeEach(func() {
   477  					routeRepo.BindReturns(errors.New("bind-error"))
   478  				})
   479  
   480  				It("returns an error", func() {
   481  					Expect(err).To(HaveOccurred())
   482  					Expect(err.Error()).To(Equal("bind-error"))
   483  				})
   484  			})
   485  		})
   486  
   487  		Context("when a hostname is passed", func() {
   488  			BeforeEach(func() {
   489  				err := flagContext.Parse("app-name", "domain-name", "-n", "the-hostname")
   490  				Expect(err).NotTo(HaveOccurred())
   491  				cmd.Requirements(factory, flagContext)
   492  			})
   493  
   494  			It("tries to create the route with the hostname", func() {
   495  				Expect(err).ToNot(HaveOccurred())
   496  				fakeRouteCreator, ok := fakeCreateRouteCmd.(*routefakes.OldFakeRouteCreator)
   497  				Expect(ok).To(BeTrue())
   498  				Expect(fakeRouteCreator.CreateRouteCallCount()).To(Equal(1))
   499  				hostName, _, _, _, _, _ := fakeRouteCreator.CreateRouteArgsForCall(0)
   500  				Expect(hostName).To(Equal("the-hostname"))
   501  			})
   502  		})
   503  
   504  		Context("when a hostname is not passed", func() {
   505  			BeforeEach(func() {
   506  				err := flagContext.Parse("app-name", "domain-name")
   507  				Expect(err).NotTo(HaveOccurred())
   508  				cmd.Requirements(factory, flagContext)
   509  			})
   510  
   511  			It("tries to create the route without a hostname", func() {
   512  				Expect(err).ToNot(HaveOccurred())
   513  				fakeRouteCreator, ok := fakeCreateRouteCmd.(*routefakes.OldFakeRouteCreator)
   514  				Expect(ok).To(BeTrue())
   515  				Expect(fakeRouteCreator.CreateRouteCallCount()).To(Equal(1))
   516  				hostName, _, _, _, _, _ := fakeRouteCreator.CreateRouteArgsForCall(0)
   517  				Expect(hostName).To(Equal(""))
   518  			})
   519  		})
   520  
   521  		Context("when a path is passed", func() {
   522  			BeforeEach(func() {
   523  				err := flagContext.Parse("app-name", "domain-name", "--path", "the-path")
   524  				Expect(err).NotTo(HaveOccurred())
   525  				cmd.Requirements(factory, flagContext)
   526  			})
   527  
   528  			It("tries to create the route with the path", func() {
   529  				Expect(err).ToNot(HaveOccurred())
   530  				fakeRouteCreator, ok := fakeCreateRouteCmd.(*routefakes.OldFakeRouteCreator)
   531  				Expect(ok).To(BeTrue())
   532  				Expect(fakeRouteCreator.CreateRouteCallCount()).To(Equal(1))
   533  				_, path, _, _, _, _ := fakeRouteCreator.CreateRouteArgsForCall(0)
   534  				Expect(path).To(Equal("the-path"))
   535  			})
   536  		})
   537  	})
   538  })