github.com/wanddynosios/cli/v8@v8.7.9-0.20240221182337-1a92e3a7017f/actor/v7action/space.go (about)

     1  package v7action
     2  
     3  import (
     4  	"fmt"
     5  	"sort"
     6  
     7  	"code.cloudfoundry.org/cli/actor/actionerror"
     8  	"code.cloudfoundry.org/cli/api/cloudcontroller/ccerror"
     9  	"code.cloudfoundry.org/cli/api/cloudcontroller/ccv3"
    10  	"code.cloudfoundry.org/cli/api/cloudcontroller/ccv3/constant"
    11  	"code.cloudfoundry.org/cli/resources"
    12  )
    13  
    14  type SpaceSummary struct {
    15  	Space                 resources.Space
    16  	Name                  string
    17  	OrgName               string
    18  	AppNames              []string
    19  	ServiceInstanceNames  []string
    20  	IsolationSegmentName  string
    21  	QuotaName             string
    22  	RunningSecurityGroups []resources.SecurityGroup
    23  	StagingSecurityGroups []resources.SecurityGroup
    24  }
    25  
    26  func (actor Actor) CreateSpace(spaceName, orgGUID string) (resources.Space, Warnings, error) {
    27  	allWarnings := Warnings{}
    28  
    29  	space, apiWarnings, err := actor.CloudControllerClient.CreateSpace(resources.Space{
    30  		Name: spaceName,
    31  		Relationships: resources.Relationships{
    32  			constant.RelationshipTypeOrganization: resources.Relationship{GUID: orgGUID},
    33  		},
    34  	})
    35  
    36  	actorWarnings := Warnings(apiWarnings)
    37  	allWarnings = append(allWarnings, actorWarnings...)
    38  
    39  	if _, ok := err.(ccerror.NameNotUniqueInOrgError); ok {
    40  		return resources.Space{}, allWarnings, actionerror.SpaceAlreadyExistsError{Space: spaceName}
    41  	}
    42  	return resources.Space{
    43  		GUID: space.GUID,
    44  		Name: spaceName,
    45  	}, allWarnings, err
    46  }
    47  
    48  // ResetSpaceIsolationSegment disassociates a space from an isolation segment.
    49  //
    50  // If the space's organization has a default isolation segment, return its
    51  // name. Otherwise return the empty string.
    52  func (actor Actor) ResetSpaceIsolationSegment(orgGUID string, spaceGUID string) (string, Warnings, error) {
    53  	var allWarnings Warnings
    54  
    55  	_, apiWarnings, err := actor.CloudControllerClient.UpdateSpaceIsolationSegmentRelationship(spaceGUID, "")
    56  	allWarnings = append(allWarnings, apiWarnings...)
    57  	if err != nil {
    58  		return "", allWarnings, err
    59  	}
    60  
    61  	isoSegRelationship, apiWarnings, err := actor.CloudControllerClient.GetOrganizationDefaultIsolationSegment(orgGUID)
    62  	allWarnings = append(allWarnings, apiWarnings...)
    63  	if err != nil {
    64  		return "", allWarnings, err
    65  	}
    66  
    67  	var isoSegName string
    68  	if isoSegRelationship.GUID != "" {
    69  		isolationSegment, apiWarnings, err := actor.CloudControllerClient.GetIsolationSegment(isoSegRelationship.GUID)
    70  		allWarnings = append(allWarnings, apiWarnings...)
    71  		if err != nil {
    72  			return "", allWarnings, err
    73  		}
    74  		isoSegName = isolationSegment.Name
    75  	}
    76  
    77  	return isoSegName, allWarnings, nil
    78  }
    79  
    80  func (actor Actor) GetSpaceByNameAndOrganization(spaceName string, orgGUID string) (resources.Space, Warnings, error) {
    81  	ccv3Spaces, _, warnings, err := actor.CloudControllerClient.GetSpaces(
    82  		ccv3.Query{Key: ccv3.NameFilter, Values: []string{spaceName}},
    83  		ccv3.Query{Key: ccv3.OrganizationGUIDFilter, Values: []string{orgGUID}},
    84  		ccv3.Query{Key: ccv3.PerPage, Values: []string{"1"}},
    85  		ccv3.Query{Key: ccv3.Page, Values: []string{"1"}},
    86  	)
    87  
    88  	if err != nil {
    89  		return resources.Space{}, Warnings(warnings), err
    90  	}
    91  
    92  	if len(ccv3Spaces) == 0 {
    93  		return resources.Space{}, Warnings(warnings), actionerror.SpaceNotFoundError{Name: spaceName}
    94  	}
    95  
    96  	return resources.Space(ccv3Spaces[0]), Warnings(warnings), nil
    97  }
    98  
    99  func (actor Actor) GetSpaceSummaryByNameAndOrganization(spaceName string, orgGUID string) (SpaceSummary, Warnings, error) {
   100  	var allWarnings Warnings
   101  
   102  	org, warnings, err := actor.GetOrganizationByGUID(orgGUID)
   103  	allWarnings = append(allWarnings, warnings...)
   104  	if err != nil {
   105  		return SpaceSummary{}, allWarnings, err
   106  	}
   107  
   108  	space, warnings, err := actor.GetSpaceByNameAndOrganization(spaceName, org.GUID)
   109  	allWarnings = append(allWarnings, warnings...)
   110  	if err != nil {
   111  		return SpaceSummary{}, allWarnings, err
   112  	}
   113  
   114  	apps, warnings, err := actor.GetApplicationsBySpace(space.GUID)
   115  	allWarnings = append(allWarnings, warnings...)
   116  	if err != nil {
   117  		return SpaceSummary{}, allWarnings, err
   118  	}
   119  
   120  	appNames := make([]string, len(apps))
   121  	for i, app := range apps {
   122  		appNames[i] = app.Name
   123  	}
   124  	sort.Strings(appNames)
   125  
   126  	serviceInstances, _, ccv3Warnings, err := actor.CloudControllerClient.GetServiceInstances(
   127  		ccv3.Query{
   128  			Key:    ccv3.SpaceGUIDFilter,
   129  			Values: []string{space.GUID},
   130  		})
   131  	allWarnings = append(allWarnings, Warnings(ccv3Warnings)...)
   132  	if err != nil {
   133  		return SpaceSummary{}, allWarnings, err
   134  	}
   135  
   136  	serviceInstanceNames := make([]string, len(serviceInstances))
   137  	for i, instance := range serviceInstances {
   138  		serviceInstanceNames[i] = instance.Name
   139  	}
   140  	sort.Strings(serviceInstanceNames)
   141  
   142  	isoSegRelationship, ccv3Warnings, err := actor.CloudControllerClient.GetSpaceIsolationSegment(space.GUID)
   143  	allWarnings = append(allWarnings, Warnings(ccv3Warnings)...)
   144  	if err != nil {
   145  		return SpaceSummary{}, allWarnings, err
   146  	}
   147  
   148  	isoSegName := ""
   149  	isoSegGUID := isoSegRelationship.GUID
   150  	isDefaultIsoSeg := false
   151  
   152  	if isoSegGUID == "" {
   153  		defaultIsoSeg, ccv3Warnings, err := actor.CloudControllerClient.GetOrganizationDefaultIsolationSegment(org.GUID)
   154  		allWarnings = append(allWarnings, Warnings(ccv3Warnings)...)
   155  		if err != nil {
   156  			return SpaceSummary{}, allWarnings, err
   157  		}
   158  		isoSegGUID = defaultIsoSeg.GUID
   159  		if isoSegGUID != "" {
   160  			isDefaultIsoSeg = true
   161  		}
   162  	}
   163  
   164  	if isoSegGUID != "" {
   165  		isoSeg, ccv3warnings, err := actor.CloudControllerClient.GetIsolationSegment(isoSegGUID)
   166  		allWarnings = append(allWarnings, Warnings(ccv3warnings)...)
   167  		if err != nil {
   168  			return SpaceSummary{}, allWarnings, err
   169  		}
   170  		if isDefaultIsoSeg {
   171  			isoSegName = fmt.Sprintf("%s (org default)", isoSeg.Name)
   172  		} else {
   173  			isoSegName = isoSeg.Name
   174  		}
   175  	}
   176  
   177  	appliedQuotaRelationshipGUID := space.Relationships[constant.RelationshipTypeQuota].GUID
   178  
   179  	var spaceQuota resources.SpaceQuota
   180  	if appliedQuotaRelationshipGUID != "" {
   181  		spaceQuota, ccv3Warnings, err = actor.CloudControllerClient.GetSpaceQuota(space.Relationships[constant.RelationshipTypeQuota].GUID)
   182  		allWarnings = append(allWarnings, Warnings(ccv3Warnings)...)
   183  
   184  		if err != nil {
   185  			return SpaceSummary{}, allWarnings, err
   186  		}
   187  	}
   188  
   189  	runningSecurityGroups, ccv3Warnings, err := actor.CloudControllerClient.GetRunningSecurityGroups(space.GUID)
   190  	allWarnings = append(allWarnings, ccv3Warnings...)
   191  	if err != nil {
   192  		return SpaceSummary{}, allWarnings, err
   193  	}
   194  
   195  	stagingSecurityGroups, ccv3Warnings, err := actor.CloudControllerClient.GetStagingSecurityGroups(space.GUID)
   196  	allWarnings = append(allWarnings, ccv3Warnings...)
   197  	if err != nil {
   198  		return SpaceSummary{}, allWarnings, err
   199  	}
   200  
   201  	spaceSummary := SpaceSummary{
   202  		OrgName:               org.Name,
   203  		Name:                  space.Name,
   204  		Space:                 space,
   205  		AppNames:              appNames,
   206  		ServiceInstanceNames:  serviceInstanceNames,
   207  		IsolationSegmentName:  isoSegName,
   208  		QuotaName:             spaceQuota.Name,
   209  		RunningSecurityGroups: runningSecurityGroups,
   210  		StagingSecurityGroups: stagingSecurityGroups,
   211  	}
   212  
   213  	return spaceSummary, allWarnings, nil
   214  }
   215  
   216  // GetOrganizationSpacesWithLabelSelector returns a list of spaces in the specified org
   217  func (actor Actor) GetOrganizationSpacesWithLabelSelector(orgGUID string, labelSelector string) ([]resources.Space, Warnings, error) {
   218  
   219  	queries := []ccv3.Query{
   220  		ccv3.Query{Key: ccv3.OrganizationGUIDFilter, Values: []string{orgGUID}},
   221  		ccv3.Query{Key: ccv3.OrderBy, Values: []string{ccv3.NameOrder}},
   222  	}
   223  	if len(labelSelector) > 0 {
   224  		queries = append(queries, ccv3.Query{Key: ccv3.LabelSelectorFilter, Values: []string{labelSelector}})
   225  	}
   226  
   227  	ccv3Spaces, _, warnings, err := actor.CloudControllerClient.GetSpaces(queries...)
   228  	if err != nil {
   229  		return []resources.Space{}, Warnings(warnings), err
   230  	}
   231  
   232  	spaces := make([]resources.Space, len(ccv3Spaces))
   233  	for i, ccv3Space := range ccv3Spaces {
   234  		spaces[i] = resources.Space(ccv3Space)
   235  	}
   236  
   237  	return spaces, Warnings(warnings), nil
   238  }
   239  
   240  // GetOrganizationSpaces returns a list of spaces in the specified org
   241  func (actor Actor) GetOrganizationSpaces(orgGUID string) ([]resources.Space, Warnings, error) {
   242  	return actor.GetOrganizationSpacesWithLabelSelector(orgGUID, "")
   243  }
   244  
   245  func (actor Actor) DeleteSpaceByNameAndOrganizationName(spaceName string, orgName string) (Warnings, error) {
   246  	var allWarnings Warnings
   247  
   248  	org, actorWarnings, err := actor.GetOrganizationByName(orgName)
   249  	allWarnings = append(allWarnings, actorWarnings...)
   250  	if err != nil {
   251  		return allWarnings, err
   252  	}
   253  
   254  	space, warnings, err := actor.GetSpaceByNameAndOrganization(spaceName, org.GUID)
   255  	allWarnings = append(allWarnings, warnings...)
   256  	if err != nil {
   257  		return allWarnings, err
   258  	}
   259  
   260  	jobURL, deleteWarnings, err := actor.CloudControllerClient.DeleteSpace(space.GUID)
   261  	allWarnings = append(allWarnings, Warnings(deleteWarnings)...)
   262  	if err != nil {
   263  		return allWarnings, err
   264  	}
   265  
   266  	ccWarnings, err := actor.CloudControllerClient.PollJob(jobURL)
   267  	allWarnings = append(allWarnings, Warnings(ccWarnings)...)
   268  
   269  	return allWarnings, err
   270  }
   271  
   272  func (actor Actor) RenameSpaceByNameAndOrganizationGUID(oldSpaceName, newSpaceName, orgGUID string) (resources.Space, Warnings, error) {
   273  	var allWarnings Warnings
   274  
   275  	space, getWarnings, err := actor.GetSpaceByNameAndOrganization(oldSpaceName, orgGUID)
   276  	allWarnings = append(allWarnings, getWarnings...)
   277  	if err != nil {
   278  		return resources.Space{}, allWarnings, err
   279  	}
   280  
   281  	ccSpace, updateWarnings, err := actor.CloudControllerClient.UpdateSpace(resources.Space{GUID: space.GUID, Name: newSpaceName})
   282  	allWarnings = append(allWarnings, Warnings(updateWarnings)...)
   283  
   284  	return resources.Space(ccSpace), allWarnings, err
   285  }