From: <pn...@hy...> - 2010-03-26 01:07:10
|
Author: pnguyen Date: 2010-03-25 17:18:54 -0700 (Thu, 25 Mar 2010) New Revision: 14425 URL: http://svn.hyperic.org/?view=rev&root=Hyperic+HQ&revision=14425 Modified: trunk/src/org/hyperic/hq/authz/Resources.properties trunk/src/org/hyperic/hq/authz/server/session/ResourceGroupManagerEJBImpl.java trunk/src/org/hyperic/hq/bizapp/server/session/AppdefBossEJBImpl.java trunk/src/org/hyperic/hq/ui/action/resource/common/inventory/AddResourceGroupsAction.java trunk/src/org/hyperic/hq/ui/action/resource/common/inventory/RemoveResourceGroupsAction.java trunk/src/org/hyperic/hq/ui/action/resource/group/inventory/AddGroupResourcesAction.java trunk/src/org/hyperic/hq/ui/action/resource/group/inventory/RemoveAction.java trunk/src/org/hyperic/hq/ui/service/RESTService.java trunk/web/WEB-INF/classes/ApplicationResources.properties trunk/web/WEB-INF/struts-config.xml trunk/web/js/lib/lib.js trunk/web/resource/group/inventory/ListResources.jsp Log: [HQ-2038] Prevent resource group membership from being updated if scheduled downtime is in progress Modified: trunk/src/org/hyperic/hq/authz/Resources.properties =================================================================== --- trunk/src/org/hyperic/hq/authz/Resources.properties 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/src/org/hyperic/hq/authz/Resources.properties 2010-03-26 00:18:54 UTC (rev 14425) @@ -18,4 +18,6 @@ subject.field.dept=department subject.field.active=active status -resourceGroup.sortField.name=Name \ No newline at end of file +resourceGroup.sortField.name=Name +resourceGroup.update.error.downtime.running=Cannot update resource list for {0} while downtime is in progress. +resourceGroup.update.error.downtime.scheduler.failure=Failure getting the downtime schedule for {0}. \ No newline at end of file Modified: trunk/src/org/hyperic/hq/authz/server/session/ResourceGroupManagerEJBImpl.java =================================================================== --- trunk/src/org/hyperic/hq/authz/server/session/ResourceGroupManagerEJBImpl.java 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/src/org/hyperic/hq/authz/server/session/ResourceGroupManagerEJBImpl.java 2010-03-26 00:18:54 UTC (rev 14425) @@ -6,7 +6,7 @@ * normal use of the program, and does *not* fall under the heading of * "derived work". * - * Copyright (C) [2004-2009], Hyperic, Inc. + * Copyright (C) [2004-2010], Hyperic, Inc. * This file is part of HQ. * * HQ is free software; you can redistribute it and/or modify @@ -25,6 +25,7 @@ package org.hyperic.hq.authz.server.session; +import java.text.MessageFormat; import java.util.ArrayList; import java.util.Arrays; import java.util.Collection; @@ -33,6 +34,7 @@ import java.util.Iterator; import java.util.List; import java.util.Map; +import java.util.ResourceBundle; import javax.ejb.CreateException; import javax.ejb.FinderException; @@ -71,6 +73,7 @@ import org.hyperic.hq.common.DuplicateObjectException; import org.hyperic.hq.common.SystemException; import org.hyperic.hq.common.VetoException; +import org.hyperic.hq.events.MaintenanceEvent; import org.hyperic.hq.events.server.session.EventLogManagerEJBImpl; import org.hyperic.hq.events.shared.EventLogManagerLocal; import org.hyperic.hq.grouping.CritterList; @@ -81,6 +84,7 @@ import org.hyperic.util.pager.PageControl; import org.hyperic.util.pager.PageList; import org.hyperic.util.pager.Pager; +import org.quartz.SchedulerException; /** * Use this session bean to manipulate ResourceGroups, @@ -100,6 +104,7 @@ extends AuthzSession implements SessionBean { + private final String BUNDLE = "org.hyperic.hq.authz.Resources"; private Pager _groupPager; private Pager _ownedGroupPager; private final String GROUP_PAGER = @@ -167,6 +172,37 @@ } /** + * Do not allow resources to be added or removed from a group + * if the group has a downtime schedule in progress. + */ + private void checkGroupMaintenance(AuthzSubject subj, ResourceGroup group) + throws PermissionException, VetoException { + + try { + MaintenanceEvent event = PermissionManagerFactory.getInstance() + .getMaintenanceEventManager() + .getMaintenanceEvent(subj, group.getId()); + + if (event != null && MaintenanceEvent.STATE_RUNNING.equals(event.getState())) { + String msg = ResourceBundle.getBundle(BUNDLE) + .getString("resourceGroup.update.error.downtime.running"); + + throw new VetoException( + MessageFormat.format(msg, new String[] {group.getName()})); + } + } catch (SchedulerException se) { + // This should not happen. Indicates a serious system error. + + String msg = ResourceBundle.getBundle(BUNDLE) + .getString("resourceGroup.update.error.downtime.scheduler.failure"); + + throw new SystemException( + MessageFormat.format(msg, new String[] {group.getName()}), + se); + } + } + + /** * Find the group that has the given ID. Does not do any authz checking * @ejb:interface-method */ @@ -302,14 +338,17 @@ */ public void addResources(AuthzSubject subj, ResourceGroup group, List resources) - throws PermissionException + throws PermissionException, VetoException { checkGroupPermission(subj, group.getId(), AuthzConstants.perm_modifyResourceGroup); + + checkGroupMaintenance(subj, group); + addResources(group, resources); } - private void addResources(ResourceGroup group, List resources) { + private void addResources(ResourceGroup group, Collection resources) { getResourceGroupDAO().addMembers(group, resources); GroupingStartupListener.getCallbackObj().groupMembersChanged(group); } @@ -320,18 +359,87 @@ */ public ResourceGroup addResource(AuthzSubject whoami, ResourceGroup group, Resource resource) - throws PermissionException + throws PermissionException, VetoException { checkGroupPermission(whoami, group.getId(), AuthzConstants.perm_modifyResourceGroup); - getResourceGroupDAO().addMembers(group, - Collections.singleton(resource)); - GroupingStartupListener.getCallbackObj().groupMembersChanged(group); + checkGroupMaintenance(whoami, group); + + addResources(group, Collections.singletonList(resource)); + return group; } - + /** + * Add a resource to a collection of groups + * + * @param whoami The current running user. + * @param resource The resource + * @param groups The groups to add to. + * + * @ejb:interface-method + */ + public void addResource(AuthzSubject whoami, + Resource resource, + Collection groups) + throws PermissionException, VetoException + { + // Do all of the pre-condition checks first before + // iterating through addResources() because + // ResourceGroupDAO().addMembers() will commit + // the changes after each iteration. + + for (Iterator i = groups.iterator(); i.hasNext();) { + ResourceGroup g = (ResourceGroup) i.next(); + + checkGroupPermission(whoami, g.getId(), + AuthzConstants.perm_modifyResourceGroup); + + checkGroupMaintenance(whoami, g); + } + + for (Iterator i = groups.iterator(); i.hasNext();) { + ResourceGroup g = (ResourceGroup) i.next(); + addResources(g, Collections.singletonList(resource)); + } + } + + /** + * Remove a resource from a collection of groups + * + * @param whoami The current running user. + * @param resource The resource + * @param groups The groups to remove from. + * + * @ejb:interface-method + */ + public void removeResource(AuthzSubject whoami, + Resource resource, + Collection groups) + throws PermissionException, VetoException + { + // Do all of the pre-condition checks first before + // iterating through removeResources() because + // ResourceGroupDAO().removeMembers() will commit + // the changes after each iteration. + + for (Iterator i = groups.iterator(); i.hasNext();) { + ResourceGroup g = (ResourceGroup) i.next(); + + checkGroupPermission(whoami, g.getId(), + AuthzConstants.perm_modifyResourceGroup); + + checkGroupMaintenance(whoami, g); + } + + for (Iterator i = groups.iterator(); i.hasNext();) { + ResourceGroup g = (ResourceGroup) i.next(); + removeResources(g, Collections.singletonList(resource)); + } + } + + /** * RemoveResources from a group. * @param whoami The current running user. * @param group The group . @@ -340,16 +448,21 @@ public void removeResources(AuthzSubject whoami, ResourceGroup group, Collection resources) - throws PermissionException + throws PermissionException, VetoException { checkGroupPermission(whoami, group.getId(), AuthzConstants.perm_modifyResourceGroup); - - ResourceGroupDAO grpDao = getResourceGroupDAO(); - grpDao.removeMembers(group, resources); + + checkGroupMaintenance(whoami, group); + + removeResources(group, resources); + } + + private void removeResources(ResourceGroup group, Collection resources) { + getResourceGroupDAO().removeMembers(group, resources); GroupingStartupListener.getCallbackObj().groupMembersChanged(group); } - + /** * Sets the criteria list for this group. * @param whoami The current running user. @@ -378,11 +491,13 @@ */ public void setResources(AuthzSubject whoami, ResourceGroup group, Collection resources) - throws PermissionException + throws PermissionException, VetoException { checkGroupPermission(whoami, group.getId(), AuthzConstants.perm_modifyResourceGroup); + checkGroupMaintenance(whoami, group); + getResourceGroupDAO().setMembers(group, resources); GroupingStartupListener.getCallbackObj().groupMembersChanged(group); } Modified: trunk/src/org/hyperic/hq/bizapp/server/session/AppdefBossEJBImpl.java =================================================================== --- trunk/src/org/hyperic/hq/bizapp/server/session/AppdefBossEJBImpl.java 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/src/org/hyperic/hq/bizapp/server/session/AppdefBossEJBImpl.java 2010-03-26 00:18:54 UTC (rev 14425) @@ -2376,7 +2376,7 @@ */ public void removeResourcesFromGroup(int sessionId, ResourceGroup group, Collection resources) - throws SessionException, PermissionException + throws SessionException, PermissionException, VetoException { AuthzSubject subject = manager.getSubject(sessionId); @@ -2643,7 +2643,7 @@ */ public void addResourcesToGroup(int sessionID, ResourceGroup group, List aeids) - throws SessionException, PermissionException + throws SessionException, PermissionException, VetoException { AuthzSubject subject = manager.getSubject(sessionID); ResourceGroupManagerLocal groupMan = @@ -3317,12 +3317,15 @@ ResourceGroupManagerLocal groupMan = getResourceGroupManager(); ResourceManagerLocal resourceMan = getResourceManager(); Resource resource = resourceMan.findResource(entityId); + List groups = new ArrayList(groupIds.length); for (int i=0; i < groupIds.length; i++) { ResourceGroup group = groupMan.findResourceGroupById(subject, groupIds[i]); - groupMan.addResource(subject, group, resource); + groups.add(group); } + + groupMan.addResource(subject, resource, groups); } /** @@ -3375,13 +3378,15 @@ ResourceGroupManagerLocal groupMan = getResourceGroupManager(); ResourceManagerLocal resourceMan = getResourceManager(); Resource resource = resourceMan.findResource(entityId); - + List groups = new ArrayList(groupIds.length); + for (int i=0;i<groupIds.length;i++) { ResourceGroup group = groupMan.findResourceGroupById(subject, groupIds[i]); - groupMan.removeResources(subject, group, - Collections.singleton(resource)); + groups.add(group); } + + groupMan.removeResource(subject, resource, groups); } /** Modified: trunk/src/org/hyperic/hq/ui/action/resource/common/inventory/AddResourceGroupsAction.java =================================================================== --- trunk/src/org/hyperic/hq/ui/action/resource/common/inventory/AddResourceGroupsAction.java 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/src/org/hyperic/hq/ui/action/resource/common/inventory/AddResourceGroupsAction.java 2010-03-26 00:18:54 UTC (rev 14425) @@ -6,7 +6,7 @@ * normal use of the program, and does *not* fall under the heading of * "derived work". * - * Copyright (C) [2004, 2005, 2006], Hyperic, Inc. + * Copyright (C) [2004-2010], Hyperic, Inc. * This file is part of HQ. * * HQ is free software; you can redistribute it and/or modify @@ -42,6 +42,7 @@ import org.hyperic.hq.appdef.shared.AppdefEntityConstants; import org.hyperic.hq.appdef.shared.AppdefEntityID; import org.hyperic.hq.bizapp.shared.AppdefBoss; +import org.hyperic.hq.common.VetoException; import org.hyperic.hq.ui.Constants; import org.hyperic.hq.ui.action.BaseAction; import org.hyperic.hq.ui.action.BaseValidatorForm; @@ -140,12 +141,16 @@ RequestUtils.setConfirmation(request, "resource.common.inventory.confirm.AddResourceGroups"); return returnSuccess(request, mapping, forwardParams); - } - catch (AppSvcClustDuplicateAssignException e1) { - RequestUtils - .setError(request, - "resource.common.inventory.error.DuplicateClusterAssignment"); + } catch (AppSvcClustDuplicateAssignException e1) { + RequestUtils.setError(request, + "resource.common.inventory.error.DuplicateClusterAssignment"); return returnFailure(request, mapping); + } catch (VetoException ve) { + RequestUtils.setErrorObject(request, + "resource.group.inventory.error.UpdateResourceListVetoed", + ve.getMessage()); + + return returnFailure(request, mapping); } } Modified: trunk/src/org/hyperic/hq/ui/action/resource/common/inventory/RemoveResourceGroupsAction.java =================================================================== --- trunk/src/org/hyperic/hq/ui/action/resource/common/inventory/RemoveResourceGroupsAction.java 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/src/org/hyperic/hq/ui/action/resource/common/inventory/RemoveResourceGroupsAction.java 2010-03-26 00:18:54 UTC (rev 14425) @@ -6,7 +6,7 @@ * normal use of the program, and does *not* fall under the heading of * "derived work". * - * Copyright (C) [2004-2008], Hyperic, Inc. + * Copyright (C) [2004-2010], Hyperic, Inc. * This file is part of HQ. * * HQ is free software; you can redistribute it and/or modify @@ -38,6 +38,7 @@ import org.apache.struts.action.ActionMapping; import org.hyperic.hq.appdef.shared.AppdefEntityID; import org.hyperic.hq.bizapp.shared.AppdefBoss; +import org.hyperic.hq.common.VetoException; import org.hyperic.hq.ui.Constants; import org.hyperic.hq.ui.action.BaseAction; import org.hyperic.hq.ui.util.ContextUtils; @@ -73,20 +74,27 @@ AppdefEntityID entityId = new AppdefEntityID(resourceType.intValue(), resourceId); - Integer[] groups = rmForm.getG(); - if (groups != null) { - log.trace("removing groups " + groups + - " for resource [" + resourceId + "]"); - boss.batchGroupRemove(sessionId.intValue(), entityId, - groups); + try { + Integer[] groups = rmForm.getG(); + if (groups != null) { + log.trace("removing groups " + groups + + " for resource [" + resourceId + "]"); + boss.batchGroupRemove(sessionId.intValue(), entityId, + groups); - RequestUtils - .setConfirmation(request, - "resource.common.inventory.confirm.RemoveResourceGroups"); - } + RequestUtils.setConfirmation(request, + "resource.common.inventory.confirm.RemoveResourceGroups"); + } - return returnSuccess(request, mapping, forwardParams); + return returnSuccess(request, mapping, forwardParams); + } catch (VetoException ve) { + RequestUtils.setErrorObject(request, + "resource.group.inventory.error.UpdateResourceListVetoed", + ve.getMessage()); + + return returnFailure(request, mapping, forwardParams); + } } } Modified: trunk/src/org/hyperic/hq/ui/action/resource/group/inventory/AddGroupResourcesAction.java =================================================================== --- trunk/src/org/hyperic/hq/ui/action/resource/group/inventory/AddGroupResourcesAction.java 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/src/org/hyperic/hq/ui/action/resource/group/inventory/AddGroupResourcesAction.java 2010-03-26 00:18:54 UTC (rev 14425) @@ -6,7 +6,7 @@ * normal use of the program, and does *not* fall under the heading of * "derived work". * - * Copyright (C) [2004, 2005, 2006], Hyperic, Inc. + * Copyright (C) [2004-2010], Hyperic, Inc. * This file is part of HQ. * * HQ is free software; you can redistribute it and/or modify @@ -52,6 +52,7 @@ import org.hyperic.hq.authz.shared.ResourceGroupManagerLocal; import org.hyperic.hq.authz.shared.ResourceManagerLocal; import org.hyperic.hq.bizapp.shared.AppdefBoss; +import org.hyperic.hq.common.VetoException; import org.hyperic.hq.ui.Constants; import org.hyperic.hq.ui.action.BaseAction; import org.hyperic.hq.ui.action.BaseValidatorForm; @@ -145,6 +146,12 @@ RequestUtils.setError(request, "resource.common.inventory.error.ResourceNotFound"); return returnFailure(request, mapping, forwardParams); + } catch (VetoException ve) { + RequestUtils.setErrorObject(request, + "resource.group.inventory.error.UpdateResourceListVetoed", + ve.getMessage()); + + return returnFailure(request, mapping); } } Modified: trunk/src/org/hyperic/hq/ui/action/resource/group/inventory/RemoveAction.java =================================================================== --- trunk/src/org/hyperic/hq/ui/action/resource/group/inventory/RemoveAction.java 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/src/org/hyperic/hq/ui/action/resource/group/inventory/RemoveAction.java 2010-03-26 00:18:54 UTC (rev 14425) @@ -6,7 +6,7 @@ * normal use of the program, and does *not* fall under the heading of * "derived work". * - * Copyright (C) [2004, 2005, 2006], Hyperic, Inc. + * Copyright (C) [2004-2010], Hyperic, Inc. * This file is part of HQ. * * HQ is free software; you can redistribute it and/or modify @@ -49,6 +49,7 @@ import org.hyperic.hq.authz.server.session.ResourceManagerEJBImpl; import org.hyperic.hq.authz.shared.ResourceManagerLocal; import org.hyperic.hq.bizapp.shared.AppdefBoss; +import org.hyperic.hq.common.VetoException; import org.hyperic.hq.ui.Constants; import org.hyperic.hq.ui.action.BaseAction; import org.hyperic.hq.ui.exception.ParameterNotFoundException; @@ -97,6 +98,9 @@ boss.removeResourcesFromGroup(sessionId.intValue(), group, resources); + RequestUtils.setConfirmation(request, + "resource.group.inventory.confirm.RemoveResources"); + return returnSuccess(request, mapping,forwardParams); } catch (ParameterNotFoundException e2) { RequestUtils.setError(request, @@ -107,6 +111,12 @@ "resource.common.inventory.error.ResourceNotFound"); return returnFailure(request, mapping, forwardParams); - } + } catch (VetoException ve) { + RequestUtils.setErrorObject(request, + "resource.group.inventory.error.UpdateResourceListVetoed", + ve.getMessage()); + + return returnFailure(request, mapping, forwardParams); + } } } Modified: trunk/src/org/hyperic/hq/ui/service/RESTService.java =================================================================== --- trunk/src/org/hyperic/hq/ui/service/RESTService.java 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/src/org/hyperic/hq/ui/service/RESTService.java 2010-03-26 00:18:54 UTC (rev 14425) @@ -547,9 +547,6 @@ for (int i=0; i<aeidJArray.length(); i++) { AppdefEntityID aeid = new AppdefEntityID(aeidJArray.getString(i)); if (!aeid.isGroup()) { - Resource resource = ResourceManagerEJBImpl.getOne() - .findResource(aeid); - AppdefBossEJBImpl.getOne() .batchGroupAdd( user.getSessionId(), @@ -581,7 +578,7 @@ } jRes.put("groups", jarr); } - } catch (Exception e) { + } catch (Throwable e) { log.debug(e.getLocalizedMessage()); try { @@ -590,7 +587,7 @@ } catch (Exception e2) {} } - return (jRes.length() > 0) ? jRes.toString() : ERROR_GENERIC; + return jRes.toString(); } /** Modified: trunk/web/WEB-INF/classes/ApplicationResources.properties =================================================================== --- trunk/web/WEB-INF/classes/ApplicationResources.properties 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/web/WEB-INF/classes/ApplicationResources.properties 2010-03-26 00:18:54 UTC (rev 14425) @@ -1438,6 +1438,7 @@ resource.group.inventory.confirm.EditGeneralProperties=Your changes have been saved. resource.group.inventory.confirm.AddResources=The requested resources have been added to the group. resource.group.inventory.confirm.AddRoles=The requested roles have been added to the group. +resource.group.inventory.confirm.RemoveResources=The requested resources have been removed from the group. resource.group.inventory.error.DuplicateGroupName=Group Name is already used. resource.group.inventory.error.GroupNameIsRequired=Group name is required. @@ -1449,6 +1450,7 @@ resource.group.inventory.error.EditPermission=You do not have permission to edit this group. resource.group.inventory.error.ViewPermission=You do not have permission to view this group. resource.group.inventory.error.DuplicateClusterAssignment=One or more services in this group have already been assigned to a cluster. +resource.group.inventory.error.UpdateResourceListVetoed={0} resource.group.AddToGroup.Title=Add to Group resource.group.AddToGroup.NewGroup=Add to new group Modified: trunk/web/WEB-INF/struts-config.xml =================================================================== --- trunk/web/WEB-INF/struts-config.xml 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/web/WEB-INF/struts-config.xml 2010-03-26 00:18:54 UTC (rev 14425) @@ -1603,12 +1603,13 @@ <forward name="success" path="/resource/group/Inventory.do?mode=view"/> </action> - <action path="/resource/group/inventory/RemoveApp" + <action path="/resource/group/inventory/RemoveGroupResources" name="RemoveGroupResourcesForm" type="org.hyperic.hq.ui.action.resource.group.inventory.RemoveAction" scope="request" input="/resource/service/Inventory.do?mode=view"> - <forward name="success" path="/resource/group/Inventory.do?mode=view" redirect="true"/> + <forward name="failure" path="/resource/group/Inventory.do?mode=view"/> + <forward name="success" path="/resource/group/Inventory.do?mode=view"/> </action> <!-- / --> Modified: trunk/web/js/lib/lib.js =================================================================== --- trunk/web/js/lib/lib.js 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/web/js/lib/lib.js 2010-03-26 00:18:54 UTC (rev 14425) @@ -2997,9 +2997,14 @@ groupId: "['" + formArray.group.toString().split(",").join("','") + "']"}, handleAs: 'json', load: function(data) { - var successText = "The requested groups have been assigned."; - that.displayConfirmation(that.message_area.AddToExistingGroup, successText); - setTimeout('MyGroupManager.dialogs.AddToExistingGroup.hide()', 2000); + if (data && data.error) { + console.debug(data.error_message, data); + that.displayError(that.message_area.AddToExistingGroup, data.error_message); + } else { + var successText = "The requested groups have been assigned."; + that.displayConfirmation(that.message_area.AddToExistingGroup, successText); + setTimeout('MyGroupManager.dialogs.AddToExistingGroup.hide()', 2000); + } }, error: function(data) { var errorText = "An error occurred processing your request."; Modified: trunk/web/resource/group/inventory/ListResources.jsp =================================================================== --- trunk/web/resource/group/inventory/ListResources.jsp 2010-03-25 23:03:40 UTC (rev 14424) +++ trunk/web/resource/group/inventory/ListResources.jsp 2010-03-26 00:18:54 UTC (rev 14425) @@ -92,7 +92,7 @@ </c:if> </c:url> -<html:form action="/resource/group/inventory/RemoveApp"> +<html:form action="/resource/group/inventory/RemoveGroupResources"> <html:hidden property="eid" value="${Resource.entityId}"/> <!-- RESOURCES, COMPATIBLE CONTENTS --> |