github.com/mook-as/cf-cli@v7.0.0-beta.28.0.20200120190804-b91c115fae48+incompatible/cf/commands/route/delete_route_test.go (about) 1 package route_test 2 3 import ( 4 "strings" 5 6 "code.cloudfoundry.org/cli/cf/commandregistry" 7 "code.cloudfoundry.org/cli/cf/commands/route" 8 "code.cloudfoundry.org/cli/cf/configuration/coreconfig" 9 "code.cloudfoundry.org/cli/cf/errors" 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 15 "code.cloudfoundry.org/cli/cf/api/apifakes" 16 17 testconfig "code.cloudfoundry.org/cli/cf/util/testhelpers/configuration" 18 testterm "code.cloudfoundry.org/cli/cf/util/testhelpers/terminal" 19 20 . "code.cloudfoundry.org/cli/cf/util/testhelpers/matchers" 21 . "github.com/onsi/ginkgo" 22 . "github.com/onsi/gomega" 23 ) 24 25 var _ = Describe("DeleteRoute", func() { 26 var ( 27 ui *testterm.FakeUI 28 configRepo coreconfig.Repository 29 routeRepo *apifakes.FakeRouteRepository 30 31 cmd commandregistry.Command 32 deps commandregistry.Dependency 33 factory *requirementsfakes.FakeFactory 34 flagContext flags.FlagContext 35 36 loginRequirement requirements.Requirement 37 domainRequirement *requirementsfakes.FakeDomainRequirement 38 39 fakeDomain models.DomainFields 40 ) 41 42 BeforeEach(func() { 43 ui = &testterm.FakeUI{} 44 45 configRepo = testconfig.NewRepositoryWithDefaults() 46 routeRepo = new(apifakes.FakeRouteRepository) 47 repoLocator := deps.RepoLocator.SetRouteRepository(routeRepo) 48 49 deps = commandregistry.Dependency{ 50 UI: ui, 51 Config: configRepo, 52 RepoLocator: repoLocator, 53 } 54 55 cmd = &route.DeleteRoute{} 56 cmd.SetDependency(deps, false) 57 58 flagContext = flags.NewFlagContext(cmd.MetaData().Flags) 59 60 factory = new(requirementsfakes.FakeFactory) 61 62 loginRequirement = &passingRequirement{Name: "login-requirement"} 63 factory.NewLoginRequirementReturns(loginRequirement) 64 65 domainRequirement = new(requirementsfakes.FakeDomainRequirement) 66 factory.NewDomainRequirementReturns(domainRequirement) 67 68 fakeDomain = models.DomainFields{ 69 GUID: "fake-domain-guid", 70 Name: "fake-domain-name", 71 } 72 domainRequirement.GetDomainReturns(fakeDomain) 73 }) 74 75 Describe("Help text", func() { 76 var usage []string 77 78 BeforeEach(func() { 79 dr := &route.DeleteRoute{} 80 up := commandregistry.CLICommandUsagePresenter(dr) 81 usage = strings.Split(up.Usage(), "\n") 82 }) 83 84 It("has a HTTP route usage", func() { 85 Expect(usage).To(ContainElement(" Delete an HTTP route:")) 86 Expect(usage).To(ContainElement(" cf delete-route DOMAIN [--hostname HOSTNAME] [--path PATH] [-f]")) 87 }) 88 89 It("has a TCP route usage", func() { 90 Expect(usage).To(ContainElement(" Delete a TCP route:")) 91 Expect(usage).To(ContainElement(" cf delete-route DOMAIN --port PORT [-f]")) 92 }) 93 94 It("has a TCP route example", func() { 95 Expect(usage).To(ContainElement(" cf delete-route example.com --port 50000 # example.com:50000")) 96 }) 97 98 It("has a TCP option", func() { 99 Expect(usage).To(ContainElement(" --port Port used to identify the TCP route")) 100 }) 101 }) 102 103 Describe("Requirements", func() { 104 Context("when not provided exactly one arg", func() { 105 BeforeEach(func() { 106 flagContext.Parse("app-name", "extra-arg") 107 }) 108 109 It("fails with usage", func() { 110 _, err := cmd.Requirements(factory, flagContext) 111 Expect(err).To(HaveOccurred()) 112 Expect(ui.Outputs()).To(ContainSubstrings( 113 []string{"FAILED"}, 114 []string{"Incorrect Usage. Requires an argument"}, 115 )) 116 }) 117 }) 118 119 Context("when provided exactly one arg", func() { 120 BeforeEach(func() { 121 flagContext.Parse("domain-name") 122 }) 123 124 It("returns a LoginRequirement", func() { 125 actualRequirements, err := cmd.Requirements(factory, flagContext) 126 Expect(err).NotTo(HaveOccurred()) 127 Expect(factory.NewLoginRequirementCallCount()).To(Equal(1)) 128 Expect(actualRequirements).To(ContainElement(loginRequirement)) 129 }) 130 131 It("returns a DomainRequirement", func() { 132 actualRequirements, err := cmd.Requirements(factory, flagContext) 133 Expect(err).NotTo(HaveOccurred()) 134 Expect(factory.NewDomainRequirementCallCount()).To(Equal(1)) 135 136 Expect(factory.NewDomainRequirementArgsForCall(0)).To(Equal("domain-name")) 137 Expect(actualRequirements).To(ContainElement(domainRequirement)) 138 }) 139 140 Describe("deleting a tcp route", func() { 141 Context("when passing port with a hostname", func() { 142 BeforeEach(func() { 143 flagContext.Parse("example.com", "--port", "8080", "--hostname", "something-else") 144 }) 145 146 It("fails", func() { 147 _, err := cmd.Requirements(factory, flagContext) 148 Expect(err).To(HaveOccurred()) 149 Expect(ui.Outputs()).To(ContainSubstrings( 150 []string{"FAILED"}, 151 []string{"Cannot specify port together with hostname and/or path."}, 152 )) 153 }) 154 }) 155 156 Context("when passing port with a path", func() { 157 BeforeEach(func() { 158 flagContext.Parse("example.com", "--port", "8080", "--path", "something-else") 159 }) 160 161 It("fails", func() { 162 _, err := cmd.Requirements(factory, flagContext) 163 Expect(err).To(HaveOccurred()) 164 Expect(ui.Outputs()).To(ContainSubstrings( 165 []string{"FAILED"}, 166 []string{"Cannot specify port together with hostname and/or path."}, 167 )) 168 }) 169 }) 170 }) 171 }) 172 }) 173 174 Describe("Execute", func() { 175 var err error 176 177 BeforeEach(func() { 178 err := flagContext.Parse("domain-name") 179 Expect(err).NotTo(HaveOccurred()) 180 cmd.Requirements(factory, flagContext) 181 }) 182 183 JustBeforeEach(func() { 184 err = cmd.Execute(flagContext) 185 }) 186 187 Context("when passed -n flag", func() { 188 BeforeEach(func() { 189 ui.Inputs = []string{"n"} 190 }) 191 192 It("asks the user if they would like to proceed", func() { 193 Expect(err).NotTo(HaveOccurred()) 194 Eventually(func() []string { return ui.Prompts }).Should(ContainSubstrings( 195 []string{"Really delete the route"}, 196 )) 197 }) 198 }) 199 200 Context("when the response is to proceed", func() { 201 BeforeEach(func() { 202 ui.Inputs = []string{"y"} 203 }) 204 205 It("tries to find the route", func() { 206 Expect(err).NotTo(HaveOccurred()) 207 Eventually(routeRepo.FindCallCount).Should(Equal(1)) 208 host, domain, path, port := routeRepo.FindArgsForCall(0) 209 Expect(host).To(Equal("")) 210 Expect(path).To(Equal("")) 211 Expect(port).To(Equal(0)) 212 Expect(domain).To(Equal(fakeDomain)) 213 }) 214 215 Context("when a path is passed", func() { 216 BeforeEach(func() { 217 err := flagContext.Parse("domain-name", "-f", "--path", "the-path") 218 Expect(err).NotTo(HaveOccurred()) 219 cmd.Requirements(factory, flagContext) 220 }) 221 222 It("tries to find the route with the path", func() { 223 Expect(err).NotTo(HaveOccurred()) 224 Expect(routeRepo.FindCallCount()).To(Equal(1)) 225 _, _, path, _ := routeRepo.FindArgsForCall(0) 226 Expect(path).To(Equal("the-path")) 227 }) 228 }) 229 230 Context("when a port is passed", func() { 231 BeforeEach(func() { 232 err := flagContext.Parse("domain-name", "-f", "--port", "60000") 233 Expect(err).NotTo(HaveOccurred()) 234 cmd.Requirements(factory, flagContext) 235 }) 236 237 It("tries to find the route with the port", func() { 238 Expect(err).NotTo(HaveOccurred()) 239 Expect(routeRepo.FindCallCount()).To(Equal(1)) 240 _, _, _, port := routeRepo.FindArgsForCall(0) 241 Expect(port).To(Equal(60000)) 242 }) 243 }) 244 245 Context("when the route can be found", func() { 246 BeforeEach(func() { 247 routeRepo.FindReturns(models.Route{ 248 GUID: "route-guid", 249 }, nil) 250 }) 251 252 It("tries to delete the route", func() { 253 Expect(err).NotTo(HaveOccurred()) 254 Expect(routeRepo.DeleteCallCount()).To(Equal(1)) 255 Expect(routeRepo.DeleteArgsForCall(0)).To(Equal("route-guid")) 256 }) 257 258 Context("when deleting the route succeeds", func() { 259 BeforeEach(func() { 260 routeRepo.DeleteReturns(nil) 261 }) 262 263 It("tells the user that it succeeded", func() { 264 Expect(err).NotTo(HaveOccurred()) 265 Expect(ui.Outputs()).To(ContainSubstrings( 266 []string{"OK"}, 267 )) 268 }) 269 }) 270 271 Context("when deleting the route fails", func() { 272 BeforeEach(func() { 273 routeRepo.DeleteReturns(errors.New("delete-err")) 274 }) 275 276 It("fails with error", func() { 277 Expect(err).To(HaveOccurred()) 278 Expect(err.Error()).To(Equal("delete-err")) 279 }) 280 }) 281 }) 282 283 Context("when there is an error finding the route", func() { 284 BeforeEach(func() { 285 routeRepo.FindReturns(models.Route{}, errors.New("find-err")) 286 }) 287 288 It("fails with error", func() { 289 Expect(err).To(HaveOccurred()) 290 Expect(err.Error()).To(Equal("find-err")) 291 }) 292 293 It("does not try to delete the route", func() { 294 Expect(err).To(HaveOccurred()) 295 Expect(routeRepo.DeleteCallCount()).To(BeZero()) 296 }) 297 }) 298 299 Context("when there is a ModelNotFoundError when finding the route", func() { 300 BeforeEach(func() { 301 routeRepo.FindReturns(models.Route{}, errors.NewModelNotFoundError("model-type", "model-name")) 302 }) 303 304 It("tells the user that it could not delete the route", func() { 305 Expect(err).NotTo(HaveOccurred()) 306 Expect(ui.Outputs()).To(ContainSubstrings( 307 []string{"Unable to delete, route", "does not exist"}, 308 )) 309 }) 310 311 It("does not try to delete the route", func() { 312 Expect(err).NotTo(HaveOccurred()) 313 Expect(routeRepo.DeleteCallCount()).To(BeZero()) 314 }) 315 }) 316 317 }) 318 319 Context("when the response is not to proceed", func() { 320 BeforeEach(func() { 321 ui.Inputs = []string{"n"} 322 }) 323 324 It("does not try to delete the route", func() { 325 Expect(err).NotTo(HaveOccurred()) 326 Expect(routeRepo.DeleteCallCount()).To(Equal(0)) 327 }) 328 }) 329 330 Context("when force is set", func() { 331 BeforeEach(func() { 332 err := flagContext.Parse("domain-name", "-f") 333 Expect(err).NotTo(HaveOccurred()) 334 }) 335 336 It("does not ask the user if they would like to proceed", func() { 337 Expect(err).NotTo(HaveOccurred()) 338 Consistently(func() []string { return ui.Prompts }).ShouldNot(ContainSubstrings( 339 []string{"Really delete the route"}, 340 )) 341 }) 342 }) 343 }) 344 })