diff --git a/api/src/org/apache/cloudstack/api/ApiConstants.java b/api/src/org/apache/cloudstack/api/ApiConstants.java index b80514d46e7..e714ca42316 100755 --- a/api/src/org/apache/cloudstack/api/ApiConstants.java +++ b/api/src/org/apache/cloudstack/api/ApiConstants.java @@ -428,6 +428,7 @@ public class ApiConstants { public static final String COUNTERPARAM_LIST = "counterparam"; public static final String AUTOSCALE_USER_ID = "autoscaleuserid"; public static final String BAREMETAL_DISCOVER_NAME = "baremetaldiscovername"; + public static final String UCS_DN = "ucsdn"; public enum HostDetails { all, capacity, events, stats, min; diff --git a/plugins/hypervisors/ucs/pom.xml b/plugins/hypervisors/ucs/pom.xml new file mode 100755 index 00000000000..aecace85fce --- /dev/null +++ b/plugins/hypervisors/ucs/pom.xml @@ -0,0 +1,37 @@ + + + 4.0.0 + + org.apache.cloudstack + cloudstack-plugins + 4.1.0-SNAPSHOT + ../../pom.xml + + org.apache.cloudstack + cloud-plugin-hypervisor-ucs + 4.1.0-SNAPSHOT + cloud-plugin-hypervisor-ucs + http://maven.apache.org + + UTF-8 + + + + junit + junit + 3.8.1 + test + + + org.apache.cloudstack + cloud-utils + ${project.version} + + + org.apache.cloudstack + cloud-api + ${project.version} + + + diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsBladeDao.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsBladeDao.java new file mode 100755 index 00000000000..de7c6192dc6 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsBladeDao.java @@ -0,0 +1,7 @@ +package com.cloud.ucs.database; + +import com.cloud.utils.db.GenericDao; + +public interface UcsBladeDao extends GenericDao { + +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsBladeDaoImpl.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsBladeDaoImpl.java new file mode 100755 index 00000000000..ebeecf8e9a0 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsBladeDaoImpl.java @@ -0,0 +1,11 @@ +package com.cloud.ucs.database; + +import javax.ejb.Local; + +import com.cloud.utils.db.DB; +import com.cloud.utils.db.GenericDaoBase; +@Local(value = { UcsBladeDao.class }) +@DB(txn = false) +public class UcsBladeDaoImpl extends GenericDaoBase implements UcsBladeDao { + +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsBladeVO.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsBladeVO.java new file mode 100755 index 00000000000..64c1a721f17 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsBladeVO.java @@ -0,0 +1,69 @@ +package com.cloud.ucs.database; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.GeneratedValue; +import javax.persistence.GenerationType; +import javax.persistence.Id; +import javax.persistence.Table; + +@Entity +@Table(name="ucs_blade") +public class UcsBladeVO { + @Id + @GeneratedValue(strategy=GenerationType.IDENTITY) + @Column(name="id") + private long id; + + @Column(name="uuid") + private String uuid; + + @Column(name="ucs_manager_id") + private long ucsManagerId; + + @Column(name="host_id") + private Long hostId; + + @Column(name="dn") + private String dn; + + public long getId() { + return id; + } + + public void setId(long id) { + this.id = id; + } + + public long getUcsManagerId() { + return ucsManagerId; + } + + public void setUcsManagerId(long ucsManagerId) { + this.ucsManagerId = ucsManagerId; + } + + public Long getHostId() { + return hostId; + } + + public void setHostId(Long hostId) { + this.hostId = hostId; + } + + public String getDn() { + return dn; + } + + public void setDn(String dn) { + this.dn = dn; + } + + public String getUuid() { + return uuid; + } + + public void setUuid(String uuid) { + this.uuid = uuid; + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsManagerDao.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsManagerDao.java new file mode 100755 index 00000000000..eb4c2573d94 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsManagerDao.java @@ -0,0 +1,16 @@ +package com.cloud.ucs.database; + +import java.util.List; +import java.util.Map; + +import javax.naming.ConfigurationException; + +import com.cloud.utils.db.Filter; +import com.cloud.utils.db.GenericDao; +import com.cloud.utils.db.GenericSearchBuilder; +import com.cloud.utils.db.SearchBuilder; +import com.cloud.utils.db.SearchCriteria; +import com.cloud.utils.db.SearchCriteria2; + +public interface UcsManagerDao extends GenericDao { +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsManagerDaoImpl.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsManagerDaoImpl.java new file mode 100755 index 00000000000..f1475ab6581 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsManagerDaoImpl.java @@ -0,0 +1,12 @@ +package com.cloud.ucs.database; + +import javax.ejb.Local; + +import com.cloud.utils.db.DB; +import com.cloud.utils.db.GenericDaoBase; + +@Local(value = { UcsManagerDao.class }) +@DB(txn = false) +public class UcsManagerDaoImpl extends GenericDaoBase implements UcsManagerDao { +} + diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsManagerVO.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsManagerVO.java new file mode 100755 index 00000000000..7c451beeec8 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/database/UcsManagerVO.java @@ -0,0 +1,78 @@ +package com.cloud.ucs.database; + +import javax.persistence.Column; +import javax.persistence.Entity; +import javax.persistence.GeneratedValue; +import javax.persistence.GenerationType; +import javax.persistence.Id; +import javax.persistence.Table; + +@Entity +@Table(name="ucs_manager") +public class UcsManagerVO { + @Id + @GeneratedValue(strategy=GenerationType.IDENTITY) + @Column(name="id") + private long id; + + @Column(name="zone_id") + private long zoneId; + + @Column(name="uuid") + private String uuid; + + @Column(name="name") + private String name; + + @Column(name="url") + private String url; + + @Column(name="username") + private String username; + + @Column(name="password") + private String password; + + public long getId() { + return id; + } + public void setId(long id) { + this.id = id; + } + public String getUuid() { + return uuid; + } + public void setUuid(String uuid) { + this.uuid = uuid; + } + public String getUrl() { + return url; + } + public void setUrl(String url) { + this.url = url; + } + public String getUsername() { + return username; + } + public void setUsername(String username) { + this.username = username; + } + public String getPassword() { + return password; + } + public void setPassword(String password) { + this.password = password; + } + public long getZoneId() { + return zoneId; + } + public void setZoneId(long zoneId) { + this.zoneId = zoneId; + } + public String getName() { + return name; + } + public void setName(String name) { + this.name = name; + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AddUcsManagerCmd.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AddUcsManagerCmd.java new file mode 100755 index 00000000000..1e405c142e4 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AddUcsManagerCmd.java @@ -0,0 +1,108 @@ +package com.cloud.ucs.manager; + +import javax.inject.Inject; + +import org.apache.cloudstack.api.APICommand; +import org.apache.cloudstack.api.ApiConstants; +import org.apache.cloudstack.api.ApiErrorCode; +import org.apache.cloudstack.api.BaseCmd; +import org.apache.cloudstack.api.BaseCmd.CommandType; +import org.apache.cloudstack.api.Parameter; +import org.apache.cloudstack.api.ServerApiException; +import org.apache.log4j.Logger; + +import com.cloud.exception.ConcurrentOperationException; +import com.cloud.exception.InsufficientCapacityException; +import com.cloud.exception.NetworkRuleConflictException; +import com.cloud.exception.ResourceAllocationException; +import com.cloud.exception.ResourceUnavailableException; +import com.cloud.server.ManagementService; +import com.cloud.user.Account; + +@APICommand(description="Adds a Ucs manager", responseObject=AddUcsManagerResponse.class) +public class AddUcsManagerCmd extends BaseCmd { + public static final Logger s_logger = Logger.getLogger(AddUcsManagerCmd.class); + + @Inject + private UcsManager mgr; + + @Parameter(name=ApiConstants.ZONE_ID, type=CommandType.LONG, description="the Zone id for the ucs manager", required=true) + private Long zoneId; + + @Parameter(name=ApiConstants.NAME, type=CommandType.STRING, description="the name of UCS manager") + private String name; + + @Parameter(name=ApiConstants.URL, type=CommandType.STRING, description="the name of UCS url") + private String url; + + @Parameter(name=ApiConstants.USERNAME, type=CommandType.STRING, description="the username of UCS") + private String username; + + @Parameter(name=ApiConstants.PASSWORD, type=CommandType.STRING, description="the password of UCS") + private String password; + + @Override + public void execute() throws ResourceUnavailableException, InsufficientCapacityException, ServerApiException, ConcurrentOperationException, + ResourceAllocationException, NetworkRuleConflictException { + try { + AddUcsManagerResponse rsp = mgr.addUcsManager(this); + rsp.setObjectName("ucsmanager"); + rsp.setResponseName(getCommandName()); + this.setResponseObject(rsp); + } catch (Exception e) { + s_logger.warn("Exception: ", e); + throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, e.getMessage()); + } + } + + @Override + public String getCommandName() { + return "addUcsManagerResponse"; + } + + @Override + public long getEntityOwnerId() { + return Account.ACCOUNT_ID_SYSTEM; + } + + public Long getZoneId() { + return zoneId; + } + + public void setZoneId(Long zoneId) { + this.zoneId = zoneId; + } + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getUrl() { + return url; + } + + public void setUrl(String url) { + this.url = url; + } + + public String getUsername() { + return username; + } + + public void setUsername(String username) { + this.username = username; + } + + public String getPassword() { + return password; + } + + public void setPassword(String password) { + this.password = password; + } + +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AddUcsManagerResponse.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AddUcsManagerResponse.java new file mode 100755 index 00000000000..eff30b955f7 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AddUcsManagerResponse.java @@ -0,0 +1,53 @@ +package com.cloud.ucs.manager; + +import org.apache.cloudstack.api.ApiConstants; +import org.apache.cloudstack.api.BaseResponse; + +import com.cloud.serializer.Param; +import com.google.gson.annotations.SerializedName; + +public class AddUcsManagerResponse extends BaseResponse { + @SerializedName(ApiConstants.ID) @Param(description="the ID of the ucs manager") + private String id; + + @SerializedName(ApiConstants.NAME) @Param(description="the name of ucs manager") + private String name; + + @SerializedName(ApiConstants.URL) @Param(description="the url of ucs manager") + private String url; + + @SerializedName(ApiConstants.ZONE_ID) @Param(description="the zone ID of ucs manager") + private String zoneId; + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getUrl() { + return url; + } + + public void setUrl(String url) { + this.url = url; + } + + public String getId() { + return id; + } + + public void setId(String id) { + this.id = id; + } + + public String getZoneId() { + return zoneId; + } + + public void setZoneId(String zoneId) { + this.zoneId = zoneId; + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AssociateUcsProfileToBladeCmd.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AssociateUcsProfileToBladeCmd.java new file mode 100755 index 00000000000..7de9f78b713 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AssociateUcsProfileToBladeCmd.java @@ -0,0 +1,76 @@ +package com.cloud.ucs.manager; + +import javax.inject.Inject; + +import org.apache.cloudstack.api.APICommand; +import org.apache.cloudstack.api.ApiErrorCode; +import org.apache.cloudstack.api.BaseCmd; +import org.apache.cloudstack.api.ServerApiException; +import org.apache.log4j.Logger; + +import com.cloud.exception.ConcurrentOperationException; +import com.cloud.exception.InsufficientCapacityException; +import com.cloud.exception.NetworkRuleConflictException; +import com.cloud.exception.ResourceAllocationException; +import com.cloud.exception.ResourceUnavailableException; +import com.cloud.user.Account; +@APICommand(description="associate a profile to a blade", responseObject=AssociateUcsProfileToBladesInClusterResponse.class) +public class AssociateUcsProfileToBladeCmd extends BaseCmd { + public static final Logger s_logger = Logger.getLogger(AssociateUcsProfileToBladeCmd.class); + + @Inject + private UcsManager mgr; + + private Long ucsManagerId; + private String profileDn; + private Long bladeId; + + @Override + public void execute() throws ResourceUnavailableException, InsufficientCapacityException, ServerApiException, ConcurrentOperationException, + ResourceAllocationException, NetworkRuleConflictException { + try { + mgr.associateProfileToBlade(this); + AssociateUcsProfileToBladesInClusterResponse rsp = new AssociateUcsProfileToBladesInClusterResponse(); + rsp.setResponseName(getCommandName()); + rsp.setObjectName("associateucsprofiletobalde"); + this.setResponseObject(rsp); + } catch (Exception e) { + s_logger.warn("Exception: ", e); + throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, e.getMessage()); + } + } + + @Override + public String getCommandName() { + return "associateucsprofiletobladeresponse"; + } + + @Override + public long getEntityOwnerId() { + return Account.ACCOUNT_ID_SYSTEM; + } + + public Long getUcsManagerId() { + return ucsManagerId; + } + + public void setUcsManagerId(Long ucsManagerId) { + this.ucsManagerId = ucsManagerId; + } + + public String getProfileDn() { + return profileDn; + } + + public void setProfileDn(String profileDn) { + this.profileDn = profileDn; + } + + public Long getBladeId() { + return bladeId; + } + + public void setBladeId(Long bladeId) { + this.bladeId = bladeId; + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AssociateUcsProfileToBladesInClusterResponse.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AssociateUcsProfileToBladesInClusterResponse.java new file mode 100755 index 00000000000..eedd9fc2841 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/AssociateUcsProfileToBladesInClusterResponse.java @@ -0,0 +1,6 @@ +package com.cloud.ucs.manager; + +import org.apache.cloudstack.api.BaseResponse; + +public class AssociateUcsProfileToBladesInClusterResponse extends BaseResponse { +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsManagerCmd.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsManagerCmd.java new file mode 100755 index 00000000000..53b09a25c40 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsManagerCmd.java @@ -0,0 +1,62 @@ +package com.cloud.ucs.manager; + +import javax.inject.Inject; + +import org.apache.cloudstack.api.APICommand; +import org.apache.cloudstack.api.ApiConstants; +import org.apache.cloudstack.api.ApiErrorCode; +import org.apache.cloudstack.api.BaseCmd; +import org.apache.cloudstack.api.Parameter; +import org.apache.cloudstack.api.ServerApiException; +import org.apache.cloudstack.api.response.ListResponse; +import org.apache.log4j.Logger; + +import com.cloud.exception.ConcurrentOperationException; +import com.cloud.exception.InsufficientCapacityException; +import com.cloud.exception.NetworkRuleConflictException; +import com.cloud.exception.ResourceAllocationException; +import com.cloud.exception.ResourceUnavailableException; +import com.cloud.server.ManagementService; +import com.cloud.user.Account; +@APICommand(description="List ucs manager", responseObject=ListUcsManagerResponse.class) +public class ListUcsManagerCmd extends BaseCmd { + public static final Logger s_logger = Logger.getLogger(ListUcsManagerCmd.class); + + @Parameter(name=ApiConstants.ZONE_ID, type=CommandType.LONG, description="the zone id", required=true) + private Long zoneId; + + @Inject + private UcsManager mgr; + + @Override + public void execute() throws ResourceUnavailableException, InsufficientCapacityException, ServerApiException, ConcurrentOperationException, + ResourceAllocationException, NetworkRuleConflictException { + try { + ListResponse response = mgr.listUcsManager(this); + response.setResponseName(getCommandName()); + response.setObjectName("ucsmanager"); + this.setResponseObject(response); + } catch (Exception e) { + s_logger.warn("Exception: ", e); + throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, e.getMessage()); + } + } + + @Override + public String getCommandName() { + return "listucsmanagerreponse"; + } + + @Override + public long getEntityOwnerId() { + return Account.ACCOUNT_ID_SYSTEM; + } + + public Long getZoneId() { + return zoneId; + } + + public void setZoneId(Long zoneId) { + this.zoneId = zoneId; + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsManagerResponse.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsManagerResponse.java new file mode 100755 index 00000000000..d45aec58e61 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsManagerResponse.java @@ -0,0 +1,42 @@ +package com.cloud.ucs.manager; + +import org.apache.cloudstack.api.ApiConstants; +import org.apache.cloudstack.api.BaseResponse; + +import com.cloud.serializer.Param; +import com.google.gson.annotations.SerializedName; + +public class ListUcsManagerResponse extends BaseResponse { + @SerializedName(ApiConstants.ID) @Param(description="id of ucs manager") + private String id; + + @SerializedName(ApiConstants.NAME) @Param(description="name of ucs manager") + private String name; + + @SerializedName(ApiConstants.ZONE_ID) @Param(description="zone id the ucs manager belongs to") + private String zoneId; + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getId() { + return id; + } + + public void setId(String id) { + this.id = id; + } + + public String getZoneId() { + return zoneId; + } + + public void setZoneId(String zoneId) { + this.zoneId = zoneId; + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsProfileCmd.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsProfileCmd.java new file mode 100755 index 00000000000..4d69c74ff7d --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsProfileCmd.java @@ -0,0 +1,63 @@ +package com.cloud.ucs.manager; + +import javax.inject.Inject; + +import org.apache.cloudstack.api.APICommand; +import org.apache.cloudstack.api.ApiConstants; +import org.apache.cloudstack.api.ApiErrorCode; +import org.apache.cloudstack.api.BaseCmd; +import org.apache.cloudstack.api.BaseCmd.CommandType; +import org.apache.cloudstack.api.Parameter; +import org.apache.cloudstack.api.ServerApiException; +import org.apache.cloudstack.api.response.ListResponse; +import org.apache.log4j.Logger; + +import com.cloud.exception.ConcurrentOperationException; +import com.cloud.exception.InsufficientCapacityException; +import com.cloud.exception.NetworkRuleConflictException; +import com.cloud.exception.ResourceAllocationException; +import com.cloud.exception.ResourceUnavailableException; +import com.cloud.server.ManagementService; +import com.cloud.user.Account; +@APICommand(description="List profile in ucs manager", responseObject=ListUcsProfileResponse.class) +public class ListUcsProfileCmd extends BaseCmd { + public static final Logger s_logger = Logger.getLogger(ListUcsProfileCmd.class); + + @Inject UcsManager mgr; + + @Parameter(name=ApiConstants.ID, type=CommandType.LONG, description="the id for the ucs manager", required=true) + private Long ucsManagerId; + + public Long getUcsManagerId() { + return ucsManagerId; + } + + public void setUcsManagerId(Long ucsManagerId) { + this.ucsManagerId = ucsManagerId; + } + + @Override + public void execute() throws ResourceUnavailableException, InsufficientCapacityException, ServerApiException, ConcurrentOperationException, + ResourceAllocationException, NetworkRuleConflictException { + try { + ListResponse response = mgr.listUcsProfiles(this); + response.setResponseName(getCommandName()); + response.setObjectName("ucsprofile"); + this.setResponseObject(response); + } catch (Exception e) { + s_logger.warn("Exception: ", e); + throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, e.getMessage()); + } + } + + @Override + public String getCommandName() { + return "listucsprofileresponse"; + } + + @Override + public long getEntityOwnerId() { + return Account.ACCOUNT_ID_SYSTEM; + } + +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsProfileResponse.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsProfileResponse.java new file mode 100755 index 00000000000..846ac278cf6 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/ListUcsProfileResponse.java @@ -0,0 +1,20 @@ +package com.cloud.ucs.manager; + +import org.apache.cloudstack.api.ApiConstants; +import org.apache.cloudstack.api.BaseResponse; + +import com.cloud.serializer.Param; +import com.google.gson.annotations.SerializedName; + +public class ListUcsProfileResponse extends BaseResponse { + @SerializedName(ApiConstants.UCS_DN) @Param(description="the dn of ucs profile") + private String dn; + + public String getDn() { + return dn; + } + + public void setDn(String dn) { + this.dn = dn; + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/StringTemplate.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/StringTemplate.java new file mode 100755 index 00000000000..f7cd31564f2 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/StringTemplate.java @@ -0,0 +1,22 @@ +package com.cloud.ucs.manager; + +import java.util.Map; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +public class StringTemplate { + public static String replaceTokens(String text, Map replacements) { + Pattern pattern = Pattern.compile("\\[(.+?)\\]"); + Matcher matcher = pattern.matcher(text); + StringBuffer buffer = new StringBuffer(); + while (matcher.find()) { + String replacement = replacements.get(matcher.group(1)); + if (replacement != null) { + matcher.appendReplacement(buffer, ""); + buffer.append(replacement); + } + } + matcher.appendTail(buffer); + return buffer.toString(); + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsCommands.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsCommands.java new file mode 100755 index 00000000000..b6f22c75dbe --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsCommands.java @@ -0,0 +1,83 @@ +package com.cloud.ucs.manager; + +import com.cloud.utils.xmlobject.XmlObject; + +public class UcsCommands { + public static String loginCmd(String username, String password) { + XmlObject cmd = new XmlObject("aaaLogin"); + cmd.putElement("inName", username); + cmd.putElement("inPassword", password); + return cmd.dump(); + } + + public static String listComputeBlades(String cookie) { + XmlObject cmd = new XmlObject("configResolveClass"); + cmd.putElement("classId", "computeBlade"); + cmd.putElement("cookie", cookie); + cmd.putElement("inHierarchical", "false"); + return cmd.dump(); + } + + public static String listProfiles(String cookie) { + XmlObject cmd = new XmlObject("configFindDnsByClassId"); + cmd.putElement("classId", "lsServer"); + cmd.putElement("cookie", cookie); + return cmd.dump(); + } + + public static String cloneProfile(String cookie, String srcDn, String newProfileName) { + XmlObject cmd = new XmlObject("lsClone"); + cmd.putElement("cookie", cookie); + cmd.putElement("dn", srcDn); + cmd.putElement("inTargetOrg", "org-root"); + cmd.putElement("inServerName", newProfileName); + cmd.putElement("inHierarchical", "false"); + return cmd.dump(); + } + + public static String configResolveDn(String cookie, String dn) { + XmlObject cmd = new XmlObject("configResolveDn"); + cmd.putElement("cookie", cookie); + cmd.putElement("dn", dn); + return cmd.toString(); + } + + public static String associateProfileToBlade(String cookie, String profileDn, String bladeDn) { + XmlObject cmd = new XmlObject("configConfMos").putElement("inHierarchical", "true").putElement( + "inConfigs", new XmlObject("inConfigs").putElement( + "pair", new XmlObject("pair").putElement("key", profileDn).putElement( + "lsServer", new XmlObject("lsServer") + .putElement("agentPolicyName", "") + .putElement("biosProfileName", "") + .putElement("bootPolicyName", "") + .putElement("descr", "") + .putElement("dn", profileDn) + .putElement("dynamicConPolicyName", "") + .putElement("extIPState", "none") + .putElement("hostFwPolicyName", "") + .putElement("identPoolName", "") + .putElement("localDiskPolicyName", "") + .putElement("maintPolicyName", "") + .putElement("mgmtAccessPolicyName", "") + .putElement("mgmtFwPolicyName", "") + .putElement("powerPolicyName", "") + .putElement("scrubPolicyName", "") + .putElement("solPolicyName", "") + .putElement("srcTemplName", "") + .putElement("statsPolicyName", "default") + .putElement("status", "") + .putElement("usrLbl", "") + .putElement("", "") + .putElement("vconProfileName", "") + .putElement("lsBinding", new XmlObject("lsBinding") + .putElement("pnDn", bladeDn) + .putElement("restrictMigration", "no") + .putElement("rn", "pn") + ) + ) + ) + ); + + return cmd.dump(); + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsHttpClient.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsHttpClient.java new file mode 100755 index 00000000000..978f67afb05 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsHttpClient.java @@ -0,0 +1,33 @@ +package com.cloud.ucs.manager; + +import org.apache.commons.httpclient.HttpClient; +import org.apache.commons.httpclient.methods.PostMethod; +import org.apache.commons.httpclient.methods.StringRequestEntity; + +import com.cloud.utils.exception.CloudRuntimeException; + +public class UcsHttpClient { + private static HttpClient client = new HttpClient(); + private String url; + + public UcsHttpClient(String ip) { + this.url = String.format("http://%s/nuova", ip); + } + + public String call(String xml) { + PostMethod post = new PostMethod(url); + post.setRequestEntity(new StringRequestEntity(xml)); + post.setRequestHeader("Content-type", "text/xml"); + try { + int result = client.executeMethod(post); + if (result != 200) { + throw new CloudRuntimeException("Call failed: " + post.getResponseBodyAsString()); + } + return post.getResponseBodyAsString(); + } catch (Exception e) { + throw new CloudRuntimeException(e.getMessage(), e); + } finally { + post.releaseConnection(); + } + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsManager.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsManager.java new file mode 100755 index 00000000000..56837606916 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsManager.java @@ -0,0 +1,15 @@ +package com.cloud.ucs.manager; + +import org.apache.cloudstack.api.response.ListResponse; + +import com.cloud.utils.component.Manager; + +public interface UcsManager extends Manager { + AddUcsManagerResponse addUcsManager(AddUcsManagerCmd cmd); + + ListResponse listUcsProfiles(ListUcsProfileCmd cmd); + + ListResponse listUcsManager(ListUcsManagerCmd cmd); + + void associateProfileToBlade(AssociateUcsProfileToBladeCmd cmd); +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsManagerImpl.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsManagerImpl.java new file mode 100755 index 00000000000..03a28dd8985 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/manager/UcsManagerImpl.java @@ -0,0 +1,288 @@ +package com.cloud.ucs.manager; + +import java.io.File; +import java.io.StringReader; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; +import java.util.UUID; +import java.util.concurrent.TimeUnit; + +import javax.ejb.Local; +import javax.inject.Inject; +import javax.naming.ConfigurationException; +import javax.xml.bind.JAXBContext; +import javax.xml.bind.Unmarshaller; + +import org.apache.cloudstack.api.ApiConstants; +import org.apache.cloudstack.api.BaseCmd; +import org.apache.cloudstack.api.ResponseGenerator; +import org.apache.cloudstack.api.ServerApiException; +import org.apache.cloudstack.api.response.ClusterResponse; +import org.apache.cloudstack.api.response.ListResponse; +import org.apache.cxf.helpers.FileUtils; +import org.apache.log4j.Logger; +import org.springframework.stereotype.Component; + +import com.cloud.dc.ClusterDetailsDao; +import com.cloud.dc.dao.ClusterDao; +import com.cloud.host.HostVO; +import com.cloud.hypervisor.Hypervisor.HypervisorType; +import com.cloud.org.Cluster; +import com.cloud.resource.ResourceService; +import com.cloud.ucs.database.UcsBladeDao; +import com.cloud.ucs.database.UcsBladeVO; +import com.cloud.ucs.database.UcsManagerDao; +import com.cloud.ucs.database.UcsManagerVO; +import com.cloud.ucs.structure.ComputeBlade; +import com.cloud.ucs.structure.UcsProfile; +import com.cloud.utils.db.DB; +import com.cloud.utils.db.SearchCriteria.Op; +import com.cloud.utils.db.SearchCriteria2; +import com.cloud.utils.db.SearchCriteriaService; +import com.cloud.utils.db.Transaction; +import com.cloud.utils.exception.CloudRuntimeException; +import com.cloud.utils.script.Script; +import com.cloud.utils.xmlobject.XmlObject; +import com.cloud.utils.xmlobject.XmlObjectParser; + +@Local(value = { UcsManager.class }) +@Component +public class UcsManagerImpl implements UcsManager { + public static final Logger s_logger = Logger.getLogger(UcsManagerImpl.class); + + @Inject + private UcsManagerDao ucsDao; + @Inject + private ResourceService resourceService; + @Inject + private ClusterDao clusterDao; + @Inject + private ClusterDetailsDao clusterDetailsDao; + @Inject + private UcsBladeDao bladeDao; + + private Map cookies = new HashMap(); + + @Override + public boolean configure(String name, Map params) throws ConfigurationException { + return true; + } + + @Override + public boolean start() { + return true; + } + + @Override + public boolean stop() { + return true; + } + + @Override + public String getName() { + return "UcsManager"; + } + + private void discoverBlades(UcsManagerVO ucsMgrVo) { + List blades = listBlades(ucsMgrVo.getId()); + for (ComputeBlade b : blades) { + UcsBladeVO vo = new UcsBladeVO(); + vo.setDn(b.getDn()); + vo.setUcsManagerId(ucsMgrVo.getId()); + vo.setUuid(UUID.randomUUID().toString()); + bladeDao.persist(vo); + } + } + + @Override + @DB + public AddUcsManagerResponse addUcsManager(AddUcsManagerCmd cmd) { + UcsManagerVO vo = new UcsManagerVO(); + vo.setUuid(UUID.randomUUID().toString()); + vo.setPassword(cmd.getPassword()); + vo.setUrl(cmd.getUrl()); + vo.setUsername(cmd.getUsername()); + vo.setZoneId(cmd.getZoneId()); + vo.setName(cmd.getName()); + + Transaction txn = Transaction.currentTxn(); + txn.start(); + ucsDao.persist(vo); + txn.commit(); + AddUcsManagerResponse rsp = new AddUcsManagerResponse(); + rsp.setId(String.valueOf(vo.getId())); + rsp.setName(vo.getName()); + rsp.setUrl(vo.getUrl()); + rsp.setZoneId(String.valueOf(vo.getZoneId())); + + discoverBlades(vo); + + return rsp; + } + + private String getCookie(Long ucsMgrId) { + try { + String cookie = cookies.get(ucsMgrId); + if (cookie == null) { + UcsManagerVO mgrvo = ucsDao.findById(ucsMgrId); + UcsHttpClient client = new UcsHttpClient(mgrvo.getUrl()); + String login = UcsCommands.loginCmd(mgrvo.getUsername(), mgrvo.getPassword()); + cookie = client.call(login); + cookies.put(ucsMgrId, cookie); + } + + return cookie; + } catch (Exception e) { + throw new CloudRuntimeException("Cannot get cookie", e); + } + } + + private List listBlades(Long ucsMgrId) { + String cookie = getCookie(ucsMgrId); + UcsManagerVO mgrvo = ucsDao.findById(ucsMgrId); + UcsHttpClient client = new UcsHttpClient(mgrvo.getUrl()); + String cmd = UcsCommands.listComputeBlades(cookie); + String ret = client.call(cmd); + return ComputeBlade.fromXmString(ret); + } + + private List getUcsProfiles(Long ucsMgrId) { + String cookie = getCookie(ucsMgrId); + UcsManagerVO mgrvo = ucsDao.findById(ucsMgrId); + String cmd = UcsCommands.listProfiles(cookie); + UcsHttpClient client = new UcsHttpClient(mgrvo.getUrl()); + String res = client.call(cmd); + List profiles = UcsProfile.fromXmlString(res); + return profiles; + } + + @Override + public ListResponse listUcsProfiles(ListUcsProfileCmd cmd) { + List profiles = getUcsProfiles(cmd.getUcsManagerId()); + ListResponse response = new ListResponse(); + List rs = new ArrayList(); + for (UcsProfile p : profiles) { + ListUcsProfileResponse r = new ListUcsProfileResponse(); + r.setObjectName("ucsprofile"); + r.setDn(p.getDn()); + rs.add(r); + } + response.setResponses(rs); + return response; + } + + private String cloneProfile(Long ucsMgrId, String srcDn, String newProfileName) { + UcsManagerVO mgrvo = ucsDao.findById(ucsMgrId); + UcsHttpClient client = new UcsHttpClient(mgrvo.getUrl()); + String cookie = getCookie(ucsMgrId); + String cmd = UcsCommands.cloneProfile(cookie, srcDn, newProfileName); + String res = client.call(cmd); + XmlObject xo = XmlObjectParser.parseFromString(res); + return xo.get("lsClone.outConfig.lsServer.dn"); + } + + private boolean isProfileAssociated(Long ucsMgrId, String dn) { + UcsManagerVO mgrvo = ucsDao.findById(ucsMgrId); + UcsHttpClient client = new UcsHttpClient(mgrvo.getUrl()); + String cookie = getCookie(ucsMgrId); + String cmd = UcsCommands.configResolveDn(cookie, dn); + String res = client.call(cmd); + XmlObject xo = XmlObjectParser.parseFromString(res); + return xo.get("outConfig.lsServer.assocState").equals("associated"); + } + + @Override + public void associateProfileToBlade(AssociateUcsProfileToBladeCmd cmd) { + SearchCriteriaService q = SearchCriteria2.create(UcsBladeVO.class); + q.addAnd(q.getEntity().getUcsManagerId(), Op.EQ, cmd.getUcsManagerId()); + q.addAnd(q.getEntity().getId(), Op.EQ, cmd.getBladeId()); + UcsBladeVO bvo = q.find(); + if (bvo == null) { + throw new IllegalArgumentException(String.format("cannot find UCS blade[id:%s, ucs manager id:%s]", cmd.getBladeId(), cmd.getUcsManagerId())); + } + + if (bvo.getHostId() != null) { + throw new CloudRuntimeException(String.format("blade[id:%s, dn:%s] has been associated with host[id:%s]", bvo.getId(), bvo.getDn(), bvo.getHostId())); + } + + UcsManagerVO mgrvo = ucsDao.findById(cmd.getUcsManagerId()); + String cookie = getCookie(cmd.getUcsManagerId()); + String pdn = cloneProfile(mgrvo.getId(), cmd.getProfileDn(), "profile-for-blade-" + bvo.getId()); + String ucscmd = UcsCommands.associateProfileToBlade(cookie, pdn, bvo.getDn()); + UcsHttpClient client = new UcsHttpClient(mgrvo.getUrl()); + String res = client.call(ucscmd); + int count = 0; + int timeout = 600; + while (count < timeout) { + if (isProfileAssociated(mgrvo.getId(), bvo.getDn())) { + break; + } + + try { + TimeUnit.SECONDS.sleep(2); + } catch (InterruptedException e) { + throw new CloudRuntimeException(e); + } + + count += 2; + } + + if (count >= timeout) { + throw new CloudRuntimeException(String.format("associating profile[%s] to balde[%s] timeout after 600 seconds", pdn, bvo.getDn())); + } + + s_logger.debug(String.format("successfully associated profile[%s] to blade[%s]", pdn, bvo.getDn())); + } + + @Override + public ListResponse listUcsManager(ListUcsManagerCmd cmd) { + SearchCriteriaService serv = SearchCriteria2.create(UcsManagerVO.class); + serv.addAnd(serv.getEntity().getZoneId(), Op.EQ, cmd.getZoneId()); + List vos = serv.list(); + + List rsps = new ArrayList(vos.size()); + for (UcsManagerVO vo : vos) { + ListUcsManagerResponse rsp = new ListUcsManagerResponse(); + rsp.setObjectName("ucsmanager"); + rsp.setId(String.valueOf(vo.getId())); + rsp.setName(vo.getName()); + rsp.setZoneId(String.valueOf(vo.getZoneId())); + rsps.add(rsp); + } + ListResponse response = new ListResponse(); + response.setResponses(rsps); + return response; + } + + @Override + public void setName(String name) { + // TODO Auto-generated method stub + + } + + @Override + public void setConfigParams(Map params) { + // TODO Auto-generated method stub + + } + + @Override + public Map getConfigParams() { + // TODO Auto-generated method stub + return null; + } + + @Override + public int getRunLevel() { + // TODO Auto-generated method stub + return 0; + } + + @Override + public void setRunLevel(int level) { + // TODO Auto-generated method stub + + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/structure/ComputeBlade.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/structure/ComputeBlade.java new file mode 100755 index 00000000000..6251ecf23b2 --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/structure/ComputeBlade.java @@ -0,0 +1,165 @@ +package com.cloud.ucs.structure; + +import java.util.ArrayList; +import java.util.List; + +import com.cloud.utils.xmlobject.XmlObject; +import com.cloud.utils.xmlobject.XmlObjectParser; + +public class ComputeBlade { + String adminPower; + String adminState; + String assignedToDn; + String association; + String availability; + String availableMemory; + String chassisId; + String dn; + String name; + String numOfAdaptors; + String numOfCores; + String numOfCoresEnabled; + String numOfCpus; + String numOfEthHostIfs; + String numOfFcHostIfs; + String numOfThreads; + String operPower; + String totalMemory; + String uuid; + + public static List fromXmString(String xmlstr) { + XmlObject root = XmlObjectParser.parseFromString(xmlstr); + List lst = root.getAsList("configResolveClass.outConfigs.computeBlade"); + List blades = new ArrayList(); + if (lst == null) { + return blades; + } + for (XmlObject xo : lst) { + blades.add(fromXmlObject(xo)); + } + return blades; + } + + public static ComputeBlade fromXmlObject(XmlObject obj) { + ComputeBlade ret = new ComputeBlade(); + return obj.evaluateObject(ret); + } + + public String getAdminPower() { + return adminPower; + } + public void setAdminPower(String adminPower) { + this.adminPower = adminPower; + } + public String getAdminState() { + return adminState; + } + public void setAdminState(String adminState) { + this.adminState = adminState; + } + public String getAssignedToDn() { + return assignedToDn; + } + public void setAssignedToDn(String assignedToDn) { + this.assignedToDn = assignedToDn; + } + public String getAssociation() { + return association; + } + public void setAssociation(String association) { + this.association = association; + } + public String getAvailability() { + return availability; + } + public void setAvailability(String availability) { + this.availability = availability; + } + public String getAvailableMemory() { + return availableMemory; + } + public void setAvailableMemory(String availableMemory) { + this.availableMemory = availableMemory; + } + public String getChassisId() { + return chassisId; + } + public void setChassisId(String chassisId) { + this.chassisId = chassisId; + } + public String getDn() { + return dn; + } + public void setDn(String dn) { + this.dn = dn; + } + public String getName() { + return name; + } + public void setName(String name) { + this.name = name; + } + public String getNumOfAdaptors() { + return numOfAdaptors; + } + public void setNumOfAdaptors(String numOfAdaptors) { + this.numOfAdaptors = numOfAdaptors; + } + public String getNumOfCores() { + return numOfCores; + } + public void setNumOfCores(String numOfCores) { + this.numOfCores = numOfCores; + } + public String getNumOfCoresEnabled() { + return numOfCoresEnabled; + } + public void setNumOfCoresEnabled(String numOfCoresEnabled) { + this.numOfCoresEnabled = numOfCoresEnabled; + } + public String getNumOfCpus() { + return numOfCpus; + } + public void setNumOfCpus(String numOfCpus) { + this.numOfCpus = numOfCpus; + } + public String getNumOfEthHostIfs() { + return numOfEthHostIfs; + } + public void setNumOfEthHostIfs(String numOfEthHostIfs) { + this.numOfEthHostIfs = numOfEthHostIfs; + } + public String getNumOfFcHostIfs() { + return numOfFcHostIfs; + } + public void setNumOfFcHostIfs(String numOfFcHostIfs) { + this.numOfFcHostIfs = numOfFcHostIfs; + } + public String getNumOfThreads() { + return numOfThreads; + } + public void setNumOfThreads(String numOfThreads) { + this.numOfThreads = numOfThreads; + } + public String getOperPower() { + return operPower; + } + public void setOperPower(String operPower) { + this.operPower = operPower; + } + public String getTotalMemory() { + return totalMemory; + } + public void setTotalMemory(String totalMemory) { + this.totalMemory = totalMemory; + } + public String getUuid() { + return uuid; + } + public void setUuid(String uuid) { + this.uuid = uuid; + } + public boolean isAssociated() { + return this.assignedToDn.equals(""); + } +} diff --git a/plugins/hypervisors/ucs/src/com/cloud/ucs/structure/UcsProfile.java b/plugins/hypervisors/ucs/src/com/cloud/ucs/structure/UcsProfile.java new file mode 100755 index 00000000000..b8b2646e13e --- /dev/null +++ b/plugins/hypervisors/ucs/src/com/cloud/ucs/structure/UcsProfile.java @@ -0,0 +1,37 @@ +package com.cloud.ucs.structure; + +import java.util.ArrayList; +import java.util.List; + +import com.cloud.utils.xmlobject.XmlObject; +import com.cloud.utils.xmlobject.XmlObjectParser; + +public class UcsProfile { + private String dn; + + public static UcsProfile fromXmlObject(XmlObject xo) { + UcsProfile p = new UcsProfile(); + return xo.evaluateObject(p); + } + + public static List fromXmlString(String xmlstr) { + List ps = new ArrayList(); + XmlObject xo = XmlObjectParser.parseFromString(xmlstr); + List xos = xo.getAsList("outDns.dn"); + if (xos != null) { + for (XmlObject x : xos) { + UcsProfile p = UcsProfile.fromXmlObject(x); + ps.add(p); + } + } + return ps; + } + + public String getDn() { + return dn; + } + + public void setDn(String dn) { + this.dn = dn; + } +} diff --git a/plugins/pom.xml b/plugins/pom.xml old mode 100644 new mode 100755 index 12c05ca2cec..a3a3189a671 --- a/plugins/pom.xml +++ b/plugins/pom.xml @@ -1,3 +1,4 @@ + - +--> 4.0.0 cloudstack-plugins Apache CloudStack Plugin POM @@ -43,6 +43,7 @@ hypervisors/kvm hypervisors/simulator hypervisors/baremetal + hypervisors/ucs network-elements/elastic-loadbalancer network-elements/ovs network-elements/nicira-nvp diff --git a/utils/src/com/cloud/utils/exception/CloudRuntimeException.java b/utils/src/com/cloud/utils/exception/CloudRuntimeException.java index 3862e2223d6..00141f24122 100755 --- a/utils/src/com/cloud/utils/exception/CloudRuntimeException.java +++ b/utils/src/com/cloud/utils/exception/CloudRuntimeException.java @@ -74,4 +74,8 @@ public class CloudRuntimeException extends RuntimeException { public int getCSErrorCode() { return this.csErrorCode; } + + public CloudRuntimeException(Throwable t) { + super(t); + } } diff --git a/utils/src/com/cloud/utils/xmlobject/XmlObject.java b/utils/src/com/cloud/utils/xmlobject/XmlObject.java new file mode 100755 index 00000000000..fc8043d4702 --- /dev/null +++ b/utils/src/com/cloud/utils/xmlobject/XmlObject.java @@ -0,0 +1,177 @@ +package com.cloud.utils.xmlobject; + +import java.lang.reflect.Field; +import java.util.ArrayList; +import java.util.Collection; +import java.util.HashMap; +import java.util.Iterator; +import java.util.List; +import java.util.Map; + +import com.cloud.utils.exception.CloudRuntimeException; + +import edu.emory.mathcs.backport.java.util.Collections; + +public class XmlObject { + private Map elements = new HashMap(); + private String text; + private String tag; + + XmlObject() { + } + + public XmlObject(String tag) { + this.tag = tag; + } + + public XmlObject putElement(String key, Object e) { + Object old = elements.get(key); + if (old == null) { + System.out.println(String.format("no %s, add new", key)); + elements.put(key, e); + } else { + if (old instanceof List) { + System.out.println(String.format("already list %s, add", key)); + ((List)old).add(e); + } else { + System.out.println(String.format("not list list %s, add list", key)); + List lst = new ArrayList(); + lst.add(old); + lst.add(e); + elements.put(key, lst); + } + } + + return this; + } + + private Object recurGet(XmlObject obj, Iterator it) { + String key = it.next(); + Object e = obj.elements.get(key); + if (e == null) { + return null; + } + + if (!it.hasNext()) { + return e; + } else { + if (!(e instanceof XmlObject)) { + throw new CloudRuntimeException(String.format("%s doesn't reference to a XmlObject", it.next())); + } + return recurGet((XmlObject) e, it); + } + } + + public T get(String elementStr) { + String[] strs = elementStr.split("\\."); + List lst = new ArrayList(strs.length); + Collections.addAll(lst, strs); + return (T)recurGet(this, lst.iterator()); + } + + public List getAsList(String elementStr) { + Object e = get(elementStr); + if (e instanceof List) { + return (List)e; + } + List lst = new ArrayList(1); + lst.add(e); + return lst; + } + + public String getText() { + return text; + } + + public XmlObject setText(String text) { + this.text = text; + return this; + } + + public String getTag() { + return tag; + } + + public XmlObject setTag(String tag) { + this.tag = tag; + return this; + } + + public String dump() { + StringBuilder sb = new StringBuilder(); + sb.append("<").append(tag); + List children = new ArrayList(); + for (Map.Entry e : elements.entrySet()) { + String key = e.getKey(); + Object val = e.getValue(); + if (val instanceof String) { + sb.append(String.format(" %s=\"%s\"", key, val.toString())); + } else if (val instanceof XmlObject) { + children.add((XmlObject) val); + } else if (val instanceof List) { + children.addAll((Collection) val); + } else { + throw new CloudRuntimeException(String.format("unsupported element type[tag:%s, class: %s], only allowed type of [String, List, Object]", key, val.getClass().getName())); + } + } + + if (!children.isEmpty() && text != null) { + throw new CloudRuntimeException(String.format("element %s cannot have both text[%s] and child elements", tag, text)); + } + + if (!children.isEmpty()) { + sb.append(">"); + for (XmlObject x : children) { + sb.append(x.dump()); + } + sb.append(String.format("", tag)); + } else { + if (text != null) { + sb.append(">"); + sb.append(text); + sb.append(String.format("", tag)); + } else { + sb.append(" />"); + } + } + return sb.toString(); + } + + @Override + public String toString() { + StringBuilder sb = new StringBuilder("<" + tag); + for (Map.Entry e : elements.entrySet()) { + String key = e.getKey(); + Object value = e.getValue(); + if (!(value instanceof String)) { + continue; + } + sb.append(String.format(" %s=\"%s\"", key, value.toString())); + } + + if (text == null || "".equals(text.trim())) { + sb.append(" />"); + } else { + sb.append(">").append(text).append(String.format("", tag)); + } + return sb.toString(); + } + + public T evaluateObject(T obj) { + Class clazz = obj.getClass(); + try { + do { + Field[] fs = clazz.getDeclaredFields(); + for (Field f : fs) { + f.setAccessible(true); + Object value = get(f.getName()); + f.set(obj, value); + } + clazz = clazz.getSuperclass(); + } while (clazz != null && clazz != Object.class); + return obj; + } catch (Exception e) { + throw new CloudRuntimeException(e); + } + } +} diff --git a/utils/src/com/cloud/utils/xmlobject/XmlObjectParser.java b/utils/src/com/cloud/utils/xmlobject/XmlObjectParser.java new file mode 100755 index 00000000000..68a822f5429 --- /dev/null +++ b/utils/src/com/cloud/utils/xmlobject/XmlObjectParser.java @@ -0,0 +1,107 @@ +package com.cloud.utils.xmlobject; + +import java.io.ByteArrayInputStream; +import java.io.File; +import java.io.FileInputStream; +import java.io.FileNotFoundException; +import java.io.InputStream; +import java.util.Stack; + +import javax.xml.parsers.SAXParser; +import javax.xml.parsers.SAXParserFactory; + +import org.xml.sax.Attributes; +import org.xml.sax.SAXException; +import org.xml.sax.helpers.DefaultHandler; + +import com.cloud.utils.exception.CloudRuntimeException; + +public class XmlObjectParser { + final private InputStream is; + + private class XmlHandler extends DefaultHandler { + private Stack stack; + private String currentValue; + private XmlObject root; + + XmlHandler() { + stack = new Stack(); + } + + @Override + public void startElement(String namespaceURI, String localName, String qName, Attributes atts) throws SAXException { + //System.out.println(String.format("startElement: namespaceURI:%s, localName:%s, qName:%s", namespaceURI, localName, qName)); + currentValue = null; + XmlObject obj = new XmlObject(); + for (int i=0; i lst = xo.get("management-server.adapters"); + for (XmlObject x : lst) { + List lst1 = x.getAsList("adapter"); + for (XmlObject y : lst1) { + p(y.toString()); + } + } + } + +} diff --git a/utils/test/com/cloud/utils/xmlobject/TestXmlObject2.java b/utils/test/com/cloud/utils/xmlobject/TestXmlObject2.java new file mode 100755 index 00000000000..ccef3aa7f6d --- /dev/null +++ b/utils/test/com/cloud/utils/xmlobject/TestXmlObject2.java @@ -0,0 +1,37 @@ +package com.cloud.utils.xmlobject; + +import static org.junit.Assert.*; + +import org.junit.Test; + +public class TestXmlObject2 { + void p(String str) { + System.out.println(str); + } + + XmlObject xo(String name) { + return new XmlObject(name); + } + + @Test + public void test() { + XmlObject root = new XmlObject("test"); + root.putElement("key1", "value1").putElement("key2", "value2"); + p(root.dump()); + + XmlObject c1 = new XmlObject("child1"); + XmlObject c2 = new XmlObject("child2"); + c2.putElement("ckey1", "value1"); + c1.putElement(c2.getTag(), c2); + root.putElement(c1.getTag(), c1); + p(root.dump()); + + root = xo("test2").putElement("key1", "value1").putElement("child1", xo("child1").setText("yyy")) + .putElement("child1", xo("child1") + .putElement("child2", xo("child2") + .putElement("child3", xo("child3").putElement("key3", "value3").setText("xxxxx")))); + + p(root.dump()); + } + +}