/* * To change this template, choose Tools | Templates * and open the template in the editor. */ package org.hyperic.plugin.vrealize.automation; import static com.vmware.hyperic.model.relations.RelationType.CHILD; import static com.vmware.hyperic.model.relations.RelationType.PARENT; import static com.vmware.hyperic.model.relations.RelationType.SIBLING; import static org.hyperic.plugin.vrealize.automation.VRAUtils.configFile; import static org.hyperic.plugin.vrealize.automation.VRAUtils.executeXMLQuery; import static org.hyperic.plugin.vrealize.automation.VraConstants.*; import java.util.ArrayList; import java.util.Collection; import java.util.List; import java.util.Properties; import org.apache.commons.codec.binary.Base64; import org.apache.commons.lang.StringUtils; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import org.hyperic.hq.product.PluginException; import org.hyperic.hq.product.ServerResource; import org.hyperic.util.config.ConfigResponse; import com.vmware.hyperic.model.relations.CommonModelUtils; import com.vmware.hyperic.model.relations.ObjectFactory; import com.vmware.hyperic.model.relations.Relation; import com.vmware.hyperic.model.relations.Resource; import com.vmware.hyperic.model.relations.ResourceTier; /** * @author laullon */ public class DiscoveryVRAServer extends Discovery { private static final Log log = LogFactory.getLog(DiscoveryVRAServer.class); private final String appName = CommonModelUtils.getParametrizedName(KEY_APPLICATION_NAME); @Override public List<ServerResource> getServerResources(ConfigResponse platformConfig) throws PluginException { log.debug("[getServerResources] platformConfig=" + platformConfig); String platformFqdn = platformConfig.getValue("platform.fqdn"); VRAUtils.setLocalFqdn(platformFqdn); log.debug("[getServerResources] platformFqdn=" + platformFqdn); @SuppressWarnings("unchecked") List<ServerResource> servers = super.getServerResources(platformConfig); if (servers.isEmpty()) return servers; Properties props = configFile("/etc/vcac/security.properties"); String vraApplicationFqdn = props.getProperty("csp.component.registry.url"); String webSsoLoadBalancer = props.getProperty("vmidentity.websso.host"); webSsoLoadBalancer = VRAUtils.getFqdn(webSsoLoadBalancer); vraApplicationFqdn = VRAUtils.getFqdn(vraApplicationFqdn); log.debug("[getServerResources] vraApplicationFqdn=" + vraApplicationFqdn); log.debug("[getServerResources] webSsoLoadBalancer=" + webSsoLoadBalancer); if (StringUtils.isBlank(vraApplicationFqdn)) return servers; String applicationServicesPath = getApplicationServicePath(platformFqdn); // Get Database URL String vraDatabaseURL = executeXMLQuery("//Resource[@name=\"jdbc/cafe\"]/@url", "/etc/vcac/server.xml"); log.debug("[discoverServices] vraDatabaseURL=" + vraDatabaseURL); String databaseServerFqdn = getDatabaseFqdn(vraDatabaseURL); log.debug("[discoverServices] databaseServerFqdn=" + databaseServerFqdn); for (ServerResource server : servers) { String model = VRAUtils.marshallResource( getCommonModel(vraApplicationFqdn, webSsoLoadBalancer, getPlatformName(), applicationServicesPath, databaseServerFqdn)); server.getProductConfig().setValue(PROP_EXTENDED_REL_MODEL, new String(Base64.encodeBase64(model.getBytes()))); // do not remove, why? please don't ask. server.setProductConfig(server.getProductConfig()); } return servers; } /** * @return Returns vRA Server FQDN (not Load Balancer) */ private Collection<String> getIaaSFqdns() { Collection<String> iaasFqdns = new ArrayList<String>(); VRAUtils.VraVersion vraVersion = VRAUtils.getVraVersion(isWin32()); if (vraVersion.getMajor() >= 6 && vraVersion.getMinor() > 1) { String componentsRegistryJson = VRAUtils.getJsonFromVcacConfigListCommand(); log.debug("[getIaaSFqdns] The json is: " + componentsRegistryJson); try { Collection<String> iaasFqdnsOrIps = VRAUtils.getNodeHostUrlsFromClusterConfigJson(componentsRegistryJson, "IAAS"); for (String fqdnOrIp : iaasFqdnsOrIps) { iaasFqdns.add(VRAUtils.getFqdn(fqdnOrIp)); } log.debug("Following IaaS Service FQDNs were found => " + iaasFqdnsOrIps); } catch (Exception e) { log.error("Unable to get IaaS node host names from vRA configuration", e); } } return iaasFqdns; } private String getApplicationServicePath(String platformFqdn) { String applicationServicesPath = null; try { String componentRegistry = VRAUtils.getWGet( String.format("https://%s/component-registry/services/status/current?$top=50", platformFqdn)); Collection<String> applicationServices = VRAUtils.getFqdnFromComponentRegistryJson(componentRegistry, "Application Services"); applicationServicesPath = getFirstElementOrNull(applicationServices); log.debug("Application services host is = " + applicationServicesPath); } catch (Exception e) { log.debug("Failed to get getApplicationServicePath", e); } return applicationServicesPath; } /** * @param Collection of String * @return only first element for given collection */ private String getFirstElementOrNull(Collection<String> collection) { String result = null; if (collection != null) { for (String element : collection) { result = element; break; } } return result; } private String getIaasLoadBalancerFqdn(String platformFqdn) { String iaasLoadBalancerFqdn = null; try { String iaasLoadBalancerFqdnJson = VRAUtils.getWGet( String.format("https://%s/component-registry/services/status/current?$top=50", platformFqdn)); Collection<String> iaasLoadBalancerFqdns = VRAUtils.getFqdnFromComponentRegistryJson(iaasLoadBalancerFqdnJson, "iaas-service"); iaasLoadBalancerFqdn = getFirstElementOrNull(iaasLoadBalancerFqdns); log.debug("Iaas Load Balancer Fqdn is = " + iaasLoadBalancerFqdn); } catch (Exception e) { log.debug("Failed to get Iaas Load Balancer Fqdn"); return null; } return iaasLoadBalancerFqdn; } private Resource getCommonModel( String vraApplicationFqdn, String webSsoOrSsoLoadBalancer, String platformName, String applicationServicesHost, String vraDatabaseFqdn) { ObjectFactory factory = new ObjectFactory(); Resource vraApplication = factory.createApplicationResource(TYPE_VRA_APPLICATION, vraApplicationFqdn); vraApplication.addProperty(factory.createProperty(KEY_APPLICATION_NAME, vraApplicationFqdn)); Relation relationToVraApp = factory.createRelation(vraApplication, PARENT, Boolean.TRUE); Resource vRaServer = factory.createResource(Boolean.FALSE, TYPE_VRA_SERVER, platformName, ResourceTier.SERVER); Resource vraServersGroup = factory.createLogicalResource(TYPE_VRA_SERVER_TAG, vraApplicationFqdn); vRaServer.addRelations(factory.createRelation(vraServersGroup, PARENT)); vraServersGroup.addRelations(relationToVraApp); createApplicationServiceRelations(vraApplicationFqdn, applicationServicesHost, factory, vraApplication, vRaServer); createRelationSsoOrLoadBalancer(vraApplicationFqdn, webSsoOrSsoLoadBalancer, factory, relationToVraApp, vRaServer); createLoadBalancerRelations(vraApplicationFqdn, platformName, factory, relationToVraApp, vRaServer, vraServersGroup); createVcoRelations(factory, vraApplication); createVraDatabaseRelations(factory, vraApplicationFqdn, vRaServer, vraApplication, vraDatabaseFqdn); createIaaSWebRelations(factory, vraApplicationFqdn, vRaServer, vraApplication); return vRaServer; } private void createIaaSWebRelations(ObjectFactory factory, String vRaApplicationFqdn, Resource vRaServer, Resource vraApplication) { log.debug("[createIaaSWebRelations] vRaApplicationFqdn = " + vRaApplicationFqdn); Collection<String> iaasFqdns = getIaaSFqdns(); for (String iaasWebServerFqdn : iaasFqdns) { log.debug("[createIaaSWebRelations] iaasFqdn = " + iaasWebServerFqdn); Resource iaasWebServer = factory.createResource(!CREATE_IF_NOT_EXIST, TYPE_VRA_IAAS_WEB, iaasWebServerFqdn, ResourceTier.SERVER); Resource iaasWebManagement = factory.createResource(!CREATE_IF_NOT_EXIST, TYPE_VRA_IAAS_MANAGEMENT, iaasWebServerFqdn, ResourceTier.SERVER); Resource iaasWebServerTag = factory.createLogicalResource(TYPE_VRA_IAAS_WEB_TAG, vRaApplicationFqdn); iaasWebServer.addRelations(factory.createRelation(iaasWebServerTag, PARENT)); iaasWebServerTag.addRelations(factory.createRelation(iaasWebManagement, CHILD)); iaasWebServerTag.addRelations(factory.createRelation(vraApplication, PARENT)); vRaServer.addRelations(factory.createRelation(iaasWebServer, SIBLING), factory.createRelation(iaasWebManagement, SIBLING)); } VRAUtils.VraVersion vraVersion = VRAUtils.getVraVersion(isWin32()); createRelationIaasWebLoadBalancer(factory, vRaApplicationFqdn, vRaServer, vraApplication, vraVersion); } private void createRelationIaasWebLoadBalancer(ObjectFactory factory, String vRaApplicationFqdn, Resource vRaServer, Resource vraApplication, VRAUtils.VraVersion vraVersion) { if (vraVersion.getMinor() <= 1) { return; } String iaasWebLoadBalancerFqdn = getIaasLoadBalancerFqdn(vRaApplicationFqdn); if (StringUtils.isBlank(iaasWebLoadBalancerFqdn)) { return; } log.debug("[createRelationIaasWebLoadBalancer] iaasLoadBalancerFqdn = " + iaasWebLoadBalancerFqdn); Resource iaasWebLoadBalancer = factory.createResource(false, TYPE_VRA_IAAS_WEB_LOAD_BALANCER, iaasWebLoadBalancerFqdn, ResourceTier.SERVER); vRaServer.addRelations(factory.createRelation(iaasWebLoadBalancer, SIBLING)); Resource iaasWebLoadBalancerTag = factory.createLogicalResource(TYPE_VRA_IAAS_WEB_LOAD_BALANCER_TAG, vRaApplicationFqdn); iaasWebLoadBalancer.addRelations(factory.createRelation(iaasWebLoadBalancerTag, PARENT)); Resource loadBalancerSuperTag = factory.createLogicalResource(TYPE_LOAD_BALANCER_TAG, vRaApplicationFqdn); iaasWebLoadBalancerTag.addRelations(factory.createRelation(loadBalancerSuperTag, PARENT)); loadBalancerSuperTag.addRelations(factory.createRelation(vraApplication, PARENT)); } private void createVraDatabaseRelations( ObjectFactory factory, String applicationName, Resource vraServer, Resource vraApplication, String databaseServerFqdn) { Resource vraDatabasesGroup = factory.createLogicalResource(TYPE_VRA_DATABASES_GROUP, applicationName); vraDatabasesGroup.addRelations(factory.createRelation(vraApplication, PARENT)); Resource databaseServerHostWin = factory.createResource(!CREATE_IF_NOT_EXIST, VraConstants.TYPE_WINDOWS, databaseServerFqdn, ResourceTier.PLATFORM); Resource databaseServerHostLinux = factory.createResource(!CREATE_IF_NOT_EXIST, VraConstants.TYPE_LINUX, databaseServerFqdn, ResourceTier.PLATFORM); databaseServerHostWin.addRelations(factory.createRelation(vraDatabasesGroup, PARENT)); databaseServerHostLinux.addRelations(factory.createRelation(vraDatabasesGroup, PARENT)); if (!VRAUtils.areFqdnsEquivalent(VRAUtils.getLocalFqdn(), databaseServerFqdn)) { vraServer.addRelations( factory.createRelation(databaseServerHostWin, VRAUtils.getDataBaseRalationType(databaseServerFqdn)), factory.createRelation(databaseServerHostLinux, VRAUtils.getDataBaseRalationType(databaseServerFqdn))); } } /** * @param factory */ private void createVcoRelations( ObjectFactory factory, Resource vraApplication) { // VCO Server Resource vcoGroup = factory.createLogicalResource(TYPE_VCO_TAG, vraApplication.getName()); Resource vcoServer = factory.createResource(false, TYPE_VRA_VCO, CommonModelUtils.getParametrizedName(VraConstants.KEY_VCO_SERVER_FQDN), ResourceTier.SERVER); vcoServer.addRelations(factory.createRelation(vcoGroup, PARENT)); vcoGroup.addRelations(factory.createRelation(vraApplication, CHILD)); } private void createLoadBalancerRelations( String lbHostName, String platform, ObjectFactory factory, Relation relationToVraApp, Resource vRaServer, Resource vraServersGroup) { if (StringUtils.isBlank(lbHostName) || lbHostName.equals(platform)) { return; } Resource topLbGroup = factory.createLogicalResource(TYPE_LOAD_BALANCER_TAG, lbHostName); Resource vraLbServer = factory.createResource(false, TYPE_VRA_SERVER_LOAD_BALANCER, lbHostName, ResourceTier.SERVER); Resource vraLbServerGroup = factory.createLogicalResource(TYPE_VRA_LOAD_BALANCER_TAG, lbHostName); vraLbServer.addRelations(factory.createRelation(vraLbServerGroup, PARENT, true)); vraLbServer.addRelations(factory.createRelation(vraServersGroup, PARENT, true)); vraLbServerGroup.addRelations(factory.createRelation(topLbGroup, PARENT, true)); topLbGroup.addRelations(relationToVraApp); vRaServer.addRelations(factory.createRelation(vraLbServer, SIBLING, true)); } private void createRelationSsoOrLoadBalancer( String vraApplicationName, String webSsoOrSsoLoadBalancer, ObjectFactory factory, Relation relationToVraApp, Resource vRaServer) { if (StringUtils.isBlank(webSsoOrSsoLoadBalancer)) { return; } Resource ssoGroup = factory.createLogicalResource(TYPE_SSO_TAG, vraApplicationName); Resource vraSsoServer = factory.createResource(!CREATE_IF_NOT_EXIST, TYPE_VRA_VSPHERE_SSO, webSsoOrSsoLoadBalancer, ResourceTier.SERVER); vraSsoServer.setContextPropagationBarrier(true); vraSsoServer.addRelations(factory.createRelation(ssoGroup, PARENT)); ssoGroup.addRelations(relationToVraApp); vRaServer.addRelations(factory.createRelation(vraSsoServer, SIBLING)); createRelationSsoLoadBalancer(webSsoOrSsoLoadBalancer, vraApplicationName, factory, relationToVraApp, vRaServer, ssoGroup); } private void createRelationSsoLoadBalancer( String webSso, String vraApplicationName, ObjectFactory factory, Relation relationToVraApp, Resource vRaServer, Resource ssoGroup) { Resource topLoadBalancerTag = factory.createLogicalResource(TYPE_LOAD_BALANCER_TAG, appName); topLoadBalancerTag.addRelations(relationToVraApp); Resource ssoLoadBalancerTag = factory.createLogicalResource(TYPE_VSPHERE_SSO_LOAD_BALANCER_TAG, CommonModelUtils.getParametrizedName(KEY_APPLICATION_NAME)); ssoLoadBalancerTag.addRelations(factory.createRelation(topLoadBalancerTag, PARENT, CREATE_IF_NOT_EXIST)); Resource ssoLoadBalancer = factory.createResource(false, TYPE_VSPHERE_SSO_LOAD_BALANCER, webSso, ResourceTier.SERVER); ssoLoadBalancer.setContextPropagationBarrier(true); ssoLoadBalancer.addRelations(factory.createRelation(ssoLoadBalancerTag, PARENT, CREATE_IF_NOT_EXIST)); ssoLoadBalancer.addRelations(factory.createRelation(ssoGroup, PARENT, CREATE_IF_NOT_EXIST)); vRaServer.addRelations(factory.createRelation(ssoLoadBalancer, SIBLING)); } private void createApplicationServiceRelations( String lbHostName, String applicationServicesHost, ObjectFactory factory, Resource vraApplication, Resource vRaServer) { if (StringUtils.isBlank(applicationServicesHost)) { return; } Resource appServicesGroup = factory.createLogicalResource(TYPE_APP_SERVICES_TAG, lbHostName); Resource vraAppServicesServer = factory.createResource(Boolean.FALSE, TYPE_VRA_APP_SERVICES, applicationServicesHost, ResourceTier.SERVER); vraAppServicesServer.addRelations(factory.createRelation(appServicesGroup, PARENT)); appServicesGroup.addRelations(factory.createRelation(vraApplication, PARENT)); vRaServer.addRelations(factory.createRelation(vraAppServicesServer, SIBLING)); } private String getDatabaseFqdn(String jdbcConnectionString) { // url="jdbc:postgresql://ra-psql-a-01.refarch.eng.vmware.com:5432/vcac" return VRAUtils.getFqdn(jdbcConnectionString, AddressExtractorFactory.getDatabaseServerFqdnExtractor()); } // inline unit test /* @Test public void test() { ServerResource server = new ServerResource(); server.setName("THE_SERVER"); server.setType("THE_SERVER_TYPE"); String vraDatabaseServerFqdn = getDatabaseFqdn("jdbc:postgresql://ra-psql-a-01.refarch.eng.vmware.com:5432/vcac"); Resource modelResource = getCommonModel("THE_APP", "THE_SSO", "THE_PLATFORM", "shmulik.com", vraDatabaseServerFqdn); String modelXml = VRAUtils.marshallResource(modelResource); Assert.assertNotNull(modelXml); System.out.println(modelXml); } */ }