github.com/loggregator/cli@v6.33.1-0.20180224010324-82334f081791+incompatible/integration/global/service_command_test.go (about)

     1  package global
     2  
     3  import (
     4  	"code.cloudfoundry.org/cli/integration/helpers"
     5  	. "github.com/onsi/ginkgo"
     6  	. "github.com/onsi/gomega"
     7  	. "github.com/onsi/gomega/gbytes"
     8  	. "github.com/onsi/gomega/gexec"
     9  )
    10  
    11  var _ = Describe("service command", func() {
    12  	var serviceInstanceName string
    13  
    14  	BeforeEach(func() {
    15  		serviceInstanceName = helpers.PrefixedRandomName("SI")
    16  	})
    17  
    18  	Describe("help", func() {
    19  		Context("when --help flag is set", func() {
    20  			It("displays command usage to output", func() {
    21  				session := helpers.CF("service", "--help")
    22  				Eventually(session).Should(Say("NAME:"))
    23  				Eventually(session).Should(Say("\\s+service - Show service instance info"))
    24  				Eventually(session).Should(Say("USAGE:"))
    25  				Eventually(session).Should(Say("\\s+cf service SERVICE_INSTANCE"))
    26  				Eventually(session).Should(Say("OPTIONS:"))
    27  				Eventually(session).Should(Say("\\s+\\-\\-guid\\s+Retrieve and display the given service's guid\\. All other output for the service is suppressed\\."))
    28  				Eventually(session).Should(Say("SEE ALSO:"))
    29  				Eventually(session).Should(Say("\\s+bind-service, rename-service, update-service"))
    30  				Eventually(session).Should(Exit(0))
    31  			})
    32  		})
    33  	})
    34  
    35  	Context("when the environment is not setup correctly", func() {
    36  		It("fails with the appropriate errors", func() {
    37  			helpers.CheckEnvironmentTargetedCorrectly(true, true, ReadOnlyOrg, "service", "some-service")
    38  		})
    39  	})
    40  
    41  	Context("when an api is targeted, the user is logged in, and an org and space are targeted", func() {
    42  		var (
    43  			orgName   string
    44  			spaceName string
    45  			userName  string
    46  		)
    47  
    48  		BeforeEach(func() {
    49  			orgName = helpers.NewOrgName()
    50  			spaceName = helpers.NewSpaceName()
    51  			setupCF(orgName, spaceName)
    52  
    53  			userName, _ = helpers.GetCredentials()
    54  		})
    55  
    56  		AfterEach(func() {
    57  			helpers.QuickDeleteOrg(orgName)
    58  		})
    59  
    60  		Context("when the service instance does not exist", func() {
    61  			It("returns an error and exits 1", func() {
    62  				session := helpers.CF("service", serviceInstanceName)
    63  				Eventually(session).Should(Say("Showing info of service %s in org %s / space %s as %s", serviceInstanceName, orgName, spaceName, userName))
    64  				Eventually(session).Should(Say(""))
    65  				Eventually(session).Should(Say("FAILED"))
    66  				Eventually(session.Err).Should(Say("Service instance %s not found", serviceInstanceName))
    67  				Eventually(session).Should(Exit(1))
    68  			})
    69  		})
    70  
    71  		Context("when the service instance belongs to this space", func() {
    72  			Context("when the service instance is a user provided service instance", func() {
    73  				BeforeEach(func() {
    74  					Eventually(helpers.CF("create-user-provided-service", serviceInstanceName)).Should(Exit(0))
    75  				})
    76  
    77  				AfterEach(func() {
    78  					Eventually(helpers.CF("delete-service", serviceInstanceName, "-f")).Should(Exit(0))
    79  				})
    80  
    81  				Context("when the --guid flag is provided", func() {
    82  					It("displays the service instance GUID", func() {
    83  						session := helpers.CF("service", serviceInstanceName, "--guid")
    84  						Consistently(session).ShouldNot(Say("Showing info of service %s in org %s / space %s as %s", serviceInstanceName, orgName, spaceName, userName))
    85  						Eventually(session).Should(Say(helpers.UserProvidedServiceInstanceGUID(serviceInstanceName)))
    86  						Eventually(session).Should(Exit(0))
    87  					})
    88  				})
    89  
    90  				Context("when apps are bound to the service instance", func() {
    91  					var (
    92  						appName1 string
    93  						appName2 string
    94  					)
    95  
    96  					BeforeEach(func() {
    97  						appName1 = helpers.NewAppName()
    98  						appName2 = helpers.NewAppName()
    99  						helpers.WithHelloWorldApp(func(appDir string) {
   100  							Eventually(helpers.CF("push", appName1, "--no-start", "-p", appDir, "-b", "staticfile_buildpack", "--no-route")).Should(Exit(0))
   101  							Eventually(helpers.CF("push", appName2, "--no-start", "-p", appDir, "-b", "staticfile_buildpack", "--no-route")).Should(Exit(0))
   102  						})
   103  						Eventually(helpers.CF("bind-service", appName1, serviceInstanceName)).Should(Exit(0))
   104  						Eventually(helpers.CF("bind-service", appName2, serviceInstanceName)).Should(Exit(0))
   105  					})
   106  
   107  					AfterEach(func() {
   108  						Eventually(helpers.CF("unbind-service", appName1, serviceInstanceName)).Should(Exit(0))
   109  						Eventually(helpers.CF("unbind-service", appName2, serviceInstanceName)).Should(Exit(0))
   110  						Eventually(helpers.CF("delete", appName1, "-f")).Should(Exit(0))
   111  						Eventually(helpers.CF("delete", appName2, "-f")).Should(Exit(0))
   112  					})
   113  
   114  					It("displays service instance info", func() {
   115  						session := helpers.CF("service", serviceInstanceName)
   116  						Eventually(session).Should(Say("Showing info of service %s in org %s / space %s as %s", serviceInstanceName, orgName, spaceName, userName))
   117  						Eventually(session).Should(Say(""))
   118  						Eventually(session).Should(Say("name:\\s+%s", serviceInstanceName))
   119  						Consistently(session).ShouldNot(Say("shared from:"))
   120  						Eventually(session).Should(Say("service:\\s+user-provided"))
   121  						Eventually(session).Should(Say("bound apps:\\s+%s, %s", appName1, appName2))
   122  						Consistently(session).ShouldNot(Say("tags:"))
   123  						Consistently(session).ShouldNot(Say("plan:"))
   124  						Consistently(session).ShouldNot(Say("description:"))
   125  						Consistently(session).ShouldNot(Say("documentation:"))
   126  						Consistently(session).ShouldNot(Say("dashboard:"))
   127  						Consistently(session).ShouldNot(Say("shared with spaces:"))
   128  						Consistently(session).ShouldNot(Say("last operation"))
   129  						Consistently(session).ShouldNot(Say("status:"))
   130  						Consistently(session).ShouldNot(Say("message:"))
   131  						Consistently(session).ShouldNot(Say("started:"))
   132  						Consistently(session).ShouldNot(Say("updated:"))
   133  						Eventually(session).Should(Exit(0))
   134  					})
   135  				})
   136  			})
   137  
   138  			Context("when the service instance is a managed service instance", func() {
   139  				var (
   140  					domain      string
   141  					service     string
   142  					servicePlan string
   143  					broker      helpers.ServiceBroker
   144  				)
   145  
   146  				BeforeEach(func() {
   147  					domain = defaultSharedDomain()
   148  					service = helpers.PrefixedRandomName("SERVICE")
   149  					servicePlan = helpers.PrefixedRandomName("SERVICE-PLAN")
   150  
   151  					broker = helpers.NewServiceBroker(helpers.NewServiceBrokerName(), helpers.NewAssets().ServiceBroker, domain, service, servicePlan)
   152  					broker.Push()
   153  					broker.Configure(true)
   154  					broker.Create()
   155  
   156  					Eventually(helpers.CF("enable-service-access", service)).Should(Exit(0))
   157  					Eventually(helpers.CF("create-service", service, servicePlan, serviceInstanceName, "-t", "database, email")).Should(Exit(0))
   158  				})
   159  
   160  				AfterEach(func() {
   161  					Eventually(helpers.CF("delete-service", serviceInstanceName, "-f")).Should(Exit(0))
   162  					broker.Destroy()
   163  				})
   164  
   165  				Context("when the --guid flag is provided", func() {
   166  					It("displays the service instance GUID", func() {
   167  						session := helpers.CF("service", serviceInstanceName, "--guid")
   168  						Consistently(session).ShouldNot(Say("Showing info of service %s in org %s / space %s as %s", serviceInstanceName, orgName, spaceName, userName))
   169  						Eventually(session).Should(Say(helpers.ManagedServiceInstanceGUID(serviceInstanceName)))
   170  						Eventually(session).Should(Exit(0))
   171  					})
   172  				})
   173  
   174  				Context("when apps are bound to the service instance", func() {
   175  					var (
   176  						appName1 string
   177  						appName2 string
   178  					)
   179  
   180  					BeforeEach(func() {
   181  						appName1 = helpers.NewAppName()
   182  						appName2 = helpers.NewAppName()
   183  						helpers.WithHelloWorldApp(func(appDir string) {
   184  							Eventually(helpers.CF("push", appName1, "--no-start", "-p", appDir, "-b", "staticfile_buildpack", "--no-route")).Should(Exit(0))
   185  							Eventually(helpers.CF("push", appName2, "--no-start", "-p", appDir, "-b", "staticfile_buildpack", "--no-route")).Should(Exit(0))
   186  						})
   187  						Eventually(helpers.CF("bind-service", appName1, serviceInstanceName)).Should(Exit(0))
   188  						Eventually(helpers.CF("bind-service", appName2, serviceInstanceName)).Should(Exit(0))
   189  					})
   190  
   191  					AfterEach(func() {
   192  						Eventually(helpers.CF("unbind-service", appName1, serviceInstanceName)).Should(Exit(0))
   193  						Eventually(helpers.CF("unbind-service", appName2, serviceInstanceName)).Should(Exit(0))
   194  						Eventually(helpers.CF("delete", appName1, "-f")).Should(Exit(0))
   195  						Eventually(helpers.CF("delete", appName2, "-f")).Should(Exit(0))
   196  					})
   197  
   198  					It("displays service instance info", func() {
   199  						session := helpers.CF("service", serviceInstanceName)
   200  						Eventually(session).Should(Say("Showing info of service %s in org %s / space %s as %s\\.\\.\\.", serviceInstanceName, orgName, spaceName, userName))
   201  						Eventually(session).Should(Say("\n\n"))
   202  						Eventually(session).Should(Say("name:\\s+%s", serviceInstanceName))
   203  						Consistently(session).ShouldNot(Say("shared from:"))
   204  						Eventually(session).Should(Say("service:\\s+%s", service))
   205  						Eventually(session).Should(Say("bound apps:\\s+%s, %s", appName1, appName2))
   206  						Eventually(session).Should(Say("tags:\\s+database, email"))
   207  						Eventually(session).Should(Say("plan:\\s+%s", servicePlan))
   208  						Eventually(session).Should(Say("description:\\s+fake service"))
   209  						Eventually(session).Should(Say("documentation:"))
   210  						Eventually(session).Should(Say("dashboard:\\s+http://example\\.com"))
   211  						Eventually(session).Should(Say("\n\n"))
   212  						Consistently(session).ShouldNot(Say("shared with spaces:"))
   213  						Eventually(session).Should(Say("Showing status of last operation from service %s\\.\\.\\.", serviceInstanceName))
   214  						Eventually(session).Should(Say("\n\n"))
   215  						Eventually(session).Should(Say("status:\\s+create succeeded"))
   216  						Eventually(session).Should(Say("message:"))
   217  						Eventually(session).Should(Say("started:\\s+\\d{4}-[01]\\d-[0-3]\\dT[0-2][0-9]:[0-5]\\d:[0-5]\\dZ"))
   218  						Eventually(session).Should(Say("updated:\\s+\\d{4}-[01]\\d-[0-3]\\dT[0-2][0-9]:[0-5]\\d:[0-5]\\dZ"))
   219  
   220  						Eventually(session).Should(Exit(0))
   221  					})
   222  				})
   223  			})
   224  		})
   225  	})
   226  
   227  	Context("service instance sharing when there are multiple spaces", func() {
   228  		var (
   229  			orgName         string
   230  			sourceSpaceName string
   231  
   232  			service     string
   233  			servicePlan string
   234  			broker      helpers.ServiceBroker
   235  		)
   236  
   237  		BeforeEach(func() {
   238  			orgName = helpers.NewOrgName()
   239  			sourceSpaceName = helpers.NewSpaceName()
   240  			setupCF(orgName, sourceSpaceName)
   241  
   242  			domain := defaultSharedDomain()
   243  			service = helpers.PrefixedRandomName("SERVICE")
   244  			servicePlan = helpers.PrefixedRandomName("SERVICE-PLAN")
   245  			broker = helpers.NewServiceBroker(helpers.NewServiceBrokerName(), helpers.NewAssets().ServiceBroker, domain, service, servicePlan)
   246  			broker.Push()
   247  			broker.Configure(true)
   248  			broker.Create()
   249  
   250  			Eventually(helpers.CF("enable-service-access", service)).Should(Exit(0))
   251  			Eventually(helpers.CF("create-service", service, servicePlan, serviceInstanceName)).Should(Exit(0))
   252  		})
   253  
   254  		AfterEach(func() {
   255  			// need to login as admin
   256  			helpers.LoginCF()
   257  			helpers.TargetOrgAndSpace(orgName, sourceSpaceName)
   258  			broker.Destroy()
   259  			helpers.QuickDeleteOrg(orgName)
   260  		})
   261  
   262  		Context("service has no type of shares", func() {
   263  			Context("when the service is shareable", func() {
   264  				It("should not display shared from or shared with information, but DOES display not currently shared info", func() {
   265  					session := helpers.CF("service", serviceInstanceName)
   266  					Eventually(session).Should(Say("This service is not currently shared."))
   267  					Eventually(session).Should(Exit(0))
   268  				})
   269  			})
   270  		})
   271  
   272  		Context("service is shared between two spaces", func() {
   273  			var (
   274  				targetSpaceName string
   275  			)
   276  
   277  			BeforeEach(func() {
   278  				targetSpaceName = helpers.NewSpaceName()
   279  				helpers.CreateOrgAndSpace(orgName, targetSpaceName)
   280  				helpers.TargetOrgAndSpace(orgName, sourceSpaceName)
   281  				Eventually(helpers.CF("v3-share-service", serviceInstanceName, "-s", targetSpaceName)).Should(Exit(0))
   282  			})
   283  
   284  			Context("when the user is targeted to the source space", func() {
   285  				Context("when there are externally bound apps to the service", func() {
   286  					BeforeEach(func() {
   287  						helpers.TargetOrgAndSpace(orgName, targetSpaceName)
   288  						helpers.WithHelloWorldApp(func(appDir string) {
   289  							appName1 := helpers.NewAppName()
   290  							Eventually(helpers.CF("push", appName1, "--no-start", "-p", appDir, "-b", "staticfile_buildpack", "--no-route")).Should(Exit(0))
   291  							Eventually(helpers.CF("bind-service", appName1, serviceInstanceName)).Should(Exit(0))
   292  
   293  							appName2 := helpers.NewAppName()
   294  							Eventually(helpers.CF("push", appName2, "--no-start", "-p", appDir, "-b", "staticfile_buildpack", "--no-route")).Should(Exit(0))
   295  							Eventually(helpers.CF("bind-service", appName2, serviceInstanceName)).Should(Exit(0))
   296  						})
   297  						helpers.TargetOrgAndSpace(orgName, sourceSpaceName)
   298  					})
   299  
   300  					It("should display the number of bound apps next to the target space name", func() {
   301  						session := helpers.CF("service", serviceInstanceName)
   302  						Eventually(session).Should(Say("shared with spaces:"))
   303  						Eventually(session).Should(Say("org\\s+space\\s+bindings"))
   304  						Eventually(session).Should(Say("%s\\s+%s\\s+2", orgName, targetSpaceName))
   305  						Eventually(session).Should(Exit(0))
   306  					})
   307  				})
   308  
   309  				Context("when there are no externally bound apps to the service", func() {
   310  					It("should NOT display the number of bound apps next to the target space name", func() {
   311  						session := helpers.CF("service", serviceInstanceName)
   312  						Eventually(session).Should(Say("shared with spaces:"))
   313  						Eventually(session).Should(Say("org\\s+space\\s+bindings"))
   314  						Eventually(session).Should(Exit(0))
   315  					})
   316  				})
   317  
   318  				Context("when the service is no longer shareable", func() {
   319  					Context("due to global settings", func() {
   320  						BeforeEach(func() {
   321  							helpers.DisableFeatureFlag("service_instance_sharing")
   322  						})
   323  
   324  						AfterEach(func() {
   325  							helpers.EnableFeatureFlag("service_instance_sharing")
   326  						})
   327  
   328  						It("should display that the service instance feature flag is disabled", func() {
   329  							session := helpers.CF("service", serviceInstanceName)
   330  							Eventually(session).Should(Say(`The "service_instance_sharing" feature flag is disabled for this Cloud Foundry platform.`))
   331  							Eventually(session).Should(Exit(0))
   332  						})
   333  					})
   334  
   335  					Context("due to service broker settings", func() {
   336  						BeforeEach(func() {
   337  							broker.Configure(false)
   338  							broker.Update()
   339  						})
   340  
   341  						It("should display that service instance sharing is disabled for this service", func() {
   342  							session := helpers.CF("service", serviceInstanceName)
   343  							Eventually(session).Should(Say("Service instance sharing is disabled for this service."))
   344  							Eventually(session).Should(Exit(0))
   345  						})
   346  					})
   347  
   348  					Context("due to global settings AND service broker settings", func() {
   349  						BeforeEach(func() {
   350  							helpers.DisableFeatureFlag("service_instance_sharing")
   351  							broker.Configure(false)
   352  							broker.Update()
   353  						})
   354  
   355  						AfterEach(func() {
   356  							helpers.EnableFeatureFlag("service_instance_sharing")
   357  						})
   358  
   359  						It("should display that service instance sharing is disabled for this service", func() {
   360  							session := helpers.CF("service", serviceInstanceName)
   361  							Eventually(session).Should(Say(`The "service_instance_sharing" feature flag is disabled for this Cloud Foundry platform. Also, service instance sharing is disabled for this service.`))
   362  							Eventually(session).Should(Exit(0))
   363  						})
   364  					})
   365  				})
   366  			})
   367  
   368  			Context("when the user is targeted to the target space", func() {
   369  				var appName1, appName2 string
   370  
   371  				BeforeEach(func() {
   372  					helpers.TargetOrgAndSpace(orgName, targetSpaceName)
   373  					helpers.WithHelloWorldApp(func(appDir string) {
   374  						appName1 = helpers.NewAppName()
   375  						Eventually(helpers.CF("push", appName1, "--no-start", "-p", appDir, "-b", "staticfile_buildpack", "--no-route")).Should(Exit(0))
   376  						Eventually(helpers.CF("bind-service", appName1, serviceInstanceName)).Should(Exit(0))
   377  
   378  						appName2 = helpers.NewAppName()
   379  						Eventually(helpers.CF("push", appName2, "--no-start", "-p", appDir, "-b", "staticfile_buildpack", "--no-route")).Should(Exit(0))
   380  						Eventually(helpers.CF("bind-service", appName2, serviceInstanceName)).Should(Exit(0))
   381  					})
   382  				})
   383  
   384  				Context("when there are bound apps to the service", func() {
   385  					It("should display the bound apps", func() {
   386  						session := helpers.CF("service", serviceInstanceName)
   387  						Eventually(session).Should(Say("shared from org/space:\\s+%s / %s", orgName, sourceSpaceName))
   388  						Eventually(session).Should(Say("bound apps:\\s+(%s, %s|%s, %s)", appName1, appName2, appName2, appName1))
   389  						Eventually(session).Should(Exit(0))
   390  					})
   391  				})
   392  			})
   393  		})
   394  	})
   395  })