From afd79a9b1bbf0ffaf06c5fc27a006c984e7d1748 Mon Sep 17 00:00:00 2001 From: alena Date: Tue, 19 Oct 2010 09:50:13 -0700 Subject: [PATCH 01/13] Code cleanup --- server/src/com/cloud/api/doc/ApiXmlDocReader.java | 3 --- server/src/com/cloud/api/doc/ApiXmlDocWriter.java | 3 --- 2 files changed, 6 deletions(-) diff --git a/server/src/com/cloud/api/doc/ApiXmlDocReader.java b/server/src/com/cloud/api/doc/ApiXmlDocReader.java index b4f3f1f4680..b5b19937073 100644 --- a/server/src/com/cloud/api/doc/ApiXmlDocReader.java +++ b/server/src/com/cloud/api/doc/ApiXmlDocReader.java @@ -236,14 +236,11 @@ public class ApiXmlDocReader { } } - - out.close(); } catch (IOException e) { e.printStackTrace(); } - } } diff --git a/server/src/com/cloud/api/doc/ApiXmlDocWriter.java b/server/src/com/cloud/api/doc/ApiXmlDocWriter.java index aed4f87669c..922819f0409 100644 --- a/server/src/com/cloud/api/doc/ApiXmlDocWriter.java +++ b/server/src/com/cloud/api/doc/ApiXmlDocWriter.java @@ -129,7 +129,6 @@ public class ApiXmlDocWriter { // //Get fields from superclass Class superClass = clas.getSuperclass(); String superName = superClass.getName(); -// while (BaseCmd.class.isAssignableFrom(superClass) && !superClass.getName().equals(BaseCmd.class.getName())) { if (!superName.equals(BaseCmd.class.getName()) && !superName.equals(BaseAsyncCmd.class.getName()) && !superName.equals(BaseAsyncCreateCmd.class.getName())) { Field[] superClassFields = superClass.getDeclaredFields(); if (superClassFields != null) { @@ -140,8 +139,6 @@ public class ApiXmlDocWriter { } superClass = superClass.getSuperclass(); } - -// } for (Field f : fields) { Parameter parameterAnnotation = f.getAnnotation(Parameter.class); From dadfdc93e342390e56d782edf51ae5cd6a9dcc3a Mon Sep 17 00:00:00 2001 From: alena Date: Tue, 26 Oct 2010 11:09:30 -0700 Subject: [PATCH 02/13] Added package-tools target to package.xml --- build/package.xml | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/build/package.xml b/build/package.xml index 0cac5782a98..b5e571a6574 100755 --- a/build/package.xml +++ b/build/package.xml @@ -207,6 +207,13 @@ + + + + + + + From 233675b53d99afb9065d0751bacd01d6cb491fd9 Mon Sep 17 00:00:00 2001 From: Jessica Wang Date: Tue, 26 Oct 2010 14:11:35 -0700 Subject: [PATCH 03/13] new UI - keep middle menu and its content when host page or primary storage page is loaded into right panel. --- ui/new/scripts/cloud.core2.resource.js | 39 +++++++++++++++----------- 1 file changed, 23 insertions(+), 16 deletions(-) diff --git a/ui/new/scripts/cloud.core2.resource.js b/ui/new/scripts/cloud.core2.resource.js index 4c34dae8391..319359dbe10 100644 --- a/ui/new/scripts/cloud.core2.resource.js +++ b/ui/new/scripts/cloud.core2.resource.js @@ -191,8 +191,7 @@ function clusterJSONToTreeNode(json, $clusterNode) { } //$menuItem1 is either $leftmenuItem1 or $midmenuItem1 -function showPage($pageToShow, $menuItem1) { - clearMiddleMenu(); +function showPage($pageToShow, $menuItem1) { if($pageToShow.length == 0) { //resource.jsp is not loaded in right panel $("#right_panel").load("jsp/resource.jsp", function(){ showPage2($($pageToShow.selector), $menuItem1); //$pageToShow is still empty (i.e. $pageToShow.length == 0), So, select the element again. @@ -223,11 +222,16 @@ function showPage2($pageToShow, $menuItem1) { $pageToShow.data("jsonObj", jsonObj); } - if($pageToShow.attr("id") == "resource_page") { + if($pageToShow.attr("id") == "resource_page") { + clearMiddleMenu(); + hideMiddleMenu(); + initAddZoneButton($("#midmenu_add_link")); initDialog("dialog_add_zone"); } - else if($pageToShow.attr("id") == "zone_page") { + else if($pageToShow.attr("id") == "zone_page") { + hideMiddleMenu(); + initAddPodButton($("#midmenu_add_link")); initAddVLANButton($("#midmenu_add2_link")); initAddSecondaryStorageButton($("#midmenu_add3_link")); @@ -249,11 +253,12 @@ function showPage2($pageToShow, $menuItem1) { //var afterSwitchFnArray = [afterSwitchToDetailsTab, afterSwitchToNetworkTab, afterSwitchToSecondaryStorageTab]; switchBetweenDifferentTabs(tabArray, tabContentArray); $zonePage.find("#tab_details").click(); - - hideMiddleMenu(); + zoneJsonToRightPanel($menuItem1); } - else if($pageToShow.attr("id") == "pod_page") { + else if($pageToShow.attr("id") == "pod_page") { + hideMiddleMenu(); + initAddHostButton($("#midmenu_add_link")); initAddPrimaryStorageButton($("#midmenu_add2_link")); @@ -264,21 +269,22 @@ function showPage2($pageToShow, $menuItem1) { if (getHypervisorType() == 'kvm') $("#dialog_add_pool").find("#add_pool_protocol").empty().html(''); bindEventHandlerToDialogAddPool(); - - showMiddleMenu(); + podJsonToRightPanel($menuItem1); - var podId = jsonObj.id; - $("#midmenu_container").empty(); - listMidMenuItems2(("listHosts&type=Routing&podid="+podId), "listhostsresponse", "host", hostToMidmenu, hostToRightPanel, hostGetMidmenuId, false, false); - listMidMenuItems2(("listStoragePools&podid="+podId), "liststoragepoolsresponse", "storagepool", primarystorageToMidmenu, primarystorageToRightPanel, primarystorageGetMidmenuId, false, false); + //var podId = jsonObj.id; + //$("#midmenu_container").empty(); + //listMidMenuItems2(("listHosts&type=Routing&podid="+podId), "listhostsresponse", "host", hostToMidmenu, hostToRightPanel, hostGetMidmenuId, false, false); + //listMidMenuItems2(("listStoragePools&podid="+podId), "liststoragepoolsresponse", "storagepool", primarystorageToMidmenu, primarystorageToRightPanel, primarystorageGetMidmenuId, false, false); } else if($pageToShow.attr("id") == "cluster_page") { + clearMiddleMenu(); + showMiddleMenu(); + $("#midmenu_add_link").unbind("click").hide(); $("#midmenu_add2_link").unbind("click").hide(); - $("#midmenu_add3_link").unbind("click").hide(); - - showMiddleMenu(); + $("#midmenu_add3_link").unbind("click").hide(); + clusterJsonToRightPanel($menuItem1); var clusterId = jsonObj.id; @@ -1304,6 +1310,7 @@ function initAddHostButton($midmenuAddLink1) { $thisDialog.find("#spinning_wheel").hide(); $thisDialog.dialog("close"); + showMiddleMenu(); var $midmenuItem1 = $("#midmenu_item").clone(); $("#midmenu_container").append($midmenuItem1.fadeIn("slow")); var items = json.addhostresponse.host; From f0fd34c5b4facfadbfaa2000ff76d36d07bce895 Mon Sep 17 00:00:00 2001 From: NIKITA Date: Tue, 26 Oct 2010 14:11:35 -0700 Subject: [PATCH 04/13] Ui added to error msgs whown in protforwarding and text field has been reduced --- ui/new/css/main.css | 24 ++++++++++++++++++++++++ ui/new/jsp/ipaddress.jsp | 14 +++++++------- 2 files changed, 31 insertions(+), 7 deletions(-) diff --git a/ui/new/css/main.css b/ui/new/css/main.css index b1b2738e638..81e4e53561b 100644 --- a/ui/new/css/main.css +++ b/ui/new/css/main.css @@ -2448,6 +2448,30 @@ a:hover.search_button { color:#333; font-size:11px; } +.grid_row_cell .error_text { + width:92%; + height:16px; + float:left; + margin:0 0 0 10px; + display:inline; + padding:0 0 0 2px; + border:1px solid #999; + background:#ffe5e5; + color:#333; + font-size:11px; +} + +.errormsg { + width:80%; + height:auto; + float:left; + margin:3px 0 0 10px; + display:inline; + padding:0 0 0 2px; + color:#a90000; + font-size:11px; + font-weight:normal; +} .grid_row_cell .select { width:92%; diff --git a/ui/new/jsp/ipaddress.jsp b/ui/new/jsp/ipaddress.jsp index 1526309e42f..875a1eb2f8d 100644 --- a/ui/new/jsp/ipaddress.jsp +++ b/ui/new/jsp/ipaddress.jsp @@ -166,15 +166,15 @@
- +
- +
- @@ -220,19 +220,19 @@
- +
- +
- +
- From 822ee2d8993dc56e47d4912ab757c696bb90d6c9 Mon Sep 17 00:00:00 2001 From: abhishek Date: Mon, 25 Oct 2010 17:51:39 -0700 Subject: [PATCH 05/13] more changes for the console proxy custom certificate part; some code cleanup as well as event generation with console proxy reboot logic --- .../consoleproxy/ConsoleProxyResource.java | 25 ++++++----- core/src/com/cloud/host/dao/HostDao.java | 4 +- core/src/com/cloud/host/dao/HostDaoImpl.java | 21 ++++++++- .../cloud/server/ManagementServerImpl.java | 45 +++++++++++++------ 4 files changed, 68 insertions(+), 27 deletions(-) diff --git a/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java b/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java index ebc86633f8c..e9bab07ffdf 100644 --- a/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java +++ b/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java @@ -113,27 +113,30 @@ public class ConsoleProxyResource extends ServerResourceBase implements ServerRe String certificate = cmd.getCertificate(); //write the cert to /etc/cloud/consoleproxy/cert/ - String strDirectoy ="/etc/cloud/consoleproxy/cert/"; - boolean dirCreated = (new File(strDirectoy)).mkdir(); - if (dirCreated) { - s_logger.info("Directory: " + strDirectoy + " created"); + String strDirectoy = null; + boolean dirCreated = false; + + strDirectoy = "/etc/cloud/consoleproxy/cert/"; + dirCreated = (new File(strDirectoy)).mkdirs(); + + if (dirCreated) + { + s_logger.info("Directory: " + strDirectoy + " created"); - //copy cert to the dir - try { + //copy cert to the dir FileWriter fstream = new FileWriter("/etc/cloud/consoleproxy/cert/customcert"); BufferedWriter out = new BufferedWriter(fstream); out.write(certificate); //Close the output stream out.close(); - }catch (Exception e){ - s_logger.warn("Unable to write file to /etc/cloud/consoleproxy/cert/ on console proxy", e); - } + success = true; } - success = true; + return new Answer(cmd, success, "Cert string in the console proxy resource status:"); }catch (Exception e) { - s_logger.error("Unable to read the cert string in console proxy resource"); + s_logger.error("Unable to read the cert string in console proxy resource",e); + success = false; } return new Answer(cmd, success, "Cert string in the console proxy resource status:"); } diff --git a/core/src/com/cloud/host/dao/HostDao.java b/core/src/com/cloud/host/dao/HostDao.java index 78eeea89bfb..b68d7755245 100644 --- a/core/src/com/cloud/host/dao/HostDao.java +++ b/core/src/com/cloud/host/dao/HostDao.java @@ -135,7 +135,9 @@ public interface HostDao extends GenericDao { long getNextSequence(long hostId); - void loadDetails(HostVO host); + void loadDetails(HostVO host); + + HostVO findConsoleProxyHost(String name, Type type); } diff --git a/core/src/com/cloud/host/dao/HostDaoImpl.java b/core/src/com/cloud/host/dao/HostDaoImpl.java index 47d3134e0b6..3acc97db6a5 100644 --- a/core/src/com/cloud/host/dao/HostDaoImpl.java +++ b/core/src/com/cloud/host/dao/HostDaoImpl.java @@ -79,6 +79,7 @@ public class HostDaoImpl extends GenericDaoBase implements HostDao protected final SearchBuilder UnmanagedDirectConnectSearch; protected final SearchBuilder MaintenanceCountSearch; protected final SearchBuilder ClusterSearch; + protected final SearchBuilder ConsoleProxyHostSearch; protected final Attribute _statusAttr; protected final Attribute _msIdAttr; @@ -154,6 +155,11 @@ public class HostDaoImpl extends GenericDaoBase implements HostDao ClusterSearch = createSearchBuilder(); ClusterSearch.and("cluster", ClusterSearch.entity().getClusterId(), SearchCriteria.Op.EQ); ClusterSearch.done(); + + ConsoleProxyHostSearch = createSearchBuilder(); + ConsoleProxyHostSearch.and("name", ConsoleProxyHostSearch.entity().getName(), SearchCriteria.Op.EQ); + ConsoleProxyHostSearch.and("type", ConsoleProxyHostSearch.entity().getType(), SearchCriteria.Op.EQ); + ConsoleProxyHostSearch.done(); PodSearch = createSearchBuilder(); PodSearch.and("pod", PodSearch.entity().getPodId(), SearchCriteria.Op.EQ); @@ -442,7 +448,20 @@ public class HostDaoImpl extends GenericDaoBase implements HostDao SearchCriteria sc = DcSearch.create("dc", dcId); return listBy(sc); } - + + @Override + public HostVO findConsoleProxyHost(String name, Type type) { + SearchCriteria sc = ConsoleProxyHostSearch.create(); + sc.setParameters("name", name); + sc.setParameters("type", type); + ListhostList = listBy(sc); + + if(hostList==null || hostList.size() == 0) + return null; + else + return hostList.get(0); + } + public List listByHostPod(long podId) { SearchCriteria sc = PodSearch.create("pod", podId); return listBy(sc); diff --git a/server/src/com/cloud/server/ManagementServerImpl.java b/server/src/com/cloud/server/ManagementServerImpl.java index d1df3adbf23..bcd2a37d0e2 100755 --- a/server/src/com/cloud/server/ManagementServerImpl.java +++ b/server/src/com/cloud/server/ManagementServerImpl.java @@ -174,6 +174,7 @@ import com.cloud.dc.dao.PodVlanMapDao; import com.cloud.dc.dao.VlanDao; import com.cloud.domain.DomainVO; import com.cloud.domain.dao.DomainDao; +import com.cloud.event.EventState; import com.cloud.event.EventTypes; import com.cloud.event.EventUtils; import com.cloud.event.EventVO; @@ -6931,6 +6932,18 @@ public class ManagementServerImpl implements ManagementServer { } return version; } + + private Long saveScheduledEvent(Long userId, Long accountId, String type, String description) + { + EventVO event = new EventVO(); + event.setUserId(userId); + event.setAccountId(accountId); + event.setType(type); + event.setState(EventState.Scheduled); + event.setDescription("Scheduled async job for "+description); + event = _eventDao.persist(event); + return event.getId(); + } @Override public boolean uploadCertificate(UploadCustomCertificateCmd cmd) { @@ -6940,32 +6953,36 @@ public class ManagementServerImpl implements ManagementServer { if (certVOId!=null && certVOId!=0) { //certficate uploaded to db successfully - //get a list of all hosts from host table - List hosts = _hostDao.listAll(); + //get a list of all Console proxies from the cp table + List cpList = _consoleProxyDao.listAll(); - List consoleProxyList = new ArrayList(); - - //find the console proxies, and send the command to them - for(HostVO host : hosts) { - if(host.getType().equals(com.cloud.host.Host.Type.ConsoleProxy)){ - consoleProxyList.add(host); - } - } - - for(HostVO consoleProxy : consoleProxyList){ + for(ConsoleProxyVO cp : cpList) + { + HostVO cpHost = _hostDao.findConsoleProxyHost(cp.getName(), com.cloud.host.Host.Type.ConsoleProxy); + //now send a command to each console proxy UpdateCertificateCommand certCmd = new UpdateCertificateCommand(_certDao.findById(certVOId).getCertificate()); try { - Answer updateCertAns = _agentMgr.send(consoleProxy.getId(), certCmd); + Answer updateCertAns = _agentMgr.send(cpHost.getId(), certCmd); + + if(updateCertAns.getResult() == true) + { + //we have the cert copied over on cpvm + long eventId = saveScheduledEvent(User.UID_SYSTEM, Account.ACCOUNT_ID_SYSTEM, EventTypes.EVENT_PROXY_REBOOT, "stopping console proxy with Id: "+cp.getId()); + boolean cpReboot = _consoleProxyMgr.rebootProxy(cp.getId(), eventId); + //when cp reboots, the context will be reinit with the new cert + } } catch (AgentUnavailableException e) { s_logger.warn("Unable to send command to the console proxy resource", e); } catch (OperationTimedoutException e) { s_logger.warn("Unable to send command to the console proxy resource", e); } + } + } - return false; + return true; } @Override From cb4a80b8acc0b522107829ecd6c4e127ceb7134e Mon Sep 17 00:00:00 2001 From: abhishek Date: Mon, 25 Oct 2010 18:41:26 -0700 Subject: [PATCH 06/13] starting off with the listener logic.This will ensure that every new console proxy vm that starts, will potentially look for any custom certs uploaded to our db. If they exist, we will send a command to the agent, so that the cert is uploaded, and the ssl context is re-initialized. --- .../consoleproxy/ConsoleProxyResource.java | 9 ++++----- .../cloud/server/ManagementServerImpl.java | 20 ++++++++++--------- setup/db/create-schema.sql | 2 +- 3 files changed, 16 insertions(+), 15 deletions(-) diff --git a/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java b/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java index e9bab07ffdf..12443c1a17f 100644 --- a/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java +++ b/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java @@ -121,8 +121,8 @@ public class ConsoleProxyResource extends ServerResourceBase implements ServerRe if (dirCreated) { - s_logger.info("Directory: " + strDirectoy + " created"); - + if(s_logger.isDebugEnabled()) + s_logger.info("Directory: " + strDirectoy + " created"); //copy cert to the dir FileWriter fstream = new FileWriter("/etc/cloud/consoleproxy/cert/customcert"); BufferedWriter out = new BufferedWriter(fstream); @@ -131,14 +131,13 @@ public class ConsoleProxyResource extends ServerResourceBase implements ServerRe out.close(); success = true; } - - return new Answer(cmd, success, "Cert string in the console proxy resource status:"); + return new Answer(cmd, success, "Custom certificate update required status"); }catch (Exception e) { s_logger.error("Unable to read the cert string in console proxy resource",e); success = false; } - return new Answer(cmd, success, "Cert string in the console proxy resource status:"); + return new Answer(cmd, success, "Custom certificate response from the updatecertificate flow"); } protected Answer execute(final CheckConsoleProxyLoadCommand cmd) { diff --git a/server/src/com/cloud/server/ManagementServerImpl.java b/server/src/com/cloud/server/ManagementServerImpl.java index bcd2a37d0e2..7b3caf4e962 100755 --- a/server/src/com/cloud/server/ManagementServerImpl.java +++ b/server/src/com/cloud/server/ManagementServerImpl.java @@ -6950,9 +6950,9 @@ public class ManagementServerImpl implements ManagementServer { String certificatePath = cmd.getPath(); Long certVOId = _certDao.persistCustomCertToDb(certificatePath);//0 implies failure - if (certVOId!=null && certVOId!=0) { - //certficate uploaded to db successfully - + if (certVOId!=null && certVOId!=0) + { + //certficate uploaded to db successfully //get a list of all Console proxies from the cp table List cpList = _consoleProxyDao.listAll(); @@ -6964,12 +6964,11 @@ public class ManagementServerImpl implements ManagementServer { UpdateCertificateCommand certCmd = new UpdateCertificateCommand(_certDao.findById(certVOId).getCertificate()); try { Answer updateCertAns = _agentMgr.send(cpHost.getId(), certCmd); - if(updateCertAns.getResult() == true) { //we have the cert copied over on cpvm - long eventId = saveScheduledEvent(User.UID_SYSTEM, Account.ACCOUNT_ID_SYSTEM, EventTypes.EVENT_PROXY_REBOOT, "stopping console proxy with Id: "+cp.getId()); - boolean cpReboot = _consoleProxyMgr.rebootProxy(cp.getId(), eventId); + long eventId = saveScheduledEvent(User.UID_SYSTEM, Account.ACCOUNT_ID_SYSTEM, EventTypes.EVENT_PROXY_REBOOT, "rebooting console proxy with Id: "+cp.getId()); + _consoleProxyMgr.rebootProxy(cp.getId(), eventId); //when cp reboots, the context will be reinit with the new cert } } catch (AgentUnavailableException e) { @@ -6979,10 +6978,13 @@ public class ManagementServerImpl implements ManagementServer { } } - + + return true; + } + else + { + return false; } - - return true; } @Override diff --git a/setup/db/create-schema.sql b/setup/db/create-schema.sql index 3f2b97dff4d..69b0c5d800c 100755 --- a/setup/db/create-schema.sql +++ b/setup/db/create-schema.sql @@ -118,7 +118,7 @@ CREATE TABLE `cloud`.`account_network_ref` ( CREATE TABLE `cloud`.`certificate` ( `id` bigint unsigned NOT NULL AUTO_INCREMENT COMMENT 'id', - `certificate` text COMMENT 'the actual custom certificate being stored in the db', + `certificate` text NOT NULL UNIQUE COMMENT 'the actual custom certificate being stored in the db', PRIMARY KEY (`id`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8; From f64abad8f5110da3a99b60a723ac9b7375d3318f Mon Sep 17 00:00:00 2001 From: abhishek Date: Tue, 26 Oct 2010 11:04:51 -0700 Subject: [PATCH 07/13] completed the listener logic. Based on the startup command, we will try and update a cust cert to a new running cpvm, and fail if such a cert doesn't exist in the cert table in our db. --- .../consoleproxy/ConsoleProxyResource.java | 4 +- .../AgentBasedConsoleProxyManager.java | 17 +++++- .../src/com/cloud/consoleproxy/AgentHook.java | 2 + .../consoleproxy/ConsoleProxyListener.java | 5 ++ .../consoleproxy/ConsoleProxyManagerImpl.java | 59 ++++++++++++++++++- .../cloud/server/ManagementServerImpl.java | 4 +- 6 files changed, 81 insertions(+), 10 deletions(-) diff --git a/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java b/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java index 12443c1a17f..7ae873581d8 100644 --- a/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java +++ b/agent/src/com/cloud/agent/resource/consoleproxy/ConsoleProxyResource.java @@ -113,10 +113,8 @@ public class ConsoleProxyResource extends ServerResourceBase implements ServerRe String certificate = cmd.getCertificate(); //write the cert to /etc/cloud/consoleproxy/cert/ - String strDirectoy = null; boolean dirCreated = false; - - strDirectoy = "/etc/cloud/consoleproxy/cert/"; + String strDirectoy = "/etc/cloud/consoleproxy/cert/"; dirCreated = (new File(strDirectoy)).mkdirs(); if (dirCreated) diff --git a/server/src/com/cloud/consoleproxy/AgentBasedConsoleProxyManager.java b/server/src/com/cloud/consoleproxy/AgentBasedConsoleProxyManager.java index 875d535941e..0968cbf2f91 100644 --- a/server/src/com/cloud/consoleproxy/AgentBasedConsoleProxyManager.java +++ b/server/src/com/cloud/consoleproxy/AgentBasedConsoleProxyManager.java @@ -34,9 +34,11 @@ import com.cloud.agent.api.ConsoleProxyLoadReportCommand; import com.cloud.agent.api.GetVncPortAnswer; import com.cloud.agent.api.GetVncPortCommand; import com.cloud.agent.api.StartupCommand; +import com.cloud.agent.api.StartupProxyCommand; import com.cloud.agent.api.StopCommand; import com.cloud.api.ServerApiException; import com.cloud.api.commands.DestroyConsoleProxyCmd; +import com.cloud.certificate.dao.CertificateDao; import com.cloud.configuration.dao.ConfigurationDao; import com.cloud.exception.AgentUnavailableException; import com.cloud.exception.ConcurrentOperationException; @@ -48,6 +50,7 @@ import com.cloud.host.HostVO; import com.cloud.host.Status; import com.cloud.host.dao.HostDao; import com.cloud.info.ConsoleProxyInfo; +import com.cloud.server.ManagementServer; import com.cloud.utils.NumbersUtil; import com.cloud.utils.component.ComponentLocator; import com.cloud.utils.component.Inject; @@ -57,8 +60,10 @@ import com.cloud.vm.VMInstanceVO; import com.cloud.vm.VirtualMachine.Type; import com.cloud.vm.VirtualMachineManager; import com.cloud.vm.VirtualMachineName; +import com.cloud.vm.dao.ConsoleProxyDao; import com.cloud.vm.dao.UserVmDao; import com.cloud.vm.dao.VMInstanceDao; +import com.sun.org.apache.xml.internal.security.keys.content.MgmtData; @Local(value = { ConsoleProxyManager.class }) public class AgentBasedConsoleProxyManager implements ConsoleProxyManager, VirtualMachineManager, AgentHook { @@ -74,13 +79,13 @@ public class AgentBasedConsoleProxyManager implements ConsoleProxyManager, Virtu @Inject private VMInstanceDao _instanceDao; private ConsoleProxyListener _listener; - protected int _consoleProxyUrlPort = ConsoleProxyManager.DEFAULT_PROXY_URL_PORT; protected int _consoleProxyPort = ConsoleProxyManager.DEFAULT_PROXY_VNC_PORT; protected boolean _sslEnabled = false; @Inject AgentManager _agentMgr; - + @Inject + protected ConsoleProxyDao _cpDao; public int getVncPort(VMInstanceVO vm) { if (vm.getHostId() == null) { return -1; @@ -324,5 +329,11 @@ public class AgentBasedConsoleProxyManager implements ConsoleProxyManager, Virtu @Override public boolean destroyConsoleProxy(DestroyConsoleProxyCmd cmd) throws ServerApiException { return false; - } + } + + @Override + public boolean applyCustomCertToNewProxy(StartupProxyCommand cmd) { + // TODO Auto-generated method stub + return false; + } } diff --git a/server/src/com/cloud/consoleproxy/AgentHook.java b/server/src/com/cloud/consoleproxy/AgentHook.java index a25e555e92f..4874718e218 100644 --- a/server/src/com/cloud/consoleproxy/AgentHook.java +++ b/server/src/com/cloud/consoleproxy/AgentHook.java @@ -7,6 +7,7 @@ import com.cloud.agent.api.AgentControlAnswer; import com.cloud.agent.api.ConsoleAccessAuthenticationCommand; import com.cloud.agent.api.ConsoleProxyLoadReportCommand; import com.cloud.agent.api.StartupCommand; +import com.cloud.agent.api.StartupProxyCommand; import com.cloud.host.HostVO; import com.cloud.host.Status; @@ -16,4 +17,5 @@ public interface AgentHook { void onAgentConnect(HostVO host, StartupCommand cmd); public void onAgentDisconnect(long agentId, Status state); + boolean applyCustomCertToNewProxy(StartupProxyCommand cmd); } diff --git a/server/src/com/cloud/consoleproxy/ConsoleProxyListener.java b/server/src/com/cloud/consoleproxy/ConsoleProxyListener.java index ef653085f23..61bdc14147b 100644 --- a/server/src/com/cloud/consoleproxy/ConsoleProxyListener.java +++ b/server/src/com/cloud/consoleproxy/ConsoleProxyListener.java @@ -25,6 +25,7 @@ import com.cloud.agent.api.Command; import com.cloud.agent.api.ConsoleAccessAuthenticationCommand; import com.cloud.agent.api.ConsoleProxyLoadReportCommand; import com.cloud.agent.api.StartupCommand; +import com.cloud.agent.api.StartupProxyCommand; import com.cloud.host.HostVO; import com.cloud.host.Status; @@ -66,6 +67,10 @@ public class ConsoleProxyListener implements Listener { @Override public void processConnect(HostVO host, StartupCommand cmd) { _proxyMgr.onAgentConnect(host, cmd); + + if (cmd instanceof StartupProxyCommand) { + _proxyMgr.applyCustomCertToNewProxy((StartupProxyCommand)cmd); + } } @Override diff --git a/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java b/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java index 875d7fe483f..5315b6bf856 100644 --- a/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java +++ b/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java @@ -56,9 +56,11 @@ import com.cloud.agent.api.Start2Command; import com.cloud.agent.api.StartConsoleProxyAnswer; import com.cloud.agent.api.StartConsoleProxyCommand; import com.cloud.agent.api.StartupCommand; +import com.cloud.agent.api.StartupProxyCommand; import com.cloud.agent.api.StopAnswer; import com.cloud.agent.api.StopCommand; import com.cloud.agent.api.proxy.ConsoleProxyLoadAnswer; +import com.cloud.agent.api.proxy.UpdateCertificateCommand; import com.cloud.agent.api.to.NicTO; import com.cloud.agent.api.to.VirtualMachineTO; import com.cloud.agent.api.to.VirtualMachineTO.SshMonitor; @@ -70,6 +72,8 @@ import com.cloud.async.AsyncJobExecutor; import com.cloud.async.AsyncJobManager; import com.cloud.async.AsyncJobVO; import com.cloud.async.BaseAsyncJobExecutor; +import com.cloud.certificate.CertificateVO; +import com.cloud.certificate.dao.CertificateDao; import com.cloud.cluster.ClusterManager; import com.cloud.configuration.Config; import com.cloud.configuration.dao.ConfigurationDao; @@ -117,6 +121,7 @@ import com.cloud.network.dao.IPAddressDao; import com.cloud.offering.NetworkOffering; import com.cloud.offerings.NetworkOfferingVO; import com.cloud.offerings.dao.NetworkOfferingDao; +import com.cloud.server.ManagementServer; import com.cloud.service.ServiceOfferingVO; import com.cloud.service.dao.ServiceOfferingDao; import com.cloud.servlet.ConsoleProxyServlet; @@ -165,6 +170,7 @@ import com.cloud.vm.dao.ConsoleProxyDao; import com.cloud.vm.dao.VMInstanceDao; import com.google.gson.Gson; import com.google.gson.GsonBuilder; +import com.sun.org.apache.xml.internal.security.keys.content.MgmtData; // // Possible console proxy state transition cases @@ -229,12 +235,12 @@ public class ConsoleProxyManagerImpl implements ConsoleProxyManager, VirtualMach private HostDao _hostDao; @Inject private ConfigurationDao _configDao; - + @Inject + private CertificateDao _certDao; @Inject private VMInstanceDao _instanceDao; @Inject private AccountDao _accountDao; - @Inject private VMTemplateHostDao _vmTemplateHostDao; @Inject private AgentManager _agentMgr; @Inject private StorageManager _storageMgr; @@ -2432,4 +2438,53 @@ public class ConsoleProxyManagerImpl implements ConsoleProxyManager, VirtualMach public boolean processDeploymentResult(Commands cmds, ConsoleProxyVO proxy, VirtualMachineProfile profile, DeployDestination dest) { return true; } + + @Override + public boolean applyCustomCertToNewProxy(StartupProxyCommand cmd){ + //this is the case for updating cust cert on each new starting proxy, if such cert exists + //get cert from db + CertificateVO cert = _certDao.listAll().get(0); + + if(cert!=null){ + String certStr = cert.getCertificate(); + long proxyVmId = ((StartupProxyCommand)cmd).getProxyVmId(); + ConsoleProxyVO consoleProxy = _consoleProxyDao.findById(proxyVmId); + //find corresponding host + HostVO consoleProxyHost = _hostDao.findConsoleProxyHost(consoleProxy.getName(), Type.ConsoleProxy); + //now send a command to console proxy + UpdateCertificateCommand certCmd = new UpdateCertificateCommand(certStr); + try { + Answer updateCertAns = _agentMgr.send(consoleProxyHost.getId(), certCmd); + if(updateCertAns.getResult() == true) + { + //we have the cert copied over on cpvm + long eventId = saveScheduledEvent(User.UID_SYSTEM, Account.ACCOUNT_ID_SYSTEM, EventTypes.EVENT_PROXY_REBOOT, "rebooting console proxy with Id: "+consoleProxy.getId()); + rebootProxy(consoleProxy.getId(), eventId); + //when cp reboots, the context will be reinit with the new cert + s_logger.info("Successfully rebooted console proxy resource after custom certificate application"); + } + } catch (AgentUnavailableException e) { + s_logger.warn("Unable to send update certificate command to the console proxy resource", e); + return false; + } catch (OperationTimedoutException e) { + s_logger.warn("Unable to send update certificate command to the console proxy resource", e); + return false; + } + }else{ + return false;//no cert + } + return true; + } + + private Long saveScheduledEvent(Long userId, Long accountId, String type, String description) + { + EventVO event = new EventVO(); + event.setUserId(userId); + event.setAccountId(accountId); + event.setType(type); + event.setState(EventState.Scheduled); + event.setDescription("Scheduled async job for "+description); + event = _eventDao.persist(event); + return event.getId(); + } } diff --git a/server/src/com/cloud/server/ManagementServerImpl.java b/server/src/com/cloud/server/ManagementServerImpl.java index 7b3caf4e962..c57b91e4c70 100755 --- a/server/src/com/cloud/server/ManagementServerImpl.java +++ b/server/src/com/cloud/server/ManagementServerImpl.java @@ -6972,9 +6972,9 @@ public class ManagementServerImpl implements ManagementServer { //when cp reboots, the context will be reinit with the new cert } } catch (AgentUnavailableException e) { - s_logger.warn("Unable to send command to the console proxy resource", e); + s_logger.warn("Unable to send update certificate command to the console proxy resource", e); } catch (OperationTimedoutException e) { - s_logger.warn("Unable to send command to the console proxy resource", e); + s_logger.warn("Unable to send update certificate command to the console proxy resource", e); } } From 42f1ff92a97e85baefd5e48feca95ce4249c53e7 Mon Sep 17 00:00:00 2001 From: root Date: Tue, 26 Oct 2010 11:14:12 -0700 Subject: [PATCH 08/13] resolved merge conflicts after git pull --rebase --- .../AgentBasedConsoleProxyManager.java | 5 +---- .../consoleproxy/ConsoleProxyManagerImpl.java | 14 ++++++-------- 2 files changed, 7 insertions(+), 12 deletions(-) diff --git a/server/src/com/cloud/consoleproxy/AgentBasedConsoleProxyManager.java b/server/src/com/cloud/consoleproxy/AgentBasedConsoleProxyManager.java index 0968cbf2f91..623c0afd9e7 100644 --- a/server/src/com/cloud/consoleproxy/AgentBasedConsoleProxyManager.java +++ b/server/src/com/cloud/consoleproxy/AgentBasedConsoleProxyManager.java @@ -38,7 +38,6 @@ import com.cloud.agent.api.StartupProxyCommand; import com.cloud.agent.api.StopCommand; import com.cloud.api.ServerApiException; import com.cloud.api.commands.DestroyConsoleProxyCmd; -import com.cloud.certificate.dao.CertificateDao; import com.cloud.configuration.dao.ConfigurationDao; import com.cloud.exception.AgentUnavailableException; import com.cloud.exception.ConcurrentOperationException; @@ -50,20 +49,18 @@ import com.cloud.host.HostVO; import com.cloud.host.Status; import com.cloud.host.dao.HostDao; import com.cloud.info.ConsoleProxyInfo; -import com.cloud.server.ManagementServer; import com.cloud.utils.NumbersUtil; import com.cloud.utils.component.ComponentLocator; import com.cloud.utils.component.Inject; import com.cloud.vm.ConsoleProxyVO; import com.cloud.vm.UserVmVO; import com.cloud.vm.VMInstanceVO; -import com.cloud.vm.VirtualMachine.Type; import com.cloud.vm.VirtualMachineManager; import com.cloud.vm.VirtualMachineName; +import com.cloud.vm.VirtualMachine.Type; import com.cloud.vm.dao.ConsoleProxyDao; import com.cloud.vm.dao.UserVmDao; import com.cloud.vm.dao.VMInstanceDao; -import com.sun.org.apache.xml.internal.security.keys.content.MgmtData; @Local(value = { ConsoleProxyManager.class }) public class AgentBasedConsoleProxyManager implements ConsoleProxyManager, VirtualMachineManager, AgentHook { diff --git a/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java b/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java index 5315b6bf856..5bee57d0f71 100644 --- a/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java +++ b/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java @@ -79,8 +79,8 @@ import com.cloud.configuration.Config; import com.cloud.configuration.dao.ConfigurationDao; import com.cloud.dc.DataCenterVO; import com.cloud.dc.HostPodVO; -import com.cloud.dc.Vlan.VlanType; import com.cloud.dc.VlanVO; +import com.cloud.dc.Vlan.VlanType; import com.cloud.dc.dao.DataCenterDao; import com.cloud.dc.dao.HostPodDao; import com.cloud.dc.dao.VlanDao; @@ -101,8 +101,8 @@ import com.cloud.exception.ResourceUnavailableException; import com.cloud.exception.StorageUnavailableException; import com.cloud.ha.HighAvailabilityManager; import com.cloud.host.Host; -import com.cloud.host.Host.Type; import com.cloud.host.HostVO; +import com.cloud.host.Host.Type; import com.cloud.host.dao.HostDao; import com.cloud.info.ConsoleProxyConnectionInfo; import com.cloud.info.ConsoleProxyInfo; @@ -113,15 +113,14 @@ import com.cloud.info.RunningHostInfoAgregator; import com.cloud.info.RunningHostInfoAgregator.ZoneHostInfo; import com.cloud.maid.StackMaid; import com.cloud.network.IpAddrAllocator; -import com.cloud.network.IpAddrAllocator.networkInfo; -import com.cloud.network.Network.TrafficType; import com.cloud.network.NetworkConfigurationVO; import com.cloud.network.NetworkManager; +import com.cloud.network.IpAddrAllocator.networkInfo; +import com.cloud.network.Network.TrafficType; import com.cloud.network.dao.IPAddressDao; import com.cloud.offering.NetworkOffering; import com.cloud.offerings.NetworkOfferingVO; import com.cloud.offerings.dao.NetworkOfferingDao; -import com.cloud.server.ManagementServer; import com.cloud.service.ServiceOfferingVO; import com.cloud.service.dao.ServiceOfferingDao; import com.cloud.servlet.ConsoleProxyServlet; @@ -129,9 +128,9 @@ import com.cloud.storage.GuestOSVO; import com.cloud.storage.StorageManager; import com.cloud.storage.StoragePoolVO; import com.cloud.storage.VMTemplateHostVO; -import com.cloud.storage.VMTemplateStorageResourceAssoc.Status; import com.cloud.storage.VMTemplateVO; import com.cloud.storage.VolumeVO; +import com.cloud.storage.VMTemplateStorageResourceAssoc.Status; import com.cloud.storage.dao.GuestOSDao; import com.cloud.storage.dao.VMTemplateDao; import com.cloud.storage.dao.VMTemplateHostDao; @@ -160,17 +159,16 @@ import com.cloud.vm.NicProfile; import com.cloud.vm.State; import com.cloud.vm.VMInstanceVO; import com.cloud.vm.VirtualMachine; -import com.cloud.vm.VirtualMachine.Event; import com.cloud.vm.VirtualMachineGuru; import com.cloud.vm.VirtualMachineManager; import com.cloud.vm.VirtualMachineName; import com.cloud.vm.VirtualMachineProfile; import com.cloud.vm.VmManager; +import com.cloud.vm.VirtualMachine.Event; import com.cloud.vm.dao.ConsoleProxyDao; import com.cloud.vm.dao.VMInstanceDao; import com.google.gson.Gson; import com.google.gson.GsonBuilder; -import com.sun.org.apache.xml.internal.security.keys.content.MgmtData; // // Possible console proxy state transition cases From c6588c0e25a0a9c98845620b1e07e69a0ac012cd Mon Sep 17 00:00:00 2001 From: abhishek Date: Tue, 26 Oct 2010 12:03:15 -0700 Subject: [PATCH 09/13] adding some error return handling to api dispatcher, and cleaning up some of the code paths to return the right error messages --- server/src/com/cloud/api/ApiDispatcher.java | 3 ++ .../commands/UploadCustomCertificateCmd.java | 37 +++++++++++++---- .../consoleproxy/ConsoleProxyManagerImpl.java | 40 ++++++++++--------- .../com/cloud/server/ManagementServer.java | 2 +- .../cloud/server/ManagementServerImpl.java | 9 ++++- setup/db/create-schema.sql | 2 +- 6 files changed, 64 insertions(+), 29 deletions(-) diff --git a/server/src/com/cloud/api/ApiDispatcher.java b/server/src/com/cloud/api/ApiDispatcher.java index 12e45a8df8a..822a7cdee17 100644 --- a/server/src/com/cloud/api/ApiDispatcher.java +++ b/server/src/com/cloud/api/ApiDispatcher.java @@ -36,6 +36,7 @@ import com.cloud.configuration.ConfigurationManager; import com.cloud.consoleproxy.ConsoleProxyManager; import com.cloud.exception.InvalidParameterValueException; import com.cloud.exception.PermissionDeniedException; +import com.cloud.exception.ResourceAllocationException; import com.cloud.network.DomainRouterService; import com.cloud.network.NetworkManager; import com.cloud.network.security.NetworkGroupManager; @@ -154,6 +155,8 @@ public class ApiDispatcher { throw new ServerApiException(BaseCmd.PARAM_ERROR, cause.getMessage()); } else if (cause instanceof PermissionDeniedException) { throw new ServerApiException(BaseCmd.ACCOUNT_ERROR, cause.getMessage()); + } else if (cause instanceof ResourceAllocationException){ + throw new ServerApiException(BaseCmd.UNSUPPORTED_ACTION_ERROR, cause.getMessage()); } s_logger.warn("Exception executing method " + methodName + " for command " + cmd.getClass().getSimpleName(), ite); throw new ServerApiException(BaseCmd.INTERNAL_ERROR, "Unable to execute method " + methodName + " for command " + cmd.getClass().getSimpleName() + ", internal error in the implementation."); diff --git a/server/src/com/cloud/api/commands/UploadCustomCertificateCmd.java b/server/src/com/cloud/api/commands/UploadCustomCertificateCmd.java index 887f4676ded..53f3066f3e9 100644 --- a/server/src/com/cloud/api/commands/UploadCustomCertificateCmd.java +++ b/server/src/com/cloud/api/commands/UploadCustomCertificateCmd.java @@ -19,13 +19,15 @@ package com.cloud.api.commands; import org.apache.log4j.Logger; -import com.cloud.api.BaseCmd; +import com.cloud.api.BaseAsyncCmd; import com.cloud.api.Implementation; import com.cloud.api.Parameter; import com.cloud.api.response.StatusResponse; +import com.cloud.event.EventTypes; +import com.cloud.user.Account; @Implementation(method="uploadCertificate") -public class UploadCustomCertificateCmd extends BaseCmd { +public class UploadCustomCertificateCmd extends BaseAsyncCmd { public static final Logger s_logger = Logger.getLogger(UploadCustomCertificateCmd.class.getName()); private static final String s_name = "uploadcustomcertificateresponse"; @@ -37,11 +39,7 @@ public class UploadCustomCertificateCmd extends BaseCmd { return path; } - @Override - public String getName() { - return s_name; - } - + @Override @SuppressWarnings("unchecked") public StatusResponse getResponse() { Boolean status = (Boolean)getResponseObject(); @@ -51,4 +49,29 @@ public class UploadCustomCertificateCmd extends BaseCmd { response.setResponseName(getName()); return response; } + + @Override + public String getEventType() { + return EventTypes.EVENT_VOLUME_CREATE; + } + + @Override + public String getEventDescription() { + return ("Uploading custom certificate to the db, and applying it to the cpvm"); + } + + @Override + public String getName() { + return s_name; + } + + public static String getResultObjectName() { + return "volume"; + } + + @Override + public long getAccountId() { + return Account.ACCOUNT_ID_SYSTEM; // no account info given, parent this command to SYSTEM so ERROR events are tracked + } + } diff --git a/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java b/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java index 5bee57d0f71..69e094bcccd 100644 --- a/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java +++ b/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java @@ -2448,25 +2448,27 @@ public class ConsoleProxyManagerImpl implements ConsoleProxyManager, VirtualMach long proxyVmId = ((StartupProxyCommand)cmd).getProxyVmId(); ConsoleProxyVO consoleProxy = _consoleProxyDao.findById(proxyVmId); //find corresponding host - HostVO consoleProxyHost = _hostDao.findConsoleProxyHost(consoleProxy.getName(), Type.ConsoleProxy); - //now send a command to console proxy - UpdateCertificateCommand certCmd = new UpdateCertificateCommand(certStr); - try { - Answer updateCertAns = _agentMgr.send(consoleProxyHost.getId(), certCmd); - if(updateCertAns.getResult() == true) - { - //we have the cert copied over on cpvm - long eventId = saveScheduledEvent(User.UID_SYSTEM, Account.ACCOUNT_ID_SYSTEM, EventTypes.EVENT_PROXY_REBOOT, "rebooting console proxy with Id: "+consoleProxy.getId()); - rebootProxy(consoleProxy.getId(), eventId); - //when cp reboots, the context will be reinit with the new cert - s_logger.info("Successfully rebooted console proxy resource after custom certificate application"); - } - } catch (AgentUnavailableException e) { - s_logger.warn("Unable to send update certificate command to the console proxy resource", e); - return false; - } catch (OperationTimedoutException e) { - s_logger.warn("Unable to send update certificate command to the console proxy resource", e); - return false; + if(consoleProxy!=null){ + HostVO consoleProxyHost = _hostDao.findConsoleProxyHost(consoleProxy.getName(), Type.ConsoleProxy); + //now send a command to console proxy + UpdateCertificateCommand certCmd = new UpdateCertificateCommand(certStr); + try { + Answer updateCertAns = _agentMgr.send(consoleProxyHost.getId(), certCmd); + if(updateCertAns.getResult() == true) + { + //we have the cert copied over on cpvm + long eventId = saveScheduledEvent(User.UID_SYSTEM, Account.ACCOUNT_ID_SYSTEM, EventTypes.EVENT_PROXY_REBOOT, "rebooting console proxy with Id: "+consoleProxy.getId()); + rebootProxy(consoleProxy.getId(), eventId); + //when cp reboots, the context will be reinit with the new cert + s_logger.info("Successfully rebooted console proxy resource after custom certificate application"); + } + } catch (AgentUnavailableException e) { + s_logger.warn("Unable to send update certificate command to the console proxy resource", e); + return false; + } catch (OperationTimedoutException e) { + s_logger.warn("Unable to send update certificate command to the console proxy resource", e); + return false; + } } }else{ return false;//no cert diff --git a/server/src/com/cloud/server/ManagementServer.java b/server/src/com/cloud/server/ManagementServer.java index e620d53ef25..8ac62e001f1 100755 --- a/server/src/com/cloud/server/ManagementServer.java +++ b/server/src/com/cloud/server/ManagementServer.java @@ -1219,5 +1219,5 @@ public interface ManagementServer { */ String[] getHypervisors(ListHypervisorsCmd cmd); - boolean uploadCertificate(UploadCustomCertificateCmd cmd); + boolean uploadCertificate(UploadCustomCertificateCmd cmd) throws ResourceAllocationException; } diff --git a/server/src/com/cloud/server/ManagementServerImpl.java b/server/src/com/cloud/server/ManagementServerImpl.java index c57b91e4c70..dbd6b488b0b 100755 --- a/server/src/com/cloud/server/ManagementServerImpl.java +++ b/server/src/com/cloud/server/ManagementServerImpl.java @@ -26,6 +26,7 @@ import java.net.URLEncoder; import java.net.UnknownHostException; import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; +import java.security.cert.Certificate; import java.util.ArrayList; import java.util.Arrays; import java.util.Calendar; @@ -148,6 +149,7 @@ import com.cloud.async.dao.AsyncJobDao; import com.cloud.async.executor.ExtractJobResultObject; import com.cloud.capacity.CapacityVO; import com.cloud.capacity.dao.CapacityDao; +import com.cloud.certificate.CertificateVO; import com.cloud.certificate.dao.CertificateDao; import com.cloud.configuration.Config; import com.cloud.configuration.ConfigurationManager; @@ -6946,7 +6948,12 @@ public class ManagementServerImpl implements ManagementServer { } @Override - public boolean uploadCertificate(UploadCustomCertificateCmd cmd) { + public boolean uploadCertificate(UploadCustomCertificateCmd cmd) throws ResourceAllocationException { + //limit no.of certs uploaded to 1 + if(_certDao.listAll().size()>0){ + throw new ResourceAllocationException("There is already a custom certificate in the db"); + } + String certificatePath = cmd.getPath(); Long certVOId = _certDao.persistCustomCertToDb(certificatePath);//0 implies failure diff --git a/setup/db/create-schema.sql b/setup/db/create-schema.sql index 69b0c5d800c..3f2b97dff4d 100755 --- a/setup/db/create-schema.sql +++ b/setup/db/create-schema.sql @@ -118,7 +118,7 @@ CREATE TABLE `cloud`.`account_network_ref` ( CREATE TABLE `cloud`.`certificate` ( `id` bigint unsigned NOT NULL AUTO_INCREMENT COMMENT 'id', - `certificate` text NOT NULL UNIQUE COMMENT 'the actual custom certificate being stored in the db', + `certificate` text COMMENT 'the actual custom certificate being stored in the db', PRIMARY KEY (`id`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8; From a698c0327dc545653831b9607f12e91eec56ca25 Mon Sep 17 00:00:00 2001 From: abhishek Date: Tue, 26 Oct 2010 14:27:03 -0700 Subject: [PATCH 10/13] adding more logging around successful cert upload --- .../com/cloud/consoleproxy/ConsoleProxyManagerImpl.java | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java b/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java index 69e094bcccd..08d2515e758 100644 --- a/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java +++ b/server/src/com/cloud/consoleproxy/ConsoleProxyManagerImpl.java @@ -2441,9 +2441,10 @@ public class ConsoleProxyManagerImpl implements ConsoleProxyManager, VirtualMach public boolean applyCustomCertToNewProxy(StartupProxyCommand cmd){ //this is the case for updating cust cert on each new starting proxy, if such cert exists //get cert from db - CertificateVO cert = _certDao.listAll().get(0); + List certList = _certDao.listAll(); - if(cert!=null){ + if(certList.size()>0){ + CertificateVO cert = certList.get(0);//there will only be 1 cert in db for now String certStr = cert.getCertificate(); long proxyVmId = ((StartupProxyCommand)cmd).getProxyVmId(); ConsoleProxyVO consoleProxy = _consoleProxyDao.findById(proxyVmId); @@ -2461,6 +2462,7 @@ public class ConsoleProxyManagerImpl implements ConsoleProxyManager, VirtualMach rebootProxy(consoleProxy.getId(), eventId); //when cp reboots, the context will be reinit with the new cert s_logger.info("Successfully rebooted console proxy resource after custom certificate application"); + return true; } } catch (AgentUnavailableException e) { s_logger.warn("Unable to send update certificate command to the console proxy resource", e); @@ -2473,7 +2475,7 @@ public class ConsoleProxyManagerImpl implements ConsoleProxyManager, VirtualMach }else{ return false;//no cert } - return true; + return false; } private Long saveScheduledEvent(Long userId, Long accountId, String type, String description) From 72f0940f7a503943fd92c355b02d82bf3ecab207 Mon Sep 17 00:00:00 2001 From: Jessica Wang Date: Tue, 26 Oct 2010 14:51:43 -0700 Subject: [PATCH 11/13] new UI - after addHost with new cluster, refresh cluster under pod and automatically click the newly created cluster node (to show cluster page in right panel and host in middle menu if the host is created successfully). --- ui/new/scripts/cloud.core2.resource.js | 31 +++++++++++++++++--------- 1 file changed, 20 insertions(+), 11 deletions(-) diff --git a/ui/new/scripts/cloud.core2.resource.js b/ui/new/scripts/cloud.core2.resource.js index 319359dbe10..5b8c7f6467e 100644 --- a/ui/new/scripts/cloud.core2.resource.js +++ b/ui/new/scripts/cloud.core2.resource.js @@ -1280,9 +1280,10 @@ function initAddHostButton($midmenuAddLink1) { var password = trim($thisDialog.find("#host_password").val()); array1.push("&password="+encodeURIComponent(password)); - + + var newClusterName; if(clusterRadio == "new_cluster_radio") { - var newClusterName = trim($thisDialog.find("#new_cluster_name").val()); + newClusterName = trim($thisDialog.find("#new_cluster_name").val()); array1.push("&clustername="+todb(newClusterName)); } else if(clusterRadio == "existing_cluster_radio") { @@ -1326,13 +1327,16 @@ function initAddHostButton($midmenuAddLink1) { } } - if(clusterRadio == "new_cluster_radio") - $thisDialog.find("#new_cluster_name").val(""); - - refreshClusterUnderPod($("#pod_" + podObj.id)); + if(clusterRadio == "new_cluster_radio") { + refreshClusterUnderPod($("#pod_" + podObj.id), newClusterName); + $thisDialog.find("#new_cluster_name").val(""); + } }, error: function(XMLHttpResponse) { - refreshClusterUnderPod($("#pod_" + podObj.id)); + if(clusterRadio == "new_cluster_radio") { + refreshClusterUnderPod($("#pod_" + podObj.id), newClusterName); + $thisDialog.find("#new_cluster_name").val(""); //even AddHost fails, new cluster is still created. So, we clean up new cluster field to avoid the same one gets created twice. + } handleErrorInDialog(XMLHttpResponse, $thisDialog); } }); @@ -1345,7 +1349,7 @@ function initAddHostButton($midmenuAddLink1) { }); } -function refreshClusterUnderPod($podNode) { +function refreshClusterUnderPod($podNode, newClusterName) { var podId = $podNode.data("podId"); $.ajax({ data: createURL("command=listClusters&podid="+podId+maxPageSize), @@ -1356,9 +1360,14 @@ function refreshClusterUnderPod($podNode) { var container = $podNode.find("#clusters_container").empty(); if (items != null && items.length > 0) { for (var i = 0; i < items.length; i++) { - var clusterTemplate = $("#leftmenu_cluster_node_template").clone(true); - clusterJSONToTreeNode(items[i], clusterTemplate); - container.append(clusterTemplate.show()); + var $clusterNode = $("#leftmenu_cluster_node_template").clone(true); + var item = items[i]; + clusterJSONToTreeNode(item, $clusterNode); + container.append($clusterNode.show()); + + if(newClusterName != null && fromdb(item.name) == newClusterName) { + $clusterNode.find("#cluster_name").click(); + } } $podNode.find("#pod_arrow").removeClass("white_nonexpanded_close").addClass("expanded_open"); $podNode.find("#pod_content").show(); From 8fafc892d39f132bc25292ba6f6f4909c64aa8c1 Mon Sep 17 00:00:00 2001 From: Kris McQueen Date: Tue, 26 Oct 2010 14:55:27 -0700 Subject: [PATCH 12/13] bug 6730: if a volume was never attached to a VM, then the poolId will be null and this will be flagged as not on shared storage. Since the code was deleting detached volumes only on shared storage, the never-attached volume was in an undeletable state. Instead, allow deletion of any detached volume, regardless of storage pool until some technical reason limits this from happening. Also, the UI was not allowing volumes to be deleted due to a bug in looking at the vmname property of the volume. The 'if' conditional always returned true that the volume was attached to a VM to due a boolean logic error. status 6730: resolved fixed --- server/src/com/cloud/storage/StorageManagerImpl.java | 9 ++++++--- ui/scripts/cloud.core.storage.js | 2 +- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/server/src/com/cloud/storage/StorageManagerImpl.java b/server/src/com/cloud/storage/StorageManagerImpl.java index 842e0330602..047ca9fb469 100755 --- a/server/src/com/cloud/storage/StorageManagerImpl.java +++ b/server/src/com/cloud/storage/StorageManagerImpl.java @@ -2487,9 +2487,12 @@ public class StorageManagerImpl implements StorageManager { // Check that the volume is stored on shared storage - if (!volumeOnSharedStoragePool(volume)) { - throw new InvalidParameterValueException("Please specify a volume that has been created on a shared storage pool."); - } + // NOTE: We used to ensure the volume is on shared storage before deleting. However, this seems like an unnecessary check since all we allow + // is deleting a detached volume. Is there a technical reason why the volume has to be on shared storage? If so, uncomment this...otherwise, + // just delete the detached volume regardless of storage pool. +// if (!volumeOnSharedStoragePool(volume)) { +// throw new InvalidParameterValueException("Please specify a volume that has been created on a shared storage pool."); +// } // Check that the volume is not currently attached to any VM if (volume.getInstanceId() != null) { diff --git a/ui/scripts/cloud.core.storage.js b/ui/scripts/cloud.core.storage.js index 580b03046d8..10ca6570729 100644 --- a/ui/scripts/cloud.core.storage.js +++ b/ui/scripts/cloud.core.storage.js @@ -959,7 +959,7 @@ function showStorageTab(domainId, targetTab) { switch (linkAction) { case "volume_action_delete" : //check if this volume is attached to a virtual machine. If yes, can't be deleted. - if(vmname != null && (vmname != "" || vmname != "none")) { + if(vmname != null && vmname != "" && vmname != "none") { $("#dialog_alert").html("

This volume is attached to virtual machine " + vmname + " and can't be deleted.

") $("#dialog_alert").dialog("open"); return; From 56509fe1f1cfa151612802a09eefb210e3325333 Mon Sep 17 00:00:00 2001 From: NIKITA Date: Tue, 26 Oct 2010 15:04:01 -0700 Subject: [PATCH 13/13] Midmenu blank msg box --- ui/new/css/main.css | 22 +++++++++++++++++++++- ui/new/images/midmenu_emptymsg.gif | Bin 0 -> 215 bytes ui/new/index.jsp | 2 +- 3 files changed, 22 insertions(+), 2 deletions(-) create mode 100644 ui/new/images/midmenu_emptymsg.gif diff --git a/ui/new/css/main.css b/ui/new/css/main.css index 81e4e53561b..3563d418fbe 100644 --- a/ui/new/css/main.css +++ b/ui/new/css/main.css @@ -2006,6 +2006,7 @@ a:hover.search_button { height:auto; float:left; text-align:left; + background:#FFF url(../images/midmenu_hover.gif) repeat-x top left; color:#CCC; font-size:11px; font-weight:normal; @@ -2251,6 +2252,25 @@ a:hover.search_button { color:#999; } +.midmenu_emptymsgbox { + width:220px; + height:auto; + float:left; + background:#d4d4d4 url(../images/midmenu_emptymsg.gif) repeat-x top left; + margin:0 0 0 0; + padding:0; +} + +.midmenu_emptymsgbox p{ + width:200px; + height:auto; + float:left; + color:#666; + font-size:11px; + font-weight:normal; + margin:0 0 0 0; + padding:0; +} .main_contentarea_with_midmenu { width:auto; @@ -3067,7 +3087,7 @@ a:hover.search_button { height:auto; float:left; position:absolute; - background:#FFF url(../images/midmenu_hover.gif) repeat top left; + background:#FFF repeat top left; border:1px solid #CCC; top:18px; right:1px; diff --git a/ui/new/images/midmenu_emptymsg.gif b/ui/new/images/midmenu_emptymsg.gif new file mode 100644 index 0000000000000000000000000000000000000000..d668944b8c8f602917db6a5fe00587b865dd623f GIT binary patch literal 215 zcmZ?wbhEHbVQa)oeZoY4;1^JWX#Fv63ThK z%}3{aQPTY%Z{O6McRsMdKtn^S|5#(u$r!PD7c{;&u8mqfaZTCk+=~4V^pkw_CNsa- fVzoA7_x*RRHGcD%-~HHAcmDnF{|${ziVW5ORcB&+ literal 0 HcmV?d00001 diff --git a/ui/new/index.jsp b/ui/new/index.jsp index bee9823d813..e91278a55f5 100644 --- a/ui/new/index.jsp +++ b/ui/new/index.jsp @@ -316,7 +316,7 @@ long milliseconds = new Date().getTime();
- +

No Items Available