github.com/loafoe/cli@v7.1.0+incompatible/integration/v7/global/unshare_service_command_test.go (about)

     1  package global
     2  
     3  import (
     4  	"code.cloudfoundry.org/cli/integration/helpers"
     5  	"code.cloudfoundry.org/cli/integration/helpers/servicebrokerstub"
     6  	. "github.com/onsi/ginkgo"
     7  	. "github.com/onsi/gomega"
     8  	. "github.com/onsi/gomega/gbytes"
     9  	. "github.com/onsi/gomega/gexec"
    10  	. "github.com/onsi/gomega/ghttp"
    11  )
    12  
    13  var _ = Describe("unshare-service command", func() {
    14  	var (
    15  		sourceOrgName     string
    16  		sourceSpaceName   string
    17  		sharedToOrgName   string
    18  		sharedToSpaceName string
    19  		serviceInstance   string
    20  	)
    21  
    22  	BeforeEach(func() {
    23  		sourceOrgName = helpers.NewOrgName()
    24  		sourceSpaceName = helpers.NewSpaceName()
    25  		sharedToOrgName = helpers.NewOrgName()
    26  		sharedToSpaceName = helpers.NewSpaceName()
    27  		serviceInstance = helpers.PrefixedRandomName("svc-inst")
    28  
    29  		helpers.LoginCF()
    30  	})
    31  
    32  	Describe("help", func() {
    33  		When("--help flag is set", func() {
    34  			It("Displays command usage to output", func() {
    35  				session := helpers.CF("unshare-service", "--help")
    36  				Eventually(session).Should(Say("NAME:"))
    37  				Eventually(session).Should(Say("unshare-service - Unshare a shared service instance from a space"))
    38  				Eventually(session).Should(Say("USAGE:"))
    39  				Eventually(session).Should(Say(`cf unshare-service SERVICE_INSTANCE -s OTHER_SPACE \[-o OTHER_ORG\] \[-f\]`))
    40  				Eventually(session).Should(Say("OPTIONS:"))
    41  				Eventually(session).Should(Say(`-o\s+Org of the other space \(Default: targeted org\)`))
    42  				Eventually(session).Should(Say(`-s\s+Space to unshare the service instance from`))
    43  				Eventually(session).Should(Say(`-f\s+Force unshare without confirmation`))
    44  				Eventually(session).Should(Say("SEE ALSO:"))
    45  				Eventually(session).Should(Say("delete-service, service, services, share-service, unbind-service"))
    46  				Eventually(session).Should(Exit(0))
    47  			})
    48  		})
    49  	})
    50  
    51  	When("the service instance name is not provided", func() {
    52  		It("tells the user that the service instance name is required, prints help text, and exits 1", func() {
    53  			session := helpers.CF("unshare-service", "-s", sharedToSpaceName)
    54  
    55  			Eventually(session.Err).Should(Say("Incorrect Usage: the required argument `SERVICE_INSTANCE` was not provided"))
    56  			Eventually(session).Should(Say("NAME:"))
    57  			Eventually(session).Should(Exit(1))
    58  		})
    59  	})
    60  
    61  	When("the space name is not provided", func() {
    62  		It("tells the user that the space name is required, prints help text, and exits 1", func() {
    63  			session := helpers.CF("unshare-service")
    64  
    65  			Eventually(session.Err).Should(Say("Incorrect Usage: the required flag `-s' was not specified"))
    66  			Eventually(session).Should(Say("NAME:"))
    67  			Eventually(session).Should(Exit(1))
    68  		})
    69  	})
    70  
    71  	When("the environment is not setup correctly", func() {
    72  		It("fails with the appropriate errors", func() {
    73  			helpers.CheckEnvironmentTargetedCorrectly(true, true, ReadOnlyOrg, "unshare-service", serviceInstance, "-s", sharedToSpaceName)
    74  		})
    75  
    76  		When("the v3 api version is lower than the minimum version", func() {
    77  			var server *Server
    78  
    79  			BeforeEach(func() {
    80  				server = helpers.StartAndTargetMockServerWithAPIVersions(helpers.DefaultV2Version, "3.0.0")
    81  			})
    82  
    83  			AfterEach(func() {
    84  				server.Close()
    85  			})
    86  
    87  			It("fails with error message that the minimum version is not met", func() {
    88  				session := helpers.CF("unshare-service", serviceInstance, "-s", sharedToSpaceName)
    89  				Eventually(session).Should(Say("FAILED"))
    90  				Eventually(session.Err).Should(Say(`This command requires CF API version 3\.63\.0 or higher\.`))
    91  				Eventually(session).Should(Exit(1))
    92  			})
    93  		})
    94  	})
    95  
    96  	When("the environment is set up correctly", func() {
    97  		var (
    98  			service     string
    99  			servicePlan string
   100  		)
   101  
   102  		BeforeEach(func() {
   103  			helpers.CreateOrgAndSpace(sharedToOrgName, sharedToSpaceName)
   104  			helpers.SetupCF(sourceOrgName, sourceSpaceName)
   105  		})
   106  
   107  		AfterEach(func() {
   108  			helpers.QuickDeleteOrg(sourceOrgName)
   109  			helpers.QuickDeleteOrg(sharedToOrgName)
   110  		})
   111  
   112  		When("there is a managed service instance in my current targeted space", func() {
   113  			var broker *servicebrokerstub.ServiceBrokerStub
   114  
   115  			BeforeEach(func() {
   116  				broker = servicebrokerstub.EnableServiceAccess()
   117  				service = broker.FirstServiceOfferingName()
   118  				servicePlan = broker.FirstServicePlanName()
   119  
   120  				Eventually(helpers.CF("create-service", service, servicePlan, serviceInstance)).Should(Exit(0))
   121  			})
   122  
   123  			AfterEach(func() {
   124  				broker.Forget()
   125  			})
   126  
   127  			When("the service instance has not been shared to this space", func() {
   128  				It("displays info and idempotently exits 0", func() {
   129  					session := helpers.CF("unshare-service", serviceInstance, "-s", sharedToSpaceName, "-o", sharedToOrgName, "-f")
   130  					Eventually(session).Should(Say(`Service instance %s is not shared with space %s in organization %s\.`, serviceInstance, sharedToSpaceName, sharedToOrgName))
   131  					Eventually(session).Should(Say("OK"))
   132  					Eventually(session).Should(Exit(0))
   133  				})
   134  			})
   135  
   136  			When("I have shared my service instance to a space in another org ('-o' flag provided)", func() {
   137  				BeforeEach(func() {
   138  					session := helpers.CF("share-service", serviceInstance, "-s", sharedToSpaceName, "-o", sharedToOrgName)
   139  					Eventually(session).Should(Exit(0))
   140  				})
   141  
   142  				When("the org I want to unshare from does not exist", func() {
   143  					It("fails with an org not found error", func() {
   144  						session := helpers.CF("unshare-service", serviceInstance, "-s", sharedToSpaceName, "-o", "missing-org", "-f")
   145  						Eventually(session).Should(Say(`Service instance %s is not shared with space %s in organization missing-org\.`, serviceInstance, sharedToSpaceName))
   146  						Eventually(session).Should(Say("OK"))
   147  						Eventually(session).Should(Exit(0))
   148  					})
   149  				})
   150  
   151  				When("the space I want to unshare from does not exist", func() {
   152  					It("fails with a space not found error", func() {
   153  						session := helpers.CF("unshare-service", serviceInstance, "-s", "missing-space", "-o", sharedToOrgName, "-f")
   154  						Eventually(session).Should(Say(`Service instance %s is not shared with space missing-space in organization %s\.`, serviceInstance, sharedToOrgName))
   155  						Eventually(session).Should(Say("OK"))
   156  						Eventually(session).Should(Exit(0))
   157  					})
   158  				})
   159  
   160  				When("I want to unshare my service instance from a space and org", func() {
   161  					It("successfully unshares the service instance", func() {
   162  						username, _ := helpers.GetCredentials()
   163  						session := helpers.CF("unshare-service", serviceInstance, "-s", sharedToSpaceName, "-o", sharedToOrgName, "-f")
   164  						Eventually(session).Should(Say(`Unsharing service instance %s from org %s / space %s as %s\.\.\.`, serviceInstance, sharedToOrgName, sharedToSpaceName, username))
   165  						Eventually(session).Should(Say("OK"))
   166  						Eventually(session).Should(Exit(0))
   167  					})
   168  				})
   169  			})
   170  
   171  			When("I have shared my service instance to a space within the targeted org ('-o' flag NOT provided)", func() {
   172  				BeforeEach(func() {
   173  					helpers.CreateSpace(sharedToSpaceName)
   174  
   175  					session := helpers.CF("share-service", serviceInstance, "-s", sharedToSpaceName)
   176  					Eventually(session).Should(Exit(0))
   177  				})
   178  
   179  				When("the space I want to unshare from does not exist", func() {
   180  					It("fails with a space not found error", func() {
   181  						session := helpers.CF("unshare-service", serviceInstance, "-s", "missing-space", "-f")
   182  						Eventually(session).Should(Say(`Service instance %s is not shared with space missing-space in organization %s\.`, serviceInstance, sourceOrgName))
   183  						Eventually(session).Should(Say("OK"))
   184  						Eventually(session).Should(Exit(0))
   185  					})
   186  				})
   187  
   188  				When("I want to unshare my service instance from the space", func() {
   189  					It("successfully unshares the service instance when I am admin", func() {
   190  						username, _ := helpers.GetCredentials()
   191  						session := helpers.CF("unshare-service", serviceInstance, "-s", sharedToSpaceName, "-f")
   192  						Eventually(session).Should(Say(`Unsharing service instance %s from org %s / space %s as %s\.\.\.`, serviceInstance, sourceOrgName, sharedToSpaceName, username))
   193  						Eventually(session).Should(Say("OK"))
   194  						Eventually(session).Should(Exit(0))
   195  					})
   196  
   197  					When("I have no access to the shared-to space", func() {
   198  						var (
   199  							username string
   200  							password string
   201  						)
   202  
   203  						BeforeEach(func() {
   204  							username = helpers.NewUsername()
   205  							password = helpers.NewPassword()
   206  							Eventually(helpers.CF("create-user", username, password)).Should(Exit(0))
   207  							Eventually(helpers.CF("set-space-role", username, sourceOrgName, sourceSpaceName, "SpaceDeveloper")).Should(Exit(0))
   208  							env := map[string]string{
   209  								"CF_USERNAME": username,
   210  								"CF_PASSWORD": password,
   211  							}
   212  							helpers.LogoutCF()
   213  							Eventually(helpers.CFWithEnv(env, "auth")).Should(Exit(0))
   214  							helpers.TargetOrgAndSpace(sourceOrgName, sourceSpaceName)
   215  						})
   216  
   217  						AfterEach(func() {
   218  							helpers.LoginCF()
   219  							helpers.TargetOrgAndSpace(sourceOrgName, sourceSpaceName)
   220  							session := helpers.CF("delete-user", username, "-f")
   221  							Eventually(session).Should(Say("OK"))
   222  							Eventually(session).Should(Exit(0))
   223  						})
   224  
   225  						It("successfully unshares the service instance", func() {
   226  							session := helpers.CF("unshare-service", serviceInstance, "-s", sharedToSpaceName, "-f")
   227  							Eventually(session).Should(Say("OK"))
   228  							Eventually(session).Should(Exit(0))
   229  						})
   230  					})
   231  				})
   232  			})
   233  		})
   234  
   235  		When("the service instance does not exist", func() {
   236  			When("the -f flag is provided", func() {
   237  				It("fails with a service instance not found error", func() {
   238  					session := helpers.CF("unshare-service", serviceInstance, "-s", sharedToSpaceName, "-f")
   239  					Eventually(session).Should(Say("FAILED"))
   240  					Eventually(session.Err).Should(Say(`Specified instance not found or not a managed service instance\. Sharing is not supported for user provided services\.`))
   241  					Eventually(session).Should(Exit(1))
   242  				})
   243  			})
   244  
   245  			When("the -f flag not is provided", func() {
   246  				var buffer *Buffer
   247  
   248  				BeforeEach(func() {
   249  					buffer = NewBuffer()
   250  				})
   251  
   252  				When("the user enters 'y'", func() {
   253  					BeforeEach(func() {
   254  						_, err := buffer.Write([]byte("y\n"))
   255  						Expect(err).ToNot(HaveOccurred())
   256  					})
   257  
   258  					It("fails with a service instance not found error", func() {
   259  						username, _ := helpers.GetCredentials()
   260  						session := helpers.CFWithStdin(buffer, "unshare-service", serviceInstance, "-s", sharedToSpaceName)
   261  						Eventually(session.Err).Should(Say(`WARNING: Unsharing this service instance will remove any existing bindings originating from the service instance in the space "%s". This could cause apps to stop working.`, sharedToSpaceName))
   262  						Eventually(session).Should(Say(`Really unshare the service instance\? \[yN\]`))
   263  						Eventually(session).Should(Say(`Unsharing service instance %s from org %s / space %s as %s\.\.\.`, serviceInstance, sourceOrgName, sharedToSpaceName, username))
   264  						Eventually(session).Should(Say("FAILED"))
   265  						Eventually(session.Err).Should(Say(`Specified instance not found or not a managed service instance\. Sharing is not supported for user provided services\.`))
   266  						Eventually(session).Should(Exit(1))
   267  					})
   268  				})
   269  
   270  				When("the user enters 'n'", func() {
   271  					BeforeEach(func() {
   272  						_, err := buffer.Write([]byte("n\n"))
   273  						Expect(err).ToNot(HaveOccurred())
   274  					})
   275  
   276  					It("does not attempt to unshare", func() {
   277  						session := helpers.CFWithStdin(buffer, "unshare-service", serviceInstance, "-s", sharedToSpaceName)
   278  						Eventually(session.Err).Should(Say(`WARNING: Unsharing this service instance will remove any existing bindings originating from the service instance in the space "%s". This could cause apps to stop working.`, sharedToSpaceName))
   279  						Eventually(session).Should(Say(`Really unshare the service instance\? \[yN\]`))
   280  						Eventually(session).Should(Say("Unshare cancelled"))
   281  						Eventually(session).Should(Exit(0))
   282  					})
   283  				})
   284  
   285  				When("the user enters the default input (hits return)", func() {
   286  					BeforeEach(func() {
   287  						_, err := buffer.Write([]byte("\n"))
   288  						Expect(err).ToNot(HaveOccurred())
   289  					})
   290  
   291  					It("does not attempt to unshare", func() {
   292  						session := helpers.CFWithStdin(buffer, "unshare-service", serviceInstance, "-s", sharedToSpaceName)
   293  						Eventually(session.Err).Should(Say(`WARNING: Unsharing this service instance will remove any existing bindings originating from the service instance in the space "%s". This could cause apps to stop working.`, sharedToSpaceName))
   294  						Eventually(session).Should(Say(`Really unshare the service instance\? \[yN\]`))
   295  						Eventually(session).Should(Say("Unshare cancelled"))
   296  						Eventually(session).Should(Exit(0))
   297  					})
   298  				})
   299  
   300  				When("the user enters an invalid answer", func() {
   301  					BeforeEach(func() {
   302  						// The second '\n' is intentional. Otherwise the buffer will be
   303  						// closed while the interaction is still waiting for input; it gets
   304  						// an EOF and causes an error.
   305  						_, err := buffer.Write([]byte("wat\n\n"))
   306  						Expect(err).ToNot(HaveOccurred())
   307  					})
   308  
   309  					It("asks again", func() {
   310  						session := helpers.CFWithStdin(buffer, "unshare-service", serviceInstance, "-s", sharedToSpaceName)
   311  						Eventually(session.Err).Should(Say(`WARNING: Unsharing this service instance will remove any existing bindings originating from the service instance in the space "%s". This could cause apps to stop working.`, sharedToSpaceName))
   312  						Eventually(session).Should(Say(`Really unshare the service instance\? \[yN\]`))
   313  						Eventually(session).Should(Say(`invalid input \(not y, n, yes, or no\)`))
   314  						Eventually(session).Should(Say(`Really unshare the service instance\? \[yN\]`))
   315  						Eventually(session).Should(Say("Unshare cancelled"))
   316  						Eventually(session).Should(Exit(0))
   317  					})
   318  				})
   319  			})
   320  		})
   321  
   322  		When("there is a shared service instance in my currently targeted space", func() {
   323  			var (
   324  				broker   *servicebrokerstub.ServiceBrokerStub
   325  				user     string
   326  				password string
   327  			)
   328  
   329  			BeforeEach(func() {
   330  				broker = servicebrokerstub.EnableServiceAccess()
   331  				service = broker.FirstServiceOfferingName()
   332  				servicePlan = broker.FirstServicePlanName()
   333  
   334  				user = helpers.NewUsername()
   335  				password = helpers.NewPassword()
   336  
   337  				helpers.SetupCF(sourceOrgName, sourceSpaceName)
   338  				Eventually(helpers.CF("enable-service-access", service)).Should(Exit(0))
   339  				Eventually(helpers.CF("create-service", service, servicePlan, serviceInstance)).Should(Exit(0))
   340  				Eventually(helpers.CF("share-service", serviceInstance, "-s", sharedToSpaceName, "-o", sharedToOrgName)).Should(Exit(0))
   341  
   342  				Eventually(helpers.CF("create-user", user, password)).Should(Exit(0))
   343  				Eventually(helpers.CF("set-space-role", user, sharedToOrgName, sharedToSpaceName, "SpaceDeveloper")).Should(Exit(0))
   344  			})
   345  
   346  			AfterEach(func() {
   347  				helpers.SetupCF(sourceOrgName, sourceSpaceName)
   348  				Eventually(helpers.CF("delete-user", user)).Should(Exit(0))
   349  				broker.Forget()
   350  			})
   351  
   352  			Context("and I have no access to the source space", func() {
   353  				BeforeEach(func() {
   354  					env := map[string]string{
   355  						"CF_USERNAME": user,
   356  						"CF_PASSWORD": password,
   357  					}
   358  					helpers.LogoutCF()
   359  					Eventually(helpers.CFWithEnv(env, "auth")).Should(Exit(0))
   360  					Eventually(helpers.CF("target", "-o", sharedToOrgName, "-s", sharedToSpaceName)).Should(Exit(0))
   361  				})
   362  
   363  				It("returns a permission error on an attempt to unshare the service", func() {
   364  					session := helpers.CF("unshare-service", serviceInstance, "-s", sharedToSpaceName, "-o", sharedToOrgName, "-f")
   365  					Eventually(session).Should(Say("FAILED"))
   366  					Eventually(session.Err).Should(Say("You are not authorized to perform the requested action"))
   367  					Eventually(session).Should(Exit(1))
   368  				})
   369  			})
   370  
   371  			Context("and I have SpaceAuditor access to the source space", func() {
   372  				BeforeEach(func() {
   373  					env := map[string]string{
   374  						"CF_USERNAME": user,
   375  						"CF_PASSWORD": password,
   376  					}
   377  					Eventually(helpers.CF("set-space-role", user, sourceOrgName, sourceSpaceName, "SpaceAuditor")).Should(Exit(0))
   378  					helpers.LogoutCF()
   379  					Eventually(helpers.CFWithEnv(env, "auth")).Should(Exit(0))
   380  					Eventually(helpers.CF("target", "-o", sharedToOrgName, "-s", sharedToSpaceName)).Should(Exit(0))
   381  				})
   382  
   383  				It("returns a permission error on an attempt to unshare the service", func() {
   384  					session := helpers.CF("unshare-service", serviceInstance, "-s", sharedToSpaceName, "-o", sharedToOrgName, "-f")
   385  					Eventually(session).Should(Say("FAILED"))
   386  					Eventually(session.Err).Should(Say("You are not authorized to perform the requested action"))
   387  					Eventually(session).Should(Exit(1))
   388  				})
   389  			})
   390  		})
   391  	})
   392  })