Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(cf): add location filtering to cloudfoundry #5088

Merged
merged 10 commits into from
Nov 12, 2020
Original file line number Diff line number Diff line change
Expand Up @@ -115,11 +115,14 @@ public CloudFoundryServerGroup findById(String guid) {
.orElse(null);
}

public List<CloudFoundryApplication> all() {
public List<CloudFoundryApplication> all(List<String> spaceGuids) {
log.debug("Listing all applications from account {}", this.account);

String spaceGuidsQ =
spaceGuids == null || spaceGuids.isEmpty() ? null : String.join(",", spaceGuids);

List<Application> newCloudFoundryAppList =
collectPages("applications", page -> api.all(page, resultsPerPage, null, null));
collectPages("applications", page -> api.all(page, resultsPerPage, null, spaceGuidsQ));

log.debug(
"Fetched {} total apps from foundation account {}",
Expand Down Expand Up @@ -232,7 +235,7 @@ public List<CloudFoundryApplication> all() {
@Nullable
public CloudFoundryServerGroup findServerGroupByNameAndSpaceId(String name, String spaceId) {
Optional<CloudFoundryServerGroup> result =
safelyCall(() -> api.all(null, 1, singletonList(name), singletonList(spaceId)))
safelyCall(() -> api.all(null, 1, singletonList(name), spaceId))
.flatMap(page -> page.getResources().stream().findFirst().map(this::map));
result.ifPresent(sg -> serverGroupCache.put(sg.getId(), sg));
return result.orElse(null);
Expand All @@ -249,7 +252,7 @@ public String findServerGroupId(String name, String spaceId) {
.map(CloudFoundryServerGroup::getId)
.orElseGet(
() ->
safelyCall(() -> api.all(null, 1, singletonList(name), singletonList(spaceId)))
safelyCall(() -> api.all(null, 1, singletonList(name), spaceId))
.flatMap(
page ->
page.getResources().stream()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,10 +24,11 @@
import com.google.common.cache.LoadingCache;
import com.netflix.spinnaker.clouddriver.cloudfoundry.client.api.OrganizationService;
import com.netflix.spinnaker.clouddriver.cloudfoundry.model.CloudFoundryOrganization;
import java.util.Collections;
import java.util.List;
import java.util.Optional;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
import lombok.RequiredArgsConstructor;
Expand Down Expand Up @@ -67,11 +68,19 @@ public CloudFoundryOrganization findById(String orgId) throws CloudFoundryApiExc

public Optional<CloudFoundryOrganization> findByName(String orgName)
throws CloudFoundryApiException {
return collectPages("organizations", page -> api.all(page, Collections.singletonList(orgName)))
.stream()
return collectPages("organizations", page -> api.all(page, orgName)).stream()
.findAny()
.map(
org ->
CloudFoundryOrganization.builder().id(org.getGuid()).name(org.getName()).build());
}

public List<CloudFoundryOrganization> findAllByNames(List<String> names) {
if (names == null || names.isEmpty())
throw new IllegalArgumentException("Organization names must not be empty or null");
return collectPages("organizations", page -> api.all(page, String.join(",", names))).stream()
.map(
org -> CloudFoundryOrganization.builder().id(org.getGuid()).name(org.getName()).build())
.collect(Collectors.toList());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
import static com.netflix.spinnaker.clouddriver.cloudfoundry.client.CloudFoundryClientUtils.collectPageResources;
import static com.netflix.spinnaker.clouddriver.cloudfoundry.client.CloudFoundryClientUtils.safelyCall;
import static java.util.Collections.emptySet;
import static java.util.Collections.singletonList;

import com.google.common.cache.CacheBuilder;
import com.google.common.cache.CacheLoader;
Expand Down Expand Up @@ -161,16 +162,36 @@ public RouteId toRouteId(String uri) throws CloudFoundryApiException {
}
}

public List<CloudFoundryLoadBalancer> all() throws CloudFoundryApiException {
public List<CloudFoundryLoadBalancer> all(List<CloudFoundrySpace> spaces)
throws CloudFoundryApiException {
try {
return forkJoinPool
.submit(
() ->
collectPageResources("routes", pg -> api.all(pg, resultsPerPage, null))
.parallelStream()
.map(this::map)
.collect(Collectors.toList()))
.get();
if (!spaces.isEmpty()) {
List<String> spaceGuids = spaces.stream().map(s -> s.getId()).collect(Collectors.toList());
String orgFilter =
"organization_guid IN "
+ spaces.stream()
.map(s -> s.getOrganization().getId())
.collect(Collectors.joining(","));
return forkJoinPool
.submit(
() ->
collectPageResources(
"routes", pg -> api.all(pg, resultsPerPage, singletonList(orgFilter)))
.parallelStream()
.map(this::map)
.filter(lb -> spaceGuids.contains(lb.getSpace().getId()))
.collect(Collectors.toList()))
.get();
} else {
return forkJoinPool
.submit(
() ->
collectPageResources("routes", pg -> api.all(pg, resultsPerPage, null))
.parallelStream()
.map(this::map)
.collect(Collectors.toList()))
.get();
}
} catch (Exception e) {
throw new RuntimeException(e);
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,14 +23,11 @@
import com.google.common.cache.CacheLoader;
import com.google.common.cache.LoadingCache;
import com.netflix.spinnaker.clouddriver.cloudfoundry.client.api.SpaceService;
import com.netflix.spinnaker.clouddriver.cloudfoundry.client.model.v2.*;
import com.netflix.spinnaker.clouddriver.cloudfoundry.client.model.v3.Space;
import com.netflix.spinnaker.clouddriver.cloudfoundry.model.CloudFoundryOrganization;
import com.netflix.spinnaker.clouddriver.cloudfoundry.model.CloudFoundryServiceInstance;
import com.netflix.spinnaker.clouddriver.cloudfoundry.model.CloudFoundrySpace;
import java.util.Collections;
import java.util.List;
import java.util.Optional;
import java.util.*;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.TimeUnit;
import javax.annotation.Nonnull;
Expand Down Expand Up @@ -93,12 +90,7 @@ public CloudFoundryServiceInstance getServiceInstanceById(
@Nullable
public CloudFoundrySpace findByName(String orgId, String spaceName)
throws CloudFoundryApiException {
return collectPages(
"spaces",
page ->
api.all(
page, Collections.singletonList(spaceName), Collections.singletonList(orgId)))
.stream()
return collectPages("spaces", page -> api.all(page, spaceName, orgId)).stream()
.findAny()
.map(this::map)
.orElse(null);
Expand Down Expand Up @@ -133,13 +125,7 @@ public Optional<CloudFoundrySpace> findSpaceByRegion(String region) {
"Unable to find organization: " + space.getOrganization().getName()));

Optional<CloudFoundrySpace> spaceOptional =
collectPages(
"spaces",
page ->
api.all(
page,
Collections.singletonList(space.getName()),
Collections.singletonList(organization.getId())))
collectPages("spaces", page -> api.all(page, space.getName(), organization.getId()))
.stream()
.findAny()
.map(
Expand All @@ -160,4 +146,29 @@ public Optional<CloudFoundrySpace> findSpaceByRegion(String region) {

return spaceOptional;
}

public List<CloudFoundrySpace> findAllBySpaceNamesAndOrgNames(
List<String> spaceNames, List<String> orgNames) {
Map<String, CloudFoundryOrganization> allOrgsByGuids = new HashMap<>();
organizations.findAllByNames(orgNames).stream().forEach(o -> allOrgsByGuids.put(o.getId(), o));

String spaceNamesQ =
spaceNames == null || spaceNames.isEmpty() ? null : String.join(",", spaceNames);
String orgGuidsQ =
allOrgsByGuids.keySet().isEmpty() ? null : String.join(",", allOrgsByGuids.keySet());

return collectPages("spaces", page -> api.all(page, spaceNamesQ, orgGuidsQ)).stream()
.map(
s ->
CloudFoundrySpace.builder()
.organization(
allOrgsByGuids.getOrDefault(
s.getRelationships().get("organization").getData().getGuid(), null))
.name(s.getName())
.id(s.getGuid())
.build())
.filter(
s -> s.getOrganization() != null && orgNames.contains(s.getOrganization().getName()))
.collect(toList());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ Pagination<Application> all(
@Query("page") Integer page,
@Query("per_page") Integer perPage,
@Query("names") List<String> names,
@Query("space_guids") List<String> spaceGuids);
@Query("space_guids") String spaceGuids);

@GET("/v3/apps/{guid}")
Application findById(@Path("guid") String guid);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,14 +18,13 @@

import com.netflix.spinnaker.clouddriver.cloudfoundry.client.model.v3.Organization;
import com.netflix.spinnaker.clouddriver.cloudfoundry.client.model.v3.Pagination;
import java.util.List;
import retrofit.http.GET;
import retrofit.http.Path;
import retrofit.http.Query;

public interface OrganizationService {
@GET("/v3/organizations")
Pagination<Organization> all(@Query("page") Integer page, @Query("names") List<String> orgNames);
Pagination<Organization> all(@Query("page") Integer page, @Query("names") String orgNames);

@GET("/v3/organizations/{guid}")
Organization findById(@Path("guid") String guid);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,8 @@ public interface SpaceService {
@GET("/v3/spaces")
Pagination<Space> all(
@Query("page") Integer page,
@Query("names") List<String> names,
@Query("organization_guids") List<String> orgGuids);
@Query("names") String names,
@Query("organization_guids") String orgGuids);

@GET("/v3/spaces/{guid}")
Space findById(@Path("guid") String guid);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,7 @@

import com.netflix.spinnaker.credentials.definition.CredentialsDefinition;
import com.netflix.spinnaker.fiat.model.resources.Permissions;
import java.util.ArrayList;
import java.util.List;
import java.util.*;
import lombok.Data;
import lombok.Getter;
import lombok.Setter;
Expand Down Expand Up @@ -71,5 +70,6 @@ public static class ManagedAccount implements CredentialsDefinition {
maxCapiConnectionsForCache; // Deprecated in favor of cloudfoundry.apiRequestParallelism

private Permissions.Builder permissions = new Permissions.Builder();
private Map<String, Set<String>> locationFilter = Collections.emptyMap();
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
/*
* Copyright 2020 Armory, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/

package com.netflix.spinnaker.clouddriver.cloudfoundry.deploy.validators;

import com.netflix.spinnaker.clouddriver.cloudfoundry.deploy.description.AbstractCloudFoundryDescription;
import com.netflix.spinnaker.clouddriver.deploy.DescriptionValidator;
import com.netflix.spinnaker.clouddriver.deploy.ValidationErrors;
import java.util.List;

public abstract class AbstractCloudFoundryDescriptionValidator
extends DescriptionValidator<AbstractCloudFoundryDescription> {

@Override
public void validate(
List<AbstractCloudFoundryDescription> priorDescriptions,
AbstractCloudFoundryDescription description,
ValidationErrors errors) {
StandardCloudFoundryAttributeValidator helper =
new StandardCloudFoundryAttributeValidator(description.getClass().getSimpleName(), errors);
helper.validateRegions(description.getRegion(), description.getCredentials());
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/*
* Copyright 2020 Armory, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/

package com.netflix.spinnaker.clouddriver.cloudfoundry.deploy.validators;

import com.netflix.spinnaker.clouddriver.cloudfoundry.CloudFoundryOperation;
import com.netflix.spinnaker.clouddriver.orchestration.AtomicOperations;
import org.springframework.stereotype.Component;

@CloudFoundryOperation(AtomicOperations.RUN_JOB)
@Component("cloudFoundryRunJobOperationDescriptionValidator")
public class CloudFoundryRunJobOperationDescriptionValidator
extends AbstractCloudFoundryDescriptionValidator {}
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/*
* Copyright 2020 Armory, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/

package com.netflix.spinnaker.clouddriver.cloudfoundry.deploy.validators;

import com.netflix.spinnaker.clouddriver.cloudfoundry.CloudFoundryOperation;
import com.netflix.spinnaker.clouddriver.orchestration.AtomicOperations;
import org.springframework.stereotype.Component;

@CloudFoundryOperation(AtomicOperations.CREATE_SERVICE_KEY)
@Component("createCloudFoundryServiceKeyDescriptionValidator")
public class CreateCloudFoundryServiceKeyDescriptionValidator
extends AbstractCloudFoundryDescriptionValidator {}
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
/*
* Copyright 2020 Armory, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
*/

package com.netflix.spinnaker.clouddriver.cloudfoundry.deploy.validators;

import com.netflix.spinnaker.clouddriver.cloudfoundry.CloudFoundryOperation;
import com.netflix.spinnaker.clouddriver.orchestration.AtomicOperations;
import org.springframework.stereotype.Component;

@CloudFoundryOperation(AtomicOperations.DELETE_LOAD_BALANCER)
@Component("deleteCloudFoundryLoadBalancerDescriptionValidator")
public class DeleteCloudFoundryLoadBalancerDescriptionValidator
extends AbstractCloudFoundryDescriptionValidator {}
Loading