You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by mc...@apache.org on 2014/03/14 00:55:06 UTC

[13/50] [abbrv] iam/plugin: Rename Acl to IAM everywhere

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/187f9cd0/services/iam/plugin/src/org/apache/cloudstack/iam/IAMApiServiceImpl.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/src/org/apache/cloudstack/iam/IAMApiServiceImpl.java b/services/iam/plugin/src/org/apache/cloudstack/iam/IAMApiServiceImpl.java
new file mode 100644
index 0000000..de57a41
--- /dev/null
+++ b/services/iam/plugin/src/org/apache/cloudstack/iam/IAMApiServiceImpl.java
@@ -0,0 +1,690 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package org.apache.cloudstack.iam;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import javax.ejb.Local;
+import javax.inject.Inject;
+import javax.naming.ConfigurationException;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.IAMEntityType;
+import org.apache.cloudstack.acl.PermissionScope;
+import org.apache.cloudstack.acl.SecurityChecker.AccessType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.BaseListCmd;
+import org.apache.cloudstack.api.command.iam.AddAccountToIAMGroupCmd;
+import org.apache.cloudstack.api.command.iam.AddIAMPermissionToIAMPolicyCmd;
+import org.apache.cloudstack.api.command.iam.AttachIAMPolicyToAccountCmd;
+import org.apache.cloudstack.api.command.iam.AttachIAMPolicyToIAMGroupCmd;
+import org.apache.cloudstack.api.command.iam.CreateIAMGroupCmd;
+import org.apache.cloudstack.api.command.iam.CreateIAMPolicyCmd;
+import org.apache.cloudstack.api.command.iam.DeleteIAMGroupCmd;
+import org.apache.cloudstack.api.command.iam.DeleteIAMPolicyCmd;
+import org.apache.cloudstack.api.command.iam.ListIAMGroupsCmd;
+import org.apache.cloudstack.api.command.iam.ListIAMPoliciesCmd;
+import org.apache.cloudstack.api.command.iam.RemoveAccountFromIAMGroupCmd;
+import org.apache.cloudstack.api.command.iam.RemoveIAMPermissionFromIAMPolicyCmd;
+import org.apache.cloudstack.api.command.iam.RemoveIAMPolicyFromAccountCmd;
+import org.apache.cloudstack.api.command.iam.RemoveIAMPolicyFromIAMGroupCmd;
+import org.apache.cloudstack.api.response.ListResponse;
+import org.apache.cloudstack.api.response.iam.IAMGroupResponse;
+import org.apache.cloudstack.api.response.iam.IAMPermissionResponse;
+import org.apache.cloudstack.api.response.iam.IAMPolicyResponse;
+import org.apache.cloudstack.context.CallContext;
+import org.apache.cloudstack.framework.messagebus.MessageBus;
+import org.apache.cloudstack.framework.messagebus.MessageSubscriber;
+import org.apache.cloudstack.iam.api.IAMGroup;
+import org.apache.cloudstack.iam.api.IAMPolicy;
+import org.apache.cloudstack.iam.api.IAMPolicyPermission;
+import org.apache.cloudstack.iam.api.IAMPolicyPermission.Permission;
+import org.apache.cloudstack.iam.api.IAMService;
+
+import com.cloud.api.ApiServerService;
+import com.cloud.domain.Domain;
+import com.cloud.domain.DomainVO;
+import com.cloud.domain.dao.DomainDao;
+import com.cloud.event.ActionEvent;
+import com.cloud.event.EventTypes;
+import com.cloud.exception.InvalidParameterValueException;
+import com.cloud.template.TemplateManager;
+import com.cloud.user.Account;
+import com.cloud.user.AccountManager;
+import com.cloud.user.AccountVO;
+import com.cloud.user.DomainManager;
+import com.cloud.user.dao.AccountDao;
+import com.cloud.utils.Pair;
+import com.cloud.utils.component.Manager;
+import com.cloud.utils.component.ManagerBase;
+import com.cloud.utils.db.DB;
+import com.cloud.utils.db.EntityManager;
+
+@Local(value = {IAMApiService.class})
+public class IAMApiServiceImpl extends ManagerBase implements IAMApiService, Manager {
+
+    public static final Logger s_logger = Logger.getLogger(IAMApiServiceImpl.class);
+    private String _name;
+
+    @Inject
+    ApiServerService _apiServer;
+
+    @Inject
+    IAMService _iamSrv;
+
+    @Inject
+    DomainDao _domainDao;
+
+    @Inject
+    AccountDao _accountDao;
+
+    @Inject
+    AccountManager _accountMgr;
+
+    @Inject
+    MessageBus _messageBus;
+
+    @Override
+    public boolean configure(final String name, final Map<String, Object> params) throws ConfigurationException {
+        _messageBus.subscribe(AccountManager.MESSAGE_ADD_ACCOUNT_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                HashMap<Long, Long> acctGroupMap = (HashMap<Long, Long>) obj;
+                for (Long accountId : acctGroupMap.keySet()) {
+                    Long groupId = acctGroupMap.get(accountId);
+                    s_logger.debug("MessageBus message: new Account Added: " + accountId + ", adding it to groupId :"
+                            + groupId);
+                    addAccountToIAMGroup(accountId, groupId);
+                    // add it to domain group too
+                    AccountVO account = _accountDao.findById(accountId);
+                    Domain domain = _domainDao.findById(account.getDomainId());
+                    if (domain != null) {
+                        List<IAMGroup> domainGroups = listDomainGroup(domain);
+
+                        if (domainGroups != null) {
+                            for (IAMGroup group : domainGroups) {
+                                addAccountToIAMGroup(accountId, new Long(group.getId()));
+                            }
+                        }
+                    }
+                }
+            }
+        });
+
+        _messageBus.subscribe(AccountManager.MESSAGE_REMOVE_ACCOUNT_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                Long accountId = ((Long) obj);
+                if (accountId != null) {
+                    s_logger.debug("MessageBus message: Account removed: " + accountId
+                            + ", releasing the group associations");
+                    removeAccountFromIAMGroups(accountId);
+                }
+            }
+        });
+
+        _messageBus.subscribe(DomainManager.MESSAGE_ADD_DOMAIN_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                Long domainId = ((Long) obj);
+                if (domainId != null) {
+                    s_logger.debug("MessageBus message: new Domain created: " + domainId + ", creating a new group");
+                    Domain domain = _domainDao.findById(domainId);
+                    _iamSrv.createAclGroup("DomainGrp-" + domain.getUuid(), "Domain group", domain.getPath());
+                }
+            }
+        });
+
+        _messageBus.subscribe(DomainManager.MESSAGE_REMOVE_DOMAIN_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                Long domainId = ((Long) obj);
+                if (domainId != null) {
+                    s_logger.debug("MessageBus message: Domain removed: " + domainId + ", removing the domain group");
+                    Domain domain = _domainDao.findById(domainId);
+                    List<IAMGroup> groups = listDomainGroup(domain);
+                    for (IAMGroup group : groups) {
+                        _iamSrv.deleteAclGroup(group.getId());
+                    }
+                }
+            }
+        });
+
+        _messageBus.subscribe(TemplateManager.MESSAGE_REGISTER_PUBLIC_TEMPLATE_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                Long templateId = (Long)obj;
+                if (templateId != null) {
+                    s_logger.debug("MessageBus message: new public template registered: " + templateId + ", grant permission to domain admin and normal user policies");
+                    _iamSrv.addAclPermissionToAclPolicy(new Long(Account.ACCOUNT_TYPE_DOMAIN_ADMIN + 1), IAMEntityType.VirtualMachineTemplate.toString(),
+                            PermissionScope.RESOURCE.toString(), templateId, "listTemplates", AccessType.UseEntry.toString(), Permission.Allow, false);
+                    _iamSrv.addAclPermissionToAclPolicy(new Long(Account.ACCOUNT_TYPE_NORMAL + 1), IAMEntityType.VirtualMachineTemplate.toString(),
+                            PermissionScope.RESOURCE.toString(), templateId, "listTemplates", AccessType.UseEntry.toString(), Permission.Allow, false);
+                }
+            }
+        });
+
+        _messageBus.subscribe(TemplateManager.MESSAGE_RESET_TEMPLATE_PERMISSION_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                Long templateId = (Long)obj;
+                if (templateId != null) {
+                    s_logger.debug("MessageBus message: reset template permission: " + templateId);
+                    resetTemplatePermission(templateId);
+                }
+            }
+        });
+
+        _messageBus.subscribe(EntityManager.MESSAGE_REMOVE_ENTITY_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                Pair<IAMEntityType, Long> entity = (Pair<IAMEntityType, Long>)obj;
+                if (entity != null) {
+                    String entityType = entity.first().toString();
+                    Long entityId = entity.second();
+                    s_logger.debug("MessageBus message: delete an entity: (" + entityType + "," + entityId + "), remove its related permission");
+                    _iamSrv.removeAclPermissionForEntity(entityType, entityId);
+                }
+            }
+        });
+
+
+        _messageBus.subscribe(EntityManager.MESSAGE_GRANT_ENTITY_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                Map<String, Object> permit = (Map<String, Object>)obj;
+                if (permit != null) {
+                    String entityType = (String)permit.get(ApiConstants.ENTITY_TYPE);
+                    Long entityId = (Long)permit.get(ApiConstants.ENTITY_ID);
+                    AccessType accessType = (AccessType)permit.get(ApiConstants.ACCESS_TYPE);
+                    String action = (String)permit.get(ApiConstants.IAM_ACTION);
+                    List<Long> acctIds = (List<Long>)permit.get(ApiConstants.ACCOUNTS);
+                    s_logger.debug("MessageBus message: grant accounts permission to an entity: (" + entityType + "," + entityId + ")");
+                    grantEntityPermissioinToAccounts(entityType, entityId, accessType, action, acctIds);
+                }
+            }
+        });
+
+        _messageBus.subscribe(EntityManager.MESSAGE_REVOKE_ENTITY_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                Map<String, Object> permit = (Map<String, Object>)obj;
+                if (permit != null) {
+                    String entityType = (String)permit.get(ApiConstants.ENTITY_TYPE);
+                    Long entityId = (Long)permit.get(ApiConstants.ENTITY_ID);
+                    AccessType accessType = (AccessType)permit.get(ApiConstants.ACCESS_TYPE);
+                    String action = (String)permit.get(ApiConstants.IAM_ACTION);
+                    List<Long> acctIds = (List<Long>)permit.get(ApiConstants.ACCOUNTS);
+                    s_logger.debug("MessageBus message: revoke from accounts permission to an entity: (" + entityType + "," + entityId + ")");
+                    revokeEntityPermissioinFromAccounts(entityType, entityId, accessType, action, acctIds);
+                }
+            }
+        });
+
+        _messageBus.subscribe(EntityManager.MESSAGE_ADD_DOMAIN_WIDE_ENTITY_EVENT, new MessageSubscriber() {
+            @Override
+            public void onPublishMessage(String senderAddress, String subject, Object obj) {
+                Map<String, Object> params = (Map<String, Object>) obj;
+                if (params != null) {
+                    addDomainWideResourceAccess(params);
+                }
+            }
+        });
+
+        return super.configure(name, params);
+    }
+
+    private void addDomainWideResourceAccess(Map<String, Object> params) {
+
+        IAMEntityType entityType = (IAMEntityType)params.get(ApiConstants.ENTITY_TYPE);
+        Long entityId = (Long) params.get(ApiConstants.ENTITY_ID);
+        Long domainId = (Long) params.get(ApiConstants.DOMAIN_ID);
+        Boolean isRecursive = (Boolean) params.get(ApiConstants.SUBDOMAIN_ACCESS);
+
+        if (entityType == IAMEntityType.Network) {
+            createPolicyAndAddToDomainGroup("DomainWideNetwork-" + entityId, "domain wide network", entityType.toString(),
+                    entityId, "listNetworks", AccessType.UseEntry, domainId, isRecursive);
+        } else if (entityType == IAMEntityType.AffinityGroup) {
+            createPolicyAndAddToDomainGroup("DomainWideNetwork-" + entityId, "domain wide affinityGroup", entityType.toString(),
+                    entityId, "listAffinityGroups", AccessType.UseEntry, domainId, isRecursive);
+        }
+
+    }
+
+    private void createPolicyAndAddToDomainGroup(String policyName, String description, String entityType,
+            Long entityId, String action, AccessType accessType, Long domainId, Boolean recursive) {
+
+       Domain domain = _domainDao.findById(domainId);
+       if (domain != null) {
+            IAMPolicy policy = _iamSrv.createAclPolicy(policyName, description, null, domain.getPath());
+            _iamSrv.addAclPermissionToAclPolicy(policy.getId(), entityType, PermissionScope.RESOURCE.toString(),
+                    entityId, action, accessType.toString(), Permission.Allow, recursive);
+            List<Long> policyList = new ArrayList<Long>();
+            policyList.add(new Long(policy.getId()));
+
+           List<IAMGroup> domainGroups = listDomainGroup(domain);
+           if (domainGroups != null) {
+               for (IAMGroup group : domainGroups) {
+                   _iamSrv.attachAclPoliciesToGroup(policyList, group.getId());
+               }
+           }
+       }
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_GROUP_CREATE, eventDescription = "Creating Acl Group", create = true)
+    public IAMGroup createIAMGroup(Account caller, String iamGroupName, String description) {
+        Long domainId = caller.getDomainId();
+        Domain callerDomain = _domainDao.findById(domainId);
+        if (callerDomain == null) {
+            throw new InvalidParameterValueException("Caller does not have a domain");
+        }
+        return _iamSrv.createAclGroup(iamGroupName, description, callerDomain.getPath());
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_GROUP_DELETE, eventDescription = "Deleting Acl Group")
+    public boolean deleteIAMGroup(final Long iamGroupId) {
+        return _iamSrv.deleteAclGroup(iamGroupId);
+    }
+
+    @Override
+    public List<IAMGroup> listIAMGroups(long accountId) {
+        return _iamSrv.listAclGroups(accountId);
+    }
+
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_GROUP_UPDATE, eventDescription = "Adding accounts to acl group")
+    public IAMGroup addAccountsToGroup(final List<Long> acctIds, final Long groupId) {
+        return _iamSrv.addAccountsToGroup(acctIds, groupId);
+    }
+
+
+    private void removeAccountFromIAMGroups(long accountId) {
+        List<IAMGroup> groups = listIAMGroups(accountId);
+        List<Long> accts = new ArrayList<Long>();
+        accts.add(accountId);
+        if (groups != null) {
+            for (IAMGroup grp : groups) {
+                removeAccountsFromGroup(accts, grp.getId());
+            }
+        }
+    }
+
+    private void addAccountToIAMGroup(long accountId, long groupId) {
+        List<Long> accts = new ArrayList<Long>();
+        accts.add(accountId);
+        addAccountsToGroup(accts, groupId);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_GROUP_UPDATE, eventDescription = "Removing accounts from acl group")
+    public IAMGroup removeAccountsFromGroup(final List<Long> acctIds, final Long groupId) {
+        return _iamSrv.removeAccountsFromGroup(acctIds, groupId);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_POLICY_CREATE, eventDescription = "Creating IAM Policy", create = true)
+    public IAMPolicy createIAMPolicy(Account caller, final String iamPolicyName, final String description, final Long parentPolicyId) {
+        Long domainId = caller.getDomainId();
+        Domain callerDomain = _domainDao.findById(domainId);
+        if (callerDomain == null) {
+            throw new InvalidParameterValueException("Caller does not have a domain");
+        }
+        return _iamSrv.createAclPolicy(iamPolicyName, description, parentPolicyId, callerDomain.getPath());
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_POLICY_DELETE, eventDescription = "Deleting IAM Policy")
+    public boolean deleteIAMPolicy(final long iamPolicyId) {
+        return _iamSrv.deleteAclPolicy(iamPolicyId);
+    }
+
+
+    @Override
+    public List<IAMPolicy> listIAMPolicies(long accountId) {
+        return _iamSrv.listAclPolicies(accountId);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_GROUP_UPDATE, eventDescription = "Attaching policy to acl group")
+    public IAMGroup attachIAMPoliciesToGroup(final List<Long> policyIds, final Long groupId) {
+        return _iamSrv.attachAclPoliciesToGroup(policyIds, groupId);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_GROUP_UPDATE, eventDescription = "Removing policies from acl group")
+    public IAMGroup removeIAMPoliciesFromGroup(final List<Long> policyIds, final Long groupId) {
+        return _iamSrv.removeAclPoliciesFromGroup(policyIds, groupId);
+    }
+
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_ACCOUNT_POLICY_UPDATE, eventDescription = "Attaching policy to accounts")
+    public void attachIAMPolicyToAccounts(final Long policyId, final List<Long> accountIds) {
+        _iamSrv.attachAclPolicyToAccounts(policyId, accountIds);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_ACCOUNT_POLICY_UPDATE, eventDescription = "Removing policy from accounts")
+    public void removeIAMPolicyFromAccounts(final Long policyId, final List<Long> accountIds) {
+        _iamSrv.removeAclPolicyFromAccounts(policyId, accountIds);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_POLICY_GRANT, eventDescription = "Granting acl permission to IAM Policy")
+    public IAMPolicy addIAMPermissionToIAMPolicy(long iamPolicyId, String entityType, PermissionScope scope,
+            Long scopeId, String action, Permission perm, Boolean recursive) {
+        Class<?> cmdClass = _apiServer.getCmdClass(action);
+        AccessType accessType = null;
+        if (BaseListCmd.class.isAssignableFrom(cmdClass)) {
+            accessType = AccessType.UseEntry;
+        }
+        return _iamSrv.addAclPermissionToAclPolicy(iamPolicyId, entityType, scope.toString(), scopeId, action,
+                accessType.toString(), perm, recursive);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_IAM_POLICY_REVOKE, eventDescription = "Revoking acl permission from IAM Policy")
+    public IAMPolicy removeIAMPermissionFromIAMPolicy(long iamPolicyId, String entityType, PermissionScope scope, Long scopeId, String action) {
+        return _iamSrv.removeAclPermissionFromAclPolicy(iamPolicyId, entityType, scope.toString(), scopeId, action);
+    }
+
+    @Override
+    public IAMPolicyPermission getIAMPolicyPermission(long accountId, String entityType, String action) {
+        List<IAMPolicy> policies = _iamSrv.listAclPolicies(accountId);
+        IAMPolicyPermission curPerm = null;
+        for (IAMPolicy policy : policies) {
+            List<IAMPolicyPermission> perms = _iamSrv.listPolicyPermissionByActionAndEntity(policy.getId(), action,
+                    entityType);
+            if (perms == null || perms.size() == 0)
+                continue;
+            IAMPolicyPermission perm = perms.get(0); // just pick one
+            if (curPerm == null) {
+                curPerm = perm;
+            } else if (PermissionScope.valueOf(perm.getScope()).greaterThan(PermissionScope.valueOf(curPerm.getScope()))) {
+                // pick the more relaxed allowed permission
+                curPerm = perm;
+            }
+        }
+
+        return curPerm;
+    }
+
+
+    @Override
+    public IAMPolicyResponse createIAMPolicyResponse(IAMPolicy policy) {
+        IAMPolicyResponse response = new IAMPolicyResponse();
+        response.setId(policy.getUuid());
+        response.setName(policy.getName());
+        response.setDescription(policy.getDescription());
+        String domainPath = policy.getPath();
+        if (domainPath != null) {
+            DomainVO domain = _domainDao.findDomainByPath(domainPath);
+            if (domain != null) {
+                response.setDomainId(domain.getUuid());
+                response.setDomainName(domain.getName());
+            }
+        }
+        long accountId = policy.getAccountId();
+        AccountVO owner = _accountDao.findById(accountId);
+        if (owner != null) {
+            response.setAccountName(owner.getAccountName());
+        }
+        // find permissions associated with this policy
+        List<IAMPolicyPermission> permissions = _iamSrv.listPolicyPermissions(policy.getId());
+        if (permissions != null && permissions.size() > 0) {
+            for (IAMPolicyPermission permission : permissions) {
+                IAMPermissionResponse perm = new IAMPermissionResponse();
+                perm.setAction(permission.getAction());
+                if (permission.getEntityType() != null) {
+                    perm.setEntityType(IAMEntityType.valueOf(permission.getEntityType()));
+                }
+                if (permission.getScope() != null) {
+                    perm.setScope(PermissionScope.valueOf(permission.getScope()));
+                }
+                perm.setScopeId(permission.getScopeId());
+                perm.setPermission(permission.getPermission());
+                response.addPermission(perm);
+            }
+        }
+        response.setObjectName("aclpolicy");
+        return response;
+    }
+
+    @Override
+    public IAMGroupResponse createIAMGroupResponse(IAMGroup group) {
+        IAMGroupResponse response = new IAMGroupResponse();
+        response.setId(group.getUuid());
+        response.setName(group.getName());
+        response.setDescription(group.getDescription());
+        String domainPath = group.getPath();
+        if (domainPath != null) {
+            DomainVO domain = _domainDao.findDomainByPath(domainPath);
+            if (domain != null) {
+                response.setDomainId(domain.getUuid());
+                response.setDomainName(domain.getName());
+            }
+        }
+        long accountId = group.getAccountId();
+        AccountVO owner = _accountDao.findById(accountId);
+        if (owner != null) {
+            response.setAccountName(owner.getAccountName());
+        }
+        // find all the members in this group
+        List<Long> members = _iamSrv.listAccountsByGroup(group.getId());
+        if (members != null && members.size() > 0) {
+            for (Long member : members) {
+                AccountVO mem = _accountDao.findById(member);
+                if (mem != null) {
+                    response.addMemberAccount(mem.getAccountName());
+                }
+            }
+        }
+
+        // find all the policies attached to this group
+        List<IAMPolicy> policies = _iamSrv.listAclPoliciesByGroup(group.getId());
+        if (policies != null && policies.size() > 0) {
+            for (IAMPolicy policy : policies) {
+                response.addPolicy(policy.getName());
+            }
+        }
+
+        response.setObjectName("aclgroup");
+        return response;
+
+    }
+
+    public List<IAMGroup> listDomainGroup(Domain domain) {
+
+        if (domain != null) {
+            String domainPath = domain.getPath();
+            // search for groups
+            Pair<List<IAMGroup>, Integer> result = _iamSrv.listAclGroups(null, "DomainGrp-" + domain.getUuid(),
+                    domainPath, null, null);
+            return result.first();
+        }
+        return new ArrayList<IAMGroup>();
+
+    }
+
+    @Override
+    public ListResponse<IAMGroupResponse> listIAMGroups(Long iamGroupId, String iamGroupName, Long domainId, Long startIndex, Long pageSize) {
+        // acl check
+        Account caller = CallContext.current().getCallingAccount();
+
+        Domain domain = null;
+        if (domainId != null) {
+            domain = _domainDao.findById(domainId);
+            if (domain == null) {
+                throw new InvalidParameterValueException("Domain id=" + domainId + " doesn't exist");
+            }
+
+            _accountMgr.checkAccess(caller, domain);
+        } else {
+            domain = _domainDao.findById(caller.getDomainId());
+        }
+        String domainPath = domain.getPath();
+        // search for groups
+        Pair<List<IAMGroup>, Integer> result = _iamSrv.listAclGroups(iamGroupId, iamGroupName, domainPath, startIndex, pageSize);
+        // generate group response
+        ListResponse<IAMGroupResponse> response = new ListResponse<IAMGroupResponse>();
+        List<IAMGroupResponse> groupResponses = new ArrayList<IAMGroupResponse>();
+        for (IAMGroup group : result.first()) {
+            IAMGroupResponse resp = createIAMGroupResponse(group);
+            groupResponses.add(resp);
+        }
+        response.setResponses(groupResponses, result.second());
+        return response;
+    }
+
+    @Override
+    public ListResponse<IAMPolicyResponse> listIAMPolicies(Long iamPolicyId, String iamPolicyName, Long domainId, Long startIndex,
+            Long pageSize) {
+        // acl check
+        Account caller = CallContext.current().getCallingAccount();
+
+        Domain domain = null;
+        if (domainId != null) {
+            domain = _domainDao.findById(domainId);
+            if (domain == null) {
+                throw new InvalidParameterValueException("Domain id=" + domainId + " doesn't exist");
+            }
+
+            _accountMgr.checkAccess(caller, domain);
+        } else {
+            domain = _domainDao.findById(caller.getDomainId());
+        }
+        String domainPath = domain.getPath();
+        // search for policies
+        Pair<List<IAMPolicy>, Integer> result = _iamSrv.listAclPolicies(iamPolicyId, iamPolicyName, domainPath, startIndex, pageSize);
+        // generate policy response
+        ListResponse<IAMPolicyResponse> response = new ListResponse<IAMPolicyResponse>();
+        List<IAMPolicyResponse> policyResponses = new ArrayList<IAMPolicyResponse>();
+        for (IAMPolicy policy : result.first()) {
+            IAMPolicyResponse resp = createIAMPolicyResponse(policy);
+            policyResponses.add(resp);
+        }
+        response.setResponses(policyResponses, result.second());
+        return response;
+    }
+
+    @Override
+    public void grantEntityPermissioinToAccounts(String entityType, Long entityId, AccessType accessType, String action, List<Long> accountIds) {
+        // check if there is already a policy with only this permission added to it
+        IAMPolicy policy = _iamSrv.getResourceGrantPolicy(entityType, entityId, accessType.toString(), action);
+        if (policy == null) {
+            // not found, just create a policy with resource grant permission
+            Account caller = CallContext.current().getCallingAccount();
+            String aclPolicyName = "policyGrant" + entityType + entityId;
+            String description = "Policy to grant permission to " + entityType + entityId;
+            policy = createIAMPolicy(caller, aclPolicyName, description, null);
+            // add permission to this policy
+            addIAMPermissionToIAMPolicy(policy.getId(), entityType, PermissionScope.RESOURCE, entityId, action, Permission.Allow, false);
+        }
+        // attach this policy to list of accounts if not attached already
+        Long policyId = policy.getId();
+        for (Long acctId : accountIds) {
+            if (!isPolicyAttachedToAccount(policyId, acctId)) {
+                attachIAMPolicyToAccounts(policyId, Collections.singletonList(acctId));
+            }
+        }
+    }
+
+    @Override
+    public void revokeEntityPermissioinFromAccounts(String entityType, Long entityId, AccessType accessType, String action, List<Long> accountIds) {
+        // there should already a policy with only this permission added to it, this call is mainly used
+        IAMPolicy policy = _iamSrv.getResourceGrantPolicy(entityType, entityId, accessType.toString(), action);
+        if (policy == null) {
+            s_logger.warn("Cannot find a policy associated with this entity permissioin to be revoked, just return");
+            return;
+        }
+        // detach this policy from list of accounts if not detached already
+        Long policyId = policy.getId();
+        for (Long acctId : accountIds) {
+            if (isPolicyAttachedToAccount(policyId, acctId)) {
+                removeIAMPolicyFromAccounts(policyId, Collections.singletonList(acctId));
+            }
+        }
+
+    }
+
+    private boolean isPolicyAttachedToAccount(Long policyId, Long accountId) {
+        List<IAMPolicy> pList = listIAMPolicies(accountId);
+        for (IAMPolicy p : pList) {
+            if (p.getId() == policyId.longValue()) {
+                return true;
+            }
+        }
+        return false;
+    }
+
+    private void resetTemplatePermission(Long templateId){
+        // reset template will change template to private, so we need to remove its permission for domain admin and normal user group
+        _iamSrv.removeAclPermissionFromAclPolicy(new Long(Account.ACCOUNT_TYPE_DOMAIN_ADMIN + 1), IAMEntityType.VirtualMachineTemplate.toString(),
+                PermissionScope.RESOURCE.toString(), templateId, "listTemplates");
+        _iamSrv.removeAclPermissionFromAclPolicy(new Long(Account.ACCOUNT_TYPE_NORMAL + 1), IAMEntityType.VirtualMachineTemplate.toString(),
+                PermissionScope.RESOURCE.toString(), templateId, "listTemplates");
+        // check if there is a policy with only UseEntry permission for this template added
+        IAMPolicy policy = _iamSrv.getResourceGrantPolicy(IAMEntityType.VirtualMachineTemplate.toString(), templateId, AccessType.UseEntry.toString(), "listTemplates");
+        if ( policy == null ){
+            s_logger.info("No policy found for this template grant: " + templateId + ", no detach to be done");
+            return;
+        }
+        // delete the policy, which should detach it from groups and accounts
+        _iamSrv.deleteAclPolicy(policy.getId());
+
+    }
+
+    @Override
+    public List<Class<?>> getCommands() {
+        List<Class<?>> cmdList = new ArrayList<Class<?>>();
+        cmdList.add(CreateIAMPolicyCmd.class);
+        cmdList.add(DeleteIAMPolicyCmd.class);
+        cmdList.add(ListIAMPoliciesCmd.class);
+        cmdList.add(AddIAMPermissionToIAMPolicyCmd.class);
+        cmdList.add(RemoveIAMPermissionFromIAMPolicyCmd.class);
+        cmdList.add(AttachIAMPolicyToIAMGroupCmd.class);
+        cmdList.add(RemoveIAMPolicyFromIAMGroupCmd.class);
+        cmdList.add(CreateIAMGroupCmd.class);
+        cmdList.add(DeleteIAMGroupCmd.class);
+        cmdList.add(ListIAMGroupsCmd.class);
+        cmdList.add(AddAccountToIAMGroupCmd.class);
+        cmdList.add(RemoveAccountFromIAMGroupCmd.class);
+        cmdList.add(AttachIAMPolicyToAccountCmd.class);
+        cmdList.add(RemoveIAMPolicyFromAccountCmd.class);
+        return cmdList;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/187f9cd0/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedAPIAccessChecker.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedAPIAccessChecker.java b/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedAPIAccessChecker.java
index 448e45f..48e6ede 100644
--- a/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedAPIAccessChecker.java
+++ b/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedAPIAccessChecker.java
@@ -37,9 +37,9 @@ import org.apache.cloudstack.api.APICommand;
 import org.apache.cloudstack.api.BaseAsyncCreateCmd;
 import org.apache.cloudstack.api.BaseCmd;
 import org.apache.cloudstack.api.BaseListCmd;
-import org.apache.cloudstack.iam.api.AclPolicy;
-import org.apache.cloudstack.iam.api.AclPolicyPermission;
-import org.apache.cloudstack.iam.api.AclPolicyPermission.Permission;
+import org.apache.cloudstack.iam.api.IAMPolicy;
+import org.apache.cloudstack.iam.api.IAMPolicyPermission;
+import org.apache.cloudstack.iam.api.IAMPolicyPermission.Permission;
 import org.apache.cloudstack.iam.api.IAMService;
 
 import com.cloud.api.ApiServerService;
@@ -90,7 +90,7 @@ public class RoleBasedAPIAccessChecker extends AdapterBase implements APIChecker
                     + "is null");
         }
 
