Support retrieving, adding, and deleting credential permissions. Remove CredHubTemplate methods that take a String name to reduce the footprint.
This commit is contained in:
@@ -22,7 +22,7 @@ import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.springframework.credhub.support.JsonUtils;
|
||||
import org.springframework.credhub.support.utils.JsonUtils;
|
||||
import org.springframework.http.HttpHeaders;
|
||||
import org.springframework.http.HttpRequest;
|
||||
import org.springframework.http.MediaType;
|
||||
|
||||
@@ -18,6 +18,8 @@ package org.springframework.credhub.core;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import org.springframework.credhub.support.permissions.Actor;
|
||||
import org.springframework.credhub.support.permissions.CredentialPermission;
|
||||
import org.springframework.credhub.support.CredentialDetails;
|
||||
import org.springframework.credhub.support.CredentialName;
|
||||
import org.springframework.credhub.support.CredentialSummary;
|
||||
@@ -65,17 +67,6 @@ public interface CredHubOperations {
|
||||
*/
|
||||
<T> CredentialDetails<T> getById(final String id, Class<T> credentialType);
|
||||
|
||||
/**
|
||||
* Retrieve a credential using its name, as passed to a write request.
|
||||
* Only the current credential value will be returned.
|
||||
*
|
||||
* @param name the name of the credential; must not be {@literal null}
|
||||
* @param credentialType the type of credential expected to be returned
|
||||
* @param <T> the credential implementation type
|
||||
* @return the details of the retrieved credential
|
||||
*/
|
||||
<T> CredentialDetails<T> getByName(final String name, Class<T> credentialType);
|
||||
|
||||
/**
|
||||
* Retrieve a credential using its name, as passed to a write request.
|
||||
* Only the current credential value will be returned.
|
||||
@@ -87,18 +78,6 @@ public interface CredHubOperations {
|
||||
*/
|
||||
<T> CredentialDetails<T> getByName(final CredentialName name, Class<T> credentialType);
|
||||
|
||||
/**
|
||||
* Retrieve a credential using its name, as passed to a write request.
|
||||
* A collection of all stored values for the named credential will be returned,
|
||||
* including historical values.
|
||||
*
|
||||
* @param name the name of the credential; must not be {@literal null}
|
||||
* @param credentialType the type of credential expected to be returned
|
||||
* @param <T> the credential implementation type
|
||||
* @return the details of the retrieved credential, including history
|
||||
*/
|
||||
<T> List<CredentialDetails<T>> getByNameWithHistory(String name, Class<T> credentialType);
|
||||
|
||||
/**
|
||||
* Retrieve a credential using its name, as passed to a write request.
|
||||
* A collection of all stored values for the named credential will be returned,
|
||||
@@ -111,14 +90,6 @@ public interface CredHubOperations {
|
||||
*/
|
||||
<T> List<CredentialDetails<T>> getByNameWithHistory(CredentialName name, Class<T> credentialType);
|
||||
|
||||
/**
|
||||
* Find a credential using a full or partial name.
|
||||
*
|
||||
* @param name the name of the credential; must not be {@literal null}
|
||||
* @return a summary of the credential search results
|
||||
*/
|
||||
List<CredentialSummary> findByName(String name);
|
||||
|
||||
/**
|
||||
* Find a credential using a full or partial name.
|
||||
*
|
||||
@@ -140,14 +111,32 @@ public interface CredHubOperations {
|
||||
*
|
||||
* @param name the name of the credential; must not be {@literal null}
|
||||
*/
|
||||
void deleteByName(String name);
|
||||
void deleteByName(CredentialName name);
|
||||
|
||||
/**
|
||||
* Delete a credential by its full name.
|
||||
* Get the permissions associated with a credential.
|
||||
*
|
||||
* @param name the name of the credential; must not be {@literal null}
|
||||
* @return the collection of permissions associated with the credential
|
||||
*/
|
||||
void deleteByName(CredentialName name);
|
||||
List<CredentialPermission> getPermissions(CredentialName name);
|
||||
|
||||
/**
|
||||
* Add permissions to an existing credential.
|
||||
*
|
||||
* @param name the name of the credential; must not be {@literal null}
|
||||
* @param permissions a collection of permissions to add
|
||||
* @return the collection of permissions associated with the credential
|
||||
*/
|
||||
List<CredentialPermission> addPermissions(CredentialName name, CredentialPermission... permissions);
|
||||
|
||||
/**
|
||||
* Delete a permission associated with a credential.
|
||||
*
|
||||
* @param name the name of the credential; must not be {@literal null}
|
||||
* @param actor the actor of the permission; must not be {@literal null}
|
||||
*/
|
||||
void deletePermission(CredentialName name, Actor actor);
|
||||
|
||||
/**
|
||||
* Search the provided data structure of bound service credentials, looking for
|
||||
|
||||
@@ -22,11 +22,14 @@ import org.springframework.core.ParameterizedTypeReference;
|
||||
import org.springframework.credhub.support.CredentialDetails;
|
||||
import org.springframework.credhub.support.CredentialDetailsData;
|
||||
import org.springframework.credhub.support.CredentialName;
|
||||
import org.springframework.credhub.support.CredentialPermissions;
|
||||
import org.springframework.credhub.support.CredentialRequest;
|
||||
import org.springframework.credhub.support.CredentialSummary;
|
||||
import org.springframework.credhub.support.CredentialSummaryData;
|
||||
import org.springframework.credhub.support.ParametersRequest;
|
||||
import org.springframework.credhub.support.ServicesData;
|
||||
import org.springframework.credhub.support.CredentialRequest;
|
||||
import org.springframework.credhub.support.permissions.Actor;
|
||||
import org.springframework.credhub.support.permissions.CredentialPermission;
|
||||
import org.springframework.http.HttpEntity;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
@@ -53,6 +56,11 @@ public class CredHubTemplate implements CredHubOperations {
|
||||
static final String NAME_URL_QUERY_CURRENT = NAME_URL_QUERY + "¤t=true";
|
||||
static final String NAME_LIKE_URL_QUERY = BASE_URL_PATH + "?name-like={name}";
|
||||
static final String PATH_URL_QUERY = BASE_URL_PATH + "?path={path}";
|
||||
|
||||
static final String PERMISSIONS_URL_PATH = "/api/v1/permissions";
|
||||
static final String PERMISSIONS_URL_QUERY = PERMISSIONS_URL_PATH + "?credential_name={name}";
|
||||
static final String PERMISSIONS_ACTOR_URL_QUERY = PERMISSIONS_URL_QUERY + "&actor={actor}";
|
||||
|
||||
static final String INTERPOLATE_URL_PATH = "/api/v1/interpolate";
|
||||
|
||||
private final RestTemplate restTemplate;
|
||||
@@ -152,7 +160,7 @@ public class CredHubTemplate implements CredHubOperations {
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> CredentialDetails<T> getByName(final String name, Class<T> credentialType) {
|
||||
public <T> CredentialDetails<T> getByName(final CredentialName name, Class<T> credentialType) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
Assert.notNull(credentialType, "credential type must not be null");
|
||||
|
||||
@@ -163,7 +171,7 @@ public class CredHubTemplate implements CredHubOperations {
|
||||
@Override
|
||||
public CredentialDetails<T> doWithRestOperations(RestOperations restOperations) {
|
||||
ResponseEntity<CredentialDetails<T>> response =
|
||||
restOperations.exchange(NAME_URL_QUERY_CURRENT, GET, null, ref, name);
|
||||
restOperations.exchange(NAME_URL_QUERY_CURRENT, GET, null, ref, name.getName());
|
||||
|
||||
throwExceptionOnError(response);
|
||||
|
||||
@@ -173,14 +181,7 @@ public class CredHubTemplate implements CredHubOperations {
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> CredentialDetails<T> getByName(final CredentialName name, Class<T> credentialType) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
|
||||
return getByName(name.getName(), credentialType);
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> List<CredentialDetails<T>> getByNameWithHistory(final String name, Class<T> credentialType) {
|
||||
public <T> List<CredentialDetails<T>> getByNameWithHistory(final CredentialName name, Class<T> credentialType) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
Assert.notNull(credentialType, "credential type must not be null");
|
||||
|
||||
@@ -191,7 +192,7 @@ public class CredHubTemplate implements CredHubOperations {
|
||||
@Override
|
||||
public List<CredentialDetails<T>> doWithRestOperations(RestOperations restOperations) {
|
||||
ResponseEntity<CredentialDetailsData<T>> response =
|
||||
restOperations.exchange(NAME_URL_QUERY, GET, null, ref, name);
|
||||
restOperations.exchange(NAME_URL_QUERY, GET, null, ref, name.getName());
|
||||
|
||||
throwExceptionOnError(response);
|
||||
|
||||
@@ -201,14 +202,7 @@ public class CredHubTemplate implements CredHubOperations {
|
||||
}
|
||||
|
||||
@Override
|
||||
public <T> List<CredentialDetails<T>> getByNameWithHistory(final CredentialName name, Class<T> credentialType) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
|
||||
return getByNameWithHistory(name.getName(), credentialType);
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<CredentialSummary> findByName(final String name) {
|
||||
public List<CredentialSummary> findByName(final CredentialName name) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
|
||||
return doWithRest(new RestOperationsCallback<List<CredentialSummary>>() {
|
||||
@@ -217,7 +211,7 @@ public class CredHubTemplate implements CredHubOperations {
|
||||
RestOperations restOperations) {
|
||||
ResponseEntity<CredentialSummaryData> response = restOperations
|
||||
.getForEntity(NAME_LIKE_URL_QUERY,
|
||||
CredentialSummaryData.class, name);
|
||||
CredentialSummaryData.class, name.getName());
|
||||
|
||||
throwExceptionOnError(response);
|
||||
|
||||
@@ -226,13 +220,6 @@ public class CredHubTemplate implements CredHubOperations {
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<CredentialSummary> findByName(final CredentialName name) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
|
||||
return findByName(name.getName());
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<CredentialSummary> findByPath(final String path) {
|
||||
Assert.notNull(path, "credential path must not be null");
|
||||
@@ -253,23 +240,67 @@ public class CredHubTemplate implements CredHubOperations {
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deleteByName(final String name) {
|
||||
public void deleteByName(final CredentialName name) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
|
||||
final String name1 = name.getName();
|
||||
Assert.notNull(name1, "credential name must not be null");
|
||||
|
||||
doWithRest(new RestOperationsCallback<Void>() {
|
||||
@Override
|
||||
public Void doWithRestOperations(RestOperations restOperations) {
|
||||
restOperations.delete(NAME_URL_QUERY, name);
|
||||
restOperations.delete(NAME_URL_QUERY, name1);
|
||||
return null;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deleteByName(final CredentialName name) {
|
||||
public List<CredentialPermission> getPermissions(final CredentialName name) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
|
||||
deleteByName(name.getName());
|
||||
return doWithRest(new RestOperationsCallback<List<CredentialPermission>>() {
|
||||
@Override
|
||||
public List<CredentialPermission> doWithRestOperations(RestOperations restOperations) {
|
||||
ResponseEntity<CredentialPermissions> response =
|
||||
restOperations.getForEntity(PERMISSIONS_URL_QUERY,
|
||||
CredentialPermissions.class, name.getName());
|
||||
return response.getBody().getPermissions();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<CredentialPermission> addPermissions(final CredentialName name, CredentialPermission... permissions) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
|
||||
final CredentialPermissions credentialPermissions = new CredentialPermissions(name, permissions);
|
||||
|
||||
return doWithRest(new RestOperationsCallback<List<CredentialPermission>>() {
|
||||
@Override
|
||||
public List<CredentialPermission> doWithRestOperations(RestOperations restOperations) {
|
||||
ResponseEntity<CredentialPermissions> response =
|
||||
restOperations.exchange(PERMISSIONS_URL_PATH, POST,
|
||||
new HttpEntity<CredentialPermissions>(credentialPermissions),
|
||||
CredentialPermissions.class);
|
||||
|
||||
return response.getBody().getPermissions();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deletePermission(final CredentialName name, final Actor actor) {
|
||||
Assert.notNull(name, "credential name must not be null");
|
||||
Assert.notNull(actor, "actor must not be null");
|
||||
|
||||
doWithRest(new RestOperationsCallback<Void>() {
|
||||
@Override
|
||||
public Void doWithRestOperations(RestOperations restOperations) {
|
||||
restOperations.delete(PERMISSIONS_ACTOR_URL_QUERY, name.getName(), actor.getIdentity());
|
||||
return null;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
@@ -1,221 +0,0 @@
|
||||
/*
|
||||
*
|
||||
* * Copyright 2013-2017 the original author or authors.
|
||||
* *
|
||||
* * 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 org.springframework.credhub.support;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Permissions applied to a credential in CredHub. If provided when a
|
||||
* credential is written, these values will control what actors can access update
|
||||
* or retrieve the credential.
|
||||
*
|
||||
* Objects of this type are constructed by the application and passed
|
||||
* as part of a {@link CredentialRequest}.
|
||||
*
|
||||
* @author Scott Frederick
|
||||
*/
|
||||
public class AdditionalPermission {
|
||||
private static final String APP_ACTOR_PREFIX = "mtls-app:";
|
||||
|
||||
private String actor;
|
||||
private List<Operation> operations;
|
||||
|
||||
/**
|
||||
* Create a set of permissions. Intended to be used internally for testing.
|
||||
* Clients should use {@link #builder()} to construct instances of this class.
|
||||
*
|
||||
* @param actor the ID of the entity that will be allowed to access the credential
|
||||
* @param operations the operations that the actor will be allowed to perform on the
|
||||
* credential
|
||||
*/
|
||||
AdditionalPermission(String actor, List<Operation> operations) {
|
||||
this.actor = actor;
|
||||
this.operations = operations;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the ID of the entity that will be allowed to access the credential.
|
||||
*
|
||||
* @return the ID
|
||||
*/
|
||||
public String getActor() {
|
||||
return this.actor;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the set of operations that the actor will be allowed to perform on
|
||||
* the credential.
|
||||
*
|
||||
* @return the operations
|
||||
*/
|
||||
public List<String> getOperations() {
|
||||
List<String> operationValues = new ArrayList<String>(operations.size());
|
||||
for (Operation operation : operations) {
|
||||
operationValues.add(operation.operation());
|
||||
}
|
||||
return operationValues;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a builder that provides a fluent API for providing the values required
|
||||
* to construct a {@link AdditionalPermission}.
|
||||
*
|
||||
* @return a builder
|
||||
*/
|
||||
public static AdditionalPermissionBuilder builder() {
|
||||
return new AdditionalPermissionBuilder();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o)
|
||||
return true;
|
||||
if (!(o instanceof AdditionalPermission))
|
||||
return false;
|
||||
|
||||
AdditionalPermission that = (AdditionalPermission) o;
|
||||
|
||||
if (actor != null ? !actor.equals(that.actor) : that.actor != null)
|
||||
return false;
|
||||
return operations != null ? operations.equals(that.operations)
|
||||
: that.operations == null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = actor != null ? actor.hashCode() : 0;
|
||||
result = 31 * result + (operations != null ? operations.hashCode() : 0);
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "AdditionalPermission{"
|
||||
+ "actor='" + actor + '\''
|
||||
+ ", operations=" + operations
|
||||
+ '}';
|
||||
}
|
||||
|
||||
/**
|
||||
* A builder that provides a fluent API for constructing {@link AdditionalPermission}
|
||||
* instances.
|
||||
*/
|
||||
public static class AdditionalPermissionBuilder {
|
||||
private String actor;
|
||||
private ArrayList<Operation> operations;
|
||||
|
||||
AdditionalPermissionBuilder() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the ID of an application that will be allowed to access a credential.
|
||||
* This will often be a Cloud Foundry application GUID.
|
||||
*
|
||||
* @param appId application ID
|
||||
* @return the builder
|
||||
*/
|
||||
public AdditionalPermissionBuilder app(String appId) {
|
||||
this.actor = APP_ACTOR_PREFIX + appId;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the name of an actor that will be allowed to access the credential.
|
||||
*
|
||||
* @param actor actor name
|
||||
* @return the builder
|
||||
*/
|
||||
public AdditionalPermissionBuilder actor(String actor) {
|
||||
this.actor = actor;
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set an {@link Operation} that the actor will be allowed to perform on
|
||||
* the credential. Multiple operations can be provided with consecutive calls to
|
||||
* this method.
|
||||
*
|
||||
* @param operation the {@link Operation}
|
||||
* @return the builder
|
||||
*/
|
||||
public AdditionalPermissionBuilder operation(Operation operation) {
|
||||
initOperations();
|
||||
this.operations.add(operation);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Specify a set of {@link Operation}s that the actor will be allowed to perform
|
||||
* on the credential.
|
||||
*
|
||||
* @param operations the {@link Operation}s
|
||||
* @return the builder
|
||||
*/
|
||||
public AdditionalPermissionBuilder operations(Collection<? extends Operation> operations) {
|
||||
initOperations();
|
||||
this.operations.addAll(operations);
|
||||
return this;
|
||||
}
|
||||
|
||||
private void initOperations() {
|
||||
if (this.operations == null) this.operations = new ArrayList<Operation>();
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct an {@link AdditionalPermission} with the provided values.
|
||||
*
|
||||
* @return an {@link AdditionalPermission}
|
||||
*/
|
||||
public AdditionalPermission build() {
|
||||
List<Operation> operations;
|
||||
switch (this.operations == null ? 0 : this.operations.size()) {
|
||||
case 0:
|
||||
operations = java.util.Collections.emptyList();
|
||||
break;
|
||||
case 1:
|
||||
operations = java.util.Collections.singletonList(this.operations.get(0));
|
||||
break;
|
||||
default:
|
||||
operations = java.util.Collections.unmodifiableList(new ArrayList<Operation>(this.operations));
|
||||
}
|
||||
|
||||
return new AdditionalPermission(actor, operations);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* The set of operations that are allowed on a credential.
|
||||
*/
|
||||
public enum Operation {
|
||||
READ("read"),
|
||||
WRITE("write");
|
||||
|
||||
private final String operation;
|
||||
|
||||
Operation(String operation) {
|
||||
this.operation = operation;
|
||||
}
|
||||
|
||||
public String operation() {
|
||||
return operation;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,18 +1,18 @@
|
||||
/*
|
||||
*
|
||||
* * Copyright 2013-2017 the original author or authors.
|
||||
* *
|
||||
* * 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.
|
||||
* Copyright 2013-2017 the original author or authors.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
@@ -80,7 +80,7 @@ public class CredentialDetailsData<T> {
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "CredentialDetailResponse{"
|
||||
return "CredentialDetailData{"
|
||||
+ "data=" + data
|
||||
+ '}';
|
||||
}
|
||||
|
||||
@@ -0,0 +1,100 @@
|
||||
/*
|
||||
*
|
||||
* Copyright 2013-2017 the original author or authors.
|
||||
*
|
||||
* 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 org.springframework.credhub.support;
|
||||
|
||||
import org.springframework.credhub.support.permissions.CredentialPermission;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* A collection of {@link CredentialPermission}s. Clients don't typically instantiate
|
||||
* objects of this type, but will receive them in response to write and retrieve
|
||||
* requests.
|
||||
*
|
||||
* @author Scott Frederick
|
||||
*/
|
||||
public class CredentialPermissions {
|
||||
private CredentialName credentialName;
|
||||
private List<CredentialPermission> permissions;
|
||||
|
||||
/**
|
||||
* Create a {@link CredentialPermissions}.
|
||||
*/
|
||||
public CredentialPermissions() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a {@link CredentialPermissions} from the provided parameters. Intended for internal
|
||||
* use. Clients will get {@link CredentialPermissions} objects populated from
|
||||
* CredHub responses.
|
||||
*
|
||||
* @param credentialName the name of the credential that the permissions will apply to
|
||||
* @param permissions a collection of {@link CredentialPermission}s
|
||||
*/
|
||||
public CredentialPermissions(CredentialName credentialName, CredentialPermission... permissions) {
|
||||
this.credentialName = credentialName;
|
||||
this.permissions = Arrays.asList(permissions);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the name of the credential that the permissions apply to.
|
||||
*
|
||||
* @return the credential name
|
||||
*/
|
||||
public String getCredentialName() {
|
||||
return this.credentialName.getName();
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the collection of {@link CredentialPermission}s.
|
||||
*
|
||||
* @return the collection of {@link CredentialPermission}s
|
||||
*/
|
||||
public List<CredentialPermission> getPermissions() {
|
||||
return this.permissions;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "CredentialPermissions{"
|
||||
+ "credentialName=" + credentialName
|
||||
+ ", permissions=" + permissions
|
||||
+ '}';
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
if (!(o instanceof CredentialPermissions)) return false;
|
||||
|
||||
CredentialPermissions that = (CredentialPermissions) o;
|
||||
|
||||
if (credentialName != null ? !credentialName.equals(that.credentialName) : that.credentialName != null)
|
||||
return false;
|
||||
return permissions != null ? permissions.equals(that.permissions) : that.permissions == null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = credentialName != null ? credentialName.hashCode() : 0;
|
||||
result = 31 * result + (permissions != null ? permissions.hashCode() : 0);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
@@ -1,18 +1,18 @@
|
||||
/*
|
||||
*
|
||||
* * Copyright 2013-2017 the original author or authors.
|
||||
* *
|
||||
* * 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.
|
||||
* Copyright 2013-2017 the original author or authors.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
@@ -23,6 +23,7 @@ import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import org.springframework.credhub.support.permissions.CredentialPermission;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
/**
|
||||
@@ -32,7 +33,7 @@ import org.springframework.util.Assert;
|
||||
*/
|
||||
public class CredentialRequest<T> extends CredHubRequest {
|
||||
private T value;
|
||||
private List<AdditionalPermission> additionalPermissions;
|
||||
private List<CredentialPermission> additionalPermissions;
|
||||
|
||||
/**
|
||||
* Initialize a {@link CredentialRequest}.
|
||||
@@ -41,7 +42,7 @@ public class CredentialRequest<T> extends CredHubRequest {
|
||||
*/
|
||||
protected CredentialRequest(CredentialType type) {
|
||||
this.credentialType = type;
|
||||
additionalPermissions = new ArrayList<AdditionalPermission>();
|
||||
additionalPermissions = new ArrayList<CredentialPermission>();
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -58,11 +59,11 @@ public class CredentialRequest<T> extends CredHubRequest {
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the set of {@link AdditionalPermission} to assign to the credential.
|
||||
* Get the set of {@link CredentialPermission} to assign to the credential.
|
||||
*
|
||||
* @return the set of {@link AdditionalPermission}
|
||||
* @return the set of {@link CredentialPermission}
|
||||
*/
|
||||
public List<AdditionalPermission> getAdditionalPermissions() {
|
||||
public List<CredentialPermission> getAdditionalPermissions() {
|
||||
return this.additionalPermissions;
|
||||
}
|
||||
|
||||
@@ -171,40 +172,40 @@ public class CredentialRequest<T> extends CredHubRequest {
|
||||
}
|
||||
|
||||
/**
|
||||
* Add an {@link AdditionalPermission} to the permissions that will be assigned to the
|
||||
* Add an {@link CredentialPermission} to the permissions that will be assigned to the
|
||||
* credential.
|
||||
*
|
||||
* @param permission an {@link AdditionalPermission} to assign to the
|
||||
* @param permission a {@link CredentialPermission} to assign to the
|
||||
* credential
|
||||
* @return the builder
|
||||
*/
|
||||
public B additionalPermission(AdditionalPermission permission) {
|
||||
public B permission(CredentialPermission permission) {
|
||||
targetObj.getAdditionalPermissions().add(permission);
|
||||
return thisObj;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a collection of {@link AdditionalPermission}s to the controls that will be
|
||||
* Add a collection of {@link CredentialPermission}s to the controls that will be
|
||||
* assigned to the credential.
|
||||
*
|
||||
* @param permissions an collection of {@link AdditionalPermission}s to
|
||||
* @param permissions a collection of {@link CredentialPermission}s to
|
||||
* assign to the credential
|
||||
* @return the builder
|
||||
*/
|
||||
public B additionalPermissions(Collection<? extends AdditionalPermission> permissions) {
|
||||
public B permissions(Collection<? extends CredentialPermission> permissions) {
|
||||
targetObj.getAdditionalPermissions().addAll(permissions);
|
||||
return thisObj;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a collection of {@link AdditionalPermission}s to the controls that will be
|
||||
* Add a collection of {@link CredentialPermission}s to the controls that will be
|
||||
* assigned to the credential.
|
||||
*
|
||||
* @param permissions an collection of {@link AdditionalPermission}s to
|
||||
* @param permissions a collection of {@link CredentialPermission}s to
|
||||
* assign to the credential
|
||||
* @return the builder
|
||||
*/
|
||||
public B additionalPermissions(AdditionalPermission... permissions) {
|
||||
public B permissions(CredentialPermission... permissions) {
|
||||
targetObj.getAdditionalPermissions().addAll(Arrays.asList(permissions));
|
||||
return thisObj;
|
||||
}
|
||||
|
||||
@@ -1,24 +1,23 @@
|
||||
/*
|
||||
*
|
||||
* * Copyright 2013-2017 the original author or authors.
|
||||
* *
|
||||
* * 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.
|
||||
* Copyright 2013-2017 the original author or authors.
|
||||
*
|
||||
* 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 org.springframework.credhub.support;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonCreator;
|
||||
import org.springframework.credhub.support.certificate.CertificateCredential;
|
||||
import org.springframework.credhub.support.json.JsonCredential;
|
||||
import org.springframework.credhub.support.password.PasswordCredential;
|
||||
@@ -93,18 +92,9 @@ public enum CredentialType {
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert a {@literal String} type to its enum value.
|
||||
*
|
||||
* @param type the {@literal String} type to convert
|
||||
* @return the enum value
|
||||
* {@inheritDoc}
|
||||
*/
|
||||
@JsonCreator
|
||||
public static CredentialType getTypeByString(String type) {
|
||||
for (CredentialType value : CredentialType.values()) {
|
||||
if (value.getValueType().equals(type)) {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
public String toString() {
|
||||
return valueType;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,152 @@
|
||||
/*
|
||||
*
|
||||
* Copyright 2013-2017 the original author or authors.
|
||||
*
|
||||
* 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 org.springframework.credhub.support.permissions;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonCreator;
|
||||
import com.fasterxml.jackson.annotation.JsonValue;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
import static org.springframework.credhub.support.permissions.ActorType.APP;
|
||||
import static org.springframework.credhub.support.permissions.ActorType.OAUTH_CLIENT;
|
||||
import static org.springframework.credhub.support.permissions.ActorType.USER;
|
||||
|
||||
/**
|
||||
* Identifies an entity that is authorized to perform operations on a CredHub credential.
|
||||
*
|
||||
* @author Scott Frederick
|
||||
*/
|
||||
public class Actor {
|
||||
private ActorType authType;
|
||||
private String primaryIdentifier;
|
||||
|
||||
/**
|
||||
* Create a new {@literal Actor}.
|
||||
*
|
||||
* @param actorType the type of the authorized entity
|
||||
* @param primaryIdentifier the unique identifier of the authorized entity
|
||||
*/
|
||||
private Actor(ActorType actorType, String primaryIdentifier) {
|
||||
this.authType = actorType;
|
||||
this.primaryIdentifier = primaryIdentifier;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create an application identifier. An application is identified by a GUID generated
|
||||
* by Cloud Foundry when the application is created.
|
||||
*
|
||||
* @param appId the Cloud Foundry application GUID
|
||||
* @return the created {@literal Actor}
|
||||
*/
|
||||
public static Actor app(String appId) {
|
||||
Assert.notNull(appId, "appId must not be null");
|
||||
return new Actor(APP, appId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a user identifier. A user is identified by a GUID generated by UAA when
|
||||
* a user account is created and the ID of the identity zone the user was created in.
|
||||
*
|
||||
* @param zoneId the UAA identity zone ID
|
||||
* @param userId the UAA user GUID
|
||||
* @return the created {@literal Actor}
|
||||
*/
|
||||
public static Actor user(String zoneId, String userId) {
|
||||
Assert.notNull(zoneId, "zoneId must not be null");
|
||||
Assert.notNull(userId, "userId must not be null");
|
||||
return new Actor(USER, zoneId + "/" + userId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create an OAuth2 client identifier. A client identified by user-provided identifier
|
||||
* and the ID of the identity zone the client was created in.
|
||||
*
|
||||
* @param zoneId the UAA identity zone ID
|
||||
* @param clientId the UAA client ID
|
||||
* @return the created {@literal Actor}
|
||||
*/
|
||||
public static Actor client(String zoneId, String clientId) {
|
||||
Assert.notNull(zoneId, "zoneId must not be null");
|
||||
Assert.notNull(clientId, "clientId must not be null");
|
||||
return new Actor(OAUTH_CLIENT, zoneId + "/" + clientId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the type of the authorized entity.
|
||||
*
|
||||
* @return the entity type
|
||||
*/
|
||||
public ActorType getAuthType() {
|
||||
return authType;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the identity of the authorized entity.
|
||||
*
|
||||
* @return the identifier
|
||||
*/
|
||||
public String getPrimaryIdentifier() {
|
||||
return primaryIdentifier;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the full identifier for the authorized entity, which is a combination of the type and identity.
|
||||
*
|
||||
* @return the full identifier
|
||||
*/
|
||||
@JsonValue
|
||||
public String getIdentity() {
|
||||
return authType.getType() + ":" + primaryIdentifier;
|
||||
}
|
||||
|
||||
@JsonCreator
|
||||
private static Actor createActor(String value) {
|
||||
for (ActorType type : ActorType.values()) {
|
||||
if (value.startsWith(type.getType())) {
|
||||
return new Actor(type, value.substring(type.getType().length() + 1));
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Actor{" +
|
||||
"authType=" + authType +
|
||||
", primaryIdentifier='" + primaryIdentifier + '\'' +
|
||||
'}';
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o) return true;
|
||||
if (!(o instanceof Actor)) return false;
|
||||
|
||||
Actor actor = (Actor) o;
|
||||
|
||||
if (authType != actor.authType) return false;
|
||||
return primaryIdentifier.equals(actor.primaryIdentifier);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = authType.hashCode();
|
||||
result = 31 * result + primaryIdentifier.hashCode();
|
||||
return result;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,63 @@
|
||||
/*
|
||||
*
|
||||
* Copyright 2013-2017 the original author or authors.
|
||||
*
|
||||
* 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 org.springframework.credhub.support.permissions;
|
||||
|
||||
/**
|
||||
* The types of entities that can be authorized to perform operations on CredHub credentials.
|
||||
*
|
||||
* @author Scott Frederick
|
||||
*/
|
||||
public enum ActorType {
|
||||
/**
|
||||
* An Cloud Foundry application entity
|
||||
*/
|
||||
APP("mtls-app"),
|
||||
|
||||
/**
|
||||
* A UAA user entity, as can be used with a password grant
|
||||
*/
|
||||
USER("uaa-user"),
|
||||
|
||||
/**
|
||||
* A UAA client entity, as can be used with a client credentials grant
|
||||
*/
|
||||
OAUTH_CLIENT("uaa-client");
|
||||
|
||||
private final String type;
|
||||
|
||||
ActorType(String type) {
|
||||
this.type = type;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the entity type.
|
||||
*
|
||||
* @return the entity type
|
||||
*/
|
||||
public String getType() {
|
||||
return type;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*/
|
||||
public String toString() {
|
||||
return type;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,253 @@
|
||||
/*
|
||||
*
|
||||
* Copyright 2013-2017 the original author or authors.
|
||||
*
|
||||
* 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 org.springframework.credhub.support.permissions;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonGetter;
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
import org.springframework.credhub.support.CredentialRequest;
|
||||
import org.springframework.util.Assert;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
/**
|
||||
* Permissions applied to a credential in CredHub. If provided when a
|
||||
* credential is written, these values will control what actors can access update
|
||||
* or retrieve the credential.
|
||||
*
|
||||
* Objects of this type are constructed by the application and passed
|
||||
* as part of a {@link CredentialRequest}.
|
||||
*
|
||||
* @author Scott Frederick
|
||||
*/
|
||||
public class CredentialPermission {
|
||||
private Actor actor;
|
||||
|
||||
@JsonProperty
|
||||
private List<Operation> operations;
|
||||
|
||||
/**
|
||||
* Create a {@literal CredentialPermission}.
|
||||
*/
|
||||
private CredentialPermission() {
|
||||
this.actor = null;
|
||||
this.operations = null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a set of permissions. Intended to be used internally.
|
||||
* Clients should use {@link #builder()} to construct instances of this class.
|
||||
*
|
||||
* @param actor the ID of the entity that will be allowed to access the credential
|
||||
* @param operations the operations that the actor will be allowed to perform on the
|
||||
* credential
|
||||
*/
|
||||
private CredentialPermission(Actor actor, List<Operation> operations) {
|
||||
this.actor = actor;
|
||||
this.operations = operations;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the ID of the entity that will be allowed to access the credential.
|
||||
*
|
||||
* @return the ID
|
||||
*/
|
||||
public Actor getActor() {
|
||||
return this.actor;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the set of operations that the actor will be allowed to perform on
|
||||
* the credential.
|
||||
*
|
||||
* @return the operations
|
||||
*/
|
||||
public List<Operation> getOperations() {
|
||||
return operations;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the set of operations that the actor will be allowed to perform on
|
||||
* the credential.
|
||||
*
|
||||
* @return the operations
|
||||
*/
|
||||
@JsonGetter("operations")
|
||||
private List<String> getOperationsAsString() {
|
||||
if (operations == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
List<String> operationValues = new ArrayList<String>(operations.size());
|
||||
for (Operation operation : operations) {
|
||||
operationValues.add(operation.operation());
|
||||
}
|
||||
return operationValues;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a builder that provides a fluent API for providing the values required
|
||||
* to construct a {@link CredentialPermission}.
|
||||
*
|
||||
* @return a builder
|
||||
*/
|
||||
public static CredentialPermissionBuilder builder() {
|
||||
return new CredentialPermissionBuilder();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object o) {
|
||||
if (this == o)
|
||||
return true;
|
||||
if (!(o instanceof CredentialPermission))
|
||||
return false;
|
||||
|
||||
CredentialPermission that = (CredentialPermission) o;
|
||||
|
||||
if (actor != null ? !actor.equals(that.actor) : that.actor != null)
|
||||
return false;
|
||||
return operations != null ? operations.equals(that.operations)
|
||||
: that.operations == null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = actor != null ? actor.hashCode() : 0;
|
||||
result = 31 * result + (operations != null ? operations.hashCode() : 0);
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "CredentialPermission{"
|
||||
+ "actor='" + actor + '\''
|
||||
+ ", operations=" + operations
|
||||
+ '}';
|
||||
}
|
||||
|
||||
/**
|
||||
* A builder that provides a fluent API for constructing {@link CredentialPermission}
|
||||
* instances.
|
||||
*/
|
||||
public static class CredentialPermissionBuilder {
|
||||
private Actor actor;
|
||||
private ArrayList<Operation> operations;
|
||||
|
||||
CredentialPermissionBuilder() {
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the ID of an application that will be assigned permissions on a credential.
|
||||
* This will often be a Cloud Foundry application GUID.
|
||||
*
|
||||
* @param appId application ID; must not be {@literal null}
|
||||
* @return the builder
|
||||
*/
|
||||
public CredentialPermissionBuilder app(String appId) {
|
||||
Assert.notNull(appId, "appId must not be null");
|
||||
Assert.isNull(actor, "only one actor can be specified");
|
||||
this.actor = Actor.app(appId);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the ID of a user that will be assigned permissions on a credential.
|
||||
* This is typically a GUID generated by UAA when a user account is created.
|
||||
*
|
||||
* @param zoneId zone ID; must not be {@literal null}
|
||||
* @param userId user ID; must not be {@literal null}
|
||||
* @return the builder
|
||||
*/
|
||||
public CredentialPermissionBuilder user(String zoneId, String userId) {
|
||||
Assert.notNull(zoneId, "zoneId must not be null");
|
||||
Assert.notNull(userId, "userId must not be null");
|
||||
Assert.isNull(actor, "only one actor can be specified");
|
||||
this.actor = Actor.user(zoneId, userId);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the ID of an OAuth2 client that will be assigned permissions on a credential.
|
||||
*
|
||||
* @param zoneId zone ID; must not be {@literal null}
|
||||
* @param clientId OAuth2 client ID; must not be {@literal null}
|
||||
* @return the builder
|
||||
*/
|
||||
public CredentialPermissionBuilder client(String zoneId, String clientId) {
|
||||
Assert.notNull(zoneId, "zoneId must not be null");
|
||||
Assert.notNull(clientId, "clientId must not be null");
|
||||
Assert.isNull(actor, "only one actor can be specified");
|
||||
this.actor = Actor.client(zoneId, clientId);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set an {@link Operation} that the actor will be allowed to perform on
|
||||
* the credential. Multiple operations can be provided with consecutive calls to
|
||||
* this method.
|
||||
*
|
||||
* @param operation the {@link Operation}
|
||||
* @return the builder
|
||||
*/
|
||||
public CredentialPermissionBuilder operation(Operation operation) {
|
||||
initOperations();
|
||||
this.operations.add(operation);
|
||||
return this;
|
||||
}
|
||||
|
||||
/**
|
||||
* Specify a set of {@link Operation}s that the actor will be allowed to perform
|
||||
* on the credential.
|
||||
*
|
||||
* @param operations the {@link Operation}s
|
||||
* @return the builder
|
||||
*/
|
||||
public CredentialPermissionBuilder operations(Operation... operations) {
|
||||
initOperations();
|
||||
this.operations.addAll(Arrays.asList(operations));
|
||||
return this;
|
||||
}
|
||||
|
||||
private void initOperations() {
|
||||
if (this.operations == null) this.operations = new ArrayList<Operation>();
|
||||
}
|
||||
|
||||
/**
|
||||
* Construct a {@link CredentialPermission} with the provided values.
|
||||
*
|
||||
* @return a {@link CredentialPermission}
|
||||
*/
|
||||
public CredentialPermission build() {
|
||||
List<Operation> operations;
|
||||
switch (this.operations == null ? 0 : this.operations.size()) {
|
||||
case 0:
|
||||
operations = java.util.Collections.emptyList();
|
||||
break;
|
||||
case 1:
|
||||
operations = java.util.Collections.singletonList(this.operations.get(0));
|
||||
break;
|
||||
default:
|
||||
operations = java.util.Collections.unmodifiableList(new ArrayList<Operation>(this.operations));
|
||||
}
|
||||
|
||||
return new CredentialPermission(actor, operations);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,73 @@
|
||||
/*
|
||||
*
|
||||
* Copyright 2013-2017 the original author or authors.
|
||||
*
|
||||
* 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 org.springframework.credhub.support.permissions;
|
||||
|
||||
/**
|
||||
* The set of operations that are allowed on a credential.
|
||||
*
|
||||
* @author Scott Frederick
|
||||
*/
|
||||
public enum Operation {
|
||||
/**
|
||||
* Allows the value of a credential to be read.
|
||||
*/
|
||||
READ("read"),
|
||||
|
||||
/**
|
||||
* Allows the value of a credential to be updated.
|
||||
*/
|
||||
WRITE("write"),
|
||||
|
||||
/**
|
||||
* Allows a credential to be deleted.
|
||||
*/
|
||||
DELETE("delete"),
|
||||
|
||||
/**
|
||||
* Allows the permissions of a credential to be read.
|
||||
*/
|
||||
READ_ACL("read_acl"),
|
||||
|
||||
/**
|
||||
* Allows the permissions of a credential to be updated.
|
||||
*/
|
||||
WRITE_ACL("write_acl");
|
||||
|
||||
private final String operation;
|
||||
|
||||
Operation(String operation) {
|
||||
this.operation = operation;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the value of the operation.
|
||||
*
|
||||
* @return the value of the operation.
|
||||
*/
|
||||
public String operation() {
|
||||
return operation;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritDoc}
|
||||
*/
|
||||
public String toString() {
|
||||
return operation;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
/*
|
||||
* Copyright 2016-2017 the original author or authors.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
/**
|
||||
* Java representations of CredHub JSON credential permissions.
|
||||
*/
|
||||
package org.springframework.credhub.support.permissions;
|
||||
@@ -14,14 +14,16 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.credhub.support;
|
||||
package org.springframework.credhub.support.utils;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonInclude;
|
||||
import com.fasterxml.jackson.databind.DeserializationFeature;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.fasterxml.jackson.databind.PropertyNamingStrategy;
|
||||
import com.fasterxml.jackson.databind.SerializationFeature;
|
||||
import com.fasterxml.jackson.databind.jsontype.NamedType;
|
||||
import com.fasterxml.jackson.databind.util.ISO8601DateFormat;
|
||||
import org.springframework.credhub.support.CredentialType;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
@@ -44,6 +46,8 @@ public class JsonUtils {
|
||||
objectMapper.setPropertyNamingStrategy(new PropertyNamingStrategy.SnakeCaseStrategy());
|
||||
objectMapper.setSerializationInclusion(JsonInclude.Include.NON_EMPTY);
|
||||
objectMapper.configure(DeserializationFeature.FAIL_ON_UNKNOWN_PROPERTIES, false);
|
||||
objectMapper.configure(DeserializationFeature.READ_ENUMS_USING_TO_STRING, true);
|
||||
objectMapper.configure(SerializationFeature.WRITE_ENUMS_USING_TO_STRING, true);
|
||||
|
||||
configureCredentialDetailTypeMapping(objectMapper);
|
||||
|
||||
@@ -62,6 +66,10 @@ public class JsonUtils {
|
||||
subtypes.add(new NamedType(type.getModelClass(), type.getValueType()));
|
||||
}
|
||||
|
||||
registerSubtypes(objectMapper, subtypes);
|
||||
}
|
||||
|
||||
private static void registerSubtypes(ObjectMapper objectMapper, List<NamedType> subtypes) {
|
||||
objectMapper.registerSubtypes(subtypes.toArray(new NamedType[]{}));
|
||||
}
|
||||
}
|
||||
@@ -95,26 +95,14 @@ public class CredHubTemplateDetailCertificateUnitTests
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithString(@FromDataPoints("detail-responses")
|
||||
public void getByName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<CertificateCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingString(expectedResponse);
|
||||
verifyGetByName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithCredentialName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<CertificateCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingCredentialName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingString(@FromDataPoints("data-responses")
|
||||
public void getByNameWithHistory(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<CertificateCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingString(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingCredentialName(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<CertificateCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingCredentialName(expectedResponse);
|
||||
verifyGetByNameWithHistory(expectedResponse);
|
||||
}
|
||||
}
|
||||
@@ -78,26 +78,14 @@ public class CredHubTemplateDetailJsonUnitTests
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingString(@FromDataPoints("detail-responses")
|
||||
public void getByName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<JsonCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingString(expectedResponse);
|
||||
verifyGetByName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingCredentialName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<JsonCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingCredentialName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingString(@FromDataPoints("data-responses")
|
||||
public void getByNameWithHistory(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<JsonCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingString(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingCredentialName(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<JsonCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingCredentialName(expectedResponse);
|
||||
verifyGetByNameWithHistory(expectedResponse);
|
||||
}
|
||||
}
|
||||
@@ -91,26 +91,14 @@ public class CredHubTemplateDetailPasswordUnitTests
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingString(@FromDataPoints("detail-responses")
|
||||
public void getByName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<PasswordCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingString(expectedResponse);
|
||||
verifyGetByName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingCredentialName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<PasswordCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingCredentialName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingString(@FromDataPoints("data-responses")
|
||||
public void getByNameWithHistory(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<PasswordCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingString(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingCredentialName(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<PasswordCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingCredentialName(expectedResponse);
|
||||
verifyGetByNameWithHistory(expectedResponse);
|
||||
}
|
||||
}
|
||||
@@ -92,26 +92,14 @@ public class CredHubTemplateDetailRsaUnitTests
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingString(@FromDataPoints("detail-responses")
|
||||
public void getByName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<RsaCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingString(expectedResponse);
|
||||
verifyGetByName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingCredentialName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<RsaCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingCredentialName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingString(@FromDataPoints("data-responses")
|
||||
public void getByNameWithHistory(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<RsaCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingString(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingCredentialName(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<RsaCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingCredentialName(expectedResponse);
|
||||
verifyGetByNameWithHistory(expectedResponse);
|
||||
}
|
||||
}
|
||||
@@ -92,26 +92,14 @@ public class CredHubTemplateDetailSshUnitTests
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingString(@FromDataPoints("detail-responses")
|
||||
public void getByName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<SshCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingString(expectedResponse);
|
||||
verifyGetByName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingCredentialName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<SshCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingCredentialName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingString(@FromDataPoints("data-responses")
|
||||
public void getByNameWithHistory(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<SshCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingString(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingCredentialName(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<SshCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingCredentialName(expectedResponse);
|
||||
verifyGetByNameWithHistory(expectedResponse);
|
||||
}
|
||||
}
|
||||
@@ -150,31 +150,7 @@ public abstract class CredHubTemplateDetailUnitTestsBase<T, P> extends CredHubTe
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
void verifyGetByNameUsingString(ResponseEntity<CredentialDetails<T>> expectedResponse) {
|
||||
when(restTemplate.exchange(eq(NAME_URL_QUERY_CURRENT), eq(GET), isNull(HttpEntity.class),
|
||||
isA(ParameterizedTypeReference.class), eq(NAME.getName())))
|
||||
.thenReturn(expectedResponse);
|
||||
|
||||
if (!expectedResponse.getStatusCode().equals(OK)) {
|
||||
try {
|
||||
credHubTemplate.getByName(NAME.getName(), String.class);
|
||||
fail("Exception should have been thrown");
|
||||
}
|
||||
catch (CredHubException e) {
|
||||
assertThat(e.getMessage(),
|
||||
containsString(expectedResponse.getStatusCode().toString()));
|
||||
}
|
||||
}
|
||||
else {
|
||||
CredentialDetails<T> response = credHubTemplate
|
||||
.getByName(NAME.getName(), getType());
|
||||
|
||||
assertResponseContainsExpectedCredentials(expectedResponse, response);
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
void verifyGetByNameUsingCredentialName(ResponseEntity<CredentialDetails<T>> expectedResponse) {
|
||||
void verifyGetByName(ResponseEntity<CredentialDetails<T>> expectedResponse) {
|
||||
when(restTemplate.exchange(eq(NAME_URL_QUERY_CURRENT), eq(GET), isNull(HttpEntity.class),
|
||||
isA(ParameterizedTypeReference.class), eq(NAME.getName())))
|
||||
.thenReturn(expectedResponse);
|
||||
@@ -197,30 +173,7 @@ public abstract class CredHubTemplateDetailUnitTestsBase<T, P> extends CredHubTe
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
void verifyGetByNameWithHistoryUsingString(ResponseEntity<CredentialDetailsData<T>> expectedResponse) {
|
||||
when(restTemplate.exchange(eq(NAME_URL_QUERY), eq(GET), isNull(HttpEntity.class),
|
||||
isA(ParameterizedTypeReference.class), eq(NAME.getName())))
|
||||
.thenReturn(expectedResponse);
|
||||
|
||||
if (!expectedResponse.getStatusCode().equals(OK)) {
|
||||
try {
|
||||
credHubTemplate.getByNameWithHistory(NAME.getName(), String.class);
|
||||
fail("Exception should have been thrown");
|
||||
}
|
||||
catch (CredHubException e) {
|
||||
assertThat(e.getMessage(),
|
||||
containsString(expectedResponse.getStatusCode().toString()));
|
||||
}
|
||||
}
|
||||
else {
|
||||
List<CredentialDetails<T>> response = credHubTemplate.getByNameWithHistory(NAME.getName(), getType());
|
||||
|
||||
assertResponseContainsExpectedCredentials(expectedResponse, response);
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
void verifyGetByNameWithHistoryUsingCredentialName(ResponseEntity<CredentialDetailsData<T>> expectedResponse) {
|
||||
void verifyGetByNameWithHistory(ResponseEntity<CredentialDetailsData<T>> expectedResponse) {
|
||||
when(restTemplate.exchange(eq(NAME_URL_QUERY), eq(GET), isNull(HttpEntity.class),
|
||||
isA(ParameterizedTypeReference.class), eq(NAME.getName())))
|
||||
.thenReturn(expectedResponse);
|
||||
|
||||
@@ -73,26 +73,14 @@ public class CredHubTemplateDetailUserUnitTests
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingString(@FromDataPoints("detail-responses")
|
||||
public void getByName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<UserCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingString(expectedResponse);
|
||||
verifyGetByName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingCredentialName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<UserCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingCredentialName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingString(@FromDataPoints("data-responses")
|
||||
public void getByNameWithHistory(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<UserCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingString(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingCredentialName(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<UserCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingCredentialName(expectedResponse);
|
||||
verifyGetByNameWithHistory(expectedResponse);
|
||||
}
|
||||
}
|
||||
@@ -74,26 +74,14 @@ public class CredHubTemplateDetailValueUnitTests
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingString(@FromDataPoints("detail-responses")
|
||||
public void getByName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<ValueCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingString(expectedResponse);
|
||||
verifyGetByName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameUsingCredentialName(@FromDataPoints("detail-responses")
|
||||
ResponseEntity<CredentialDetails<ValueCredential>> expectedResponse) {
|
||||
verifyGetByNameUsingCredentialName(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingString(@FromDataPoints("data-responses")
|
||||
public void getByNameWithHistory(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<ValueCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingString(expectedResponse);
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void getByNameWithHistoryUsingCredentialName(@FromDataPoints("data-responses")
|
||||
ResponseEntity<CredentialDetailsData<ValueCredential>> expectedResponse) {
|
||||
verifyGetByNameWithHistoryUsingCredentialName(expectedResponse);
|
||||
verifyGetByNameWithHistory(expectedResponse);
|
||||
}
|
||||
}
|
||||
@@ -50,29 +50,7 @@ public class CredHubTemplateSummaryResponseUnitTests extends CredHubTemplateUnit
|
||||
new ResponseEntity<CredentialSummaryData>(new CredentialSummaryData(), UNAUTHORIZED);
|
||||
|
||||
@Theory
|
||||
public void findByNameWithString(@FromDataPoints("responses")
|
||||
ResponseEntity<CredentialSummaryData> expectedResponse) {
|
||||
when(restTemplate.getForEntity(NAME_LIKE_URL_QUERY, CredentialSummaryData.class, NAME.getName()))
|
||||
.thenReturn(expectedResponse);
|
||||
|
||||
if (!expectedResponse.getStatusCode().equals(OK)) {
|
||||
try {
|
||||
credHubTemplate.findByName(NAME.getName());
|
||||
fail("Exception should have been thrown");
|
||||
}
|
||||
catch (CredHubException e) {
|
||||
assertThat(e.getMessage(), containsString(expectedResponse.getStatusCode().toString()));
|
||||
}
|
||||
}
|
||||
else {
|
||||
List<CredentialSummary> response = credHubTemplate.findByName(NAME.getName());
|
||||
|
||||
assertResponseContainsExpectedCredentials(expectedResponse, response);
|
||||
}
|
||||
}
|
||||
|
||||
@Theory
|
||||
public void findByNameWithCredentialName(@FromDataPoints("responses")
|
||||
public void findByName(@FromDataPoints("responses")
|
||||
ResponseEntity<CredentialSummaryData> expectedResponse) {
|
||||
when(restTemplate.getForEntity(NAME_LIKE_URL_QUERY, CredentialSummaryData.class, NAME.getName()))
|
||||
.thenReturn(expectedResponse);
|
||||
|
||||
@@ -17,36 +17,108 @@
|
||||
package org.springframework.credhub.core;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.util.List;
|
||||
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.junit.Test;
|
||||
import org.junit.runner.RunWith;
|
||||
import org.mockito.junit.MockitoJUnitRunner;
|
||||
|
||||
import org.springframework.credhub.support.JsonUtils;
|
||||
import org.springframework.credhub.support.permissions.Actor;
|
||||
import org.springframework.credhub.support.permissions.ActorType;
|
||||
import org.springframework.credhub.support.permissions.CredentialPermission;
|
||||
import org.springframework.credhub.support.CredentialPermissions;
|
||||
import org.springframework.credhub.support.utils.JsonUtils;
|
||||
import org.springframework.credhub.support.permissions.Operation;
|
||||
import org.springframework.credhub.support.ServiceInstanceCredentialName;
|
||||
import org.springframework.credhub.support.ServicesData;
|
||||
import org.springframework.http.HttpEntity;
|
||||
import org.springframework.http.HttpMethod;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
|
||||
import static org.hamcrest.Matchers.equalTo;
|
||||
import static org.junit.Assert.assertNotNull;
|
||||
import static org.junit.Assert.assertThat;
|
||||
import static org.mockito.Mockito.verify;
|
||||
import static org.mockito.Mockito.when;
|
||||
import static org.springframework.credhub.core.CredHubTemplate.INTERPOLATE_URL_PATH;
|
||||
import static org.springframework.credhub.core.CredHubTemplate.NAME_URL_QUERY;
|
||||
import static org.springframework.credhub.core.CredHubTemplate.PERMISSIONS_ACTOR_URL_QUERY;
|
||||
import static org.springframework.credhub.core.CredHubTemplate.PERMISSIONS_URL_PATH;
|
||||
import static org.springframework.credhub.core.CredHubTemplate.PERMISSIONS_URL_QUERY;
|
||||
import static org.springframework.http.HttpMethod.POST;
|
||||
import static org.springframework.http.HttpStatus.OK;
|
||||
|
||||
@RunWith(MockitoJUnitRunner.class)
|
||||
public class CredHubTemplateUnitTests extends CredHubTemplateUnitTestsBase {
|
||||
@Test
|
||||
public void deleteByName() {
|
||||
credHubTemplate.deleteByName(NAME.getName());
|
||||
credHubTemplate.deleteByName(NAME);
|
||||
|
||||
verify(restTemplate).delete(NAME_URL_QUERY, NAME.getName());
|
||||
}
|
||||
|
||||
@Test
|
||||
public void getPermissions() {
|
||||
CredentialPermissions expectedResponse = new CredentialPermissions(
|
||||
NAME,
|
||||
CredentialPermission.builder()
|
||||
.app("app-id")
|
||||
.operation(Operation.READ)
|
||||
.operation(Operation.WRITE)
|
||||
.build(),
|
||||
CredentialPermission.builder()
|
||||
.user("zone1", "user-id")
|
||||
.operations(Operation.READ_ACL)
|
||||
.operations(Operation.WRITE_ACL)
|
||||
.operation(Operation.DELETE)
|
||||
.build()
|
||||
);
|
||||
|
||||
when(restTemplate.getForEntity(PERMISSIONS_URL_QUERY, CredentialPermissions.class, NAME.getName()))
|
||||
.thenReturn(new ResponseEntity<CredentialPermissions>(expectedResponse, OK));
|
||||
|
||||
List<CredentialPermission> response = credHubTemplate.getPermissions(NAME);
|
||||
|
||||
assertNotNull(response);
|
||||
assertThat(response.size(), equalTo(expectedResponse.getPermissions().size()));
|
||||
assertThat(response, equalTo(expectedResponse.getPermissions()));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void addPermissions() {
|
||||
CredentialPermission permission1 = CredentialPermission.builder()
|
||||
.app("app-id")
|
||||
.operation(Operation.READ)
|
||||
.operation(Operation.WRITE)
|
||||
.build();
|
||||
|
||||
CredentialPermission permission2 = CredentialPermission.builder()
|
||||
.user("zone1", "user-id")
|
||||
.operations(Operation.READ_ACL)
|
||||
.operations(Operation.WRITE_ACL)
|
||||
.operation(Operation.DELETE)
|
||||
.build();
|
||||
|
||||
CredentialPermissions expectedResponse = new CredentialPermissions(NAME, permission1, permission2);
|
||||
|
||||
when(restTemplate.exchange(PERMISSIONS_URL_PATH, POST,
|
||||
new HttpEntity<CredentialPermissions>(expectedResponse), CredentialPermissions.class))
|
||||
.thenReturn(new ResponseEntity<CredentialPermissions>(expectedResponse, OK));
|
||||
|
||||
List<CredentialPermission> response = credHubTemplate.addPermissions(NAME, permission1, permission2);
|
||||
|
||||
assertNotNull(response);
|
||||
assertThat(response.size(), equalTo(expectedResponse.getPermissions().size()));
|
||||
assertThat(response, equalTo(expectedResponse.getPermissions()));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void deletePermission() {
|
||||
credHubTemplate.deletePermission(NAME, Actor.app("appid1"));
|
||||
|
||||
verify(restTemplate).delete(PERMISSIONS_ACTOR_URL_QUERY, NAME.getName(), ActorType.APP + ":appid1");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void interpolateServiceData() throws IOException {
|
||||
ServiceInstanceCredentialName credentialName = ServiceInstanceCredentialName.builder()
|
||||
@@ -60,7 +132,7 @@ public class CredHubTemplateUnitTests extends CredHubTemplateUnitTestsBase {
|
||||
|
||||
ServicesData expectedResponse = new ServicesData();
|
||||
|
||||
when(restTemplate.exchange(INTERPOLATE_URL_PATH, HttpMethod.POST,
|
||||
when(restTemplate.exchange(INTERPOLATE_URL_PATH, POST,
|
||||
new HttpEntity<ServicesData>(vcapServices), ServicesData.class))
|
||||
.thenReturn(new ResponseEntity<ServicesData>(expectedResponse, OK));
|
||||
|
||||
|
||||
@@ -22,12 +22,17 @@ import org.junit.Before;
|
||||
import org.junit.Test;
|
||||
|
||||
import org.springframework.credhub.support.CredentialRequest.CredentialRequestBuilder;
|
||||
import org.springframework.credhub.support.permissions.Actor;
|
||||
import org.springframework.credhub.support.permissions.CredentialPermission;
|
||||
import org.springframework.credhub.support.utils.JsonUtils;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.allOf;
|
||||
import static org.hamcrest.CoreMatchers.equalTo;
|
||||
import static org.junit.Assert.assertThat;
|
||||
import static org.springframework.credhub.support.AdditionalPermission.Operation.READ;
|
||||
import static org.springframework.credhub.support.AdditionalPermission.Operation.WRITE;
|
||||
import static org.springframework.credhub.support.permissions.Operation.READ;
|
||||
import static org.springframework.credhub.support.permissions.Operation.READ_ACL;
|
||||
import static org.springframework.credhub.support.permissions.Operation.WRITE;
|
||||
import static org.springframework.credhub.support.permissions.Operation.WRITE_ACL;
|
||||
import static org.valid4j.matchers.jsonpath.JsonPathMatchers.hasJsonPath;
|
||||
import static org.valid4j.matchers.jsonpath.JsonPathMatchers.hasNoJsonPath;
|
||||
import static org.valid4j.matchers.jsonpath.JsonPathMatchers.isJson;
|
||||
@@ -44,7 +49,7 @@ public abstract class CredentialRequestUnitTestsBase {
|
||||
@Test
|
||||
public void serializationWithOnePermission() throws Exception {
|
||||
requestBuilder
|
||||
.additionalPermission(AdditionalPermission.builder()
|
||||
.permission(CredentialPermission.builder()
|
||||
.app("app-id")
|
||||
.operation(READ)
|
||||
.build());
|
||||
@@ -53,7 +58,7 @@ public abstract class CredentialRequestUnitTestsBase {
|
||||
|
||||
assertThat(jsonValue,
|
||||
allOf(hasJsonPath("$.additional_permissions[0].actor",
|
||||
equalTo("mtls-app:app-id")),
|
||||
equalTo(Actor.app("app-id").getIdentity())),
|
||||
hasJsonPath("$.additional_permissions[0].operations[0]",
|
||||
equalTo("read"))));
|
||||
}
|
||||
@@ -61,29 +66,28 @@ public abstract class CredentialRequestUnitTestsBase {
|
||||
@Test
|
||||
public void serializationWithTwoPermissions() throws Exception {
|
||||
requestBuilder
|
||||
.additionalPermission(AdditionalPermission.builder()
|
||||
.app("app1-id")
|
||||
.permission(CredentialPermission.builder()
|
||||
.app("app-id")
|
||||
.operation(READ).operation(WRITE)
|
||||
.build())
|
||||
.additionalPermission(AdditionalPermission.builder()
|
||||
.app("app2-id")
|
||||
.operation(WRITE).operation(READ)
|
||||
.permission(CredentialPermission.builder()
|
||||
.user("zone1", "user-id")
|
||||
.operations(READ_ACL, WRITE_ACL)
|
||||
.build());
|
||||
|
||||
String jsonValue = serializeToJson(requestBuilder);
|
||||
|
||||
assertThat(jsonValue, allOf(
|
||||
hasJsonPath("$.additional_permissions[0].actor",
|
||||
equalTo("mtls-app:app1-id")),
|
||||
equalTo(Actor.app("app-id").getIdentity())),
|
||||
hasJsonPath("$.additional_permissions[0].operations[0]", equalTo("read")),
|
||||
hasJsonPath("$.additional_permissions[0].operations[1]",
|
||||
equalTo("write")),
|
||||
hasJsonPath("$.additional_permissions[0].operations[1]", equalTo("write")),
|
||||
hasJsonPath("$.additional_permissions[1].actor",
|
||||
equalTo("mtls-app:app2-id")),
|
||||
hasJsonPath("$.additional_permissions[1].operations[0]",
|
||||
equalTo("write")),
|
||||
hasJsonPath("$.additional_permissions[1].operations[1]",
|
||||
equalTo("read"))));
|
||||
equalTo(Actor.user("zone1", "user-id").getIdentity())),
|
||||
hasJsonPath("$.additional_permissions[1].operations[0]", equalTo("read_acl")),
|
||||
hasJsonPath("$.additional_permissions[1].operations[1]", equalTo("write_acl"))
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
protected <T extends CredentialRequestBuilder> String serializeToJson(T requestBuilder)
|
||||
|
||||
@@ -21,6 +21,7 @@ import java.util.Date;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.fasterxml.jackson.databind.util.ISO8601DateFormat;
|
||||
import org.junit.Before;
|
||||
import org.springframework.credhub.support.utils.JsonUtils;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.equalTo;
|
||||
import static org.junit.Assert.assertThat;
|
||||
|
||||
@@ -21,6 +21,7 @@ import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.junit.Before;
|
||||
|
||||
import org.springframework.credhub.support.ParametersRequest.ParametersRequestBuilder;
|
||||
import org.springframework.credhub.support.utils.JsonUtils;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.allOf;
|
||||
import static org.hamcrest.CoreMatchers.equalTo;
|
||||
|
||||
@@ -0,0 +1,126 @@
|
||||
/*
|
||||
*
|
||||
* Copyright 2013-2017 the original author or authors.
|
||||
*
|
||||
* 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 org.springframework.credhub.support.permissions;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||
import org.junit.Test;
|
||||
|
||||
import org.springframework.credhub.support.CredentialPermissions;
|
||||
import org.springframework.credhub.support.JsonParsingUnitTestsBase;
|
||||
import org.springframework.credhub.support.SimpleCredentialName;
|
||||
import org.springframework.credhub.support.utils.JsonUtils;
|
||||
|
||||
import static org.hamcrest.CoreMatchers.allOf;
|
||||
import static org.hamcrest.Matchers.contains;
|
||||
import static org.hamcrest.core.IsEqual.equalTo;
|
||||
import static org.junit.Assert.assertThat;
|
||||
import static org.springframework.credhub.support.permissions.ActorType.APP;
|
||||
import static org.springframework.credhub.support.permissions.ActorType.USER;
|
||||
import static org.springframework.credhub.support.permissions.Operation.DELETE;
|
||||
import static org.springframework.credhub.support.permissions.Operation.READ;
|
||||
import static org.springframework.credhub.support.permissions.Operation.READ_ACL;
|
||||
import static org.springframework.credhub.support.permissions.Operation.WRITE;
|
||||
import static org.springframework.credhub.support.permissions.Operation.WRITE_ACL;
|
||||
import static org.valid4j.matchers.jsonpath.JsonPathMatchers.hasJsonPath;
|
||||
import static org.valid4j.matchers.jsonpath.JsonPathMatchers.isJson;
|
||||
|
||||
public class CredentialPermissionsUnitTests extends JsonParsingUnitTestsBase {
|
||||
@Test
|
||||
public void deserializePermissions() throws Exception {
|
||||
String json = "{\"credential_name\": \"/c/example\"," +
|
||||
"\"permissions\": [" +
|
||||
" {" +
|
||||
" \"actor\": \"mtls-app:appid1\"," +
|
||||
" \"operations\": [" +
|
||||
" \"read\"," +
|
||||
" \"write\"," +
|
||||
" \"delete\"," +
|
||||
" \"read_acl\"," +
|
||||
" \"write_acl\"" +
|
||||
" ]" +
|
||||
" }," +
|
||||
" {" +
|
||||
" \"actor\": \"uaa-user:zone1/userid\"," +
|
||||
" \"operations\": [" +
|
||||
" \"read\"" +
|
||||
" ]" +
|
||||
" }" +
|
||||
" ]}";
|
||||
|
||||
CredentialPermissions permissions = parsePermissions(json);
|
||||
|
||||
assertThat(permissions.getCredentialName(), equalTo("/c/example"));
|
||||
assertThat(permissions.getPermissions().size(), equalTo(2));
|
||||
|
||||
CredentialPermission permission = permissions.getPermissions().get(0);
|
||||
assertThat(permission.getActor().getAuthType(), equalTo(APP));
|
||||
assertThat(permission.getActor().getPrimaryIdentifier(), equalTo("appid1"));
|
||||
|
||||
List<Operation> operations = permission.getOperations();
|
||||
assertThat(operations.size(), equalTo(5));
|
||||
assertThat(operations, contains(READ, WRITE, DELETE, READ_ACL, WRITE_ACL));
|
||||
|
||||
permission = permissions.getPermissions().get(1);
|
||||
assertThat(permission.getActor().getAuthType(), equalTo(USER));
|
||||
assertThat(permission.getActor().getPrimaryIdentifier(), equalTo("zone1/userid"));
|
||||
|
||||
operations = permission.getOperations();
|
||||
assertThat(operations.size(), equalTo(1));
|
||||
assertThat(operations, contains(READ));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void deserializeWithNoPermissions() throws Exception {
|
||||
String json = "{\"permissions\": []}";
|
||||
|
||||
CredentialPermissions permissions = parsePermissions(json);
|
||||
|
||||
assertThat(permissions.getPermissions().size(), equalTo(0));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void serialize() throws Exception {
|
||||
CredentialPermissions permissions = new CredentialPermissions(new SimpleCredentialName("example", "credentialName"),
|
||||
CredentialPermission.builder()
|
||||
.app("appid1")
|
||||
.operations(READ, WRITE)
|
||||
.build());
|
||||
|
||||
String jsonValue = serializeToJson(permissions);
|
||||
|
||||
assertThat(jsonValue,
|
||||
allOf(hasJsonPath("$.credential_name", equalTo("/example/credentialName")),
|
||||
hasJsonPath("$.permissions[0].actor", equalTo(Actor.app("appid1").getIdentity())),
|
||||
hasJsonPath("$.permissions[0].operations[0]", equalTo("read")),
|
||||
hasJsonPath("$.permissions[0].operations[1]", equalTo("write"))));
|
||||
}
|
||||
|
||||
protected String serializeToJson(Object obj) throws JsonProcessingException {
|
||||
String jsonValue = JsonUtils.buildObjectMapper().writeValueAsString(obj);
|
||||
assertThat(jsonValue, isJson());
|
||||
return jsonValue;
|
||||
}
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
private CredentialPermissions parsePermissions(String json) throws java.io.IOException {
|
||||
return objectMapper.readValue(json, CredentialPermissions.class);
|
||||
}
|
||||
}
|
||||
@@ -51,6 +51,7 @@ dependencies {
|
||||
}
|
||||
|
||||
repositories {
|
||||
mavenLocal()
|
||||
mavenCentral()
|
||||
maven { url "https://repo.spring.io/libs-snapshot-local" }
|
||||
maven { url "https://repo.spring.io/libs-milestone-local" }
|
||||
|
||||
@@ -24,9 +24,9 @@ import java.util.Map;
|
||||
import java.util.UUID;
|
||||
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.springframework.beans.factory.annotation.Value;
|
||||
import org.springframework.credhub.core.CredHubTemplate;
|
||||
import org.springframework.credhub.support.AdditionalPermission;
|
||||
import org.springframework.credhub.support.permissions.Actor;
|
||||
import org.springframework.credhub.support.permissions.CredentialPermission;
|
||||
import org.springframework.credhub.support.CredentialDetails;
|
||||
import org.springframework.credhub.support.CredentialName;
|
||||
import org.springframework.credhub.support.CredentialSummary;
|
||||
@@ -38,12 +38,16 @@ import org.springframework.web.bind.annotation.PostMapping;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
import static org.springframework.credhub.support.AdditionalPermission.Operation.READ;
|
||||
import static org.springframework.credhub.support.permissions.Operation.DELETE;
|
||||
import static org.springframework.credhub.support.permissions.Operation.READ;
|
||||
import static org.springframework.credhub.support.permissions.Operation.READ_ACL;
|
||||
import static org.springframework.credhub.support.permissions.Operation.WRITE;
|
||||
import static org.springframework.credhub.support.permissions.Operation.WRITE_ACL;
|
||||
|
||||
@RestController
|
||||
public class CredHubDemoController {
|
||||
@Value("${vcap.application.application_id:}")
|
||||
private String appId;
|
||||
private static final String APP_GUID_1 = UUID.randomUUID().toString();
|
||||
private static final String APP_GUID_2 = UUID.randomUUID().toString();
|
||||
|
||||
private CredHubTemplate credHubTemplate;
|
||||
|
||||
@@ -67,6 +71,14 @@ public class CredHubDemoController {
|
||||
|
||||
findCredentialsByPath(credentialName.getName(), results);
|
||||
|
||||
getCredentialPermissions(credentialName, results);
|
||||
|
||||
addCredentialPermissions(credentialName, results);
|
||||
|
||||
deleteCredentialPermission(credentialName, results);
|
||||
|
||||
getCredentialPermissions(credentialName, results);
|
||||
|
||||
interpolateServiceData(credentialName, results);
|
||||
|
||||
deleteCredentials(credentialName, results);
|
||||
@@ -83,9 +95,10 @@ public class CredHubDemoController {
|
||||
.overwrite(true)
|
||||
.name(new SimpleCredentialName("spring-credhub", "demo", "credentials_json"))
|
||||
.value(value)
|
||||
.additionalPermission(AdditionalPermission.builder()
|
||||
.app(UUID.randomUUID().toString())
|
||||
.permission(CredentialPermission.builder()
|
||||
.app(APP_GUID_1)
|
||||
.operation(READ)
|
||||
.operation(WRITE)
|
||||
.build())
|
||||
.build();
|
||||
|
||||
@@ -138,6 +151,37 @@ public class CredHubDemoController {
|
||||
}
|
||||
}
|
||||
|
||||
private void getCredentialPermissions(CredentialName name, Results results) {
|
||||
try {
|
||||
List<CredentialPermission> retrievedDetails = credHubTemplate.getPermissions(name);
|
||||
saveResults(results, "Successfully retrieved credential permissions: ", retrievedDetails);
|
||||
} catch (Exception e) {
|
||||
saveResults(results, "Error retrieving credential permissions: ", e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
private void addCredentialPermissions(CredentialName name, Results results) {
|
||||
try {
|
||||
CredentialPermission permission = CredentialPermission.builder()
|
||||
.app(APP_GUID_2)
|
||||
.operations(READ_ACL, WRITE_ACL, DELETE)
|
||||
.build();
|
||||
|
||||
List<CredentialPermission> permissions = credHubTemplate.addPermissions(name, permission);
|
||||
saveResults(results, "Successfully added permissions: ", permissions);
|
||||
} catch (Exception e) {
|
||||
saveResults(results, "Error adding permission: ", e.getMessage());
|
||||
} }
|
||||
|
||||
private void deleteCredentialPermission(CredentialName name, Results results) {
|
||||
try {
|
||||
credHubTemplate.deletePermission(name, Actor.app(APP_GUID_1));
|
||||
saveResults(results, "Successfully deleted permission");
|
||||
} catch (Exception e) {
|
||||
saveResults(results, "Error deleting permission: ", e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
private void interpolateServiceData(CredentialName name, Results results) {
|
||||
try {
|
||||
ServicesData request = buildServicesData(name.getName());
|
||||
|
||||
Reference in New Issue
Block a user