diff options
author | Benjamin, Max (mb388a) <mb388a@us.att.com> | 2018-11-16 12:23:48 -0500 |
---|---|---|
committer | Rob Daugherty <rd472p@att.com> | 2018-11-21 16:06:04 +0000 |
commit | 37547ac7b149381f92afe782f6682d8ffa7acc7a (patch) | |
tree | d0ca9319da57135fc5e3317c5015d95db73d3387 /adapters | |
parent | 4bae647a66bd08422ae2d9b8dec226434270eb5c (diff) |
Add Keystone V3 Support
update JEL with explicit getVariable call
set project object into scope object
add camunda properties as defaults in application.yaml
added exception handling to keystone v3 case
added in password method to identity object
initial commit of keystone v3 auth support
updated json property values with "_name"
added new columns to cloud identity
Change-Id: Ie08e9893c34d7199197efdb21fe4dd5413b25f44
Issue-ID: SO-1225
Signed-off-by: Benjamin, Max (mb388a) <mb388a@us.att.com>
Diffstat (limited to 'adapters')
14 files changed, 419 insertions, 79 deletions
diff --git a/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/AuthenticationMethodFactory.java b/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/AuthenticationMethodFactory.java index 1912cd874a..49c80b44b5 100644 --- a/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/AuthenticationMethodFactory.java +++ b/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/AuthenticationMethodFactory.java @@ -20,14 +20,22 @@ package org.onap.so.cloud.authentication; +import java.util.Collections; + +import org.onap.so.cloud.authentication.models.RackspaceAuthentication; import org.onap.so.db.catalog.beans.AuthenticationType; import org.onap.so.db.catalog.beans.CloudIdentity; -import org.onap.so.cloud.authentication.models.RackspaceAuthentication; import org.onap.so.utils.CryptoUtils; import org.springframework.stereotype.Component; import com.woorea.openstack.keystone.model.Authentication; import com.woorea.openstack.keystone.model.authentication.UsernamePassword; +import com.woorea.openstack.keystone.v3.model.Authentication.Identity; +import com.woorea.openstack.keystone.v3.model.Authentication.Identity.Password; +import com.woorea.openstack.keystone.v3.model.Authentication.Identity.Password.User; +import com.woorea.openstack.keystone.v3.model.Authentication.Identity.Password.User.Domain; +import com.woorea.openstack.keystone.v3.model.Authentication.Scope; +import com.woorea.openstack.keystone.v3.model.Authentication.Scope.Project; /** * This factory manages all the wrappers associated to authentication types. @@ -50,4 +58,30 @@ public final class AuthenticationMethodFactory { return new UsernamePassword (cloudIdentity.getMsoId (), CryptoUtils.decryptCloudConfigPassword(cloudIdentity.getMsoPass ())); } } + + + public final com.woorea.openstack.keystone.v3.model.Authentication getAuthenticationForV3(CloudIdentity cloudIdentity, String tenantId) { + Identity identity = new Identity(); + Password password = new Password(); + User user = new User(); + Domain userDomain = new Domain(); + Scope scope = new Scope(); + Project project = new Project(); + Project.Domain projectDomain = new Project.Domain(); + userDomain.setName(cloudIdentity.getUserDomainName()); + projectDomain.setName(cloudIdentity.getProjectDomainName()); + user.setName(cloudIdentity.getMsoId()); + user.setPassword(CryptoUtils.decryptCloudConfigPassword(cloudIdentity.getMsoPass())); + user.setDomain(userDomain); + password.setUser(user); + project.setDomain(projectDomain); + project.setId(tenantId); + scope.setProject(project); + identity.setPassword(password); + identity.setMethods(Collections.singletonList("password")); + com.woorea.openstack.keystone.v3.model.Authentication v3Auth = new com.woorea.openstack.keystone.v3.model.Authentication(); + v3Auth.setIdentity(identity); + v3Auth.setScope(scope); + return v3Auth; + } } diff --git a/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/KeystoneAuthHolder.java b/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/KeystoneAuthHolder.java new file mode 100644 index 0000000000..1a221a80df --- /dev/null +++ b/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/KeystoneAuthHolder.java @@ -0,0 +1,32 @@ +package org.onap.so.cloud.authentication; + +import java.io.Serializable; +import java.util.Calendar; + +public class KeystoneAuthHolder implements Serializable { + + private static final long serialVersionUID = -9073252905181739224L; + + private String id; + private Calendar expiration; + private String serviceUrl; + + public String getId() { + return id; + } + public void setId(String id) { + this.id = id; + } + public Calendar getexpiration() { + return expiration; + } + public void setexpiration(Calendar expiration) { + this.expiration = expiration; + } + public String getServiceUrl() { + return serviceUrl; + } + public void setHeatUrl(String serviceUrl) { + this.serviceUrl = serviceUrl; + } +} diff --git a/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/KeystoneV3Authentication.java b/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/KeystoneV3Authentication.java new file mode 100644 index 0000000000..05364d0c92 --- /dev/null +++ b/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/KeystoneV3Authentication.java @@ -0,0 +1,113 @@ +package org.onap.so.cloud.authentication; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; +import java.util.concurrent.TimeUnit; +import java.util.function.Predicate; + +import org.onap.so.config.beans.PoConfig; +import org.onap.so.db.catalog.beans.CloudIdentity; +import org.onap.so.db.catalog.beans.CloudSite; +import org.onap.so.openstack.exceptions.MsoException; +import org.onap.so.openstack.utils.MsoTenantUtils; +import org.onap.so.openstack.utils.MsoTenantUtilsFactory; +import org.springframework.beans.factory.annotation.Autowired; +import org.springframework.stereotype.Component; + +import com.woorea.openstack.base.client.OpenStackConnectException; +import com.woorea.openstack.base.client.OpenStackRequest; +import com.woorea.openstack.base.client.OpenStackResponse; +import com.woorea.openstack.base.client.OpenStackResponseException; +import com.woorea.openstack.keystone.v3.Keystone; +import com.woorea.openstack.keystone.v3.model.Authentication; +import com.woorea.openstack.keystone.v3.model.Token; +import com.woorea.openstack.keystone.v3.model.Token.Service; + +import net.jodah.failsafe.Failsafe; +import net.jodah.failsafe.RetryPolicy; + + +@Component +public class KeystoneV3Authentication { + + @Autowired + private AuthenticationMethodFactory authenticationMethodFactory; + + @Autowired + private MsoTenantUtilsFactory tenantUtilsFactory; + + @Autowired + private PoConfig poConfig; + + public KeystoneAuthHolder getToken(CloudSite cloudSite, String tenantId, String type) throws MsoException { + + String cloudId = cloudSite.getId(); + String region = cloudSite.getRegionId(); + + CloudIdentity cloudIdentity = cloudSite.getIdentityService(); + MsoTenantUtils tenantUtils = tenantUtilsFactory.getTenantUtilsByServerType(cloudIdentity.getIdentityServerType()); + String keystoneUrl = tenantUtils.getKeystoneUrl(cloudId, cloudIdentity); + Keystone keystoneTenantClient = new Keystone (keystoneUrl); + Authentication v3Credentials = authenticationMethodFactory.getAuthenticationForV3(cloudIdentity, tenantId); + + + OpenStackRequest<Token> v3Request = keystoneTenantClient.tokens () + .authenticate(v3Credentials); + + KeystoneAuthHolder holder = makeRequest(v3Request, type, region); + + return holder; + } + + protected KeystoneAuthHolder makeRequest(OpenStackRequest<Token> v3Request, String type, String region) { + + OpenStackResponse response = Failsafe.with(createRetryPolicy()).get(() -> { + return v3Request.request(); + }); + String id = response.header("X-Subject-Token"); + Token token = response.getEntity(Token.class); + KeystoneAuthHolder result = new KeystoneAuthHolder(); + result.setId(id); + result.setexpiration(token.getExpiresAt()); + result.setHeatUrl(findEndpointURL(token.getCatalog(), type, region, "public")); + return result; + } + + protected RetryPolicy createRetryPolicy() { + RetryPolicy policy = new RetryPolicy(); + List<Predicate<Throwable>> result = new ArrayList<>(); + result.add(e -> { + return e.getCause() instanceof OpenStackResponseException + && Arrays.asList(poConfig.getRetryCodes().split(",")) + .contains(Integer.toString(((OpenStackResponseException)e).getStatus())); + }); + result.add(e -> { + return e.getCause() instanceof OpenStackConnectException; + }); + + Predicate<Throwable> pred = result.stream().reduce(Predicate::or).orElse(x -> false); + + policy.retryOn(error -> pred.test(error)); + + policy.withDelay(poConfig.getRetryDelay(), TimeUnit.SECONDS) + .withMaxRetries(poConfig.getRetryCount()); + + return policy; + } + + protected String findEndpointURL(List<Service> serviceCatalog, String type, String region, String facing) { + for(Service service : serviceCatalog) { + if(type.equals(service.getType())) { + for(Service.Endpoint endpoint : service.getEndpoints()) { + if(region == null || region.equals(endpoint.getRegion())) { + if(facing.equals(endpoint.getInterface())) { + return endpoint.getUrl(); + } + } + } + } + } + throw new ServiceEndpointNotFoundException("endpoint url not found"); + } +} diff --git a/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/ServiceEndpointNotFoundException.java b/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/ServiceEndpointNotFoundException.java new file mode 100644 index 0000000000..3bc57a886a --- /dev/null +++ b/adapters/mso-adapter-utils/src/main/java/org/onap/so/cloud/authentication/ServiceEndpointNotFoundException.java @@ -0,0 +1,10 @@ +package org.onap.so.cloud.authentication; + +public class ServiceEndpointNotFoundException extends RuntimeException { + + private static final long serialVersionUID = -5347215451284361397L; + + public ServiceEndpointNotFoundException(String message) { + super(message); + } +} diff --git a/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoHeatUtils.java b/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoHeatUtils.java index e36d0ff30e..d87330bfd4 100644 --- a/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoHeatUtils.java +++ b/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoHeatUtils.java @@ -24,6 +24,7 @@ package org.onap.so.openstack.utils; import java.io.IOException; import java.util.ArrayList; import java.util.Arrays; +import java.util.Calendar; import java.util.HashMap; import java.util.List; import java.util.Map; @@ -41,11 +42,15 @@ import org.onap.so.adapters.vdu.VduPlugin; import org.onap.so.adapters.vdu.VduStateType; import org.onap.so.adapters.vdu.VduStatus; import org.onap.so.cloud.CloudConfig; +import org.onap.so.cloud.authentication.AuthenticationMethodFactory; +import org.onap.so.cloud.authentication.KeystoneAuthHolder; +import org.onap.so.cloud.authentication.KeystoneV3Authentication; +import org.onap.so.cloud.authentication.ServiceEndpointNotFoundException; import org.onap.so.db.catalog.beans.CloudIdentity; import org.onap.so.db.catalog.beans.CloudSite; -import org.onap.so.cloud.authentication.AuthenticationMethodFactory; import org.onap.so.db.catalog.beans.HeatTemplate; import org.onap.so.db.catalog.beans.HeatTemplateParam; +import org.onap.so.db.catalog.beans.ServerType; import org.onap.so.logger.MessageEnum; import org.onap.so.logger.MsoAlarmLogger; import org.onap.so.logger.MsoLogger; @@ -115,7 +120,10 @@ public class MsoHeatUtils extends MsoCommonUtils implements VduPlugin{ @Autowired private MsoTenantUtilsFactory tenantUtilsFactory; - + + @Autowired + private KeystoneV3Authentication keystoneV3Authentication; + private static final MsoLogger LOGGER = MsoLogger.getMsoLogger (MsoLogger.Catalog.RA, MsoHeatUtils.class); // Properties names and variables (with default values) @@ -875,7 +883,9 @@ public class MsoHeatUtils extends MsoCommonUtils implements VduPlugin{ */ public Heat getHeatClient (CloudSite cloudSite, String tenantId) throws MsoException { String cloudId = cloudSite.getId(); - + // For DCP/LCP, the region should be the cloudId. + String region = cloudSite.getRegionId (); + // Check first in the cache of previously authorized clients String cacheKey = cloudId + ":" + tenantId; if (heatClientCache.containsKey (cacheKey)) { @@ -895,16 +905,58 @@ public class MsoHeatUtils extends MsoCommonUtils implements VduPlugin{ MsoTenantUtils tenantUtils = tenantUtilsFactory.getTenantUtilsByServerType(cloudIdentity.getIdentityServerType()); String keystoneUrl = tenantUtils.getKeystoneUrl(cloudId, cloudIdentity); LOGGER.debug("keystoneUrl=" + keystoneUrl); - Keystone keystoneTenantClient = new Keystone (keystoneUrl); - Access access = null; - try { - Authentication credentials = authenticationMethodFactory.getAuthenticationFor(cloudIdentity); - - OpenStackRequest <Access> request = keystoneTenantClient.tokens () - .authenticate (credentials).withTenantId (tenantId); - - access = executeAndRecordOpenstackRequest (request); - } catch (OpenStackResponseException e) { + String heatUrl = null; + String tokenId = null; + Calendar expiration = null; + try { + if (ServerType.KEYSTONE.equals(cloudIdentity.getIdentityServerType())) { + Keystone keystoneTenantClient = new Keystone (keystoneUrl); + Access access = null; + + Authentication credentials = authenticationMethodFactory.getAuthenticationFor(cloudIdentity); + + OpenStackRequest <Access> request = keystoneTenantClient.tokens () + .authenticate (credentials).withTenantId (tenantId); + + access = executeAndRecordOpenstackRequest (request); + + try { + // Isolate trying to printout the region IDs + try { + LOGGER.debug("access=" + access.toString()); + for (Access.Service service : access.getServiceCatalog()) { + List<Access.Service.Endpoint> endpoints = service.getEndpoints(); + for (Access.Service.Endpoint endpoint : endpoints) { + LOGGER.debug("AIC returned region=" + endpoint.getRegion()); + } + } + } catch (Exception e) { + LOGGER.debug("Encountered an error trying to printout Access object returned from AIC. " + e.getMessage()); + } + heatUrl = KeystoneUtils.findEndpointURL (access.getServiceCatalog (), "orchestration", region, "public"); + LOGGER.debug("heatUrl=" + heatUrl + ", region=" + region); + } catch (RuntimeException e) { + // This comes back for not found (probably an incorrect region ID) + String error = "AIC did not match an orchestration service for: region=" + region + ",cloud=" + cloudIdentity.getIdentityUrl(); + alarmLogger.sendAlarm ("MsoConfigurationError", MsoAlarmLogger.CRITICAL, error); + throw new MsoAdapterException (error, e); + } + tokenId = access.getToken ().getId (); + expiration = access.getToken ().getExpires (); + } else if (ServerType.KEYSTONE_V3.equals(cloudIdentity.getIdentityServerType())) { + try { + KeystoneAuthHolder holder = keystoneV3Authentication.getToken(cloudSite, tenantId, "orchestration"); + tokenId = holder.getId(); + expiration = holder.getexpiration(); + heatUrl = holder.getServiceUrl(); + } catch (ServiceEndpointNotFoundException e) { + // This comes back for not found (probably an incorrect region ID) + String error = "cloud did not match an orchestration service for: region=" + region + ",cloud=" + cloudIdentity.getIdentityUrl(); + alarmLogger.sendAlarm ("MsoConfigurationError", MsoAlarmLogger.CRITICAL, error); + throw new MsoAdapterException (error, e); + } + } + } catch (OpenStackResponseException e) { if (e.getStatus () == 401) { // Authentication error. String error = "Authentication Failure: tenant=" + tenantId + ",cloud=" + cloudIdentity.getId (); @@ -922,39 +974,13 @@ public class MsoHeatUtils extends MsoCommonUtils implements VduPlugin{ // Catch-all throw runtimeExceptionToMsoException (e, TOKEN_AUTH); } - - // For DCP/LCP, the region should be the cloudId. - String region = cloudSite.getRegionId (); - String heatUrl = null; - try { - // Isolate trying to printout the region IDs - try { - LOGGER.debug("access=" + access.toString()); - for (Access.Service service : access.getServiceCatalog()) { - List<Access.Service.Endpoint> endpoints = service.getEndpoints(); - for (Access.Service.Endpoint endpoint : endpoints) { - LOGGER.debug("AIC returned region=" + endpoint.getRegion()); - } - } - } catch (Exception e) { - LOGGER.debug("Encountered an error trying to printout Access object returned from AIC. " + e.getMessage()); - } - heatUrl = KeystoneUtils.findEndpointURL (access.getServiceCatalog (), "orchestration", region, "public"); - LOGGER.debug("heatUrl=" + heatUrl + ", region=" + region); - } catch (RuntimeException e) { - // This comes back for not found (probably an incorrect region ID) - String error = "AIC did not match an orchestration service for: region=" + region + ",cloud=" + cloudIdentity.getIdentityUrl(); - alarmLogger.sendAlarm ("MsoConfigurationError", MsoAlarmLogger.CRITICAL, error); - throw new MsoAdapterException (error, e); - } - Heat heatClient = new Heat (heatUrl); - heatClient.token (access.getToken ().getId ()); + heatClient.token (tokenId); heatClientCache.put (cacheKey, new HeatCacheEntry (heatUrl, - access.getToken ().getId (), - access.getToken ().getExpires ())); + tokenId, + expiration)); LOGGER.debug ("Caching HEAT Client for " + cacheKey); return heatClient; diff --git a/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoKeystoneV3Utils.java b/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoKeystoneV3Utils.java new file mode 100644 index 0000000000..da1957f36e --- /dev/null +++ b/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoKeystoneV3Utils.java @@ -0,0 +1,41 @@ +package org.onap.so.openstack.utils; + +import java.util.Map; + +import org.onap.so.db.catalog.beans.CloudIdentity; +import org.onap.so.openstack.beans.MsoTenant; +import org.onap.so.openstack.exceptions.MsoCloudSiteNotFound; +import org.onap.so.openstack.exceptions.MsoException; +import org.springframework.stereotype.Component; + +@Component +public class MsoKeystoneV3Utils extends MsoTenantUtils { + + @Override + public String createTenant(String tenantName, String cloudSiteId, Map<String, String> metadata, boolean backout) + throws MsoException { + throw new UnsupportedOperationException(); + } + + @Override + public MsoTenant queryTenant(String tenantId, String cloudSiteId) throws MsoException, MsoCloudSiteNotFound { + throw new UnsupportedOperationException(); + } + + @Override + public MsoTenant queryTenantByName(String tenantName, String cloudSiteId) + throws MsoException, MsoCloudSiteNotFound { + throw new UnsupportedOperationException(); + } + + @Override + public boolean deleteTenant(String tenantId, String cloudSiteId) throws MsoException { + throw new UnsupportedOperationException(); + } + + @Override + public String getKeystoneUrl(String regionId, CloudIdentity cloudIdentity) throws MsoException { + return cloudIdentity.getIdentityUrl(); + } + +} diff --git a/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoNeutronUtils.java b/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoNeutronUtils.java index a9f0a39235..b7676e0041 100644 --- a/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoNeutronUtils.java +++ b/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoNeutronUtils.java @@ -22,14 +22,19 @@ package org.onap.so.openstack.utils; import java.util.ArrayList; +import java.util.Calendar; import java.util.HashMap; import java.util.List; import java.util.Map; import org.onap.so.cloud.CloudConfig; +import org.onap.so.cloud.authentication.AuthenticationMethodFactory; +import org.onap.so.cloud.authentication.KeystoneAuthHolder; +import org.onap.so.cloud.authentication.KeystoneV3Authentication; +import org.onap.so.cloud.authentication.ServiceEndpointNotFoundException; import org.onap.so.db.catalog.beans.CloudIdentity; import org.onap.so.db.catalog.beans.CloudSite; -import org.onap.so.cloud.authentication.AuthenticationMethodFactory; +import org.onap.so.db.catalog.beans.ServerType; import org.onap.so.logger.MessageEnum; import org.onap.so.logger.MsoAlarmLogger; import org.onap.so.logger.MsoLogger; @@ -78,6 +83,9 @@ public class MsoNeutronUtils extends MsoCommonUtils @Autowired private MsoTenantUtilsFactory tenantUtilsFactory; + + @Autowired + private KeystoneV3Authentication keystoneV3Authentication; private static MsoLogger LOGGER = MsoLogger.getMsoLogger (MsoLogger.Catalog.RA, MsoNeutronUtils.class); @@ -356,7 +364,8 @@ public class MsoNeutronUtils extends MsoCommonUtils private Quantum getNeutronClient(CloudSite cloudSite, String tenantId) throws MsoException { String cloudId = cloudSite.getId(); - + String region = cloudSite.getRegionId(); + // Check first in the cache of previously authorized clients String cacheKey = cloudId + ":" + tenantId; if (neutronClientCache.containsKey(cacheKey)) { @@ -378,12 +387,48 @@ public class MsoNeutronUtils extends MsoCommonUtils CloudIdentity cloudIdentity = cloudSite.getIdentityService(); MsoTenantUtils tenantUtils = tenantUtilsFactory.getTenantUtilsByServerType(cloudIdentity.getIdentityServerType()); final String keystoneUrl = tenantUtils.getKeystoneUrl(cloudId, cloudIdentity); - Keystone keystoneTenantClient = new Keystone(keystoneUrl); - Access access = null; + String neutronUrl = null; + String tokenId = null; + Calendar expiration = null; try { - Authentication credentials = authenticationMethodFactory.getAuthenticationFor(cloudIdentity); - OpenStackRequest<Access> request = keystoneTenantClient.tokens().authenticate(credentials).withTenantId(tenantId); - access = executeAndRecordOpenstackRequest(request); + if (ServerType.KEYSTONE.equals(cloudIdentity.getIdentityServerType())) { + Keystone keystoneTenantClient = new Keystone(keystoneUrl); + Access access = null; + + Authentication credentials = authenticationMethodFactory.getAuthenticationFor(cloudIdentity); + OpenStackRequest<Access> request = keystoneTenantClient.tokens().authenticate(credentials).withTenantId(tenantId); + access = executeAndRecordOpenstackRequest(request); + + + try { + neutronUrl = KeystoneUtils.findEndpointURL(access.getServiceCatalog(), "network", region, "public"); + if (! neutronUrl.endsWith("/")) { + neutronUrl += "/v2.0/"; + } + } catch (RuntimeException e) { + // This comes back for not found (probably an incorrect region ID) + String error = "Network service not found: region=" + region + ",cloud=" + cloudIdentity.getId(); + alarmLogger.sendAlarm("MsoConfigurationError", MsoAlarmLogger.CRITICAL, error); + throw new MsoAdapterException (error, e); + } + tokenId = access.getToken().getId(); + expiration = access.getToken().getExpires(); + } else if (ServerType.KEYSTONE_V3.equals(cloudIdentity.getIdentityServerType())) { + try { + KeystoneAuthHolder holder = keystoneV3Authentication.getToken(cloudSite, tenantId, "network"); + tokenId = holder.getId(); + expiration = holder.getexpiration(); + neutronUrl = holder.getServiceUrl(); + if (! neutronUrl.endsWith("/")) { + neutronUrl += "/v2.0/"; + } + } catch (ServiceEndpointNotFoundException e) { + // This comes back for not found (probably an incorrect region ID) + String error = "Network service not found: region=" + region + ",cloud=" + cloudIdentity.getId(); + alarmLogger.sendAlarm("MsoConfigurationError", MsoAlarmLogger.CRITICAL, error); + throw new MsoAdapterException (error, e); + } + } } catch (OpenStackResponseException e) { if (e.getStatus() == 401) { @@ -408,25 +453,10 @@ public class MsoNeutronUtils extends MsoCommonUtils MsoException me = runtimeExceptionToMsoException(e, "TokenAuth"); throw me; } - - String region = cloudSite.getRegionId(); - String neutronUrl = null; - try { - neutronUrl = KeystoneUtils.findEndpointURL(access.getServiceCatalog(), "network", region, "public"); - if (! neutronUrl.endsWith("/")) { - neutronUrl += "/v2.0/"; - } - } catch (RuntimeException e) { - // This comes back for not found (probably an incorrect region ID) - String error = "Network service not found: region=" + region + ",cloud=" + cloudIdentity.getId(); - alarmLogger.sendAlarm("MsoConfigurationError", MsoAlarmLogger.CRITICAL, error); - throw new MsoAdapterException (error, e); - } - Quantum neutronClient = new Quantum(neutronUrl); - neutronClient.token(access.getToken().getId()); + neutronClient.token(tokenId); - neutronClientCache.put(cacheKey, new NeutronCacheEntry(neutronUrl, access.getToken().getId(), access.getToken().getExpires())); + neutronClientCache.put(cacheKey, new NeutronCacheEntry(neutronUrl, tokenId, expiration)); LOGGER.debug ("Caching Neutron Client for " + cacheKey); return neutronClient; diff --git a/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoTenantUtilsFactory.java b/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoTenantUtilsFactory.java index 79934ccd28..08c98f3167 100644 --- a/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoTenantUtilsFactory.java +++ b/adapters/mso-adapter-utils/src/main/java/org/onap/so/openstack/utils/MsoTenantUtilsFactory.java @@ -36,6 +36,8 @@ public class MsoTenantUtilsFactory { protected CloudConfig cloudConfig; @Autowired protected MsoKeystoneUtils keystoneUtils; + @Autowired + protected MsoKeystoneV3Utils keystoneV3Utils; // based on Cloud IdentityServerType returns ORM or KEYSTONE Utils public MsoTenantUtils getTenantUtils(String cloudSiteId) throws MsoCloudSiteNotFound { @@ -50,6 +52,8 @@ public class MsoTenantUtilsFactory { MsoTenantUtils tenantU = null; if (ServerType.KEYSTONE.equals(serverType)) { tenantU = keystoneUtils; + } else if (ServerType.KEYSTONE_V3.equals(serverType)) { + tenantU = keystoneV3Utils; } return tenantU; } diff --git a/adapters/mso-adapter-utils/src/test/java/org/onap/so/cloud/authentication/AuthenticationMethodTest.java b/adapters/mso-adapter-utils/src/test/java/org/onap/so/cloud/authentication/AuthenticationMethodTest.java index 95e4352e05..a5abe75af2 100644 --- a/adapters/mso-adapter-utils/src/test/java/org/onap/so/cloud/authentication/AuthenticationMethodTest.java +++ b/adapters/mso-adapter-utils/src/test/java/org/onap/so/cloud/authentication/AuthenticationMethodTest.java @@ -20,19 +20,23 @@ package org.onap.so.cloud.authentication; +import static com.shazam.shazamcrest.matcher.Matchers.sameBeanAs; +import static org.junit.Assert.assertThat; import static org.junit.Assert.assertTrue; +import java.io.IOException; +import java.nio.file.Files; +import java.nio.file.Paths; + import org.junit.Test; -import org.junit.runner.RunWith; -import org.onap.so.BaseTest; +import org.onap.so.cloud.authentication.models.RackspaceAuthentication; import org.onap.so.db.catalog.beans.AuthenticationType; import org.onap.so.db.catalog.beans.CloudIdentity; -import org.onap.so.cloud.authentication.models.RackspaceAuthentication; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.boot.test.context.SpringBootTest; -import org.springframework.test.context.ActiveProfiles; -import org.springframework.test.context.junit4.SpringRunner; +import org.onap.so.utils.CryptoUtils; +import com.fasterxml.jackson.core.JsonParseException; +import com.fasterxml.jackson.databind.JsonMappingException; +import com.fasterxml.jackson.databind.ObjectMapper; import com.woorea.openstack.keystone.model.Authentication; import com.woorea.openstack.keystone.model.authentication.UsernamePassword; @@ -42,10 +46,9 @@ import com.woorea.openstack.keystone.model.authentication.UsernamePassword; * only are tested. * */ -public class AuthenticationMethodTest extends BaseTest { +public class AuthenticationMethodTest { - @Autowired - private AuthenticationMethodFactory authenticationMethodFactory; + private AuthenticationMethodFactory authenticationMethodFactory = new AuthenticationMethodFactory(); /** * */ @@ -99,4 +102,20 @@ public class AuthenticationMethodTest extends BaseTest { assertTrue(UsernamePassword.class.equals(auth.getClass())); } + + @Test + public void getAuthenticationForV3Test() throws JsonParseException, JsonMappingException, IOException { + + CloudIdentity identity = new CloudIdentity(); + identity.setMsoId("my-username"); + identity.setMsoPass(CryptoUtils.encryptCloudConfigPassword("my-password")); + identity.setProjectDomainName("test-domain"); + identity.setUserDomainName("user-domain"); + ObjectMapper mapper = new ObjectMapper(); + com.woorea.openstack.keystone.v3.model.Authentication expected = + mapper.readValue(new String(Files.readAllBytes(Paths.get("src/test/resources/__files/KeystoneV3Payload.json"))), com.woorea.openstack.keystone.v3.model.Authentication.class); + com.woorea.openstack.keystone.v3.model.Authentication actual = authenticationMethodFactory.getAuthenticationForV3(identity, "project-x"); + + assertThat(actual, sameBeanAs(expected)); + } } diff --git a/adapters/mso-adapter-utils/src/test/resources/__files/KeystoneV3Payload.json b/adapters/mso-adapter-utils/src/test/resources/__files/KeystoneV3Payload.json new file mode 100644 index 0000000000..dc6588ed36 --- /dev/null +++ b/adapters/mso-adapter-utils/src/test/resources/__files/KeystoneV3Payload.json @@ -0,0 +1,24 @@ +{ + "identity": { + "methods": [ + "password" + ], + "password": { + "user": { + "domain": { + "name": "user-domain" + }, + "name": "my-username", + "password": "my-password" + } + } + }, + "scope": { + "project": { + "domain": { + "name": "test-domain" + }, + "id": "project-x" + } + } +} diff --git a/adapters/mso-catalog-db-adapter/src/main/resources/db/migration/V4.12.2__AddDomainColumnsCloudIdentity.sql b/adapters/mso-catalog-db-adapter/src/main/resources/db/migration/V4.12.2__AddDomainColumnsCloudIdentity.sql new file mode 100644 index 0000000000..e2c4dc8d2f --- /dev/null +++ b/adapters/mso-catalog-db-adapter/src/main/resources/db/migration/V4.12.2__AddDomainColumnsCloudIdentity.sql @@ -0,0 +1,3 @@ +ALTER TABLE identity_services +ADD PROJECT_DOMAIN_NAME VARCHAR(255) DEFAULT NULL, +ADD USER_DOMAIN_NAME VARCHAR(255) DEFAULT NULL; diff --git a/adapters/mso-catalog-db-adapter/src/test/resources/db/migration/afterMigrate.sql b/adapters/mso-catalog-db-adapter/src/test/resources/db/migration/afterMigrate.sql index b4916bd46c..4d5105dec6 100644 --- a/adapters/mso-catalog-db-adapter/src/test/resources/db/migration/afterMigrate.sql +++ b/adapters/mso-catalog-db-adapter/src/test/resources/db/migration/afterMigrate.sql @@ -4,6 +4,8 @@ CREATE TABLE IF NOT EXISTS `identity_services` ( `IDENTITY_URL` varchar(200) DEFAULT NULL, `MSO_ID` varchar(255) DEFAULT NULL, `MSO_PASS` varchar(255) DEFAULT NULL, + `PROJECT_DOMAIN_NAME` varchar(255) DEFAULT NULL, + `USER_DOMAIN_NAME` varchar(255) DEFAULT NULL, `ADMIN_TENANT` varchar(50) DEFAULT NULL, `MEMBER_ROLE` varchar(50) DEFAULT NULL, `TENANT_METADATA` tinyint(1) DEFAULT 0, @@ -193,7 +195,7 @@ insert into vnf_components(vnf_id, component_type, heat_template_id, heat_enviro INSERT INTO `cloudify_managers` (`ID`, `CLOUDIFY_URL`, `USERNAME`, `PASSWORD`, `VERSION`, `LAST_UPDATED_BY`, `CREATION_TIMESTAMP`, `UPDATE_TIMESTAMP`) VALUES ('mtn13', 'http://localhost:28090/v2.0', 'm93945', '93937EA01B94A10A49279D4572B48369', NULL, 'MSO_USER', '2018-07-17 14:05:08', '2018-07-17 14:05:08'); -INSERT INTO `identity_services` (`ID`, `IDENTITY_URL`, `MSO_ID`, `MSO_PASS`, `ADMIN_TENANT`, `MEMBER_ROLE`, `TENANT_METADATA`, `IDENTITY_SERVER_TYPE`, `IDENTITY_AUTHENTICATION_TYPE`, `LAST_UPDATED_BY`, `CREATION_TIMESTAMP`, `UPDATE_TIMESTAMP`) VALUES ('MTN13', 'http://localhost:28090/v2.0', 'm93945', '93937EA01B94A10A49279D4572B48369', 'admin', 'admin', 1, 'KEYSTONE', 'USERNAME_PASSWORD', 'MSO_USER', '2018-07-17 14:02:33', '2018-07-17 14:02:33'); +INSERT INTO `identity_services` (`ID`, `IDENTITY_URL`, `MSO_ID`, `MSO_PASS`, `PROJECT_DOMAIN_NAME`, `USER_DOMAIN_NAME`, `ADMIN_TENANT`, `MEMBER_ROLE`, `TENANT_METADATA`, `IDENTITY_SERVER_TYPE`, `IDENTITY_AUTHENTICATION_TYPE`, `LAST_UPDATED_BY`, `CREATION_TIMESTAMP`, `UPDATE_TIMESTAMP`) VALUES ('MTN13', 'http://localhost:28090/v2.0', 'm93945', '93937EA01B94A10A49279D4572B48369', NULL, NULL, 'admin', 'admin', 1, 'KEYSTONE', 'USERNAME_PASSWORD', 'MSO_USER', '2018-07-17 14:02:33', '2018-07-17 14:02:33'); INSERT INTO `cloud_sites` (`ID`, `REGION_ID`, `IDENTITY_SERVICE_ID`, `CLOUD_VERSION`, `CLLI`, `CLOUDIFY_ID`, `PLATFORM`, `ORCHESTRATOR`, `LAST_UPDATED_BY`, `CREATION_TIMESTAMP`, `UPDATE_TIMESTAMP`) VALUES ('mtn13', 'mtn13', 'MTN13', '2.5', 'MDT13', 'mtn13', NULL, 'orchestrator', 'MSO_USER', '2018-07-17 14:06:28', '2018-07-17 14:06:28'); diff --git a/adapters/mso-openstack-adapters/src/test/resources/data.sql b/adapters/mso-openstack-adapters/src/test/resources/data.sql index 0103564b5b..77df06bb92 100644 --- a/adapters/mso-openstack-adapters/src/test/resources/data.sql +++ b/adapters/mso-openstack-adapters/src/test/resources/data.sql @@ -152,7 +152,7 @@ INSERT INTO `heat_environment` (`ARTIFACT_UUID`, `NAME`, `VERSION`, `DESCRIPTION INSERT INTO `cloudify_managers` (`ID`, `CLOUDIFY_URL`, `USERNAME`, `PASSWORD`, `VERSION`, `LAST_UPDATED_BY`, `CREATION_TIMESTAMP`, `UPDATE_TIMESTAMP`) VALUES ('mtn13', 'http://localhost:28090/v2.0', 'm93945', '93937EA01B94A10A49279D4572B48369', NULL, 'MSO_USER', '2018-07-17 14:05:08', '2018-07-17 14:05:08'); -INSERT INTO `identity_services` (`ID`, `IDENTITY_URL`, `MSO_ID`, `MSO_PASS`, `ADMIN_TENANT`, `MEMBER_ROLE`, `TENANT_METADATA`, `IDENTITY_SERVER_TYPE`, `IDENTITY_AUTHENTICATION_TYPE`, `LAST_UPDATED_BY`, `CREATION_TIMESTAMP`, `UPDATE_TIMESTAMP`) VALUES ('MTN13', 'http://localhost:28090/v2.0', 'm939454', '93937EA01B94A10A49279D4572B48369', 'admin', 'admin', 1, 'KEYSTONE', 'USERNAME_PASSWORD', 'MSO_USER', '2018-07-17 14:02:33', '2018-07-17 14:02:33'); +INSERT INTO `identity_services` (`ID`, `IDENTITY_URL`, `MSO_ID`, `MSO_PASS`, `PROJECT_DOMAIN_NAME`, `USER_DOMAIN_NAME`, `ADMIN_TENANT`, `MEMBER_ROLE`, `TENANT_METADATA`, `IDENTITY_SERVER_TYPE`, `IDENTITY_AUTHENTICATION_TYPE`, `LAST_UPDATED_BY`, `CREATION_TIMESTAMP`, `UPDATE_TIMESTAMP`) VALUES ('MTN13', 'http://localhost:28090/v2.0', 'm939454', '93937EA01B94A10A49279D4572B48369', null, null, 'admin', 'admin', 1, 'KEYSTONE', 'USERNAME_PASSWORD', 'MSO_USER', '2018-07-17 14:02:33', '2018-07-17 14:02:33'); INSERT INTO `cloud_sites` (`ID`, `region_id`, `identity_service_id`, `cloud_version`, `clli`, `cloudify_id`, `platform`, `orchestrator`, `CREATION_TIMESTAMP`, `UPDATE_TIMESTAMP`) VALUES ('MTN13', 'mtn13', 'MTN13', '3.0', 'MDT13', 'mtn13', null, 'orchestrator', '2018-07-17 14:06:28', '2018-07-17 14:06:28'); diff --git a/adapters/mso-openstack-adapters/src/test/resources/schema.sql b/adapters/mso-openstack-adapters/src/test/resources/schema.sql index a051417cc1..0c67123f56 100644 --- a/adapters/mso-openstack-adapters/src/test/resources/schema.sql +++ b/adapters/mso-openstack-adapters/src/test/resources/schema.sql @@ -788,6 +788,8 @@ CREATE TABLE IF NOT EXISTS `identity_services` ( `IDENTITY_URL` varchar(200) DEFAULT NULL, `MSO_ID` varchar(255) DEFAULT NULL, `MSO_PASS` varchar(255) DEFAULT NULL, + `PROJECT_DOMAIN_NAME` varchar(255) DEFAULT NULL, + `USER_DOMAIN_NAME` varchar(255) DEFAULT NULL, `ADMIN_TENANT` varchar(50) DEFAULT NULL, `MEMBER_ROLE` varchar(50) DEFAULT NULL, `TENANT_METADATA` tinyint(1) DEFAULT 0, |