-        List<AclPolicy> policies = _iamSrv.listAclPolicies(account.getAccountId());
+        List<IAMPolicy> policies = _iamSrv.listAclPolicies(account.getAccountId());
 
         boolean isAllowed = _iamSrv.isActionAllowedForPolicies(commandName, policies);
         if (!isAllowed) {
@@ -259,11 +259,11 @@ public class RoleBasedAPIAccessChecker extends AdapterBase implements APIChecker
 
 
         if (entityTypes == null || entityTypes.length == 0) {
-            _iamSrv.addAclPermissionToAclPolicy(policyId, null, permissionScope.toString(), new Long(AclPolicyPermission.PERMISSION_SCOPE_ID_CURRENT_CALLER),
+            _iamSrv.addAclPermissionToAclPolicy(policyId, null, permissionScope.toString(), new Long(IAMPolicyPermission.PERMISSION_SCOPE_ID_CURRENT_CALLER),
                     apiName, (accessType == null) ? null : accessType.toString(), Permission.Allow, false);
         } else {
             for (IAMEntityType entityType : entityTypes) {
-                _iamSrv.addAclPermissionToAclPolicy(policyId, entityType.toString(), permissionScope.toString(), new Long(AclPolicyPermission.PERMISSION_SCOPE_ID_CURRENT_CALLER),
+                _iamSrv.addAclPermissionToAclPolicy(policyId, entityType.toString(), permissionScope.toString(), new Long(IAMPolicyPermission.PERMISSION_SCOPE_ID_CURRENT_CALLER),
                         apiName, (accessType == null) ? null : accessType.toString(), Permission.Allow, false);
             }
          }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/187f9cd0/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityAccessChecker.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityAccessChecker.java b/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityAccessChecker.java
index 5420f84..13f6914 100644
--- a/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityAccessChecker.java
+++ b/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityAccessChecker.java
@@ -28,9 +28,9 @@ import org.apache.cloudstack.acl.ControlledEntity;
 import org.apache.cloudstack.acl.PermissionScope;
 import org.apache.cloudstack.acl.SecurityChecker;
 import org.apache.cloudstack.api.InternalIdentity;
-import org.apache.cloudstack.iam.api.AclGroup;
-import org.apache.cloudstack.iam.api.AclPolicy;
-import org.apache.cloudstack.iam.api.AclPolicyPermission;
+import org.apache.cloudstack.iam.api.IAMGroup;
+import org.apache.cloudstack.iam.api.IAMPolicy;
+import org.apache.cloudstack.iam.api.IAMPolicyPermission;
 import org.apache.cloudstack.iam.api.IAMService;
 
 import com.cloud.acl.DomainChecker;
@@ -64,7 +64,7 @@ public class RoleBasedEntityAccessChecker extends DomainChecker implements Secur
 
         if (entity == null && action != null) {
             // check if caller can do this action
-            List<AclPolicy> policies = _iamSrv.listAclPolicies(caller.getAccountId());
+            List<IAMPolicy> policies = _iamSrv.listAclPolicies(caller.getAccountId());
 
             boolean isAllowed = _iamSrv.isActionAllowedForPolicies(action, policies);
             if (!isAllowed) {
@@ -80,11 +80,11 @@ public class RoleBasedEntityAccessChecker extends DomainChecker implements Secur
         }
 
         // get all Policies of this caller w.r.t the entity
-        List<AclPolicy> policies = getEffectivePolicies(caller, entity);
-        HashMap<AclPolicy, Boolean> policyPermissionMap = new HashMap<AclPolicy, Boolean>();
+        List<IAMPolicy> policies = getEffectivePolicies(caller, entity);
+        HashMap<IAMPolicy, Boolean> policyPermissionMap = new HashMap<IAMPolicy, Boolean>();
 
-        for (AclPolicy policy : policies) {
-            List<AclPolicyPermission> permissions = new ArrayList<AclPolicyPermission>();
+        for (IAMPolicy policy : policies) {
+            List<IAMPolicyPermission> permissions = new ArrayList<IAMPolicyPermission>();
 
             if (action != null) {
                 permissions = _iamSrv.listPolicyPermissionByActionAndEntity(policy.getId(), action, entityType);
@@ -100,7 +100,7 @@ public class RoleBasedEntityAccessChecker extends DomainChecker implements Secur
                             accessType.toString(), entityType));
                 }
             }
-            for (AclPolicyPermission permission : permissions) {
+            for (IAMPolicyPermission permission : permissions) {
                 if (checkPermissionScope(caller, permission.getScope(), permission.getScopeId(), entity)) {
                     if (permission.getEntityType().equals(entityType)) {
                         policyPermissionMap.put(policy, permission.getPermission().isGranted());
@@ -129,7 +129,7 @@ public class RoleBasedEntityAccessChecker extends DomainChecker implements Secur
 
     private boolean checkPermissionScope(Account caller, String scope, Long scopeId, ControlledEntity entity) {
 
-        if(scopeId != null && !scopeId.equals(new Long(AclPolicyPermission.PERMISSION_SCOPE_ID_CURRENT_CALLER))){
+        if(scopeId != null && !scopeId.equals(new Long(IAMPolicyPermission.PERMISSION_SCOPE_ID_CURRENT_CALLER))){
             //scopeId is set
             if (scope.equals(PermissionScope.ACCOUNT.name())) {
                 if(scopeId == entity.getAccountId()){
@@ -147,7 +147,7 @@ public class RoleBasedEntityAccessChecker extends DomainChecker implements Secur
                     }
                 }
             }
-        } else if (scopeId == null || scopeId.equals(new Long(AclPolicyPermission.PERMISSION_SCOPE_ID_CURRENT_CALLER))) {
+        } else if (scopeId == null || scopeId.equals(new Long(IAMPolicyPermission.PERMISSION_SCOPE_ID_CURRENT_CALLER))) {
             if (scope.equals(PermissionScope.ACCOUNT.name())) {
                 if(caller.getAccountId() == entity.getAccountId()){
                     return true;
@@ -161,10 +161,10 @@ public class RoleBasedEntityAccessChecker extends DomainChecker implements Secur
         return false;
     }
 
-    private List<AclPolicy> getEffectivePolicies(Account caller, ControlledEntity entity) {
+    private List<IAMPolicy> getEffectivePolicies(Account caller, ControlledEntity entity) {
 
         // Get the static Policies of the Caller
-        List<AclPolicy> policies = _iamSrv.listAclPolicies(caller.getId());
+        List<IAMPolicy> policies = _iamSrv.listAclPolicies(caller.getId());
 
         // add any dynamic policies w.r.t the entity
         if (caller.getId() == entity.getAccountId()) {
@@ -172,11 +172,11 @@ public class RoleBasedEntityAccessChecker extends DomainChecker implements Secur
             policies.add(_iamSrv.getResourceOwnerPolicy());
         }
 
-        List<AclGroup> groups = _iamSrv.listAclGroups(caller.getId());
-        for (AclGroup group : groups) {
+        List<IAMGroup> groups = _iamSrv.listAclGroups(caller.getId());
+        for (IAMGroup group : groups) {
             // for each group find the grand parent groups.
-            List<AclGroup> parentGroups = _iamSrv.listParentAclGroups(group.getId());
-            for (AclGroup parentGroup : parentGroups) {
+            List<IAMGroup> parentGroups = _iamSrv.listParentAclGroups(group.getId());
+            for (IAMGroup parentGroup : parentGroups) {
                 policies.addAll(_iamSrv.listRecursiveAclPoliciesByGroup(parentGroup.getId()));
             }
         }

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/187f9cd0/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityQuerySelector.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityQuerySelector.java b/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityQuerySelector.java
index 4cec0d9..596ac7e 100644
--- a/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityQuerySelector.java
+++ b/services/iam/plugin/src/org/apache/cloudstack/iam/RoleBasedEntityQuerySelector.java
@@ -25,9 +25,9 @@ import org.apache.log4j.Logger;
 
 import org.apache.cloudstack.acl.PermissionScope;
 import org.apache.cloudstack.acl.QuerySelector;
-import org.apache.cloudstack.iam.api.AclGroup;
-import org.apache.cloudstack.iam.api.AclPolicy;
-import org.apache.cloudstack.iam.api.AclPolicyPermission;
+import org.apache.cloudstack.iam.api.IAMGroup;
+import org.apache.cloudstack.iam.api.IAMPolicy;
+import org.apache.cloudstack.iam.api.IAMPolicyPermission;
 import org.apache.cloudstack.iam.api.IAMService;
 
 import com.cloud.user.Account;
@@ -44,13 +44,13 @@ public class RoleBasedEntityQuerySelector extends AdapterBase implements QuerySe
     public List<Long> getAuthorizedDomains(Account caller, String action) {
         long accountId = caller.getAccountId();
         // Get the static Policies of the Caller
-        List<AclPolicy> policies = _iamService.listAclPolicies(accountId);
+        List<IAMPolicy> policies = _iamService.listAclPolicies(accountId);
         // for each policy, find granted permission with Domain scope
         List<Long> domainIds = new ArrayList<Long>();
-        for (AclPolicy policy : policies) {
-            List<AclPolicyPermission> pp = _iamService.listPolicyPermissionsByScope(policy.getId(), action, PermissionScope.DOMAIN.toString());
+        for (IAMPolicy policy : policies) {
+            List<IAMPolicyPermission> pp = _iamService.listPolicyPermissionsByScope(policy.getId(), action, PermissionScope.DOMAIN.toString());
             if (pp != null) {
-                for (AclPolicyPermission p : pp) {
+                for (IAMPolicyPermission p : pp) {
                     if (p.getScopeId() != null) {
                         if (p.getScopeId().longValue() == -1) {
                             domainIds.add(caller.getDomainId());
@@ -68,13 +68,13 @@ public class RoleBasedEntityQuerySelector extends AdapterBase implements QuerySe
     public List<Long> getAuthorizedAccounts(Account caller, String action) {
         long accountId = caller.getAccountId();
         // Get the static Policies of the Caller
-        List<AclPolicy> policies = _iamService.listAclPolicies(accountId);
+        List<IAMPolicy> policies = _iamService.listAclPolicies(accountId);
         // for each policy, find granted permission with Account scope
         List<Long> accountIds = new ArrayList<Long>();
-        for (AclPolicy policy : policies) {
-            List<AclPolicyPermission> pp = _iamService.listPolicyPermissionsByScope(policy.getId(), action, PermissionScope.ACCOUNT.toString());
+        for (IAMPolicy policy : policies) {
+            List<IAMPolicyPermission> pp = _iamService.listPolicyPermissionsByScope(policy.getId(), action, PermissionScope.ACCOUNT.toString());
             if (pp != null) {
-                for (AclPolicyPermission p : pp) {
+                for (IAMPolicyPermission p : pp) {
                     if (p.getScopeId() != null) {
                         if (p.getScopeId().longValue() == -1) {
                             accountIds.add(caller.getId());
@@ -92,24 +92,24 @@ public class RoleBasedEntityQuerySelector extends AdapterBase implements QuerySe
     public List<Long> getAuthorizedResources(Account caller, String action) {
         long accountId = caller.getAccountId();
         // Get the static Policies of the Caller
-        List<AclPolicy> policies = _iamService.listAclPolicies(accountId);
+        List<IAMPolicy> policies = _iamService.listAclPolicies(accountId);
 
         // add the policies that grant recursive access
-        List<AclGroup> groups = _iamService.listAclGroups(caller.getId());
-        for (AclGroup group : groups) {
+        List<IAMGroup> groups = _iamService.listAclGroups(caller.getId());
+        for (IAMGroup group : groups) {
             // for each group find the grand parent groups.
-            List<AclGroup> parentGroups = _iamService.listParentAclGroups(group.getId());
-            for (AclGroup parentGroup : parentGroups) {
+            List<IAMGroup> parentGroups = _iamService.listParentAclGroups(group.getId());
+            for (IAMGroup parentGroup : parentGroups) {
                 policies.addAll(_iamService.listRecursiveAclPoliciesByGroup(parentGroup.getId()));
             }
         }
 
         // for each policy, find granted permission with Resource scope
         List<Long> entityIds = new ArrayList<Long>();
-        for (AclPolicy policy : policies) {
-            List<AclPolicyPermission> pp = _iamService.listPolicyPermissionsByScope(policy.getId(), action, PermissionScope.RESOURCE.toString());
+        for (IAMPolicy policy : policies) {
+            List<IAMPolicyPermission> pp = _iamService.listPolicyPermissionsByScope(policy.getId(), action, PermissionScope.RESOURCE.toString());
             if (pp != null) {
-                for (AclPolicyPermission p : pp) {
+                for (IAMPolicyPermission p : pp) {
                     if (p.getScopeId() != null) {
                         entityIds.add(p.getScopeId());
                     }
@@ -123,10 +123,10 @@ public class RoleBasedEntityQuerySelector extends AdapterBase implements QuerySe
     public boolean isGrantedAll(Account caller, String action) {
         long accountId = caller.getAccountId();
         // Get the static Policies of the Caller
-        List<AclPolicy> policies = _iamService.listAclPolicies(accountId);
+        List<IAMPolicy> policies = _iamService.listAclPolicies(accountId);
         // for each policy, find granted permission with ALL scope
-        for (AclPolicy policy : policies) {
-            List<AclPolicyPermission> pp = _iamService.listPolicyPermissionsByScope(policy.getId(), action, PermissionScope.ALL.toString());
+        for (IAMPolicy policy : policies) {
+            List<IAMPolicyPermission> pp = _iamService.listPolicyPermissionsByScope(policy.getId(), action, PermissionScope.ALL.toString());
             if (pp != null && pp.size() > 0) {
                 return true;
             }
@@ -136,9 +136,9 @@ public class RoleBasedEntityQuerySelector extends AdapterBase implements QuerySe
 
     @Override
     public List<String> listAclGroupsByAccount(long accountId) {
-        List<AclGroup> groups = _iamService.listAclGroups(accountId);
+        List<IAMGroup> groups = _iamService.listAclGroups(accountId);
         List<String> groupNames = new ArrayList<String>();
-        for (AclGroup grp : groups) {
+        for (IAMGroup grp : groups) {
             groupNames.add(grp.getName());
         }
         return groupNames;

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/187f9cd0/services/iam/plugin/test/org/apache/cloudstack/acl/AclApiServiceTest.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/test/org/apache/cloudstack/acl/AclApiServiceTest.java b/services/iam/plugin/test/org/apache/cloudstack/acl/AclApiServiceTest.java
deleted file mode 100644
index daf5b64..0000000
--- a/services/iam/plugin/test/org/apache/cloudstack/acl/AclApiServiceTest.java
+++ /dev/null
@@ -1,357 +0,0 @@
-package org.apache.cloudstack.acl;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNotNull;
-import static org.junit.Assert.assertTrue;
-import static org.mockito.Mockito.doNothing;
-import static org.mockito.Mockito.when;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Set;
-import java.util.UUID;
-
-import javax.inject.Inject;
-import javax.naming.ConfigurationException;
-
-import org.junit.After;
-import org.junit.Before;
-import org.junit.BeforeClass;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mockito;
-import org.springframework.context.annotation.Bean;
-import org.springframework.context.annotation.ComponentScan;
-import org.springframework.context.annotation.ComponentScan.Filter;
-import org.springframework.context.annotation.Configuration;
-import org.springframework.context.annotation.FilterType;
-import org.springframework.core.type.classreading.MetadataReader;
-import org.springframework.core.type.classreading.MetadataReaderFactory;
-import org.springframework.core.type.filter.TypeFilter;
-import org.springframework.test.context.ContextConfiguration;
-import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
-import org.springframework.test.context.support.AnnotationConfigContextLoader;
-
-import org.apache.cloudstack.acl.SecurityChecker.AccessType;
-import org.apache.cloudstack.iam.AclApiService;
-import org.apache.cloudstack.iam.AclApiServiceImpl;
-import org.apache.cloudstack.api.command.user.vm.ListVMsCmd;
-import org.apache.cloudstack.api.response.ListResponse;
-import org.apache.cloudstack.api.response.iam.AclGroupResponse;
-import org.apache.cloudstack.api.response.iam.AclPermissionResponse;
-import org.apache.cloudstack.api.response.iam.AclPolicyResponse;
-import org.apache.cloudstack.context.CallContext;
-import org.apache.cloudstack.framework.messagebus.MessageBus;
-import org.apache.cloudstack.iam.api.AclGroup;
-import org.apache.cloudstack.iam.api.AclPolicy;
-import org.apache.cloudstack.iam.api.AclPolicyPermission;
-import org.apache.cloudstack.iam.api.AclPolicyPermission.Permission;
-import org.apache.cloudstack.iam.api.IAMService;
-import org.apache.cloudstack.iam.server.AclGroupVO;
-import org.apache.cloudstack.iam.server.AclPolicyPermissionVO;
-import org.apache.cloudstack.iam.server.AclPolicyVO;
-import org.apache.cloudstack.test.utils.SpringUtils;
-
-import com.cloud.api.ApiServerService;
-import com.cloud.domain.DomainVO;
-import com.cloud.domain.dao.DomainDao;
-import com.cloud.network.dao.NetworkDomainDao;
-import com.cloud.user.Account;
-import com.cloud.user.AccountManager;
-import com.cloud.user.AccountVO;
-import com.cloud.user.UserVO;
-import com.cloud.user.dao.AccountDao;
-import com.cloud.utils.Pair;
-import com.cloud.utils.component.ComponentContext;
-
-@RunWith(SpringJUnit4ClassRunner.class)
-@ContextConfiguration(loader = AnnotationConfigContextLoader.class)
-public class AclApiServiceTest {
-
-    @Inject
-    IAMService _iamSrv;
-
-    @Inject
-    DomainDao _domainDao;
-
-    @Inject
-    AclApiService _aclSrv;
-
-    @Inject
-    AccountManager _accountMgr;
-
-    @Inject
-    AccountDao _accountDao;
-
-    @Inject
-    ApiServerService _apiServer;
-
-    private static Account caller;
-    private static Long callerId;
-    private static String callerAccountName = "tester";
-    private static Long callerDomainId = 3L;
-    private static String callerDomainPath = "/root/testdomain";
-    private static DomainVO callerDomain;
-
-    @BeforeClass
-    public static void setUpClass() throws ConfigurationException {
-    }
-
-    @Before
-    public void setUp() {
-        ComponentContext.initComponentsLifeCycle();
-        caller = new AccountVO(callerAccountName, callerDomainId, null, Account.ACCOUNT_TYPE_ADMIN, UUID.randomUUID().toString());
-        callerId = caller.getId();
-        callerDomain = new DomainVO();
-        callerDomain.setPath(callerDomainPath);
-        UserVO user = new UserVO(1, "testuser", "password", "firstname", "lastName", "email", "timezone", UUID.randomUUID().toString());
-        CallContext.register(user, caller);
-
-        when(_domainDao.findById(callerDomainId)).thenReturn(callerDomain);
-        doNothing().when(_accountMgr).checkAccess(caller, callerDomain);
-    }
-
-    @Test
-    public void createAclGroupTest() {
-        AclGroup group = new AclGroupVO("group1", "tester group1");
-        List<AclGroup> groups = new ArrayList<AclGroup>();
-        groups.add(group);
-        Pair<List<AclGroup>, Integer> grpList = new Pair<List<AclGroup>, Integer>(groups, 1);
-        when(_iamSrv.createAclGroup("group1", "tester group1", callerDomainPath)).thenReturn(group);
-        when(_iamSrv.listAclGroups(null, null, callerDomainPath, 0L, 20L)).thenReturn(grpList);
-
-        AclGroup createdGrp = _aclSrv.createAclGroup(caller, "group1", "tester group1");
-        assertNotNull("Acl group 'group1' failed to create ", createdGrp);
-        ListResponse<AclGroupResponse> grpResp = _aclSrv.listAclGroups(null, null, callerDomainId, 0L, 20L);
-        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
-        AclGroupResponse resp = grpResp.getResponses().get(0);
-        assertEquals("Error in created group name", "group1", resp.getName());
-    }
-
-    @Test
-    public void deleteAclGroupTest() {
-        when(_iamSrv.deleteAclGroup(1L)).thenReturn(true);
-        assertTrue("failed to delete acl group 1", _aclSrv.deleteAclGroup(1L));
-    }
-
-    @Test
-    public void listAclGroupTest() {
-        AclGroup group = new AclGroupVO("group1", "tester group1");
-        List<AclGroup> groups = new ArrayList<AclGroup>();
-        groups.add(group);
-        when(_iamSrv.listAclGroups(callerId)).thenReturn(groups);
-        List<AclGroup> grps = _aclSrv.listAclGroups(callerId);
-        assertTrue(grps != null && grps.size() == 1);
-        AclGroup grp = grps.get(0);
-        assertEquals("Error to retrieve group", "group1", grp.getName());
-    }
-
-    @Test
-    public void addRemoveAccountToGroupTest() {
-        AclGroup group = new AclGroupVO("group1", "tester group1");
-        List<AclGroup> groups = new ArrayList<AclGroup>();
-        groups.add(group);
-        Long groupId = group.getId();
-        List<Long> acctIds = new ArrayList<Long>();
-        AccountVO acct1 = new AccountVO(100L);
-        acct1.setAccountName("account1");
-        AccountVO acct2 = new AccountVO(200L);
-        acct2.setAccountName("account2");
-        acctIds.add(acct1.getId());
-        acctIds.add(acct2.getId());
-        when(_accountDao.findById(acct1.getId())).thenReturn(acct1);
-        when(_accountDao.findById(acct2.getId())).thenReturn(acct2);
-        when(_iamSrv.addAccountsToGroup(acctIds, groupId)).thenReturn(group);
-        when(_iamSrv.listAccountsByGroup(groupId)).thenReturn(acctIds);
-        Pair<List<AclGroup>, Integer> grpList = new Pair<List<AclGroup>, Integer>(groups, 1);
-        when(_iamSrv.listAclGroups(null, "group1", callerDomainPath, 0L, 20L)).thenReturn(grpList);
-        _aclSrv.addAccountsToGroup(acctIds, groupId);
-        ListResponse<AclGroupResponse> grpResp = _aclSrv.listAclGroups(null, "group1", callerDomainId, 0L, 20L);
-        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
-        AclGroupResponse resp = grpResp.getResponses().get(0);
-        Set<String> acctNames = resp.getAccountNameList();
-        assertEquals("There should be 2 accounts in the group", 2, acctNames.size());
-        assertTrue("account1 should be assigned to the group", acctNames.contains("account1"));
-        assertTrue("account2 should be assigned to the group", acctNames.contains("account2"));
-        // remove "account2" from group1
-        acctIds.remove(1);
-        List<Long> rmAccts = new ArrayList<Long>();
-        rmAccts.add(acct2.getId());
-        when(_iamSrv.removeAccountsFromGroup(rmAccts, groupId)).thenReturn(group);
-        _aclSrv.removeAccountsFromGroup(acctIds, groupId);
-        grpResp = _aclSrv.listAclGroups(null, "group1", callerDomainId, 0L, 20L);
-        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
-        resp = grpResp.getResponses().get(0);
-        acctNames = resp.getAccountNameList();
-        assertEquals("There should be 1 accounts in the group", 1, acctNames.size());
-        assertFalse("account2 should not belong to the group anymore", acctNames.contains("account2"));
-    }
-
-    @Test
-    public void createAclPolicyTest() {
-        AclPolicy policy = new AclPolicyVO("policy1", "tester policy1");
-        List<AclPolicy> policies = new ArrayList<AclPolicy>();
-        policies.add(policy);
-        Pair<List<AclPolicy>, Integer> policyList = new Pair<List<AclPolicy>, Integer>(policies, 1);
-        when(_iamSrv.createAclPolicy("policy1", "tester policy1", null, callerDomainPath)).thenReturn(policy);
-        when(_iamSrv.listAclPolicies(null, null, callerDomainPath, 0L, 20L)).thenReturn(policyList);
-
-        AclPolicy createdPolicy = _aclSrv.createAclPolicy(caller, "policy1", "tester policy1", null);
-        assertNotNull("Acl policy 'policy1' failed to create ", createdPolicy);
-        ListResponse<AclPolicyResponse> policyResp = _aclSrv.listAclPolicies(null, null, callerDomainId, 0L, 20L);
-        assertTrue("No. of response items should be one", policyResp.getCount() == 1);
-        AclPolicyResponse resp = policyResp.getResponses().get(0);
-        assertEquals("Error in created group name", "policy1", resp.getName());
-    }
-
-    @Test
-    public void deleteAclPolicyTest() {
-        when(_iamSrv.deleteAclPolicy(1L)).thenReturn(true);
-        assertTrue("failed to delete acl policy 1", _aclSrv.deleteAclPolicy(1L));
-    }
-
-    @Test
-    public void listAclPolicyTest() {
-        AclPolicy policy = new AclPolicyVO("policy1", "tester policy1");
-        List<AclPolicy> policies = new ArrayList<AclPolicy>();
-        policies.add(policy);
-        when(_iamSrv.listAclPolicies(callerId)).thenReturn(policies);
-        List<AclPolicy> polys = _aclSrv.listAclPolicies(callerId);
-        assertTrue(polys != null && polys.size() == 1);
-        AclPolicy p = polys.get(0);
-        assertEquals("Error to retrieve group", "policy1", p.getName());
-    }
-
-    @Test
-    public void addRemovePolicyToGroupTest() {
-        AclGroup group = new AclGroupVO("group1", "tester group1");
-        List<AclGroup> groups = new ArrayList<AclGroup>();
-        groups.add(group);
-        Long groupId = group.getId();
-        List<Long> policyIds = new ArrayList<Long>();
-        policyIds.add(100L);
-        policyIds.add(200L);
-        AclPolicy policy1 = new AclPolicyVO("policy1", "my first policy");
-        AclPolicy policy2 = new AclPolicyVO("policy2", "my second policy");
-        List<AclPolicy> policies = new ArrayList<AclPolicy>();
-        policies.add(policy1);
-        policies.add(policy2);
-        when(_iamSrv.attachAclPoliciesToGroup(policyIds, groupId)).thenReturn(group);
-        when(_iamSrv.listAclPoliciesByGroup(groupId)).thenReturn(policies);
-        Pair<List<AclGroup>, Integer> grpList = new Pair<List<AclGroup>, Integer>(groups, 1);
-        when(_iamSrv.listAclGroups(null, "group1", callerDomainPath, 0L, 20L)).thenReturn(grpList);
-        _aclSrv.attachAclPoliciesToGroup(policyIds, groupId);
-        ListResponse<AclGroupResponse> grpResp = _aclSrv.listAclGroups(null, "group1", callerDomainId, 0L, 20L);
-        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
-        AclGroupResponse resp = grpResp.getResponses().get(0);
-        Set<String> policyNames = resp.getPolicyList();
-        assertEquals("There should be 2 policies in the group", 2, policyNames.size());
-        assertTrue("policy1 should be assigned to the group", policyNames.contains("policy1"));
-        assertTrue("policy2 should be assigned to the group", policyNames.contains("policy2"));
-        // remove "policy2" from group1
-        policyIds.remove(1);
-        policies.remove(policy2);
-        when(_iamSrv.removeAclPoliciesFromGroup(policyIds, groupId)).thenReturn(group);
-        _aclSrv.removeAclPoliciesFromGroup(policyIds, groupId);
-        grpResp = _aclSrv.listAclGroups(null, "group1", callerDomainId, 0L, 20L);
-        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
-        resp = grpResp.getResponses().get(0);
-        policyNames = resp.getPolicyList();
-        assertEquals("There should be 1 policy attached to the group", 1, policyNames.size());
-        assertFalse("policy2 should not belong to the group anymore", policyNames.contains("policy2"));
-    }
-
-    @Test
-    public void addRemovePermissionToPolicyTest() {
-        AclPolicy policy = new AclPolicyVO("policy1", "tester policy1");
-        List<AclPolicy> policies = new ArrayList<AclPolicy>();
-        policies.add(policy);
-        Long policyId = policy.getId();
-        Long resId = 200L;
-        Class clz = ListVMsCmd.class;
-        when(_apiServer.getCmdClass("listVirtualMachines")).thenReturn(clz);
-        when(
-                _iamSrv.addAclPermissionToAclPolicy(policyId, IAMEntityType.VirtualMachine.toString(), PermissionScope.RESOURCE.toString(), resId, "listVirtualMachines",
-                        AccessType.UseEntry.toString(), Permission.Allow, false)).thenReturn(policy);
-        _aclSrv.addAclPermissionToAclPolicy(policyId, IAMEntityType.VirtualMachine.toString(), PermissionScope.RESOURCE, resId, "listVirtualMachines", Permission.Allow, false);
-        Pair<List<AclPolicy>, Integer> policyList = new Pair<List<AclPolicy>, Integer>(policies, 1);
-        List<AclPolicyPermission> policyPerms = new ArrayList<AclPolicyPermission>();
-        AclPolicyPermission perm = new AclPolicyPermissionVO(policyId, "listVirtualMachines", IAMEntityType.VirtualMachine.toString(), AccessType.UseEntry.toString(),
-                PermissionScope.RESOURCE.toString(),
-                resId, Permission.Allow, false);
-        policyPerms.add(perm);
-        when(_iamSrv.listAclPolicies(null, "policy1", callerDomainPath, 0L, 20L)).thenReturn(policyList);
-        when(_iamSrv.listPolicyPermissions(policyId)).thenReturn(policyPerms);
-        ListResponse<AclPolicyResponse> policyResp = _aclSrv.listAclPolicies(null, "policy1", callerDomainId, 0L, 20L);
-        assertTrue("No. of response items should be one", policyResp.getCount() == 1);
-        AclPolicyResponse resp = policyResp.getResponses().get(0);
-        Set<AclPermissionResponse> permList = resp.getPermissionList();
-        assertTrue("Permission list should not be empty", permList != null && permList.size() > 0);
-        AclPermissionResponse permResp = permList.iterator().next();
-        assertEquals("There should be one permission for listVirtualMachines", "listVirtualMachines", permResp.getAction());
-
-        //remove permission from policy
-        policyPerms.remove(perm);
-        _aclSrv.removeAclPermissionFromAclPolicy(policyId, IAMEntityType.VirtualMachine.toString(), PermissionScope.RESOURCE, resId, "listVirtualMachines");
-        policyResp = _aclSrv.listAclPolicies(null, "policy1", callerDomainId, 0L, 20L);
-        assertTrue("No. of response items should be one", policyResp.getCount() == 1);
-        resp = policyResp.getResponses().get(0);
-        permList = resp.getPermissionList();
-        assertTrue("Permission list should be empty", permList != null && permList.size() == 0);
-    }
-
-    @After
-    public void tearDown() {
-    }
-
-    @Configuration
-    @ComponentScan(basePackageClasses = {AclApiServiceImpl.class}, includeFilters = {@Filter(value = TestConfiguration.Library.class, type = FilterType.CUSTOM)}, useDefaultFilters = false)
-    public static class TestConfiguration extends SpringUtils.CloudStackTestConfiguration {
-
-        @Bean
-        public DomainDao domainDao() {
-            return Mockito.mock(DomainDao.class);
-        }
-
-        @Bean
-        public IAMService iamService() {
-            return Mockito.mock(IAMService.class);
-        }
-
-        @Bean
-        public AccountDao accountDao() {
-            return Mockito.mock(AccountDao.class);
-        }
-
-        @Bean
-        public NetworkDomainDao networkDomainDao() {
-            return Mockito.mock(NetworkDomainDao.class);
-        }
-
-        @Bean
-        public AccountManager accountManager() {
-            return Mockito.mock(AccountManager.class);
-        }
-
-        @Bean
-        public MessageBus messageBus() {
-            return Mockito.mock(MessageBus.class);
-        }
-
-        @Bean
-        public ApiServerService apiServerService() {
-            return Mockito.mock(ApiServerService.class);
-        }
-
-        public static class Library implements TypeFilter {
-
-            @Override
-            public boolean match(MetadataReader mdr, MetadataReaderFactory arg1) throws IOException {
-                ComponentScan cs = TestConfiguration.class.getAnnotation(ComponentScan.class);
-                return SpringUtils.includedInBasePackageClasses(mdr.getClassMetadata().getClassName(), cs);
-            }
-        }
-    }
-}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/187f9cd0/services/iam/plugin/test/org/apache/cloudstack/iam/test/IAMApiServiceTest.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/test/org/apache/cloudstack/iam/test/IAMApiServiceTest.java b/services/iam/plugin/test/org/apache/cloudstack/iam/test/IAMApiServiceTest.java
new file mode 100644
index 0000000..4b376ce
--- /dev/null
+++ b/services/iam/plugin/test/org/apache/cloudstack/iam/test/IAMApiServiceTest.java
@@ -0,0 +1,363 @@
+package org.apache.cloudstack.iam.test;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertTrue;
+import static org.mockito.Mockito.doNothing;
+import static org.mockito.Mockito.when;
+
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.Set;
+import java.util.UUID;
+
+import javax.inject.Inject;
+import javax.naming.ConfigurationException;
+
+import org.junit.After;
+import org.junit.Before;
+import org.junit.BeforeClass;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.mockito.Mockito;
+import org.springframework.context.annotation.Bean;
+import org.springframework.context.annotation.ComponentScan;
+import org.springframework.context.annotation.ComponentScan.Filter;
+import org.springframework.context.annotation.Configuration;
+import org.springframework.context.annotation.FilterType;
+import org.springframework.core.type.classreading.MetadataReader;
+import org.springframework.core.type.classreading.MetadataReaderFactory;
+import org.springframework.core.type.filter.TypeFilter;
+import org.springframework.test.context.ContextConfiguration;
+import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
+import org.springframework.test.context.support.AnnotationConfigContextLoader;
+
+import org.apache.cloudstack.acl.IAMEntityType;
+import org.apache.cloudstack.acl.PermissionScope;
+import org.apache.cloudstack.acl.SecurityChecker.AccessType;
+import org.apache.cloudstack.iam.IAMApiServiceImpl;
+import org.apache.cloudstack.iam.IAMApiService;
+import org.apache.cloudstack.api.command.user.vm.ListVMsCmd;
+import org.apache.cloudstack.api.response.ListResponse;
+import org.apache.cloudstack.api.response.iam.IAMGroupResponse;
+import org.apache.cloudstack.api.response.iam.IAMPermissionResponse;
+import org.apache.cloudstack.api.response.iam.IAMPolicyResponse;
+import org.apache.cloudstack.context.CallContext;
+import org.apache.cloudstack.framework.messagebus.MessageBus;
+import org.apache.cloudstack.iam.api.IAMGroup;
+import org.apache.cloudstack.iam.api.IAMPolicy;
+import org.apache.cloudstack.iam.api.IAMPolicyPermission;
+import org.apache.cloudstack.iam.api.IAMPolicyPermission.Permission;
+import org.apache.cloudstack.iam.api.IAMService;
+import org.apache.cloudstack.iam.server.IAMGroupVO;
+import org.apache.cloudstack.iam.server.IAMPolicyPermissionVO;
+import org.apache.cloudstack.iam.server.IAMPolicyVO;
+import org.apache.cloudstack.test.utils.SpringUtils;
+
+import com.cloud.api.ApiServerService;
+import com.cloud.domain.DomainVO;
+import com.cloud.domain.dao.DomainDao;
+import com.cloud.network.dao.NetworkDomainDao;
+import com.cloud.user.Account;
+import com.cloud.user.AccountManager;
+import com.cloud.user.AccountVO;
+import com.cloud.user.UserVO;
+import com.cloud.user.dao.AccountDao;
+import com.cloud.utils.Pair;
+import com.cloud.utils.component.ComponentContext;
+
+@RunWith(SpringJUnit4ClassRunner.class)
+@ContextConfiguration(loader = AnnotationConfigContextLoader.class)
+public class IAMApiServiceTest {
+
+    @Inject
+    IAMService _iamSrv;
+
+    @Inject
+    DomainDao _domainDao;
+
+    @Inject
+    IAMApiService _aclSrv;
+
+    @Inject
+    AccountManager _accountMgr;
+
+    @Inject
+    AccountDao _accountDao;
+
+    @Inject
+    ApiServerService _apiServer;
+
+    private static Account caller;
+    private static Long callerId;
+    private static String callerAccountName = "tester";
+    private static Long callerDomainId = 3L;
+    private static String callerDomainPath = "/root/testdomain";
+    private static DomainVO callerDomain;
+
+    @BeforeClass
+    public static void setUpClass() throws ConfigurationException {
+    }
+
+    @Before
+    public void setUp() {
+        ComponentContext.initComponentsLifeCycle();
+        caller = new AccountVO(callerAccountName, callerDomainId, null, Account.ACCOUNT_TYPE_ADMIN, UUID.randomUUID().toString());
+        callerId = caller.getId();
+        callerDomain = new DomainVO();
+        callerDomain.setPath(callerDomainPath);
+        UserVO user = new UserVO(1, "testuser", "password", "firstname", "lastName", "email", "timezone", UUID.randomUUID().toString());
+        CallContext.register(user, caller);
+
+        when(_domainDao.findById(callerDomainId)).thenReturn(callerDomain);
+        doNothing().when(_accountMgr).checkAccess(caller, callerDomain);
+    }
+
+    @Test
+    public void createIAMGroupTest() {
+        IAMGroup group = new IAMGroupVO("group1", "tester group1");
+        List<IAMGroup> groups = new ArrayList<IAMGroup>();
+        groups.add(group);
+        Pair<List<IAMGroup>, Integer> grpList = new Pair<List<IAMGroup>, Integer>(groups, 1);
+        when(_iamSrv.createIAMGroup("group1", "tester group1", callerDomainPath)).thenReturn(group);
+        when(_iamSrv.listIAMGroups(null, null, callerDomainPath, 0L, 20L)).thenReturn(grpList);
+
+        IAMGroup createdGrp = _aclSrv.createIAMGroup(caller, "group1", "tester group1");
+        assertNotNull("IAM group 'group1' failed to create ", createdGrp);
+        ListResponse<IAMGroupResponse> grpResp = _aclSrv.listIAMGroups(null, null, callerDomainId, 0L, 20L);
+        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
+        IAMGroupResponse resp = grpResp.getResponses().get(0);
+        assertEquals("Error in created group name", "group1", resp.getName());
+    }
+
+    @Test
+    public void deleteIAMGroupTest() {
+        when(_iamSrv.deleteIAMGroup(1L)).thenReturn(true);
+        assertTrue("failed to delete acl group 1", _aclSrv.deleteIAMGroup(1L));
+    }
+
+    @Test
+    public void listIAMGroupTest() {
+        IAMGroup group = new IAMGroupVO("group1", "tester group1");
+        List<IAMGroup> groups = new ArrayList<IAMGroup>();
+        groups.add(group);
+        when(_iamSrv.listIAMGroups(callerId)).thenReturn(groups);
+        List<IAMGroup> grps = _aclSrv.listIAMGroups(callerId);
+        assertTrue(grps != null && grps.size() == 1);
+        IAMGroup grp = grps.get(0);
+        assertEquals("Error to retrieve group", "group1", grp.getName());
+    }
+
+    @Test
+    public void addRemoveAccountToGroupTest() {
+        IAMGroup group = new IAMGroupVO("group1", "tester group1");
+        List<IAMGroup> groups = new ArrayList<IAMGroup>();
+        groups.add(group);
+        Long groupId = group.getId();
+        List<Long> acctIds = new ArrayList<Long>();
+        AccountVO acct1 = new AccountVO(100L);
+        acct1.setAccountName("account1");
+        AccountVO acct2 = new AccountVO(200L);
+        acct2.setAccountName("account2");
+        acctIds.add(acct1.getId());
+        acctIds.add(acct2.getId());
+        when(_accountDao.findById(acct1.getId())).thenReturn(acct1);
+        when(_accountDao.findById(acct2.getId())).thenReturn(acct2);
+        when(_iamSrv.addAccountsToGroup(acctIds, groupId)).thenReturn(group);
+        when(_iamSrv.listAccountsByGroup(groupId)).thenReturn(acctIds);
+        Pair<List<IAMGroup>, Integer> grpList = new Pair<List<IAMGroup>, Integer>(groups, 1);
+        when(_iamSrv.listIAMGroups(null, "group1", callerDomainPath, 0L, 20L)).thenReturn(grpList);
+        _aclSrv.addAccountsToGroup(acctIds, groupId);
+        ListResponse<IAMGroupResponse> grpResp = _aclSrv.listIAMGroups(null, "group1", callerDomainId, 0L, 20L);
+        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
+        IAMGroupResponse resp = grpResp.getResponses().get(0);
+        Set<String> acctNames = resp.getAccountNameList();
+        assertEquals("There should be 2 accounts in the group", 2, acctNames.size());
+        assertTrue("account1 should be assigned to the group", acctNames.contains("account1"));
+        assertTrue("account2 should be assigned to the group", acctNames.contains("account2"));
+        // remove "account2" from group1
+        acctIds.remove(1);
+        List<Long> rmAccts = new ArrayList<Long>();
+        rmAccts.add(acct2.getId());
+        when(_iamSrv.removeAccountsFromGroup(rmAccts, groupId)).thenReturn(group);
+        _aclSrv.removeAccountsFromGroup(acctIds, groupId);
+        grpResp = _aclSrv.listIAMGroups(null, "group1", callerDomainId, 0L, 20L);
+        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
+        resp = grpResp.getResponses().get(0);
+        acctNames = resp.getAccountNameList();
+        assertEquals("There should be 1 accounts in the group", 1, acctNames.size());
+        assertFalse("account2 should not belong to the group anymore", acctNames.contains("account2"));
+    }
+
+    @Test
+    public void createIAMPolicyTest() {
+        IAMPolicy policy = new IAMPolicyVO("policy1", "tester policy1");
+        List<IAMPolicy> policies = new ArrayList<IAMPolicy>();
+        policies.add(policy);
+        Pair<List<IAMPolicy>, Integer> policyList = new Pair<List<IAMPolicy>, Integer>(policies, 1);
+        when(_iamSrv.createIAMPolicy("policy1", "tester policy1", null, callerDomainPath)).thenReturn(policy);
+        when(_iamSrv.listIAMPolicies(null, null, callerDomainPath, 0L, 20L)).thenReturn(policyList);
+
+        IAMPolicy createdPolicy = _aclSrv.createIAMPolicy(caller, "policy1", "tester policy1", null);
+        assertNotNull("IAM policy 'policy1' failed to create ", createdPolicy);
+        ListResponse<IAMPolicyResponse> policyResp = _aclSrv.listIAMPolicies(null, null, callerDomainId, 0L, 20L);
+        assertTrue("No. of response items should be one", policyResp.getCount() == 1);
+        IAMPolicyResponse resp = policyResp.getResponses().get(0);
+        assertEquals("Error in created group name", "policy1", resp.getName());
+    }
+
+    @Test
+    public void deleteIAMPolicyTest() {
+        when(_iamSrv.deleteIAMPolicy(1L)).thenReturn(true);
+        assertTrue("failed to delete acl policy 1", _aclSrv.deleteIAMPolicy(1L));
+    }
+
+    @Test
+    public void listIAMPolicyTest() {
+        IAMPolicy policy = new IAMPolicyVO("policy1", "tester policy1");
+        List<IAMPolicy> policies = new ArrayList<IAMPolicy>();
+        policies.add(policy);
+        when(_iamSrv.listIAMPolicies(callerId)).thenReturn(policies);
+        List<IAMPolicy> polys = _aclSrv.listIAMPolicies(callerId);
+        assertTrue(polys != null && polys.size() == 1);
+        IAMPolicy p = polys.get(0);
+        assertEquals("Error to retrieve group", "policy1", p.getName());
+    }
+
+    @Test
+    public void addRemovePolicyToGroupTest() {
+        IAMGroup group = new IAMGroupVO("group1", "tester group1");
+        List<IAMGroup> groups = new ArrayList<IAMGroup>();
+        groups.add(group);
+        Long groupId = group.getId();
+        List<Long> policyIds = new ArrayList<Long>();
+        policyIds.add(100L);
+        policyIds.add(200L);
+        IAMPolicy policy1 = new IAMPolicyVO("policy1", "my first policy");
+        IAMPolicy policy2 = new IAMPolicyVO("policy2", "my second policy");
+        List<IAMPolicy> policies = new ArrayList<IAMPolicy>();
+        policies.add(policy1);
+        policies.add(policy2);
+        when(_iamSrv.attachIAMPoliciesToGroup(policyIds, groupId)).thenReturn(group);
+        when(_iamSrv.listIAMPoliciesByGroup(groupId)).thenReturn(policies);
+        Pair<List<IAMGroup>, Integer> grpList = new Pair<List<IAMGroup>, Integer>(groups, 1);
+        when(_iamSrv.listIAMGroups(null, "group1", callerDomainPath, 0L, 20L)).thenReturn(grpList);
+        _aclSrv.attachIAMPoliciesToGroup(policyIds, groupId);
+        ListResponse<IAMGroupResponse> grpResp = _aclSrv.listIAMGroups(null, "group1", callerDomainId, 0L, 20L);
+        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
+        IAMGroupResponse resp = grpResp.getResponses().get(0);
+        Set<String> policyNames = resp.getPolicyList();
+        assertEquals("There should be 2 policies in the group", 2, policyNames.size());
+        assertTrue("policy1 should be assigned to the group", policyNames.contains("policy1"));
+        assertTrue("policy2 should be assigned to the group", policyNames.contains("policy2"));
+        // remove "policy2" from group1
+        policyIds.remove(1);
+        policies.remove(policy2);
+        when(_iamSrv.removeIAMPoliciesFromGroup(policyIds, groupId)).thenReturn(group);
+        _aclSrv.removeIAMPoliciesFromGroup(policyIds, groupId);
+        grpResp = _aclSrv.listIAMGroups(null, "group1", callerDomainId, 0L, 20L);
+        assertTrue("No. of response items should be one", grpResp.getCount() == 1);
+        resp = grpResp.getResponses().get(0);
+        policyNames = resp.getPolicyList();
+        assertEquals("There should be 1 policy attached to the group", 1, policyNames.size());
+        assertFalse("policy2 should not belong to the group anymore", policyNames.contains("policy2"));
+    }
+
+    @Test
+    public void addRemovePermissionToPolicyTest() {
+        IAMPolicy policy = new IAMPolicyVO("policy1", "tester policy1");
+        List<IAMPolicy> policies = new ArrayList<IAMPolicy>();
+        policies.add(policy);
+        Long policyId = policy.getId();
+        Long resId = 200L;
+        Class clz = ListVMsCmd.class;
+        when(_apiServer.getCmdClass("listVirtualMachines")).thenReturn(clz);
+        when(
+                _iamSrv.addIAMPermissionToIAMPolicy(policyId, IAMEntityType.VirtualMachine.toString(),
+                        PermissionScope.RESOURCE.toString(), resId, "listVirtualMachines",
+                        AccessType.UseEntry.toString(), Permission.Allow, false)).thenReturn(policy);
+        _aclSrv.addIAMPermissionToIAMPolicy(policyId, IAMEntityType.VirtualMachine.toString(),
+                PermissionScope.RESOURCE, resId, "listVirtualMachines", Permission.Allow, false);
+        Pair<List<IAMPolicy>, Integer> policyList = new Pair<List<IAMPolicy>, Integer>(policies, 1);
+        List<IAMPolicyPermission> policyPerms = new ArrayList<IAMPolicyPermission>();
+        IAMPolicyPermission perm = new IAMPolicyPermissionVO(policyId, "listVirtualMachines",
+                IAMEntityType.VirtualMachine.toString(), AccessType.UseEntry.toString(),
+                PermissionScope.RESOURCE.toString(),
+                resId, Permission.Allow, false);
+        policyPerms.add(perm);
+        when(_iamSrv.listIAMPolicies(null, "policy1", callerDomainPath, 0L, 20L)).thenReturn(policyList);
+        when(_iamSrv.listPolicyPermissions(policyId)).thenReturn(policyPerms);
+        ListResponse<IAMPolicyResponse> policyResp = _aclSrv.listIAMPolicies(null, "policy1", callerDomainId, 0L, 20L);
+        assertTrue("No. of response items should be one", policyResp.getCount() == 1);
+        IAMPolicyResponse resp = policyResp.getResponses().get(0);
+        Set<IAMPermissionResponse> permList = resp.getPermissionList();
+        assertTrue("Permission list should not be empty", permList != null && permList.size() > 0);
+        IAMPermissionResponse permResp = permList.iterator().next();
+        assertEquals("There should be one permission for listVirtualMachines", "listVirtualMachines", permResp.getAction());
+
+        //remove permission from policy
+        policyPerms.remove(perm);
+        _aclSrv.removeIAMPermissionFromIAMPolicy(policyId, IAMEntityType.VirtualMachine.toString(),
+                PermissionScope.RESOURCE, resId, "listVirtualMachines");
+        policyResp = _aclSrv.listIAMPolicies(null, "policy1", callerDomainId, 0L, 20L);
+        assertTrue("No. of response items should be one", policyResp.getCount() == 1);
+        resp = policyResp.getResponses().get(0);
+        permList = resp.getPermissionList();
+        assertTrue("Permission list should be empty", permList != null && permList.size() == 0);
+    }
+
+    @After
+    public void tearDown() {
+    }
+
+    @Configuration
+    @ComponentScan(basePackageClasses = {IAMApiServiceImpl.class}, includeFilters = {@Filter(value = TestConfiguration.Library.class, type = FilterType.CUSTOM)}, useDefaultFilters = false)
+    public static class TestConfiguration extends SpringUtils.CloudStackTestConfiguration {
+
+        @Bean
+        public DomainDao domainDao() {
+            return Mockito.mock(DomainDao.class);
+        }
+
+        @Bean
+        public IAMService iamService() {
+            return Mockito.mock(IAMService.class);
+        }
+
+        @Bean
+        public AccountDao accountDao() {
+            return Mockito.mock(AccountDao.class);
+        }
+
+        @Bean
+        public NetworkDomainDao networkDomainDao() {
+            return Mockito.mock(NetworkDomainDao.class);
+        }
+
+        @Bean
+        public AccountManager accountManager() {
+            return Mockito.mock(AccountManager.class);
+        }
+
+        @Bean
+        public MessageBus messageBus() {
+            return Mockito.mock(MessageBus.class);
+        }
+
+        @Bean
+        public ApiServerService apiServerService() {
+            return Mockito.mock(ApiServerService.class);
+        }
+
+        public static class Library implements TypeFilter {
+
+            @Override
+            public boolean match(MetadataReader mdr, MetadataReaderFactory arg1) throws IOException {
+                ComponentScan cs = TestConfiguration.class.getAnnotation(ComponentScan.class);
+                return SpringUtils.includedInBasePackageClasses(mdr.getClassMetadata().getClassName(), cs);
+            }
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/187f9cd0/services/iam/server/src/org/apache/cloudstack/iam/api/AclGroup.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/AclGroup.java b/services/iam/server/src/org/apache/cloudstack/iam/api/AclGroup.java
deleted file mode 100644
index 2bdddf7..0000000
--- a/services/iam/server/src/org/apache/cloudstack/iam/api/AclGroup.java
+++ /dev/null
@@ -1,37 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements.  See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership.  The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License.  You may obtain a copy of the License at
-//
-//   http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied.  See the License for the
-// specific language governing permissions and limitations
-// under the License.
-package org.apache.cloudstack.iam.api;
-
-import org.apache.cloudstack.api.Identity;
-import org.apache.cloudstack.api.InternalIdentity;
-
-public interface AclGroup extends InternalIdentity, Identity {
-
-    String getName();
-
-    String getDescription();
-
-    @Override
-    long getId();
-
-    @Override
-    String getUuid();
-
-    String getPath();
-
-    long getAccountId();
-}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/187f9cd0/services/iam/server/src/org/apache/cloudstack/iam/api/AclPolicy.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/AclPolicy.java b/services/iam/server/src/org/apache/cloudstack/iam/api/AclPolicy.java
deleted file mode 100644
index 302bbf3..0000000
--- a/services/iam/server/src/org/apache/cloudstack/iam/api/AclPolicy.java
+++ /dev/null
@@ -1,41 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements.  See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership.  The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License.  You may obtain a copy of the License at
-//
-//   http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied.  See the License for the
-// specific language governing permissions and limitations
-// under the License.
-package org.apache.cloudstack.iam.api;
-
-import org.apache.cloudstack.api.Identity;
-import org.apache.cloudstack.api.InternalIdentity;
-
-public interface AclPolicy extends InternalIdentity, Identity {
-
-    String getName();
-
-    String getDescription();
-
-    public enum PolicyType {
-        Static, Dynamic
-    }
-
-    @Override
-    long getId();
-
-    @Override
-    String getUuid();
-
-    String getPath();
-
-    long getAccountId();
-}