You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by pr...@apache.org on 2013/12/27 00:23:45 UTC

[1/5] git commit: updated refs/heads/rbac to 2543fbe

Updated Branches:
  refs/heads/rbac 630b7fb4a -> 2543fbe84


Adding EntityType for listAccounts


Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/337e33a0
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/337e33a0
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/337e33a0

Branch: refs/heads/rbac
Commit: 337e33a01431d3b5c3540864c8f6b9e918db4856
Parents: 630b7fb
Author: Prachi Damle <pr...@cloud.com>
Authored: Thu Dec 26 15:02:08 2013 -0800
Committer: Prachi Damle <pr...@cloud.com>
Committed: Thu Dec 26 15:17:08 2013 -0800

----------------------------------------------------------------------
 .../cloudstack/api/command/user/account/ListAccountsCmd.java      | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/337e33a0/api/src/org/apache/cloudstack/api/command/user/account/ListAccountsCmd.java
----------------------------------------------------------------------
diff --git a/api/src/org/apache/cloudstack/api/command/user/account/ListAccountsCmd.java b/api/src/org/apache/cloudstack/api/command/user/account/ListAccountsCmd.java
index d9dcada..96b4590 100644
--- a/api/src/org/apache/cloudstack/api/command/user/account/ListAccountsCmd.java
+++ b/api/src/org/apache/cloudstack/api/command/user/account/ListAccountsCmd.java
@@ -18,6 +18,7 @@ package org.apache.cloudstack.api.command.user.account;
 
 import org.apache.log4j.Logger;
 
+import org.apache.cloudstack.acl.AclEntityType;
 import org.apache.cloudstack.api.APICommand;
 import org.apache.cloudstack.api.ApiConstants;
 import org.apache.cloudstack.api.BaseListDomainResourcesCmd;
@@ -26,7 +27,7 @@ import org.apache.cloudstack.api.ResponseObject.ResponseView;
 import org.apache.cloudstack.api.response.AccountResponse;
 import org.apache.cloudstack.api.response.ListResponse;
 
-@APICommand(name = "listAccounts", description = "Lists accounts and provides detailed account information for listed accounts", responseObject = AccountResponse.class, responseView = ResponseView.Restricted)
+@APICommand(name = "listAccounts", description = "Lists accounts and provides detailed account information for listed accounts", responseObject = AccountResponse.class, responseView = ResponseView.Restricted, entityType = { AclEntityType.Account })
 public class ListAccountsCmd extends BaseListDomainResourcesCmd {
     public static final Logger s_logger = Logger.getLogger(ListAccountsCmd.class.getName());
     private static final String s_name = "listaccountsresponse";


[5/5] git commit: updated refs/heads/rbac to 2543fbe

Posted by pr...@apache.org.
Adding new IAM service under services. There are two modules to this component:

part a) plugin - This contains all adapter implementations and components necessary to interact with CloudStack.

part b) server - This contains IAM interfaces that are not aware of any CloudStack entities, they are pure IAM interface that can be implemented in varied ways.
The default implementation provided just works on DB and generic Dao layer.
But these interfaces can be implemented using connectors interacting with LDAP or AD.


Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/2543fbe8
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/2543fbe8
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/2543fbe8

Branch: refs/heads/rbac
Commit: 2543fbe846430f28c459a49d2e7d00cd29591442
Parents: b7c3411
Author: Prachi Damle <pr...@cloud.com>
Authored: Thu Dec 26 15:16:12 2013 -0800
Committer: Prachi Damle <pr...@cloud.com>
Committed: Thu Dec 26 15:17:13 2013 -0800

----------------------------------------------------------------------
 services/iam/plugin/pom.xml                     |  29 +
 .../module.properties                           |  18 +
 ...g-acl-role-based-access-checkers-context.xml |  32 +
 .../org/apache/cloudstack/acl/AclService.java   |  66 ++
 .../apache/cloudstack/acl/AclServiceImpl.java   | 736 +++++++++++++++++++
 .../acl/api/RoleBasedAPIAccessChecker.java      |  68 ++
 .../entity/RoleBasedEntityAccessChecker.java    | 131 ++++
 .../acl/entity/RoleBasedEntityQueryChecker.java |  51 ++
 services/iam/pom.xml                            |  37 +
 services/iam/server/pom.xml                     |  53 ++
 .../org/apache/cloudstack/iam/api/AclGroup.java |  28 +
 .../apache/cloudstack/iam/api/AclPolicy.java    |  32 +
 .../cloudstack/iam/api/AclPolicyPermission.java |  52 ++
 .../apache/cloudstack/iam/api/IAMService.java   |  57 ++
 .../api/command/AddAccountToAclGroupCmd.java    | 121 +++
 .../command/AddAclPermissionToAclPolicyCmd.java | 144 ++++
 .../command/AttachAclPolicyToAclGroupCmd.java   | 121 +++
 .../iam/api/command/CreateAclGroupCmd.java      | 162 ++++
 .../iam/api/command/CreateAclPolicyCmd.java     | 169 +++++
 .../iam/api/command/DeleteAclGroupCmd.java      |  96 +++
 .../iam/api/command/DeleteAclPolicyCmd.java     |  96 +++
 .../iam/api/command/ListAclGroupsCmd.java       |  82 +++
 .../iam/api/command/ListAclPoliciesCmd.java     |  82 +++
 .../command/RemoveAccountFromAclGroupCmd.java   | 121 +++
 .../RemoveAclPermissionFromAclPolicyCmd.java    | 141 ++++
 .../command/RemoveAclPolicyFromAclGroupCmd.java | 121 +++
 .../iam/server/AclGroupAccountMapVO.java        |  78 ++
 .../iam/server/AclGroupPolicyMapVO.java         |  79 ++
 .../cloudstack/iam/server/AclGroupVO.java       | 109 +++
 .../iam/server/AclPolicyPermissionVO.java       | 172 +++++
 .../cloudstack/iam/server/AclPolicyVO.java      | 136 ++++
 .../cloudstack/iam/server/IAMServiceImpl.java   | 543 ++++++++++++++
 .../iam/server/dao/AclGroupAccountMapDao.java   |  40 +
 .../server/dao/AclGroupAccountMapDaoImpl.java   | 119 +++
 .../cloudstack/iam/server/dao/AclGroupDao.java  |  28 +
 .../iam/server/dao/AclGroupDaoImpl.java         |  59 ++
 .../iam/server/dao/AclGroupPolicyMapDao.java    |  16 +
 .../server/dao/AclGroupPolicyMapDaoImpl.java    |  61 ++
 .../cloudstack/iam/server/dao/AclPolicyDao.java |  28 +
 .../iam/server/dao/AclPolicyDaoImpl.java        |  57 ++
 .../iam/server/dao/AclPolicyPermissionDao.java  |  38 +
 .../server/dao/AclPolicyPermissionDaoImpl.java  | 115 +++
 services/pom.xml                                |   1 +
 43 files changed, 4525 insertions(+)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/plugin/pom.xml
----------------------------------------------------------------------
diff --git a/services/iam/plugin/pom.xml b/services/iam/plugin/pom.xml
new file mode 100644
index 0000000..7ee3feb
--- /dev/null
+++ b/services/iam/plugin/pom.xml
@@ -0,0 +1,29 @@
+<!--
+  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.
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+  <modelVersion>4.0.0</modelVersion>
+  <artifactId>cloud-plugin-iam</artifactId>
+  <name>Apache CloudStack IAM - Plugin</name>
+  <parent>
+    <groupId>org.apache.cloudstack</groupId>
+    <artifactId>cloudstack-service-iam</artifactId>
+    <version>4.3.0-SNAPSHOT</version>
+    <relativePath>../pom.xml</relativePath>
+  </parent>
+</project>

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/plugin/resources/META-INF/cloudstack/acl-role-based-access-checkers/module.properties
----------------------------------------------------------------------
diff --git a/services/iam/plugin/resources/META-INF/cloudstack/acl-role-based-access-checkers/module.properties b/services/iam/plugin/resources/META-INF/cloudstack/acl-role-based-access-checkers/module.properties
new file mode 100644
index 0000000..206e1b0
--- /dev/null
+++ b/services/iam/plugin/resources/META-INF/cloudstack/acl-role-based-access-checkers/module.properties
@@ -0,0 +1,18 @@
+# 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.
+name=acl-role-based-access-checkers
+parent=api
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/plugin/resources/META-INF/cloudstack/acl-role-based-access-checkers/spring-acl-role-based-access-checkers-context.xml
----------------------------------------------------------------------
diff --git a/services/iam/plugin/resources/META-INF/cloudstack/acl-role-based-access-checkers/spring-acl-role-based-access-checkers-context.xml b/services/iam/plugin/resources/META-INF/cloudstack/acl-role-based-access-checkers/spring-acl-role-based-access-checkers-context.xml
new file mode 100644
index 0000000..78b233d
--- /dev/null
+++ b/services/iam/plugin/resources/META-INF/cloudstack/acl-role-based-access-checkers/spring-acl-role-based-access-checkers-context.xml
@@ -0,0 +1,32 @@
+<!--
+  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.
+-->
+<beans xmlns="http://www.springframework.org/schema/beans"
+       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
+       xmlns:context="http://www.springframework.org/schema/context"
+       xmlns:aop="http://www.springframework.org/schema/aop"
+       xsi:schemaLocation="http://www.springframework.org/schema/beans
+                      http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
+                      http://www.springframework.org/schema/aop http://www.springframework.org/schema/aop/spring-aop-3.0.xsd
+                      http://www.springframework.org/schema/context
+                      http://www.springframework.org/schema/context/spring-context-3.0.xsd"
+                      >                     
+
+    <bean id="RoleBasedEntityAccessChecker" class="org.apache.cloudstack.acl.entity.RoleBasedEntityAccessChecker" />
+
+</beans>

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/plugin/src/org/apache/cloudstack/acl/AclService.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/src/org/apache/cloudstack/acl/AclService.java b/services/iam/plugin/src/org/apache/cloudstack/acl/AclService.java
new file mode 100644
index 0000000..c8d8b48
--- /dev/null
+++ b/services/iam/plugin/src/org/apache/cloudstack/acl/AclService.java
@@ -0,0 +1,66 @@
+// 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.acl;
+
+import java.util.List;
+
+import org.apache.cloudstack.acl.AclPolicyPermission.Permission;
+
+import com.cloud.user.Account;
+
+public interface AclService {
+
+    /* ACL group related interfaces */
+    AclGroup createAclGroup(Account caller, String aclGroupName, String description);
+
+    boolean deleteAclGroup(Long aclGroupId);
+
+    List<AclGroup> listAclGroups(long accountId);
+
+    AclGroup addAccountsToGroup(List<Long> acctIds, Long groupId);
+
+    AclGroup removeAccountsFromGroup(List<Long> acctIds, Long groupId);
+
+    /* ACL Policy related interfaces */
+    AclPolicy createAclPolicy(Account caller, String aclPolicyName, String description, Long parentPolicyId);
+
+    boolean deleteAclPolicy(long aclPolicyId);
+
+    List<AclPolicy> listAclPolicies(long accountId);
+
+    AclGroup attachAclPoliciesToGroup(List<Long> roleIds, Long groupId);
+
+    AclGroup removeAclPoliciesFromGroup(List<Long> roleIds, Long groupId);
+
+    AclPolicy addAclPermissionToAclPolicy(long aclPolicyId, String entityType, PermissionScope scope, Long scopeId, String action, Permission perm);
+
+    AclPolicy removeAclPermissionFromAclPolicy(long aclPolicyId, String entityType, PermissionScope scope, Long scopeId, String action);
+
+    AclPolicyPermission getAclPolicyPermission(long accountId, String entityType, String action);
+
+    boolean isAPIAccessibleForPolicies(String apiName, List<AclPolicy> policies);
+
+    List<AclPolicy> getEffectivePolicies(Account caller, ControlledEntity entity);
+
+    /* Visibility related interfaces */
+    List<Long> getGrantedDomains(long accountId, String action);
+
+    List<Long> getGrantedAccounts(long accountId, String action);
+
+    List<Long> getGrantedResources(long accountId, String action);
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/plugin/src/org/apache/cloudstack/acl/AclServiceImpl.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/src/org/apache/cloudstack/acl/AclServiceImpl.java b/services/iam/plugin/src/org/apache/cloudstack/acl/AclServiceImpl.java
new file mode 100644
index 0000000..3581ef0
--- /dev/null
+++ b/services/iam/plugin/src/org/apache/cloudstack/acl/AclServiceImpl.java
@@ -0,0 +1,736 @@
+// 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.acl;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+
+import javax.ejb.Local;
+import javax.inject.Inject;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclPolicyPermission.Permission;
+import org.apache.cloudstack.acl.SecurityChecker.AccessType;
+import org.apache.cloudstack.acl.dao.AclApiPermissionDao;
+import org.apache.cloudstack.acl.dao.AclGroupAccountMapDao;
+import org.apache.cloudstack.acl.dao.AclGroupDao;
+import org.apache.cloudstack.acl.dao.AclGroupPolicyMapDao;
+import org.apache.cloudstack.acl.dao.AclPolicyDao;
+import org.apache.cloudstack.acl.dao.AclPolicyPermissionDao;
+import org.apache.cloudstack.api.BaseListCmd;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.api.ApiServerService;
+import com.cloud.domain.Domain;
+import com.cloud.event.ActionEvent;
+import com.cloud.event.EventTypes;
+import com.cloud.exception.InvalidParameterValueException;
+import com.cloud.exception.PermissionDeniedException;
+import com.cloud.storage.Snapshot;
+import com.cloud.storage.Volume;
+import com.cloud.template.VirtualMachineTemplate;
+import com.cloud.user.Account;
+import com.cloud.user.AccountManager;
+import com.cloud.user.dao.AccountDao;
+import com.cloud.uservm.UserVm;
+import com.cloud.utils.component.Manager;
+import com.cloud.utils.component.ManagerBase;
+import com.cloud.utils.db.DB;
+import com.cloud.utils.db.EntityManager;
+import com.cloud.utils.db.GenericSearchBuilder;
+import com.cloud.utils.db.JoinBuilder.JoinType;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+import com.cloud.utils.db.SearchCriteria.Op;
+import com.cloud.utils.db.Transaction;
+import com.cloud.utils.db.TransactionCallback;
+import com.cloud.utils.db.TransactionCallbackNoReturn;
+import com.cloud.utils.db.TransactionStatus;
+
+@Local(value = {AclService.class})
+public class AclServiceImpl extends ManagerBase implements AclService, Manager {
+
+    public static final Logger s_logger = Logger.getLogger(AclServiceImpl.class);
+    private String _name;
+
+    @Inject
+    AccountManager _accountMgr;
+
+    @Inject
+    AccountDao _accountDao;
+
+    @Inject
+    AclPolicyDao _aclPolicyDao;
+
+    @Inject
+    AclGroupDao _aclGroupDao;
+
+    @Inject
+    EntityManager _entityMgr;
+
+    @Inject
+    AclGroupPolicyMapDao _aclGroupPolicyMapDao;
+
+    @Inject
+    AclGroupAccountMapDao _aclGroupAccountMapDao;
+
+    // @Inject
+    // AclApiPermissionDao _apiPermissionDao;
+
+    @Inject
+    AclPolicyPermissionDao _policyPermissionDao;
+
+    @Inject
+    ApiServerService _apiServer;
+
+
+    public static HashMap<String, Class> entityClassMap = new HashMap<String, Class>();
+
+    static {
+        entityClassMap.put("VirtualMachine", UserVm.class);
+        entityClassMap.put("Volume", Volume.class);
+        entityClassMap.put("Template", VirtualMachineTemplate.class);
+        entityClassMap.put("Snapshot", Snapshot.class);
+        // To be filled in later depending on the entity permission grant scope
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_CREATE, eventDescription = "Creating Acl Group", create = true)
+    public AclGroup createAclGroup(Account caller, String aclGroupName, String description) {
+        Long domainId = caller.getDomainId();
+
+        if (!_accountMgr.isRootAdmin(caller.getAccountId())) {
+            // domain admin can only create role for his domain
+            if (caller.getDomainId() != domainId.longValue()) {
+                throw new PermissionDeniedException("Can't create acl group in domain " + domainId + ", permission denied");
+            }
+        }
+        // check if the role is already existing
+        AclGroup grp = _aclGroupDao.findByName(domainId, aclGroupName);
+        if (grp != null) {
+            throw new InvalidParameterValueException(
+                    "Unable to create acl group with name " + aclGroupName
+                            + " already exisits for domain " + domainId);
+        }
+        AclGroupVO rvo = new AclGroupVO(aclGroupName, description);
+        rvo.setAccountId(caller.getAccountId());
+        rvo.setDomainId(domainId);
+
+        return _aclGroupDao.persist(rvo);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_DELETE, eventDescription = "Deleting Acl Group")
+    public boolean deleteAclGroup(final Long aclGroupId) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Role entity
+        final AclGroup grp = _aclGroupDao.findById(aclGroupId);
+        if (grp == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + aclGroupId
+                    + "; failed to delete acl group.");
+        }
+        // check permissions
+        _accountMgr.checkAccess(caller, null, true, grp);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // remove this group related entry in acl_group_role_map
+                List<AclGroupPolicyMapVO> groupPolicyMap = _aclGroupPolicyMapDao.listByGroupId(grp.getId());
+                if (groupPolicyMap != null) {
+                    for (AclGroupPolicyMapVO gr : groupPolicyMap) {
+                        _aclGroupPolicyMapDao.remove(gr.getId());
+                    }
+                }
+
+                // remove this group related entry in acl_group_account table
+                List<AclGroupAccountMapVO> groupAcctMap = _aclGroupAccountMapDao.listByGroupId(grp.getId());
+                if (groupAcctMap != null) {
+                    for (AclGroupAccountMapVO grpAcct : groupAcctMap) {
+                        _aclGroupAccountMapDao.remove(grpAcct.getId());
+                    }
+                }
+
+                // remove this group from acl_group table
+                _aclGroupDao.remove(aclGroupId);
+            }
+        });
+
+        return true;
+    }
+
+    @Override
+    public List<AclGroup> listAclGroups(long accountId) {
+
+        GenericSearchBuilder<AclGroupAccountMapVO, Long> groupSB = _aclGroupAccountMapDao.createSearchBuilder(Long.class);
+        groupSB.selectFields(groupSB.entity().getAclGroupId());
+        groupSB.and("account", groupSB.entity().getAccountId(), Op.EQ);
+        SearchCriteria<Long> groupSc = groupSB.create();
+
+        List<Long> groupIds = _aclGroupAccountMapDao.customSearch(groupSc, null);
+
+        SearchBuilder<AclGroupVO> sb = _aclGroupDao.createSearchBuilder();
+        sb.and("ids", sb.entity().getId(), Op.IN);
+        SearchCriteria<AclGroupVO> sc = sb.create();
+        sc.setParameters("ids", groupIds.toArray(new Object[groupIds.size()]));
+        List<AclGroupVO> groups = _aclGroupDao.search(sc, null);
+
+        return new ArrayList<AclGroup>(groups);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_UPDATE, eventDescription = "Adding accounts to acl group")
+    public AclGroup addAccountsToGroup(final List<Long> acctIds, final Long groupId) {
+        final Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Group entity
+        AclGroup group = _aclGroupDao.findById(groupId);
+        if (group == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + groupId
+                    + "; failed to add accounts to acl group.");
+        }
+        // check group permissions
+        _accountMgr.checkAccess(caller, null, true, group);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // add entries in acl_group_account_map table
+                for (Long acctId : acctIds) {
+                    // check account permissions
+                    Account account = _accountDao.findById(acctId);
+                    if (account == null) {
+                        throw new InvalidParameterValueException("Unable to find account: " + acctId
+                                + "; failed to add account to acl group.");
+                    }
+                    _accountMgr.checkAccess(caller, null, true, account);
+
+                    AclGroupAccountMapVO grMap = _aclGroupAccountMapDao.findByGroupAndAccount(groupId, acctId);
+                    if (grMap == null) {
+                        // not there already
+                        grMap = new AclGroupAccountMapVO(groupId, acctId);
+                        _aclGroupAccountMapDao.persist(grMap);
+                    }
+                }
+            }
+        });
+        return group;
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_UPDATE, eventDescription = "Removing accounts from acl group")
+    public AclGroup removeAccountsFromGroup(final List<Long> acctIds, final Long groupId) {
+        final Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Group entity
+        AclGroup group = _aclGroupDao.findById(groupId);
+        if (group == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + groupId
+                    + "; failed to remove accounts from acl group.");
+        }
+        // check group permissions
+        _accountMgr.checkAccess(caller, null, true, group);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // remove entries from acl_group_account_map table
+                for (Long acctId : acctIds) {
+                    // check account permissions
+                    Account account = _accountDao.findById(acctId);
+                    if (account == null) {
+                        throw new InvalidParameterValueException("Unable to find account: " + acctId
+                                + "; failed to add account to acl group.");
+                    }
+                    _accountMgr.checkAccess(caller, null, true, account);
+
+                    AclGroupAccountMapVO grMap = _aclGroupAccountMapDao.findByGroupAndAccount(groupId, acctId);
+                    if (grMap != null) {
+                        // not removed yet
+                        _aclGroupAccountMapDao.remove(grMap.getId());
+                    }
+                }
+            }
+        });
+        return group;
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_CREATE, eventDescription = "Creating Acl Policy", create = true)
+    public AclPolicy createAclPolicy(Account caller, final String aclPolicyName, final String description, final Long parentPolicyId) {
+        Long domainId = caller.getDomainId();
+
+        if (!_accountMgr.isRootAdmin(caller.getAccountId())) {
+            // domain admin can only create role for his domain
+            if (caller.getDomainId() != domainId.longValue()) {
+                throw new PermissionDeniedException("Can't create acl role in domain " + domainId + ", permission denied");
+            }
+        }
+        // check if the role is already existing
+        AclPolicy ro = _aclPolicyDao.findByName(domainId, aclPolicyName);
+        if (ro != null) {
+            throw new InvalidParameterValueException(
+                    "Unable to create acl policy with name " + aclPolicyName
+                            + " already exisits for domain " + domainId);
+        }
+
+        final long account_id = caller.getAccountId();
+        final long domain_id = domainId;
+        AclPolicy role = Transaction.execute(new TransactionCallback<AclPolicy>() {
+            @Override
+            public AclPolicy doInTransaction(TransactionStatus status) {
+                AclPolicyVO rvo = new AclPolicyVO(aclPolicyName, description);
+                rvo.setAccountId(account_id);
+                rvo.setDomainId(domain_id);
+                AclPolicy role = _aclPolicyDao.persist(rvo);
+                if (parentPolicyId != null) {
+                    // copy parent role permissions
+                    List<AclPolicyPermissionVO> perms = _policyPermissionDao.listByPolicy(parentPolicyId);
+                    if (perms != null) {
+                        for (AclPolicyPermissionVO perm : perms) {
+                            perm.setAclPolicyId(role.getId());
+                            _policyPermissionDao.persist(perm);
+                        }
+                    }
+                }
+                return role;
+            }
+        });
+                
+
+        return role;
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_DELETE, eventDescription = "Deleting Acl Policy")
+    public boolean deleteAclPolicy(final long aclPolicyId) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Policy entity
+        final AclPolicy policy = _aclPolicyDao.findById(aclPolicyId);
+        if (policy == null) {
+            throw new InvalidParameterValueException("Unable to find acl policy: " + aclPolicyId
+                    + "; failed to delete acl policy.");
+        }
+        // check permissions
+        _accountMgr.checkAccess(caller, null, true, policy);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // remove this role related entry in acl_group_role_map
+                List<AclGroupPolicyMapVO> groupPolicyMap = _aclGroupPolicyMapDao.listByPolicyId(policy.getId());
+                if (groupPolicyMap != null) {
+                    for (AclGroupPolicyMapVO gr : groupPolicyMap) {
+                        _aclGroupPolicyMapDao.remove(gr.getId());
+                    }
+                }
+
+                // remove this policy related entry in acl_policy_permission table
+                List<AclPolicyPermissionVO> policyPermMap = _policyPermissionDao.listByPolicy(policy.getId());
+                if (policyPermMap != null) {
+                    for (AclPolicyPermissionVO policyPerm : policyPermMap) {
+                        _policyPermissionDao.remove(policyPerm.getId());
+                    }
+                }
+
+                // remove this role from acl_role table
+                _aclPolicyDao.remove(aclPolicyId);
+            }
+        });
+
+        return true;
+    }
+
+
+    @Override
+    public List<AclPolicy> listAclPolicies(long accountId) {
+
+        // static policies of the account
+        SearchBuilder<AclGroupAccountMapVO> groupSB = _aclGroupAccountMapDao.createSearchBuilder();
+        groupSB.and("account", groupSB.entity().getAccountId(), Op.EQ);
+
+        GenericSearchBuilder<AclGroupPolicyMapVO, Long> policySB = _aclGroupPolicyMapDao.createSearchBuilder(Long.class);
+        policySB.selectFields(policySB.entity().getAclPolicyId());
+        policySB.join("accountgroupjoin", groupSB, groupSB.entity().getAclGroupId(), policySB.entity().getAclGroupId(),
+                JoinType.INNER);
+        policySB.done();
+        SearchCriteria<Long> policySc = policySB.create();
+        policySc.setJoinParameters("accountgroupjoin", "account", accountId);
+
+        List<Long> policyIds = _aclGroupPolicyMapDao.customSearch(policySc, null);
+
+        SearchBuilder<AclPolicyVO> sb = _aclPolicyDao.createSearchBuilder();
+        sb.and("ids", sb.entity().getId(), Op.IN);
+        SearchCriteria<AclPolicyVO> sc = sb.create();
+        sc.setParameters("ids", policyIds.toArray(new Object[policyIds.size()]));
+        List<AclPolicyVO> policies = _aclPolicyDao.customSearch(sc, null);
+
+        return new ArrayList<AclPolicy>(policies);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_UPDATE, eventDescription = "Attaching policy to acl group")
+    public AclGroup attachAclPoliciesToGroup(final List<Long> policyIds, final Long groupId) {
+        final Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Group entity
+        AclGroup group = _aclGroupDao.findById(groupId);
+        if (group == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + groupId
+                    + "; failed to add roles to acl group.");
+        }
+        // check group permissions
+        _accountMgr.checkAccess(caller, null, true, group);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // add entries in acl_group_policy_map table
+                for (Long policyId : policyIds) {
+                    // check policy permissions
+                    AclPolicy policy = _aclPolicyDao.findById(policyId);
+                    if (policy == null) {
+                        throw new InvalidParameterValueException("Unable to find acl policy: " + policyId
+                                + "; failed to add policies to acl group.");
+                    }
+                    _accountMgr.checkAccess(caller, null, true, policy);
+
+                    AclGroupPolicyMapVO grMap = _aclGroupPolicyMapDao.findByGroupAndPolicy(groupId, policyId);
+                    if (grMap == null) {
+                        // not there already
+                        grMap = new AclGroupPolicyMapVO(groupId, policyId);
+                        _aclGroupPolicyMapDao.persist(grMap);
+                    }
+                }
+            }
+        });
+
+        return group;
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_UPDATE, eventDescription = "Removing policies from acl group")
+    public AclGroup removeAclPoliciesFromGroup(final List<Long> policyIds, final Long groupId) {
+        final Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Group entity
+        AclGroup group = _aclGroupDao.findById(groupId);
+        if (group == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + groupId
+                    + "; failed to remove roles from acl group.");
+        }
+        // check group permissions
+        _accountMgr.checkAccess(caller, null, true, group);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // add entries in acl_group_role_map table
+                for (Long policyId : policyIds) {
+                    // check policy permissions
+                    AclPolicy policy = _aclPolicyDao.findById(policyId);
+                    if (policy == null) {
+                        throw new InvalidParameterValueException("Unable to find acl policy: " + policyId
+                                + "; failed to add policies to acl group.");
+                    }
+                    _accountMgr.checkAccess(caller, null, true, policy);
+
+                    AclGroupPolicyMapVO grMap = _aclGroupPolicyMapDao.findByGroupAndPolicy(groupId, policyId);
+                    if (grMap != null) {
+                        // not removed yet
+                        _aclGroupPolicyMapDao.remove(grMap.getId());
+                    }
+                }
+            }
+        });
+        return group;
+    }
+
+    /*
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_GRANT, eventDescription = "Granting permission to Acl Role")
+    public AclP addAclPermissionToAclPolicy(final long aclRoleId, final List<String> apiNames) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Role entity
+        AclRole role = _aclPolicyDao.findById(aclRoleId);
+        if (role == null) {
+            throw new InvalidParameterValueException("Unable to find acl role: " + aclRoleId
+                    + "; failed to grant permission to role.");
+        }
+        // check permissions
+        _accountMgr.checkAccess(caller, null, true, role);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // add entries in acl_api_permission table
+                for (String api : apiNames) {
+                    AclApiPermissionVO perm = _apiPermissionDao.findByRoleAndApi(aclRoleId, api);
+                    if (perm == null) {
+                        // not there already
+                        perm = new AclApiPermissionVO(aclRoleId, api);
+                        _apiPermissionDao.persist(perm);
+                    }
+                }
+            }
+        });
+            
+        return role;
+
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_REVOKE, eventDescription = "Revoking permission from Acl Role")
+    public AclRole revokeApiPermissionFromAclRole(final long aclRoleId, final List<String> apiNames) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Role entity
+        AclRole role = _aclPolicyDao.findById(aclRoleId);
+        if (role == null) {
+            throw new InvalidParameterValueException("Unable to find acl role: " + aclRoleId
+                    + "; failed to revoke permission from role.");
+        }
+        // check permissions
+        _accountMgr.checkAccess(caller, null, true, role);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // remove entries from acl_api_permission table
+                for (String api : apiNames) {
+                    AclApiPermissionVO perm = _apiPermissionDao.findByRoleAndApi(aclRoleId, api);
+                    if (perm != null) {
+                        // not removed yet
+                        _apiPermissionDao.remove(perm.getId());
+                    }
+                }
+            }
+        });
+        return role;
+    }
+    */
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_GRANT, eventDescription = "Granting acl permission to Acl Policy")
+    public AclPolicy addAclPermissionToAclPolicy(long aclPolicyId, String entityType, PermissionScope scope, Long scopeId, String action, Permission perm) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Policy entity
+        AclPolicy policy = _aclPolicyDao.findById(aclPolicyId);
+        if (policy == null) {
+            throw new InvalidParameterValueException("Unable to find acl policy: " + aclPolicyId
+                    + "; failed to add permission to policy.");
+        }
+        // check permissions
+        _accountMgr.checkAccess(caller, null, true, policy);
+
+        // get the entity and check permission
+        Class entityClass = entityClassMap.get(entityType);
+        if (entityClass == null) {
+            throw new InvalidParameterValueException("Entity type " + entityType + " permission granting is not supported yet");
+        }
+        if (scope == PermissionScope.RESOURCE && scopeId != null) {
+            ControlledEntity entity = (ControlledEntity)_entityMgr.findById(entityClass, scopeId);
+            if (entity == null) {
+                throw new InvalidParameterValueException("Unable to find entity " + entityType + " by id: " + scopeId);
+            }
+            _accountMgr.checkAccess(caller, null, true, entity);
+        }
+
+        // add entry in acl_policy_permission table
+        AclPolicyPermissionVO permit = _policyPermissionDao.findByPolicyAndEntity(aclPolicyId, entityType, scope, scopeId, action, perm);
+        if (permit == null) {
+            // not there already
+            Class<?> cmdClass = _apiServer.getCmdClass(action);
+            AccessType accessType = null;
+            if (BaseListCmd.class.isAssignableFrom(cmdClass)) {
+                accessType = AccessType.ListEntry;
+            }
+            permit = new AclPolicyPermissionVO(aclPolicyId, action, entityType, accessType,
+                    scope, scopeId, perm);
+            _policyPermissionDao.persist(permit);
+        }
+        return policy;
+
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_REVOKE, eventDescription = "Revoking acl permission from Acl Policy")
+    public AclPolicy removeAclPermissionFromAclPolicy(long aclPolicyId, String entityType, PermissionScope scope, Long scopeId, String action) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Policy entity
+        AclPolicy policy = _aclPolicyDao.findById(aclPolicyId);
+        if (policy == null) {
+            throw new InvalidParameterValueException("Unable to find acl policy: " + aclPolicyId
+                    + "; failed to revoke permission from policy.");
+        }
+        // check permissions
+        _accountMgr.checkAccess(caller, null, true, policy);
+
+        // get the entity and check permission
+        Class entityClass = entityClassMap.get(entityType);
+        if (entityClass == null) {
+            throw new InvalidParameterValueException("Entity type " + entityType + " permission revoke is not supported yet");
+        }
+        if (scope == PermissionScope.RESOURCE && scopeId != null) {
+            ControlledEntity entity = (ControlledEntity)_entityMgr.findById(entityClass, scopeId);
+            if (entity == null) {
+                throw new InvalidParameterValueException("Unable to find entity " + entityType + " by id: " + scopeId);
+            }
+            _accountMgr.checkAccess(caller, null, true, entity);
+        }
+
+        // remove entry from acl_entity_permission table
+        AclPolicyPermissionVO permit = _policyPermissionDao.findByPolicyAndEntity(aclPolicyId, entityType, scope, scopeId, action, null);
+        if (permit != null) {
+            // not removed yet
+            _policyPermissionDao.remove(permit.getId());
+        }
+        return policy;
+    }
+
+
+
+    @Override
+    public AclPolicyPermission getAclPolicyPermission(long accountId, String entityType, String action) {
+        List<AclPolicy> roles = listAclPolicies(accountId);
+        AclPolicyPermission curPerm = null;
+        for (AclPolicy role : roles) {
+            AclPolicyPermissionVO perm = _policyPermissionDao.findByPolicyAndEntity(role.getId(), entityType, null, null, action, Permission.Allow);
+            if (perm == null)
+                continue;
+            if (curPerm == null) {
+                curPerm = perm;
+            } else if (perm.getScope().greaterThan(curPerm.getScope())) {
+                // pick the more relaxed allowed permission
+                curPerm = perm;
+            }
+        }
+
+        return curPerm;
+    }
+
+
+
+    @Override
+    public boolean isAPIAccessibleForPolicies(String apiName, List<AclPolicy> policies) {
+
+        boolean accessible = false;
+
+        List<Long> policyIds = new ArrayList<Long>();
+        for (AclPolicy policy : policies) {
+            policyIds.add(policy.getId());
+        }
+
+        SearchBuilder<AclPolicyPermissionVO> sb = _policyPermissionDao.createSearchBuilder();
+        sb.and("action", sb.entity().getAction(), Op.EQ);
+        sb.and("policyId", sb.entity().getAclPolicyId(), Op.IN);
+
+        SearchCriteria<AclPolicyPermissionVO> sc = sb.create();
+        sc.setParameters("policyId", policyIds.toArray(new Object[policyIds.size()]));
+
+        List<AclPolicyPermissionVO> permissions = _policyPermissionDao.customSearch(sc, null);
+
+        if (permissions != null && !permissions.isEmpty()) {
+            accessible = true;
+        }
+
+        return accessible;
+    }
+
+    @Override
+    public List<AclPolicy> getEffectivePolicies(Account caller, ControlledEntity entity) {
+
+        // Get the static Policies of the Caller
+        List<AclPolicy> policies = listAclPolicies(caller.getId());
+
+        // add any dynamic policies w.r.t the entity
+        if (caller.getId() == entity.getAccountId()) {
+            // The caller owns the entity
+            AclPolicy owner = _aclPolicyDao.findByName(Domain.ROOT_DOMAIN, "RESOURCE_OWNER");
+            policies.add(owner);
+        }
+
+        return policies;
+    }
+
+    @Override
+    public List<Long> getGrantedDomains(long accountId, String action) {
+        // Get the static Policies of the Caller
+        List<AclPolicy> policies = listAclPolicies(accountId);
+        // for each policy, find granted permission with Domain scope
+        List<Long> domainIds = new ArrayList<Long>();
+        for (AclPolicy policy : policies) {
+            List<AclPolicyPermissionVO> pp = _policyPermissionDao.listGrantedByActionAndScope(policy.getId(), action, PermissionScope.DOMAIN);
+            if (pp != null) {
+                for (AclPolicyPermissionVO p : pp) {
+                    if (p.getScopeId() != null) {
+                        domainIds.add(p.getScopeId());
+                    }
+                }
+            }
+        }
+        return domainIds;
+    }
+
+    @Override
+    public List<Long> getGrantedAccounts(long accountId, String action) {
+        // Get the static Policies of the Caller
+        List<AclPolicy> policies = listAclPolicies(accountId);
+        // for each policy, find granted permission with Account scope
+        List<Long> accountIds = new ArrayList<Long>();
+        for (AclPolicy policy : policies) {
+            List<AclPolicyPermissionVO> pp = _policyPermissionDao.listGrantedByActionAndScope(policy.getId(), action, PermissionScope.ACCOUNT);
+            if (pp != null) {
+                for (AclPolicyPermissionVO p : pp) {
+                    if (p.getScopeId() != null) {
+                        accountIds.add(p.getScopeId());
+                    }
+                }
+            }
+        }
+        return accountIds;
+    }
+
+    @Override
+    public List<Long> getGrantedResources(long accountId, String action) {
+        // Get the static Policies of the Caller
+        List<AclPolicy> policies = listAclPolicies(accountId);
+        // for each policy, find granted permission with Resource scope
+        List<Long> entityIds = new ArrayList<Long>();
+        for (AclPolicy policy : policies) {
+            List<AclPolicyPermissionVO> pp = _policyPermissionDao.listGrantedByActionAndScope(policy.getId(), action, PermissionScope.RESOURCE);
+            if (pp != null) {
+                for (AclPolicyPermissionVO p : pp) {
+                    if (p.getScopeId() != null) {
+                        entityIds.add(p.getScopeId());
+                    }
+                }
+            }
+        }
+        return entityIds;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/plugin/src/org/apache/cloudstack/acl/api/RoleBasedAPIAccessChecker.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/src/org/apache/cloudstack/acl/api/RoleBasedAPIAccessChecker.java b/services/iam/plugin/src/org/apache/cloudstack/acl/api/RoleBasedAPIAccessChecker.java
new file mode 100644
index 0000000..23f25ca
--- /dev/null
+++ b/services/iam/plugin/src/org/apache/cloudstack/acl/api/RoleBasedAPIAccessChecker.java
@@ -0,0 +1,68 @@
+// 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.acl.api;
+
+import java.util.List;
+
+import javax.ejb.Local;
+import javax.inject.Inject;
+
+import org.apache.cloudstack.acl.APIChecker;
+import org.apache.cloudstack.acl.AclPolicy;
+import org.apache.cloudstack.acl.AclRole;
+import org.apache.cloudstack.acl.AclService;
+import org.apache.log4j.Logger;
+
+import com.cloud.exception.PermissionDeniedException;
+import com.cloud.user.Account;
+import com.cloud.user.AccountService;
+import com.cloud.user.User;
+import com.cloud.utils.component.AdapterBase;
+
+// This is the Role Based API access checker that grab's the  account's roles
+// based on the set of roles, access is granted if any of the role has access to the api
+@Local(value=APIChecker.class)
+public class RoleBasedAPIAccessChecker extends AdapterBase implements APIChecker {
+
+    protected static final Logger s_logger = Logger.getLogger(RoleBasedAPIAccessChecker.class);
+
+    @Inject AccountService _accountService;
+    @Inject AclService _aclService;
+
+    protected RoleBasedAPIAccessChecker() {
+        super();
+    }
+
+    @Override
+    public boolean checkAccess(User user, String commandName)
+            throws PermissionDeniedException {
+        Account account = _accountService.getAccount(user.getAccountId());
+        if (account == null) {
+            throw new PermissionDeniedException("The account id=" + user.getAccountId() + "for user id=" + user.getId() + "is null");
+        }
+
+        List<AclPolicy> policies = _aclService.listAclPolicies(account.getAccountId());
+
+
+        boolean isAllowed = _aclService.isAPIAccessibleForPolicies(commandName, policies);
+        if (!isAllowed) {
+            throw new PermissionDeniedException("The API does not exist or is blacklisted. api: " + commandName);
+        }
+        return isAllowed;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/plugin/src/org/apache/cloudstack/acl/entity/RoleBasedEntityAccessChecker.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/src/org/apache/cloudstack/acl/entity/RoleBasedEntityAccessChecker.java b/services/iam/plugin/src/org/apache/cloudstack/acl/entity/RoleBasedEntityAccessChecker.java
new file mode 100644
index 0000000..c057bc0
--- /dev/null
+++ b/services/iam/plugin/src/org/apache/cloudstack/acl/entity/RoleBasedEntityAccessChecker.java
@@ -0,0 +1,131 @@
+// 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.acl.entity;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+
+import javax.inject.Inject;
+
+import org.apache.cloudstack.acl.AclPolicy;
+import org.apache.cloudstack.acl.AclPolicyPermissionVO;
+import org.apache.cloudstack.acl.AclService;
+import org.apache.cloudstack.acl.ControlledEntity;
+import org.apache.cloudstack.acl.AclEntityType;
+import org.apache.cloudstack.acl.PermissionScope;
+import org.apache.cloudstack.acl.SecurityChecker;
+import org.apache.cloudstack.acl.dao.AclGroupAccountMapDao;
+import org.apache.cloudstack.acl.dao.AclPolicyPermissionDao;
+import org.apache.log4j.Logger;
+
+import com.cloud.acl.DomainChecker;
+import com.cloud.domain.dao.DomainDao;
+import com.cloud.exception.PermissionDeniedException;
+import com.cloud.user.Account;
+import com.cloud.user.AccountService;
+import com.cloud.vm.VirtualMachine;
+
+public class RoleBasedEntityAccessChecker extends DomainChecker implements SecurityChecker {
+
+    private static final Logger s_logger = Logger.getLogger(RoleBasedEntityAccessChecker.class.getName());
+
+    @Inject
+    AccountService _accountService;
+    @Inject
+    AclService _aclService;
+    
+    @Inject DomainDao _domainDao;
+
+    @Inject
+    AclGroupAccountMapDao _aclGroupAccountMapDao;
+
+    @Inject
+    AclPolicyPermissionDao _policyPermissionDao;
+
+
+    @Override
+    public boolean checkAccess(Account caller, ControlledEntity entity, AccessType accessType)
+            throws PermissionDeniedException {
+        return checkAccess(caller, entity, accessType, null);
+    }
+
+    @Override
+    public boolean checkAccess(Account caller, ControlledEntity entity, AccessType accessType, String action)
+            throws PermissionDeniedException {
+
+        String entityType = entity.getEntityType().toString();
+
+        if (accessType == null) {
+            accessType = AccessType.ListEntry;
+        }
+
+        // get all Policies of this caller w.r.t the entity
+        List<AclPolicy> policies = _aclService.getEffectivePolicies(caller, entity);
+        HashMap<AclPolicy, Boolean> policyPermissionMap = new HashMap<AclPolicy, Boolean>();
+
+        for (AclPolicy policy : policies) {
+            List<AclPolicyPermissionVO> permissions = new ArrayList<AclPolicyPermissionVO>();
+
+            if (action != null) {
+                permissions = _policyPermissionDao.listByPolicyActionAndEntity(policy.getId(),
+                    action, entityType);
+            } else {
+                permissions = _policyPermissionDao.listByPolicyAccessAndEntity(policy.getId(), accessType, entityType);
+            }
+            for (AclPolicyPermissionVO permission : permissions) {
+                if (checkPermissionScope(caller, permission.getScope(), entity)) {
+                    if (permission.getEntityType().equals(entityType)) {
+                        policyPermissionMap.put(policy, permission.getPermission().isGranted());
+                        break;
+                    } else if (permission.getEntityType().equals("*")) {
+                        policyPermissionMap.put(policy, permission.getPermission().isGranted());
+                    }
+                }
+            }
+            if (policyPermissionMap.containsKey(policy) && policyPermissionMap.get(policy)) {
+                return true;
+            }
+        }
+
+        if (!policies.isEmpty()) { // Since we reach this point, none of the
+                                   // roles granted access
+            if (s_logger.isDebugEnabled()) {
+                s_logger.debug("Account " + caller + " does not have permission to access resource " + entity
+                        + " for access type: " + accessType);
+            }
+            throw new PermissionDeniedException(caller + " does not have permission to access resource " + entity);
+        }
+
+        return false;
+    }
+
+    private boolean checkPermissionScope(Account caller, PermissionScope scope, ControlledEntity entity) {
+        
+        if(scope.equals(PermissionScope.ACCOUNT)){
+            if(caller.getAccountId() == entity.getAccountId()){
+                return true;
+            }
+        }else if(scope.equals(PermissionScope.DOMAIN)){
+            if (_domainDao.isChildDomain(caller.getDomainId(), entity.getDomainId())) {
+                return true;
+            }
+        }
+        
+        return false;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/plugin/src/org/apache/cloudstack/acl/entity/RoleBasedEntityQueryChecker.java
----------------------------------------------------------------------
diff --git a/services/iam/plugin/src/org/apache/cloudstack/acl/entity/RoleBasedEntityQueryChecker.java b/services/iam/plugin/src/org/apache/cloudstack/acl/entity/RoleBasedEntityQueryChecker.java
new file mode 100644
index 0000000..7ddc8fd
--- /dev/null
+++ b/services/iam/plugin/src/org/apache/cloudstack/acl/entity/RoleBasedEntityQueryChecker.java
@@ -0,0 +1,51 @@
+// 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.acl.entity;
+
+import java.util.List;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclEntityType;
+import org.apache.cloudstack.acl.QueryChecker;
+
+import com.cloud.user.Account;
+import com.cloud.utils.component.AdapterBase;
+
+public class RoleBasedEntityQueryChecker extends AdapterBase implements QueryChecker {
+
+    private static final Logger s_logger = Logger.getLogger(RoleBasedEntityQueryChecker.class.getName());
+
+    @Override
+    public List<Long> getAuthorizedDomains(Account caller, AclEntityType entityType) {
+        // TODO Auto-generated method stub
+        return null;
+    }
+
+    @Override
+    public List<Long> getAuthorizedAccounts(Account caller, AclEntityType entityType) {
+        // TODO Auto-generated method stub
+        return null;
+    }
+
+    @Override
+    public List<Long> getAuthorizedResources(Account caller, AclEntityType entityType) {
+        // TODO Auto-generated method stub
+        return null;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/pom.xml
----------------------------------------------------------------------
diff --git a/services/iam/pom.xml b/services/iam/pom.xml
new file mode 100644
index 0000000..babb9c8
--- /dev/null
+++ b/services/iam/pom.xml
@@ -0,0 +1,37 @@
+<!--
+  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.
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+  <modelVersion>4.0.0</modelVersion>
+  <artifactId>cloudstack-service-iam</artifactId>
+  <name>Apache CloudStack IAM Service</name>
+  <packaging>pom</packaging>
+  <parent>
+    <groupId>org.apache.cloudstack</groupId>
+    <artifactId>cloudstack-services</artifactId>
+    <version>4.3.0-SNAPSHOT</version>
+    <relativePath>../pom.xml</relativePath>
+  </parent>
+  <build>
+    <defaultGoal>install</defaultGoal>
+  </build>
+  <modules>
+    <module>plugin</module>
+    <module>server</module>
+  </modules>
+</project>

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/pom.xml
----------------------------------------------------------------------
diff --git a/services/iam/server/pom.xml b/services/iam/server/pom.xml
new file mode 100644
index 0000000..cf6dcf2
--- /dev/null
+++ b/services/iam/server/pom.xml
@@ -0,0 +1,53 @@
+<!--
+  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.
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+  <modelVersion>4.0.0</modelVersion>
+  <artifactId>cloud-iam</artifactId>
+  <name>Apache CloudStack IAM - Server</name>
+  <parent>
+    <groupId>org.apache.cloudstack</groupId>
+    <artifactId>cloudstack-service-iam</artifactId>
+    <version>4.3.0-SNAPSHOT</version>
+    <relativePath>../pom.xml</relativePath>
+  </parent>
+  <dependencies>
+    <dependency>
+      <groupId>log4j</groupId>
+      <artifactId>log4j</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>com.google.code.gson</groupId>
+      <artifactId>gson</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>commons-codec</groupId>
+      <artifactId>commons-codec</artifactId>
+    </dependency>
+    <dependency>
+      <groupId>org.apache.cloudstack</groupId>
+      <artifactId>cloud-utils</artifactId>
+      <version>${project.version}</version>
+    </dependency>
+	<dependency>
+      <groupId>org.apache.cloudstack</groupId>
+      <artifactId>cloud-api</artifactId>
+      <version>${project.version}</version>
+    </dependency>
+  </dependencies>
+</project>

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/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
new file mode 100644
index 0000000..a64ca7f
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/AclGroup.java
@@ -0,0 +1,28 @@
+// 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;
+
+public interface AclGroup {
+
+    String getName();
+
+    String getDescription();
+
+    long getId();
+
+    String getUuid();
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/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
new file mode 100644
index 0000000..0794888
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/AclPolicy.java
@@ -0,0 +1,32 @@
+// 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;
+
+public interface AclPolicy {
+
+    String getName();
+
+    String getDescription();
+
+    public enum PolicyType {
+        Static, Dynamic
+    }
+
+    long getId();
+
+    String getUuid();
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/AclPolicyPermission.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/AclPolicyPermission.java b/services/iam/server/src/org/apache/cloudstack/iam/api/AclPolicyPermission.java
new file mode 100644
index 0000000..38e5d05
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/AclPolicyPermission.java
@@ -0,0 +1,52 @@
+// 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;
+
+
+public interface AclPolicyPermission {
+
+    String getAction();
+
+    long getAclPolicyId();
+
+    String getEntityType();
+
+    String getAccessType();
+
+    String getScope();
+
+    Long getScopeId();
+
+    Permission getPermission();
+
+    public enum Permission {
+        Allow(true), Deny(false);
+
+        boolean result;
+
+        Permission(boolean result) {
+            this.result = result;
+        }
+
+        public boolean isGranted() {
+            return result;
+        }
+    }
+
+    long getId();
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/IAMService.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/IAMService.java b/services/iam/server/src/org/apache/cloudstack/iam/api/IAMService.java
new file mode 100644
index 0000000..0532abb
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/IAMService.java
@@ -0,0 +1,57 @@
+// 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 java.util.List;
+
+import org.apache.cloudstack.iam.api.AclPolicyPermission.Permission;
+
+public interface IAMService {
+
+    /* ACL group related interfaces */
+    AclGroup createAclGroup(String aclGroupName, String description, String path);
+
+    boolean deleteAclGroup(Long aclGroupId);
+
+    List<AclGroup> listAclGroups(long accountId);
+
+    AclGroup addAccountsToGroup(List<Long> acctIds, Long groupId);
+
+    AclGroup removeAccountsFromGroup(List<Long> acctIds, Long groupId);
+
+    /* ACL Policy related interfaces */
+    AclPolicy createAclPolicy(String aclPolicyName, String description, Long parentPolicyId);
+
+    boolean deleteAclPolicy(long aclPolicyId);
+
+    List<AclPolicy> listAclPolicies(long accountId);
+
+    AclGroup attachAclPoliciesToGroup(List<Long> policyIds, Long groupId);
+
+    AclGroup removeAclPoliciesFromGroup(List<Long> policyIds, Long groupId);
+
+    AclPolicy addAclPermissionToAclPolicy(long aclPolicyId, String entityType, String scope, Long scopeId,
+            String action, String accessType, Permission perm);
+
+    AclPolicy removeAclPermissionFromAclPolicy(long aclPolicyId, String entityType, String scope, Long scopeId,
+            String action);
+
+    boolean isAPIAccessibleForPolicies(String apiName, List<AclPolicy> policies);
+
+    List<Long> getGrantedEntities(long accountId, String action, String scope);
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/AddAccountToAclGroupCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/AddAccountToAclGroupCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/AddAccountToAclGroupCmd.java
new file mode 100644
index 0000000..c8289da
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/AddAccountToAclGroupCmd.java
@@ -0,0 +1,121 @@
+// 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.command;
+
+import java.util.List;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclGroup;
+import org.apache.cloudstack.api.ACL;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AccountResponse;
+import org.apache.cloudstack.api.response.AclGroupResponse;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.event.EventTypes;
+import com.cloud.exception.InsufficientCapacityException;
+import com.cloud.exception.ResourceUnavailableException;
+import com.cloud.user.Account;
+
+
+@APICommand(name = "addAccountToAclGroup", description = "add account to an acl group", responseObject = AclGroupResponse.class)
+public class AddAccountToAclGroupCmd extends BaseAsyncCmd {
+    public static final Logger s_logger = Logger.getLogger(AddAccountToAclGroupCmd.class.getName());
+    private static final String s_name = "addaccounttoaclgroupresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+
+    @ACL
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, entityType = AclGroupResponse.class,
+            required = true, description = "The ID of the acl group")
+    private Long id;
+
+    @ACL
+    @Parameter(name = ApiConstants.ACCOUNTS, type = CommandType.LIST, collectionType = CommandType.UUID, entityType = AccountResponse.class, description = "comma separated list of account id that are going to be assigned to the acl group.")
+    private List<Long> accountIdList;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+
+
+    public Long getId() {
+        return id;
+    }
+
+
+    public List<Long> getAccountIdList() {
+        return accountIdList;
+    }
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+
+    @Override
+    public long getEntityOwnerId() {
+        return Account.ACCOUNT_ID_SYSTEM; // no account info given, parent this command to SYSTEM so ERROR events are tracked
+    }
+
+    @Override
+    public void execute() throws ResourceUnavailableException,
+            InsufficientCapacityException, ServerApiException {
+        CallContext.current().setEventDetails("Acl group Id: " + getId());
+        AclGroup result = _aclService.addAccountsToGroup(accountIdList, id);
+        if (result != null){
+            AclGroupResponse response = _responseGenerator.createAclGroupResponse(result);
+            response.setResponseName(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to add accounts to acl group");
+        }
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_GROUP_UPDATE;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "adding accounts to acl group";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclGroup;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/AddAclPermissionToAclPolicyCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/AddAclPermissionToAclPolicyCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/AddAclPermissionToAclPolicyCmd.java
new file mode 100644
index 0000000..ea3736c
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/AddAclPermissionToAclPolicyCmd.java
@@ -0,0 +1,144 @@
+// 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.command;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclPolicy;
+import org.apache.cloudstack.acl.AclPolicyPermission.Permission;
+import org.apache.cloudstack.acl.PermissionScope;
+import org.apache.cloudstack.api.ACL;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AclPolicyResponse;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.event.EventTypes;
+import com.cloud.exception.InsufficientCapacityException;
+import com.cloud.exception.ResourceUnavailableException;
+import com.cloud.user.Account;
+
+
+@APICommand(name = "addAclPermissionToAclPolicy", description = "Add Acl permission to an acl policy", responseObject = AclPolicyResponse.class)
+public class AddAclPermissionToAclPolicyCmd extends BaseAsyncCmd {
+    public static final Logger s_logger = Logger.getLogger(AddAclPermissionToAclPolicyCmd.class.getName());
+    private static final String s_name = "addaclpermissiontoaclpolicyresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+
+    @ACL
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, entityType = AclPolicyResponse.class,
+            required = true, description = "The ID of the acl policy")
+    private Long id;
+
+    @Parameter(name = ApiConstants.ACL_ACTION, type = CommandType.STRING, required = true, description = "action api name.")
+    private String action;
+
+    @Parameter(name = ApiConstants.ENTITY_TYPE, type = CommandType.STRING, required = false, description = "entity class simple name.")
+    private String entityType;
+
+    @Parameter(name = ApiConstants.ACL_SCOPE, type = CommandType.STRING,
+            required = false, description = "acl permission scope")
+    private String scope;
+
+    @Parameter(name = ApiConstants.ACL_SCOPE_ID, type = CommandType.UUID, required = false, description = "The ID of the permission scope id")
+    private Long scopeId;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+
+
+    public Long getId() {
+        return id;
+    }
+
+
+    public String getAction() {
+        return action;
+    }
+
+    public String getEntityType() {
+        return entityType;
+    }
+
+    public String getScope() {
+        return scope;
+    }
+
+    public Long getScopeId() {
+        return scopeId;
+    }
+
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+
+    @Override
+    public long getEntityOwnerId() {
+        return Account.ACCOUNT_ID_SYSTEM; // no account info given, parent this command to SYSTEM so ERROR events are tracked
+    }
+
+    @Override
+    public void execute() throws ResourceUnavailableException,
+            InsufficientCapacityException, ServerApiException {
+        CallContext.current().setEventDetails("Acl policy Id: " + getId());
+        // Only explicit ALLOW is supported for this release, no explicit deny
+        AclPolicy result = _aclService.addAclPermissionToAclPolicy(id, entityType, PermissionScope.valueOf(scope), scopeId, action, Permission.Allow);
+        if (result != null) {
+            AclPolicyResponse response = _responseGenerator.createAclPolicyResponse(result);
+            response.setResponseName(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to grant permission to acl policy " + getId());
+        }
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_POLICY_GRANT;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "granting permission to acl policy";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclPolicy;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/AttachAclPolicyToAclGroupCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/AttachAclPolicyToAclGroupCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/AttachAclPolicyToAclGroupCmd.java
new file mode 100644
index 0000000..719950e
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/AttachAclPolicyToAclGroupCmd.java
@@ -0,0 +1,121 @@
+// 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.command;
+
+import java.util.List;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclGroup;
+import org.apache.cloudstack.api.ACL;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AclGroupResponse;
+import org.apache.cloudstack.api.response.AclPolicyResponse;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.event.EventTypes;
+import com.cloud.exception.InsufficientCapacityException;
+import com.cloud.exception.ResourceUnavailableException;
+import com.cloud.user.Account;
+
+
+@APICommand(name = "attachAclPolicyToAclGroup", description = "attach acl policy to an acl group", responseObject = AclGroupResponse.class)
+public class AttachAclPolicyToAclGroupCmd extends BaseAsyncCmd {
+    public static final Logger s_logger = Logger.getLogger(AttachAclPolicyToAclGroupCmd.class.getName());
+    private static final String s_name = "attachaclpolicytoaclgroupresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+
+    @ACL
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, entityType = AclGroupResponse.class,
+            required = true, description = "The ID of the acl group")
+    private Long id;
+
+    @ACL
+    @Parameter(name = ApiConstants.ACL_POLICIES, type = CommandType.LIST, collectionType = CommandType.UUID, entityType = AclPolicyResponse.class, description = "comma separated list of acl policy id that are going to be applied to the acl group.")
+    private List<Long> policyIdList;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+
+
+    public Long getId() {
+        return id;
+    }
+
+
+    public List<Long> getPolicyIdList() {
+        return policyIdList;
+    }
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+
+    @Override
+    public long getEntityOwnerId() {
+        return Account.ACCOUNT_ID_SYSTEM; // no account info given, parent this command to SYSTEM so ERROR events are tracked
+    }
+
+    @Override
+    public void execute() throws ResourceUnavailableException,
+            InsufficientCapacityException, ServerApiException {
+        CallContext.current().setEventDetails("Acl group Id: " + getId());
+        AclGroup result = _aclService.attachAclPoliciesToGroup(policyIdList, id);
+        if (result != null){
+            AclGroupResponse response = _responseGenerator.createAclGroupResponse(result);
+            response.setResponseName(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to add roles to acl group");
+        }
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_GROUP_UPDATE;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "adding acl roles to acl group";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclGroup;
+    }
+
+}


[2/5] git commit: updated refs/heads/rbac to 2543fbe

Posted by pr...@apache.org.
Fixing the issues in loading the beans


Project: http://git-wip-us.apache.org/repos/asf/cloudstack/repo
Commit: http://git-wip-us.apache.org/repos/asf/cloudstack/commit/b7c3411b
Tree: http://git-wip-us.apache.org/repos/asf/cloudstack/tree/b7c3411b
Diff: http://git-wip-us.apache.org/repos/asf/cloudstack/diff/b7c3411b

Branch: refs/heads/rbac
Commit: b7c3411be9795b51e0184119eb13b8f77c21e068
Parents: 337e33a
Author: Prachi Damle <pr...@cloud.com>
Authored: Thu Dec 26 15:02:59 2013 -0800
Committer: Prachi Damle <pr...@cloud.com>
Committed: Thu Dec 26 15:17:10 2013 -0800

----------------------------------------------------------------------
 ...g-acl-role-based-access-checkers-context.xml |  2 +-
 .../com/cloud/api/query/vo/AclGroupJoinVO.java  | 36 --------------------
 2 files changed, 1 insertion(+), 37 deletions(-)
----------------------------------------------------------------------


http://git-wip-us.apache.org/repos/asf/cloudstack/blob/b7c3411b/plugins/acl/role-based-access-checkers/resources/META-INF/cloudstack/acl-role-based-access-checkers/spring-acl-role-based-access-checkers-context.xml
----------------------------------------------------------------------
diff --git a/plugins/acl/role-based-access-checkers/resources/META-INF/cloudstack/acl-role-based-access-checkers/spring-acl-role-based-access-checkers-context.xml b/plugins/acl/role-based-access-checkers/resources/META-INF/cloudstack/acl-role-based-access-checkers/spring-acl-role-based-access-checkers-context.xml
index b7f06aa..78b233d 100644
--- a/plugins/acl/role-based-access-checkers/resources/META-INF/cloudstack/acl-role-based-access-checkers/spring-acl-role-based-access-checkers-context.xml
+++ b/plugins/acl/role-based-access-checkers/resources/META-INF/cloudstack/acl-role-based-access-checkers/spring-acl-role-based-access-checkers-context.xml
@@ -27,6 +27,6 @@
                       http://www.springframework.org/schema/context/spring-context-3.0.xsd"
                       >                     
 
-    <bean id="roleBasedEntityAccessChecker" class="org.apache.cloudstack.acl.entity.RoleBasedEntityAccessChecker" />
+    <bean id="RoleBasedEntityAccessChecker" class="org.apache.cloudstack.acl.entity.RoleBasedEntityAccessChecker" />
 
 </beans>

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/b7c3411b/server/src/com/cloud/api/query/vo/AclGroupJoinVO.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/query/vo/AclGroupJoinVO.java b/server/src/com/cloud/api/query/vo/AclGroupJoinVO.java
index e4ba3d9..dd61756 100644
--- a/server/src/com/cloud/api/query/vo/AclGroupJoinVO.java
+++ b/server/src/com/cloud/api/query/vo/AclGroupJoinVO.java
@@ -28,7 +28,6 @@ import javax.persistence.Id;
 import javax.persistence.Table;
 
 import org.apache.cloudstack.acl.AclEntityType;
-import org.apache.cloudstack.acl.PermissionScope;
 import org.apache.cloudstack.acl.SecurityChecker.AccessType;
 
 import com.cloud.utils.db.GenericDao;
@@ -98,22 +97,6 @@ public class AclGroupJoinVO extends BaseViewVO implements ControlledViewEntity {
     @Column(name = "member_account_name")
     private String memberAccountName;
 
-    @Column(name = "permission_action")
-    private String permissionAction;
-
-    @Column(name = "permission_entity_type")
-    private String permissionEntityType;
-
-    @Column(name = "permission_scope_id")
-    private long permissionScopeId;
-
-    @Column(name = "permission_scope_type")
-    @Enumerated(value = EnumType.STRING)
-    PermissionScope permissionScope;
-
-    @Column(name = "permission_access_type")
-    @Enumerated(value = EnumType.STRING)
-    AccessType permissionAccessType;
 
     public AclGroupJoinVO() {
     }
@@ -222,25 +205,6 @@ public class AclGroupJoinVO extends BaseViewVO implements ControlledViewEntity {
         return memberAccountName;
     }
 
-    public String getPermissionAction() {
-        return permissionAction;
-    }
-
-    public String getPermissionEntityType() {
-        return permissionEntityType;
-    }
-
-    public long getPermissionScopeId() {
-        return permissionScopeId;
-    }
-
-    public PermissionScope getPermissionScope() {
-        return permissionScope;
-    }
-
-    public AccessType getPermissionAccessType() {
-        return permissionAccessType;
-    }
 
     @Override
     public AclEntityType getEntityType() {


[4/5] Adding new IAM service under services. There are two modules to this component:

Posted by pr...@apache.org.
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/CreateAclGroupCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/CreateAclGroupCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/CreateAclGroupCmd.java
new file mode 100644
index 0000000..3654d0d
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/CreateAclGroupCmd.java
@@ -0,0 +1,162 @@
+// 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.command;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclGroup;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCreateCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AclGroupResponse;
+import org.apache.cloudstack.api.response.DomainResponse;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.event.EventTypes;
+import com.cloud.exception.ResourceAllocationException;
+import com.cloud.user.Account;
+
+@APICommand(name = "createAclGroup", responseObject = AclGroupResponse.class, description = "Creates an acl group")
+public class CreateAclGroupCmd extends BaseAsyncCreateCmd {
+    public static final Logger s_logger = Logger.getLogger(CreateAclGroupCmd.class.getName());
+
+    private static final String s_name = "createaclgroupresponse";
+
+    // ///////////////////////////////////////////////////
+    // ////////////// API parameters /////////////////////
+    // ///////////////////////////////////////////////////
+
+    @Parameter(name = ApiConstants.ACCOUNT, type = CommandType.STRING, description = "an account for the acl group. Must be used with domainId.")
+    private String accountName;
+
+    @Parameter(name = ApiConstants.DOMAIN_ID, type = CommandType.UUID, description = "domainId of the account owning the acl group", entityType = DomainResponse.class)
+    private Long domainId;
+
+    @Parameter(name = ApiConstants.DESCRIPTION, type = CommandType.STRING, description = "optional description of the acl group")
+    private String description;
+
+    @Parameter(name = ApiConstants.NAME, type = CommandType.STRING, required = true, description = "name of the acl group")
+    private String name;
+
+
+    // ///////////////////////////////////////////////////
+    // ///////////////// Accessors ///////////////////////
+    // ///////////////////////////////////////////////////
+
+    public String getAccountName() {
+        return accountName;
+    }
+
+    public String getDescription() {
+        return description;
+    }
+
+    public Long getDomainId() {
+        return domainId;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+
+    // ///////////////////////////////////////////////////
+    // ///////////// API Implementation///////////////////
+    // ///////////////////////////////////////////////////
+
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+    @Override
+    public long getEntityOwnerId() {
+        Account account = CallContext.current().getCallingAccount();
+        if ((account == null) || _accountService.isAdmin(account.getType())) {
+            if ((domainId != null) && (accountName != null)) {
+                Account userAccount = _responseGenerator.findAccountByNameDomain(accountName, domainId);
+                if (userAccount != null) {
+                    return userAccount.getId();
+                }
+            }
+        }
+
+        if (account != null) {
+            return account.getId();
+        }
+
+        return Account.ACCOUNT_ID_SYSTEM; // no account info given, parent this
+                                          // command to SYSTEM so ERROR events
+                                          // are tracked
+    }
+
+    @Override
+    public void execute() {
+        AclGroup grp = _entityMgr.findById(AclGroup.class, getEntityId());
+        if (grp != null) {
+            AclGroupResponse response = _responseGenerator.createAclGroupResponse(grp);
+            response.setResponseName(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to create acl group:" + name);
+        }
+    }
+
+    @Override
+    public void create() throws ResourceAllocationException {
+        Account account = CallContext.current().getCallingAccount();
+        AclGroup result = _aclService.createAclGroup(account, name, description);
+        if (result != null) {
+            setEntityId(result.getId());
+            setEntityUuid(result.getUuid());
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to create acl group entity" + name);
+        }
+
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_GROUP_CREATE;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "creating Acl group";
+    }
+
+    @Override
+    public String getCreateEventType() {
+        return EventTypes.EVENT_ACL_GROUP_CREATE;
+    }
+
+    @Override
+    public String getCreateEventDescription() {
+        return "creating acl group";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclGroup;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/CreateAclPolicyCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/CreateAclPolicyCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/CreateAclPolicyCmd.java
new file mode 100644
index 0000000..6628a82
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/CreateAclPolicyCmd.java
@@ -0,0 +1,169 @@
+// 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.command;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclPolicy;
+import org.apache.cloudstack.api.ACL;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCreateCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AclPolicyResponse;
+import org.apache.cloudstack.api.response.DomainResponse;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.event.EventTypes;
+import com.cloud.exception.ResourceAllocationException;
+import com.cloud.user.Account;
+
+@APICommand(name = "createAclPolicy", responseObject = AclPolicyResponse.class, description = "Creates an acl policy")
+public class CreateAclPolicyCmd extends BaseAsyncCreateCmd {
+    public static final Logger s_logger = Logger.getLogger(CreateAclPolicyCmd.class.getName());
+
+    private static final String s_name = "createaclpolicyresponse";
+
+    // ///////////////////////////////////////////////////
+    // ////////////// API parameters /////////////////////
+    // ///////////////////////////////////////////////////
+
+    @Parameter(name = ApiConstants.ACCOUNT, type = CommandType.STRING, description = "an account for the acl policy. Must be used with domainId.")
+    private String accountName;
+
+    @Parameter(name = ApiConstants.DOMAIN_ID, type = CommandType.UUID, description = "domainId of the account owning the acl policy", entityType = DomainResponse.class)
+    private Long domainId;
+
+    @Parameter(name = ApiConstants.DESCRIPTION, type = CommandType.STRING, description = "optional description of the acl policy")
+    private String description;
+
+    @Parameter(name = ApiConstants.NAME, type = CommandType.STRING, required = true, description = "name of the acl policy")
+    private String name;
+
+    @ACL
+    @Parameter(name = ApiConstants.ACL_PARENT_POLICY_ID, type = CommandType.UUID, description = "The ID of parent acl policy.", entityType = AclPolicyResponse.class)
+    private Long parentPolicyId;
+
+
+    // ///////////////////////////////////////////////////
+    // ///////////////// Accessors ///////////////////////
+    // ///////////////////////////////////////////////////
+
+    public String getAccountName() {
+        return accountName;
+    }
+
+    public String getDescription() {
+        return description;
+    }
+
+    public Long getDomainId() {
+        return domainId;
+    }
+
+    public String getName() {
+        return name;
+    }
+
+    public Long getParentPolicyId() {
+        return parentPolicyId;
+    }
+
+    // ///////////////////////////////////////////////////
+    // ///////////// API Implementation///////////////////
+    // ///////////////////////////////////////////////////
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+    @Override
+    public long getEntityOwnerId() {
+        Account account = CallContext.current().getCallingAccount();
+        if ((account == null) || _accountService.isAdmin(account.getType())) {
+            if ((domainId != null) && (accountName != null)) {
+                Account userAccount = _responseGenerator.findAccountByNameDomain(accountName, domainId);
+                if (userAccount != null) {
+                    return userAccount.getId();
+                }
+            }
+        }
+
+        if (account != null) {
+            return account.getId();
+        }
+
+        return Account.ACCOUNT_ID_SYSTEM; // no account info given, parent this
+                                          // command to SYSTEM so ERROR events
+                                          // are tracked
+    }
+
+    @Override
+    public void execute() {
+        AclPolicy policy = _entityMgr.findById(AclPolicy.class, getEntityId());
+        if (policy != null) {
+            AclPolicyResponse response = _responseGenerator.createAclPolicyResponse(policy);
+            response.setResponseName(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to create acl policy:" + name);
+        }
+    }
+
+    @Override
+    public void create() throws ResourceAllocationException {
+        Account account = CallContext.current().getCallingAccount();
+        AclPolicy result = _aclService.createAclPolicy(account, name, description, parentPolicyId);
+        if (result != null) {
+            setEntityId(result.getId());
+            setEntityUuid(result.getUuid());
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to create acl policy entity" + name);
+        }
+
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_POLICY_CREATE;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "creating Acl policy";
+    }
+
+    @Override
+    public String getCreateEventType() {
+        return EventTypes.EVENT_ACL_POLICY_CREATE;
+    }
+
+    @Override
+    public String getCreateEventDescription() {
+        return "creating acl policy";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclPolicy;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/DeleteAclGroupCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/DeleteAclGroupCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/DeleteAclGroupCmd.java
new file mode 100644
index 0000000..110c1b5
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/DeleteAclGroupCmd.java
@@ -0,0 +1,96 @@
+// 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.command;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.api.ACL;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AclGroupResponse;
+import org.apache.cloudstack.api.response.SuccessResponse;
+
+import com.cloud.event.EventTypes;
+import com.cloud.user.Account;
+
+@APICommand(name = "deleteAclGroup", description = "Deletes acl group", responseObject = SuccessResponse.class)
+public class DeleteAclGroupCmd extends BaseAsyncCmd {
+    public static final Logger s_logger = Logger.getLogger(DeleteAclGroupCmd.class.getName());
+    private static final String s_name = "deleteaclgroupresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+    @ACL
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, description = "The ID of the acl group.", required = true, entityType = AclGroupResponse.class)
+    private Long id;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+
+    public Long getId() {
+        return id;
+    }
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+    @Override
+    public long getEntityOwnerId() {
+        return Account.ACCOUNT_ID_SYSTEM;
+    }
+
+    @Override
+    public void execute(){
+        boolean result = _aclService.deleteAclGroup(id);
+        if (result) {
+            SuccessResponse response = new SuccessResponse(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to delete acl group");
+        }
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_GROUP_DELETE;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "Deleting Acl group";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclGroup;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/DeleteAclPolicyCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/DeleteAclPolicyCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/DeleteAclPolicyCmd.java
new file mode 100644
index 0000000..06df62f
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/DeleteAclPolicyCmd.java
@@ -0,0 +1,96 @@
+// 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.command;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.api.ACL;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AclPolicyResponse;
+import org.apache.cloudstack.api.response.SuccessResponse;
+
+import com.cloud.event.EventTypes;
+import com.cloud.user.Account;
+
+@APICommand(name = "deleteAclPolicy", description = "Deletes acl policy", responseObject = SuccessResponse.class)
+public class DeleteAclPolicyCmd extends BaseAsyncCmd {
+    public static final Logger s_logger = Logger.getLogger(DeleteAclPolicyCmd.class.getName());
+    private static final String s_name = "deleteaclpolicyresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+    @ACL
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, description = "The ID of the acl role.", required = true, entityType = AclPolicyResponse.class)
+    private Long id;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+
+    public Long getId() {
+        return id;
+    }
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+    @Override
+    public long getEntityOwnerId() {
+        return Account.ACCOUNT_ID_SYSTEM;
+    }
+
+    @Override
+    public void execute(){
+        boolean result = _aclService.deleteAclPolicy(id);
+        if (result) {
+            SuccessResponse response = new SuccessResponse(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to delete acl policy");
+        }
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_POLICY_DELETE;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "Deleting Acl role";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclPolicy;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/ListAclGroupsCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/ListAclGroupsCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/ListAclGroupsCmd.java
new file mode 100644
index 0000000..e6f732c
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/ListAclGroupsCmd.java
@@ -0,0 +1,82 @@
+// 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.command;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.BaseListDomainResourcesCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.response.AclGroupResponse;
+import org.apache.cloudstack.api.response.ListResponse;
+
+
+@APICommand(name = "listAclGroups", description = "Lists acl groups", responseObject = AclGroupResponse.class)
+public class ListAclGroupsCmd extends BaseListDomainResourcesCmd {
+    public static final Logger s_logger = Logger.getLogger(ListAclGroupsCmd.class.getName());
+
+    private static final String s_name = "listaclgroupsresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+    @Parameter(name = ApiConstants.NAME, type = CommandType.STRING, description = "lists acl groups by name")
+    private String aclGroupName;
+
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, description = "list the acl group by the id provided", entityType = AclGroupResponse.class)
+    private Long id;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+    public String getAclGroupName() {
+        return aclGroupName;
+    }
+
+
+    public Long getId(){
+        return id;
+    }
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+    @Override
+    public void execute(){
+
+        ListResponse<AclGroupResponse> response = _queryService.listAclGroups(id, aclGroupName, getDomainId(),
+                getStartIndex(), getPageSizeVal());
+        response.setResponseName(getCommandName());
+        setResponseObject(response);
+
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclGroup;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/ListAclPoliciesCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/ListAclPoliciesCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/ListAclPoliciesCmd.java
new file mode 100644
index 0000000..5a99da0
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/ListAclPoliciesCmd.java
@@ -0,0 +1,82 @@
+// 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.command;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.BaseListDomainResourcesCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.response.AclPolicyResponse;
+import org.apache.cloudstack.api.response.ListResponse;
+
+
+@APICommand(name = "listAclPolicies", description = "Lists acl policies", responseObject = AclPolicyResponse.class)
+public class ListAclPoliciesCmd extends BaseListDomainResourcesCmd {
+    public static final Logger s_logger = Logger.getLogger(ListAclPoliciesCmd.class.getName());
+
+    private static final String s_name = "listaclpoliciesresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+    @Parameter(name = ApiConstants.NAME, type = CommandType.STRING, description = "lists acl policies by name")
+    private String aclPolicyName;
+
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, description = "list the acl policy by the id provided", entityType = AclPolicyResponse.class)
+    private Long id;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+    public String getAclPolicyName() {
+        return aclPolicyName;
+    }
+
+
+    public Long getId(){
+        return id;
+    }
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+    @Override
+    public void execute(){
+
+        ListResponse<AclPolicyResponse> response = _queryService.listAclPolicies(id, aclPolicyName, getDomainId(),
+                getStartIndex(), getPageSizeVal());
+        response.setResponseName(getCommandName());
+        setResponseObject(response);
+
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclPolicy;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAccountFromAclGroupCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAccountFromAclGroupCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAccountFromAclGroupCmd.java
new file mode 100644
index 0000000..8d8d28a
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAccountFromAclGroupCmd.java
@@ -0,0 +1,121 @@
+// 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.command;
+
+import java.util.List;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclGroup;
+import org.apache.cloudstack.api.ACL;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AccountResponse;
+import org.apache.cloudstack.api.response.AclGroupResponse;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.event.EventTypes;
+import com.cloud.exception.InsufficientCapacityException;
+import com.cloud.exception.ResourceUnavailableException;
+import com.cloud.user.Account;
+
+
+@APICommand(name = "removeAccountFromAclGroup", description = "remove accounts from an acl group", responseObject = AclGroupResponse.class)
+public class RemoveAccountFromAclGroupCmd extends BaseAsyncCmd {
+    public static final Logger s_logger = Logger.getLogger(RemoveAccountFromAclGroupCmd.class.getName());
+    private static final String s_name = "removeaccountfromaclgroupresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+
+    @ACL
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, entityType = AclGroupResponse.class,
+            required = true, description = "The ID of the acl group")
+    private Long id;
+
+    @ACL
+    @Parameter(name = ApiConstants.ACCOUNTS, type = CommandType.LIST, collectionType = CommandType.UUID, entityType = AccountResponse.class, description = "comma separated list of account id that are going to be assigned to the acl group.")
+    private List<Long> accountIdList;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+
+
+    public Long getId() {
+        return id;
+    }
+
+
+    public List<Long> getAccountIdList() {
+        return accountIdList;
+    }
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+
+    @Override
+    public long getEntityOwnerId() {
+        return Account.ACCOUNT_ID_SYSTEM; // no account info given, parent this command to SYSTEM so ERROR events are tracked
+    }
+
+    @Override
+    public void execute() throws ResourceUnavailableException,
+            InsufficientCapacityException, ServerApiException {
+        CallContext.current().setEventDetails("Acl group Id: " + getId());
+        AclGroup result = _aclService.removeAccountsFromGroup(accountIdList, id);
+        if (result != null){
+            AclGroupResponse response = _responseGenerator.createAclGroupResponse(result);
+            response.setResponseName(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to remove accounts from acl group");
+        }
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_GROUP_UPDATE;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "removing accounts from acl group";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclGroup;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAclPermissionFromAclPolicyCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAclPermissionFromAclPolicyCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAclPermissionFromAclPolicyCmd.java
new file mode 100644
index 0000000..dc8ff33
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAclPermissionFromAclPolicyCmd.java
@@ -0,0 +1,141 @@
+// 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.command;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclPolicy;
+import org.apache.cloudstack.acl.PermissionScope;
+import org.apache.cloudstack.api.ACL;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AclPolicyResponse;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.event.EventTypes;
+import com.cloud.exception.InsufficientCapacityException;
+import com.cloud.exception.ResourceUnavailableException;
+import com.cloud.user.Account;
+
+
+@APICommand(name = "removeAclPermissionFromAclPolicy", description = "Remove acl permission from an acl policy", responseObject = AclPolicyResponse.class)
+public class RemoveAclPermissionFromAclPolicyCmd extends BaseAsyncCmd {
+    public static final Logger s_logger = Logger.getLogger(RemoveAclPermissionFromAclPolicyCmd.class.getName());
+    private static final String s_name = "removeaclpermissionfromaclpolicyresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+
+    @ACL
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, entityType = AclPolicyResponse.class,
+            required = true, description = "The ID of the acl policy")
+    private Long id;
+
+    @Parameter(name = ApiConstants.ACL_ACTION, type = CommandType.STRING, required = true, description = "action api name.")
+    private String action;
+
+    @Parameter(name = ApiConstants.ENTITY_TYPE, type = CommandType.STRING, required = false, description = "entity class simple name.")
+    private String entityType;
+
+    @Parameter(name = ApiConstants.ACL_SCOPE, type = CommandType.STRING,
+            required = false, description = "acl permission scope")
+    private String scope;
+
+    @Parameter(name = ApiConstants.ACL_SCOPE_ID, type = CommandType.UUID, required = false, description = "The ID of the permission scope id")
+    private Long scopeId;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+
+
+    public Long getId() {
+        return id;
+    }
+
+
+    public String getAction() {
+        return action;
+    }
+
+    public String getEntityType() {
+        return entityType;
+    }
+
+    public String getScope() {
+        return scope;
+    }
+
+    public Long getScopeId() {
+        return scopeId;
+    }
+
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+
+    @Override
+    public long getEntityOwnerId() {
+        return Account.ACCOUNT_ID_SYSTEM; // no account info given, parent this command to SYSTEM so ERROR events are tracked
+    }
+
+    @Override
+    public void execute() throws ResourceUnavailableException,
+            InsufficientCapacityException, ServerApiException {
+        CallContext.current().setEventDetails("Acl policy Id: " + getId());
+        AclPolicy result = _aclService.removeAclPermissionFromAclPolicy(id, entityType, PermissionScope.valueOf(scope), scopeId, action);
+        if (result != null) {
+            AclPolicyResponse response = _responseGenerator.createAclPolicyResponse(result);
+            response.setResponseName(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to remove permission from acl policy " + getId());
+        }
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_POLICY_REVOKE;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "removing permission from acl policy";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclPolicy;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAclPolicyFromAclGroupCmd.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAclPolicyFromAclGroupCmd.java b/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAclPolicyFromAclGroupCmd.java
new file mode 100644
index 0000000..39958c0
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/api/command/RemoveAclPolicyFromAclGroupCmd.java
@@ -0,0 +1,121 @@
+// 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.command;
+
+import java.util.List;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.acl.AclGroup;
+import org.apache.cloudstack.api.ACL;
+import org.apache.cloudstack.api.APICommand;
+import org.apache.cloudstack.api.ApiCommandJobType;
+import org.apache.cloudstack.api.ApiConstants;
+import org.apache.cloudstack.api.ApiErrorCode;
+import org.apache.cloudstack.api.BaseAsyncCmd;
+import org.apache.cloudstack.api.Parameter;
+import org.apache.cloudstack.api.ServerApiException;
+import org.apache.cloudstack.api.response.AclGroupResponse;
+import org.apache.cloudstack.api.response.AclPolicyResponse;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.event.EventTypes;
+import com.cloud.exception.InsufficientCapacityException;
+import com.cloud.exception.ResourceUnavailableException;
+import com.cloud.user.Account;
+
+
+@APICommand(name = "removeAclPolicyFromAclGroup", description = "remove acl policy from an acl group", responseObject = AclGroupResponse.class)
+public class RemoveAclPolicyFromAclGroupCmd extends BaseAsyncCmd {
+    public static final Logger s_logger = Logger.getLogger(RemoveAclPolicyFromAclGroupCmd.class.getName());
+    private static final String s_name = "removeaclpolicyfromaclgroupresponse";
+
+    /////////////////////////////////////////////////////
+    //////////////// API parameters /////////////////////
+    /////////////////////////////////////////////////////
+
+
+    @ACL
+    @Parameter(name = ApiConstants.ID, type = CommandType.UUID, entityType = AclGroupResponse.class,
+            required = true, description = "The ID of the acl group")
+    private Long id;
+
+    @ACL
+    @Parameter(name = ApiConstants.ACL_POLICIES, type = CommandType.LIST, collectionType = CommandType.UUID, entityType = AclPolicyResponse.class, description = "comma separated list of acl policy id that are going to be applied to the acl group.")
+    private List<Long> policyIdList;
+
+
+    /////////////////////////////////////////////////////
+    /////////////////// Accessors ///////////////////////
+    /////////////////////////////////////////////////////
+
+
+    public Long getId() {
+        return id;
+    }
+
+
+    public List<Long> getRoleIdList() {
+        return policyIdList;
+    }
+
+    /////////////////////////////////////////////////////
+    /////////////// API Implementation///////////////////
+    /////////////////////////////////////////////////////
+
+
+    @Override
+    public String getCommandName() {
+        return s_name;
+    }
+
+
+    @Override
+    public long getEntityOwnerId() {
+        return Account.ACCOUNT_ID_SYSTEM; // no account info given, parent this command to SYSTEM so ERROR events are tracked
+    }
+
+    @Override
+    public void execute() throws ResourceUnavailableException,
+            InsufficientCapacityException, ServerApiException {
+        CallContext.current().setEventDetails("Acl group Id: " + getId());
+        AclGroup result = _aclService.removeAclPoliciesFromGroup(policyIdList, id);
+        if (result != null){
+            AclGroupResponse response = _responseGenerator.createAclGroupResponse(result);
+            response.setResponseName(getCommandName());
+            setResponseObject(response);
+        } else {
+            throw new ServerApiException(ApiErrorCode.INTERNAL_ERROR, "Failed to add roles to acl group");
+        }
+    }
+
+    @Override
+    public String getEventType() {
+        return EventTypes.EVENT_ACL_GROUP_UPDATE;
+    }
+
+    @Override
+    public String getEventDescription() {
+        return "removing acl roles from acl group";
+    }
+
+    @Override
+    public ApiCommandJobType getInstanceType() {
+        return ApiCommandJobType.AclGroup;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupAccountMapVO.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupAccountMapVO.java b/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupAccountMapVO.java
new file mode 100644
index 0000000..d39317a
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupAccountMapVO.java
@@ -0,0 +1,78 @@
+// 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.server;
+
+import java.util.Date;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Table;
+
+import com.cloud.utils.db.GenericDao;
+
+@Entity
+@Table(name = ("acl_group_account_map"))
+public class AclGroupAccountMapVO {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @Column(name = "id")
+    private Long id;
+
+    @Column(name = "group_id")
+    private long aclGroupId;
+
+    @Column(name = "account_id")
+    private long accountId;
+
+    @Column(name = GenericDao.REMOVED_COLUMN)
+    private Date removed;
+
+    @Column(name = GenericDao.CREATED_COLUMN)
+    private Date created;
+
+    public AclGroupAccountMapVO() {
+    }
+
+    public AclGroupAccountMapVO(long aclGroupId, long accountId) {
+        this.aclGroupId = aclGroupId;
+        this.accountId = accountId;
+    }
+
+    public long getId() {
+        return id;
+    }
+
+    public long getAclGroupId() {
+        return aclGroupId;
+    }
+
+
+    public long getAccountId() {
+        return accountId;
+    }
+
+    public Date getRemoved() {
+        return removed;
+    }
+
+    public Date getCreated() {
+        return created;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupPolicyMapVO.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupPolicyMapVO.java b/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupPolicyMapVO.java
new file mode 100644
index 0000000..0dfef09
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupPolicyMapVO.java
@@ -0,0 +1,79 @@
+// 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.server;
+
+import java.util.Date;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Table;
+
+
+import com.cloud.utils.db.GenericDao;
+
+@Entity
+@Table(name = ("acl_group_policy_map"))
+public class AclGroupPolicyMapVO {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @Column(name = "id")
+    private Long id;
+
+    @Column(name = "group_id")
+    private long aclGroupId;
+
+    @Column(name = "policy_id")
+    private long aclPolicyId;
+
+    @Column(name = GenericDao.REMOVED_COLUMN)
+    private Date removed;
+
+    @Column(name = GenericDao.CREATED_COLUMN)
+    private Date created;
+
+    public AclGroupPolicyMapVO() {
+    }
+
+    public AclGroupPolicyMapVO(long aclGroupId, long aclPolicyId) {
+        this.aclGroupId = aclGroupId;
+        this.aclPolicyId = aclPolicyId;
+    }
+
+    public long getId() {
+        return id;
+    }
+
+    public long getAclGroupId() {
+        return aclGroupId;
+    }
+
+
+    public long getAclPolicyId() {
+        return aclPolicyId;
+    }
+
+    public Date getRemoved() {
+        return removed;
+    }
+
+    public Date getCreated() {
+        return created;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupVO.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupVO.java b/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupVO.java
new file mode 100644
index 0000000..892803d
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/AclGroupVO.java
@@ -0,0 +1,109 @@
+// 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.server;
+
+import java.util.Date;
+import java.util.UUID;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Table;
+
+import org.apache.cloudstack.iam.api.AclGroup;
+
+import com.cloud.utils.db.GenericDao;
+
+@Entity
+@Table(name = ("acl_group"))
+public class AclGroupVO implements AclGroup {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @Column(name = "id")
+    private long id;
+
+    @Column(name = "name")
+    private String name;
+
+    @Column(name = "description")
+    private String description;
+
+    @Column(name = "uuid")
+    private String uuid;
+
+    @Column(name = "path")
+    private String path;
+
+    @Column(name = GenericDao.REMOVED_COLUMN)
+    private Date removed;
+
+    @Column(name = GenericDao.CREATED_COLUMN)
+    private Date created;
+
+    public AclGroupVO() {
+    	uuid = UUID.randomUUID().toString();
+    }
+
+    public AclGroupVO(String name, String description) {
+        this.name = name;
+        this.description = description;
+    	uuid = UUID.randomUUID().toString();
+        path = "/";
+    }
+
+    @Override
+    public long getId() {
+        return id;
+    }
+
+    @Override
+    public String getName() {
+        return name;
+    }
+
+    @Override
+    public String getDescription() {
+        return description;
+    }
+
+    public String getPath() {
+        return path;
+    }
+
+    public void setPath(String path) {
+        this.path = path;
+    }
+
+    @Override
+    public String getUuid() {
+    	return uuid;
+    }
+
+    public void setUuid(String uuid) {
+    	this.uuid = uuid;
+    }
+
+    public Date getRemoved() {
+        return removed;
+    }
+
+    public Date getCreated() {
+        return created;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/AclPolicyPermissionVO.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/AclPolicyPermissionVO.java b/services/iam/server/src/org/apache/cloudstack/iam/server/AclPolicyPermissionVO.java
new file mode 100644
index 0000000..87f490b
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/AclPolicyPermissionVO.java
@@ -0,0 +1,172 @@
+// 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.server;
+
+import java.util.Date;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.EnumType;
+import javax.persistence.Enumerated;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Table;
+
+import org.apache.cloudstack.iam.api.AclPolicyPermission;
+import com.cloud.utils.db.GenericDao;
+
+@Entity
+@Table(name = ("acl_policy_permission"))
+public class AclPolicyPermissionVO implements AclPolicyPermission {
+
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @Column(name = "id")
+    private long id;
+
+    @Column(name = "policy_id")
+    private long aclPolicyId;
+
+    @Column(name = "action")
+    private String action;
+
+    @Column(name = "resource_type")
+    private String entityType;
+
+    @Column(name = "access_type")
+    private String accessType;
+
+    @Column(name = "scope")
+    private String scope;
+
+    @Column(name = "scope_id")
+    private Long scopeId;
+
+    @Column(name = "permission")
+    @Enumerated(value = EnumType.STRING)
+    private Permission permission;
+
+    @Column(name = GenericDao.REMOVED_COLUMN)
+    private Date removed;
+
+    @Column(name = GenericDao.CREATED_COLUMN)
+    private Date created;
+
+    public AclPolicyPermissionVO() {
+
+    }
+
+    public AclPolicyPermissionVO(long aclPolicyId, String action, String entityType, String accessType, String scope,
+            Long scopeId, Permission permission) {
+        this.aclPolicyId = aclPolicyId;
+        this.action = action;
+        this.entityType = entityType;
+        this.accessType = accessType;
+        this.scope = scope;
+        this.scopeId = scopeId;
+        this.permission = permission;
+    }
+
+    @Override
+    public long getId() {
+        return id;
+    }
+
+    @Override
+    public long getAclPolicyId() {
+        return aclPolicyId;
+    }
+
+
+    public void setAclPolicyId(long aclPolicyId) {
+        this.aclPolicyId = aclPolicyId;
+    }
+
+    @Override
+    public String getEntityType() {
+        return entityType;
+    }
+
+    @Override
+    public String getAccessType() {
+        return accessType;
+    }
+
+
+    public void setEntityType(String entityType) {
+        this.entityType = entityType;
+    }
+
+    public void setAccessType(String accessType) {
+        this.accessType = accessType;
+    }
+
+    @Override
+    public String getScope() {
+        return scope;
+    }
+
+    public void setScope(String scope) {
+        this.scope = scope;
+    }
+
+
+    @Override
+    public String getAction() {
+        return action;
+    }
+
+    @Override
+    public Long getScopeId() {
+        // TODO
+        // handle special -1 scopeId, current caller domain, account
+        /*
+         * if ( scopeId < 0 ){ Account caller =
+         * CallContext.current().getCallingAccount(); if ( scope ==
+         * PermissionScope.DOMAIN){ return caller.getDomainId(); } else if
+         * (scope == PermissionScope.ACCOUNT) { return caller.getAccountId(); }
+         * }
+         */
+        return scopeId;
+    }
+
+    @Override
+    public Permission getPermission() {
+        return permission;
+    }
+
+    public void setAction(String action) {
+        this.action = action;
+    }
+
+    public void setScopeId(Long scopeId) {
+        this.scopeId = scopeId;
+    }
+
+    public void setPermission(Permission permission) {
+        this.permission = permission;
+    }
+
+    public Date getRemoved() {
+        return removed;
+    }
+
+    public Date getCreated() {
+        return created;
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/AclPolicyVO.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/AclPolicyVO.java b/services/iam/server/src/org/apache/cloudstack/iam/server/AclPolicyVO.java
new file mode 100644
index 0000000..e6e30ca
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/AclPolicyVO.java
@@ -0,0 +1,136 @@
+// 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.server;
+
+import java.util.Date;
+import java.util.UUID;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.EnumType;
+import javax.persistence.Enumerated;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Table;
+
+import org.apache.cloudstack.iam.api.AclPolicy;
+
+import com.cloud.utils.db.GenericDao;
+
+@Entity
+@Table(name = ("acl_policy"))
+public class AclPolicyVO implements AclPolicy {
+    @Id
+    @GeneratedValue(strategy = GenerationType.IDENTITY)
+    @Column(name = "id")
+    private long id;
+
+    @Column(name = "name")
+    private String name;
+
+    @Column(name = "description")
+    private String description;
+
+    @Column(name = "uuid")
+    private String uuid;
+
+    @Column(name = "domain_id")
+    private long domainId;
+
+    @Column(name = "account_id")
+    private long accountId;
+
+    @Column(name = GenericDao.REMOVED_COLUMN)
+    private Date removed;
+
+    @Column(name = GenericDao.CREATED_COLUMN)
+    private Date created;
+
+    @Column(name = "policy_type")
+    @Enumerated(value = EnumType.STRING)
+    private AclPolicy.PolicyType policyType;
+
+    public AclPolicyVO() {
+    	uuid = UUID.randomUUID().toString();
+    }
+
+    public AclPolicyVO(String name, String description) {
+        this.name = name;
+        this.description = description;
+    	uuid = UUID.randomUUID().toString();
+        policyType = AclPolicy.PolicyType.Static;
+    }
+
+    @Override
+    public long getId() {
+        return id;
+    }
+
+    @Override
+    public String getName() {
+        return name;
+    }
+
+    @Override
+    public String getDescription() {
+        return description;
+    }
+
+
+    @Override
+    public String getUuid() {
+    	return uuid;
+    }
+
+    public void setUuid(String uuid) {
+    	this.uuid = uuid;
+    }
+
+    public Date getRemoved() {
+        return removed;
+    }
+
+    public Date getCreated() {
+        return created;
+    }
+
+    public long getDomainId() {
+        return domainId;
+    }
+
+    public void setDomainId(long domainId) {
+        this.domainId = domainId;
+    }
+
+    public long getAccountId() {
+        return accountId;
+    }
+
+    public void setAccountId(long accountId) {
+        this.accountId = accountId;
+    }
+
+    public AclPolicy.PolicyType getPolicyType() {
+        return policyType;
+    }
+
+    public void setPolicyType(AclPolicy.PolicyType policyType) {
+        this.policyType = policyType;
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/IAMServiceImpl.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/IAMServiceImpl.java b/services/iam/server/src/org/apache/cloudstack/iam/server/IAMServiceImpl.java
new file mode 100644
index 0000000..3ec32e3
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/IAMServiceImpl.java
@@ -0,0 +1,543 @@
+// 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.server;
+
+import java.util.ArrayList;
+import java.util.List;
+
+import javax.ejb.Local;
+import javax.inject.Inject;
+
+import org.apache.log4j.Logger;
+
+import org.apache.cloudstack.iam.api.AclGroup;
+import org.apache.cloudstack.iam.api.AclPolicy;
+import org.apache.cloudstack.iam.api.AclPolicyPermission.Permission;
+import org.apache.cloudstack.iam.api.IAMService;
+import org.apache.cloudstack.iam.server.dao.AclGroupAccountMapDao;
+import org.apache.cloudstack.iam.server.dao.AclGroupDao;
+import org.apache.cloudstack.iam.server.dao.AclGroupPolicyMapDao;
+import org.apache.cloudstack.iam.server.dao.AclPolicyDao;
+import org.apache.cloudstack.iam.server.dao.AclPolicyPermissionDao;
+import org.apache.cloudstack.context.CallContext;
+
+import com.cloud.event.ActionEvent;
+import com.cloud.event.EventTypes;
+import com.cloud.exception.InvalidParameterValueException;
+import com.cloud.user.Account;
+import com.cloud.utils.component.Manager;
+import com.cloud.utils.component.ManagerBase;
+import com.cloud.utils.db.DB;
+import com.cloud.utils.db.EntityManager;
+import com.cloud.utils.db.GenericSearchBuilder;
+import com.cloud.utils.db.JoinBuilder.JoinType;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+import com.cloud.utils.db.SearchCriteria.Op;
+import com.cloud.utils.db.Transaction;
+import com.cloud.utils.db.TransactionCallback;
+import com.cloud.utils.db.TransactionCallbackNoReturn;
+import com.cloud.utils.db.TransactionStatus;
+
+@Local(value = {IAMService.class})
+public class IAMServiceImpl extends ManagerBase implements IAMService, Manager {
+
+    public static final Logger s_logger = Logger.getLogger(IAMServiceImpl.class);
+    private String _name;
+
+    @Inject
+    AclPolicyDao _aclPolicyDao;
+
+    @Inject
+    AclGroupDao _aclGroupDao;
+
+    @Inject
+    EntityManager _entityMgr;
+
+    @Inject
+    AclGroupPolicyMapDao _aclGroupPolicyMapDao;
+
+    @Inject
+    AclGroupAccountMapDao _aclGroupAccountMapDao;
+
+    @Inject
+    AclPolicyPermissionDao _policyPermissionDao;
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_CREATE, eventDescription = "Creating Acl Group", create = true)
+    public AclGroup createAclGroup(String aclGroupName, String description, String path) {
+        // check if the role is already existing
+        AclGroup grp = _aclGroupDao.findByName(path, aclGroupName);
+        if (grp != null) {
+            throw new InvalidParameterValueException(
+                    "Unable to create acl group with name " + aclGroupName
+                    + " already exisits for path " + path);
+        }
+        AclGroupVO rvo = new AclGroupVO(aclGroupName, description);
+        rvo.setPath(path);
+
+        return _aclGroupDao.persist(rvo);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_DELETE, eventDescription = "Deleting Acl Group")
+    public boolean deleteAclGroup(final Long aclGroupId) {
+        // get the Acl Group entity
+        final AclGroup grp = _aclGroupDao.findById(aclGroupId);
+        if (grp == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + aclGroupId
+                    + "; failed to delete acl group.");
+        }
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // remove this group related entry in acl_group_role_map
+                List<AclGroupPolicyMapVO> groupPolicyMap = _aclGroupPolicyMapDao.listByGroupId(grp.getId());
+                if (groupPolicyMap != null) {
+                    for (AclGroupPolicyMapVO gr : groupPolicyMap) {
+                        _aclGroupPolicyMapDao.remove(gr.getId());
+                    }
+                }
+
+                // remove this group related entry in acl_group_account table
+                List<AclGroupAccountMapVO> groupAcctMap = _aclGroupAccountMapDao.listByGroupId(grp.getId());
+                if (groupAcctMap != null) {
+                    for (AclGroupAccountMapVO grpAcct : groupAcctMap) {
+                        _aclGroupAccountMapDao.remove(grpAcct.getId());
+                    }
+                }
+
+                // remove this group from acl_group table
+                _aclGroupDao.remove(aclGroupId);
+            }
+        });
+
+        return true;
+    }
+
+    @Override
+    public List<AclGroup> listAclGroups(long accountId) {
+
+        GenericSearchBuilder<AclGroupAccountMapVO, Long> groupSB = _aclGroupAccountMapDao.createSearchBuilder(Long.class);
+        groupSB.selectFields(groupSB.entity().getAclGroupId());
+        groupSB.and("account", groupSB.entity().getAccountId(), Op.EQ);
+        SearchCriteria<Long> groupSc = groupSB.create();
+
+        List<Long> groupIds = _aclGroupAccountMapDao.customSearch(groupSc, null);
+
+        SearchBuilder<AclGroupVO> sb = _aclGroupDao.createSearchBuilder();
+        sb.and("ids", sb.entity().getId(), Op.IN);
+        SearchCriteria<AclGroupVO> sc = sb.create();
+        sc.setParameters("ids", groupIds.toArray(new Object[groupIds.size()]));
+        List<AclGroupVO> groups = _aclGroupDao.search(sc, null);
+
+        return new ArrayList<AclGroup>(groups);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_UPDATE, eventDescription = "Adding accounts to acl group")
+    public AclGroup addAccountsToGroup(final List<Long> acctIds, final Long groupId) {
+        final Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Group entity
+        AclGroup group = _aclGroupDao.findById(groupId);
+        if (group == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + groupId
+                    + "; failed to add accounts to acl group.");
+        }
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // add entries in acl_group_account_map table
+                for (Long acctId : acctIds) {
+                    // check account permissions
+                    AclGroupAccountMapVO grMap = _aclGroupAccountMapDao.findByGroupAndAccount(groupId, acctId);
+                    if (grMap == null) {
+                        // not there already
+                        grMap = new AclGroupAccountMapVO(groupId, acctId);
+                        _aclGroupAccountMapDao.persist(grMap);
+                    }
+                }
+            }
+        });
+        return group;
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_UPDATE, eventDescription = "Removing accounts from acl group")
+    public AclGroup removeAccountsFromGroup(final List<Long> acctIds, final Long groupId) {
+        final Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Group entity
+        AclGroup group = _aclGroupDao.findById(groupId);
+        if (group == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + groupId
+                    + "; failed to remove accounts from acl group.");
+        }
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // remove entries from acl_group_account_map table
+                for (Long acctId : acctIds) {
+                    AclGroupAccountMapVO grMap = _aclGroupAccountMapDao.findByGroupAndAccount(groupId, acctId);
+                    if (grMap != null) {
+                        // not removed yet
+                        _aclGroupAccountMapDao.remove(grMap.getId());
+                    }
+                }
+            }
+        });
+        return group;
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_CREATE, eventDescription = "Creating Acl Policy", create = true)
+    public AclPolicy createAclPolicy(final String aclPolicyName, final String description, final Long parentPolicyId) {
+
+        // check if the policy is already existing
+        AclPolicy ro = _aclPolicyDao.findByName(aclPolicyName);
+        if (ro != null) {
+            throw new InvalidParameterValueException(
+                    "Unable to create acl policy with name " + aclPolicyName
+                    + " already exisits");
+        }
+
+        AclPolicy role = Transaction.execute(new TransactionCallback<AclPolicy>() {
+            @Override
+            public AclPolicy doInTransaction(TransactionStatus status) {
+                AclPolicyVO rvo = new AclPolicyVO(aclPolicyName, description);
+
+                AclPolicy role = _aclPolicyDao.persist(rvo);
+                if (parentPolicyId != null) {
+                    // copy parent role permissions
+                    List<AclPolicyPermissionVO> perms = _policyPermissionDao.listByPolicy(parentPolicyId);
+                    if (perms != null) {
+                        for (AclPolicyPermissionVO perm : perms) {
+                            perm.setAclPolicyId(role.getId());
+                            _policyPermissionDao.persist(perm);
+                        }
+                    }
+                }
+                return role;
+            }
+        });
+                
+
+        return role;
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_DELETE, eventDescription = "Deleting Acl Policy")
+    public boolean deleteAclPolicy(final long aclPolicyId) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Policy entity
+        final AclPolicy policy = _aclPolicyDao.findById(aclPolicyId);
+        if (policy == null) {
+            throw new InvalidParameterValueException("Unable to find acl policy: " + aclPolicyId
+                    + "; failed to delete acl policy.");
+        }
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // remove this role related entry in acl_group_role_map
+                List<AclGroupPolicyMapVO> groupPolicyMap = _aclGroupPolicyMapDao.listByPolicyId(policy.getId());
+                if (groupPolicyMap != null) {
+                    for (AclGroupPolicyMapVO gr : groupPolicyMap) {
+                        _aclGroupPolicyMapDao.remove(gr.getId());
+                    }
+                }
+
+                // remove this policy related entry in acl_policy_permission table
+                List<AclPolicyPermissionVO> policyPermMap = _policyPermissionDao.listByPolicy(policy.getId());
+                if (policyPermMap != null) {
+                    for (AclPolicyPermissionVO policyPerm : policyPermMap) {
+                        _policyPermissionDao.remove(policyPerm.getId());
+                    }
+                }
+
+                // remove this role from acl_role table
+                _aclPolicyDao.remove(aclPolicyId);
+            }
+        });
+
+        return true;
+    }
+
+
+    @Override
+    public List<AclPolicy> listAclPolicies(long accountId) {
+
+        // static policies of the account
+        SearchBuilder<AclGroupAccountMapVO> groupSB = _aclGroupAccountMapDao.createSearchBuilder();
+        groupSB.and("account", groupSB.entity().getAccountId(), Op.EQ);
+
+        GenericSearchBuilder<AclGroupPolicyMapVO, Long> policySB = _aclGroupPolicyMapDao.createSearchBuilder(Long.class);
+        policySB.selectFields(policySB.entity().getAclPolicyId());
+        policySB.join("accountgroupjoin", groupSB, groupSB.entity().getAclGroupId(), policySB.entity().getAclGroupId(),
+                JoinType.INNER);
+        policySB.done();
+        SearchCriteria<Long> policySc = policySB.create();
+        policySc.setJoinParameters("accountgroupjoin", "account", accountId);
+
+        List<Long> policyIds = _aclGroupPolicyMapDao.customSearch(policySc, null);
+
+        SearchBuilder<AclPolicyVO> sb = _aclPolicyDao.createSearchBuilder();
+        sb.and("ids", sb.entity().getId(), Op.IN);
+        SearchCriteria<AclPolicyVO> sc = sb.create();
+        sc.setParameters("ids", policyIds.toArray(new Object[policyIds.size()]));
+        List<AclPolicyVO> policies = _aclPolicyDao.customSearch(sc, null);
+
+        return new ArrayList<AclPolicy>(policies);
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_UPDATE, eventDescription = "Attaching policy to acl group")
+    public AclGroup attachAclPoliciesToGroup(final List<Long> policyIds, final Long groupId) {
+        // get the Acl Group entity
+        AclGroup group = _aclGroupDao.findById(groupId);
+        if (group == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + groupId
+                    + "; failed to add roles to acl group.");
+        }
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // add entries in acl_group_policy_map table
+                for (Long policyId : policyIds) {
+                    AclPolicy policy = _aclPolicyDao.findById(policyId);
+                    if (policy == null) {
+                        throw new InvalidParameterValueException("Unable to find acl policy: " + policyId
+                                + "; failed to add policies to acl group.");
+                    }
+
+                    AclGroupPolicyMapVO grMap = _aclGroupPolicyMapDao.findByGroupAndPolicy(groupId, policyId);
+                    if (grMap == null) {
+                        // not there already
+                        grMap = new AclGroupPolicyMapVO(groupId, policyId);
+                        _aclGroupPolicyMapDao.persist(grMap);
+                    }
+                }
+            }
+        });
+
+        return group;
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_GROUP_UPDATE, eventDescription = "Removing policies from acl group")
+    public AclGroup removeAclPoliciesFromGroup(final List<Long> policyIds, final Long groupId) {
+        final Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Group entity
+        AclGroup group = _aclGroupDao.findById(groupId);
+        if (group == null) {
+            throw new InvalidParameterValueException("Unable to find acl group: " + groupId
+                    + "; failed to remove roles from acl group.");
+        }
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // add entries in acl_group_role_map table
+                for (Long policyId : policyIds) {
+                    AclPolicy policy = _aclPolicyDao.findById(policyId);
+                    if (policy == null) {
+                        throw new InvalidParameterValueException("Unable to find acl policy: " + policyId
+                                + "; failed to add policies to acl group.");
+                    }
+
+                    AclGroupPolicyMapVO grMap = _aclGroupPolicyMapDao.findByGroupAndPolicy(groupId, policyId);
+                    if (grMap != null) {
+                        // not removed yet
+                        _aclGroupPolicyMapDao.remove(grMap.getId());
+                    }
+                }
+            }
+        });
+        return group;
+    }
+
+    /*
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_GRANT, eventDescription = "Granting permission to Acl Role")
+    public AclP addAclPermissionToAclPolicy(final long aclRoleId, final List<String> apiNames) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Role entity
+        AclRole role = _aclPolicyDao.findById(aclRoleId);
+        if (role == null) {
+            throw new InvalidParameterValueException("Unable to find acl role: " + aclRoleId
+                    + "; failed to grant permission to role.");
+        }
+        // check permissions
+        _accountMgr.checkAccess(caller, null, true, role);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // add entries in acl_api_permission table
+                for (String api : apiNames) {
+                    AclApiPermissionVO perm = _apiPermissionDao.findByRoleAndApi(aclRoleId, api);
+                    if (perm == null) {
+                        // not there already
+                        perm = new AclApiPermissionVO(aclRoleId, api);
+                        _apiPermissionDao.persist(perm);
+                    }
+                }
+            }
+        });
+            
+        return role;
+
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_REVOKE, eventDescription = "Revoking permission from Acl Role")
+    public AclRole revokeApiPermissionFromAclRole(final long aclRoleId, final List<String> apiNames) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Role entity
+        AclRole role = _aclPolicyDao.findById(aclRoleId);
+        if (role == null) {
+            throw new InvalidParameterValueException("Unable to find acl role: " + aclRoleId
+                    + "; failed to revoke permission from role.");
+        }
+        // check permissions
+        _accountMgr.checkAccess(caller, null, true, role);
+
+        Transaction.execute(new TransactionCallbackNoReturn() {
+            @Override
+            public void doInTransactionWithoutResult(TransactionStatus status) {
+                // remove entries from acl_api_permission table
+                for (String api : apiNames) {
+                    AclApiPermissionVO perm = _apiPermissionDao.findByRoleAndApi(aclRoleId, api);
+                    if (perm != null) {
+                        // not removed yet
+                        _apiPermissionDao.remove(perm.getId());
+                    }
+                }
+            }
+        });
+        return role;
+    }
+    */
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_GRANT, eventDescription = "Granting acl permission to Acl Policy")
+    public AclPolicy addAclPermissionToAclPolicy(long aclPolicyId, String entityType, String scope, Long scopeId,
+            String action, String accessType, Permission perm) {
+        Account caller = CallContext.current().getCallingAccount();
+        // get the Acl Policy entity
+        AclPolicy policy = _aclPolicyDao.findById(aclPolicyId);
+        if (policy == null) {
+            throw new InvalidParameterValueException("Unable to find acl policy: " + aclPolicyId
+                    + "; failed to add permission to policy.");
+        }
+
+        // add entry in acl_policy_permission table
+        AclPolicyPermissionVO permit = _policyPermissionDao.findByPolicyAndEntity(aclPolicyId, entityType, scope, scopeId, action, perm);
+        if (permit == null) {
+            // not there already
+            permit = new AclPolicyPermissionVO(aclPolicyId, action, entityType, accessType, scope, scopeId, perm);
+            _policyPermissionDao.persist(permit);
+        }
+        return policy;
+
+    }
+
+    @DB
+    @Override
+    @ActionEvent(eventType = EventTypes.EVENT_ACL_POLICY_REVOKE, eventDescription = "Revoking acl permission from Acl Policy")
+    public AclPolicy removeAclPermissionFromAclPolicy(long aclPolicyId, String entityType, String scope, Long scopeId,
+            String action) {
+        // get the Acl Policy entity
+        AclPolicy policy = _aclPolicyDao.findById(aclPolicyId);
+        if (policy == null) {
+            throw new InvalidParameterValueException("Unable to find acl policy: " + aclPolicyId
+                    + "; failed to revoke permission from policy.");
+        }
+        // remove entry from acl_entity_permission table
+        AclPolicyPermissionVO permit = _policyPermissionDao.findByPolicyAndEntity(aclPolicyId, entityType, scope, scopeId, action, null);
+        if (permit != null) {
+            // not removed yet
+            _policyPermissionDao.remove(permit.getId());
+        }
+        return policy;
+    }
+
+
+
+    @Override
+    public boolean isAPIAccessibleForPolicies(String apiName, List<AclPolicy> policies) {
+
+        boolean accessible = false;
+
+        List<Long> policyIds = new ArrayList<Long>();
+        for (AclPolicy policy : policies) {
+            policyIds.add(policy.getId());
+        }
+
+        SearchBuilder<AclPolicyPermissionVO> sb = _policyPermissionDao.createSearchBuilder();
+        sb.and("action", sb.entity().getAction(), Op.EQ);
+        sb.and("policyId", sb.entity().getAclPolicyId(), Op.IN);
+
+        SearchCriteria<AclPolicyPermissionVO> sc = sb.create();
+        sc.setParameters("policyId", policyIds.toArray(new Object[policyIds.size()]));
+
+        List<AclPolicyPermissionVO> permissions = _policyPermissionDao.customSearch(sc, null);
+
+        if (permissions != null && !permissions.isEmpty()) {
+            accessible = true;
+        }
+
+        return accessible;
+    }
+
+
+    @Override
+    public List<Long> getGrantedEntities(long accountId, String action, String scope) {
+        // Get the static Policies of the Caller
+        List<AclPolicy> policies = listAclPolicies(accountId);
+        // for each policy, find granted permission within the given scope
+        List<Long> entityIds = new ArrayList<Long>();
+        for (AclPolicy policy : policies) {
+            List<AclPolicyPermissionVO> pp = _policyPermissionDao.listGrantedByActionAndScope(policy.getId(), action,
+                    scope);
+            if (pp != null) {
+                for (AclPolicyPermissionVO p : pp) {
+                    if (p.getScopeId() != null) {
+                        entityIds.add(p.getScopeId());
+                    }
+                }
+            }
+        }
+        return entityIds;
+    }
+
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupAccountMapDao.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupAccountMapDao.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupAccountMapDao.java
new file mode 100644
index 0000000..58f69c3
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupAccountMapDao.java
@@ -0,0 +1,40 @@
+// 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.server.dao;
+
+import java.util.List;
+
+import org.apache.cloudstack.iam.server.AclGroupAccountMapVO;
+
+import com.cloud.utils.db.GenericDao;
+
+public interface AclGroupAccountMapDao extends GenericDao<AclGroupAccountMapVO, Long> {
+
+    List<AclGroupAccountMapVO> listByGroupId(long groupId);
+
+    List<AclGroupAccountMapVO> listByAccountId(long accountId);
+
+    AclGroupAccountMapVO findAccountInAdminGroup(long accountId);
+
+    AclGroupAccountMapVO findByGroupAndAccount(long groupId, long acctId);
+
+    void removeAccountFromGroups(long accountId);
+
+    AclGroupAccountMapVO findAccountInDomainAdminGroup(long accountId);
+
+    AclGroupAccountMapVO findAccountInUserGroup(long accountId);
+}


[3/5] Adding new IAM service under services. There are two modules to this component:

Posted by pr...@apache.org.
http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupAccountMapDaoImpl.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupAccountMapDaoImpl.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupAccountMapDaoImpl.java
new file mode 100644
index 0000000..32ce64a
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupAccountMapDaoImpl.java
@@ -0,0 +1,119 @@
+// 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.server.dao;
+
+import java.util.List;
+import java.util.Map;
+
+import javax.naming.ConfigurationException;
+
+import org.apache.cloudstack.iam.server.AclGroupAccountMapVO;
+import org.apache.log4j.Logger;
+import org.springframework.stereotype.Component;
+
+
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+@Component
+public class AclGroupAccountMapDaoImpl extends GenericDaoBase<AclGroupAccountMapVO, Long> implements AclGroupAccountMapDao {
+    private SearchBuilder<AclGroupAccountMapVO> ListByGroupId;
+    private SearchBuilder<AclGroupAccountMapVO> ListByAccountId;
+    private SearchBuilder<AclGroupAccountMapVO> _findByAccountAndGroupId;
+
+    public static final Logger s_logger = Logger.getLogger(AclGroupAccountMapDaoImpl.class.getName());
+
+    @Override
+    public boolean configure(String name, Map<String, Object> params) throws ConfigurationException {
+        super.configure(name, params);
+
+        ListByGroupId = createSearchBuilder();
+        ListByGroupId.and("groupId", ListByGroupId.entity().getAclGroupId(), SearchCriteria.Op.EQ);
+        ListByGroupId.done();
+
+        ListByAccountId = createSearchBuilder();
+        ListByAccountId.and("accountId", ListByAccountId.entity().getAccountId(), SearchCriteria.Op.EQ);
+        ListByAccountId.done();
+
+        _findByAccountAndGroupId = createSearchBuilder();
+        _findByAccountAndGroupId
+                .and("groupId", _findByAccountAndGroupId.entity().getAclGroupId(), SearchCriteria.Op.EQ);
+        _findByAccountAndGroupId.and("accountId", _findByAccountAndGroupId.entity().getAccountId(),
+                SearchCriteria.Op.EQ);
+        _findByAccountAndGroupId.done();
+
+        return true;
+    }
+
+    @Override
+    public List<AclGroupAccountMapVO> listByGroupId(long groupId) {
+        SearchCriteria<AclGroupAccountMapVO> sc = ListByGroupId.create();
+        sc.setParameters("groupId", groupId);
+        return listBy(sc);
+    }
+
+    @Override
+    public List<AclGroupAccountMapVO> listByAccountId(long accountId) {
+        SearchCriteria<AclGroupAccountMapVO> sc = ListByAccountId.create();
+        sc.setParameters("accountId", accountId);
+        return listBy(sc);
+    }
+
+    @Override
+    public AclGroupAccountMapVO findAccountInAdminGroup(long accountId) {
+        SearchCriteria<AclGroupAccountMapVO> sc = _findByAccountAndGroupId.create();
+        sc.setParameters("accountId", accountId);
+        sc.setParameters("groupId", 2);
+        return findOneBy(sc);
+    }
+
+    @Override
+    public AclGroupAccountMapVO findAccountInDomainAdminGroup(long accountId) {
+        SearchCriteria<AclGroupAccountMapVO> sc = _findByAccountAndGroupId.create();
+        sc.setParameters("accountId", accountId);
+        sc.setParameters("groupId", 3);
+        return findOneBy(sc);
+    }
+
+    @Override
+    public AclGroupAccountMapVO findAccountInUserGroup(long accountId) {
+        SearchCriteria<AclGroupAccountMapVO> sc = _findByAccountAndGroupId.create();
+        sc.setParameters("accountId", accountId);
+        sc.setParameters("groupId", 1);
+        return findOneBy(sc);
+    }
+
+    @Override
+    public AclGroupAccountMapVO findByGroupAndAccount(long groupId, long acctId) {
+        SearchCriteria<AclGroupAccountMapVO> sc = _findByAccountAndGroupId.create();
+        sc.setParameters("accountId", acctId);
+        sc.setParameters("groupId", groupId);
+        return findOneBy(sc);
+    }
+
+    @Override
+    public void removeAccountFromGroups(long accountId) {
+        SearchCriteria<AclGroupAccountMapVO> sc = ListByAccountId.create();
+        sc.setParameters("accountId", accountId);
+
+        int rowsRemoved = remove(sc);
+        if (rowsRemoved > 0) {
+            s_logger.debug("Removed account id=" + accountId + " from " + rowsRemoved + " groups");
+        }
+    }
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupDao.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupDao.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupDao.java
new file mode 100644
index 0000000..aa62a0b
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupDao.java
@@ -0,0 +1,28 @@
+// 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.server.dao;
+
+import org.apache.cloudstack.iam.api.AclGroup;
+import org.apache.cloudstack.iam.server.AclGroupVO;
+
+import com.cloud.utils.db.GenericDao;
+
+public interface AclGroupDao extends GenericDao<AclGroupVO, Long> {
+
+    AclGroup findByName(String path, String groupName);
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupDaoImpl.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupDaoImpl.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupDaoImpl.java
new file mode 100644
index 0000000..e091574
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupDaoImpl.java
@@ -0,0 +1,59 @@
+// 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.server.dao;
+
+import java.util.Map;
+
+import javax.naming.ConfigurationException;
+
+import org.apache.cloudstack.iam.api.AclGroup;
+import org.apache.cloudstack.iam.server.AclGroupVO;
+import org.springframework.stereotype.Component;
+
+
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+@Component
+public class AclGroupDaoImpl extends GenericDaoBase<AclGroupVO, Long> implements AclGroupDao {
+    private SearchBuilder<AclGroupVO> nameSearch;
+
+    @Override
+    public boolean configure(String name, Map<String, Object> params) throws ConfigurationException {
+        super.configure(name, params);
+
+        nameSearch = createSearchBuilder();
+        nameSearch.and("name", nameSearch.entity().getName(), SearchCriteria.Op.EQ);
+        nameSearch.and("path", nameSearch.entity().getPath(), SearchCriteria.Op.EQ);
+        nameSearch.done();
+
+
+        return true;
+    }
+
+    @Override
+    public AclGroup findByName(String path, String name) {
+        SearchCriteria<AclGroupVO> sc = nameSearch.create();
+        sc.setParameters("name", name);
+        if (path != null) {
+            sc.setParameters("path", path);
+        }
+        return findOneBy(sc);
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupPolicyMapDao.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupPolicyMapDao.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupPolicyMapDao.java
new file mode 100644
index 0000000..a016fc5
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupPolicyMapDao.java
@@ -0,0 +1,16 @@
+package org.apache.cloudstack.iam.server.dao;
+
+import java.util.List;
+
+import org.apache.cloudstack.iam.server.AclGroupPolicyMapVO;
+import com.cloud.utils.db.GenericDao;
+
+public interface AclGroupPolicyMapDao extends GenericDao<AclGroupPolicyMapVO, Long> {
+
+    List<AclGroupPolicyMapVO> listByGroupId(long groupId);
+
+    List<AclGroupPolicyMapVO> listByPolicyId(long policyId);
+
+    AclGroupPolicyMapVO findByGroupAndPolicy(long groupId, long policyId);
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupPolicyMapDaoImpl.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupPolicyMapDaoImpl.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupPolicyMapDaoImpl.java
new file mode 100644
index 0000000..3ce2b8a
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclGroupPolicyMapDaoImpl.java
@@ -0,0 +1,61 @@
+package org.apache.cloudstack.iam.server.dao;
+
+import java.util.List;
+import java.util.Map;
+
+import javax.naming.ConfigurationException;
+
+import org.apache.cloudstack.iam.server.AclGroupPolicyMapVO;
+
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+public class AclGroupPolicyMapDaoImpl extends GenericDaoBase<AclGroupPolicyMapVO, Long> implements AclGroupPolicyMapDao {
+
+    private SearchBuilder<AclGroupPolicyMapVO> ListByGroupId;
+    private SearchBuilder<AclGroupPolicyMapVO> ListByPolicyId;
+    private SearchBuilder<AclGroupPolicyMapVO> findByPolicyGroupId;
+
+    @Override
+    public boolean configure(String name, Map<String, Object> params) throws ConfigurationException {
+        super.configure(name, params);
+
+        ListByGroupId = createSearchBuilder();
+        ListByGroupId.and("groupId", ListByGroupId.entity().getAclGroupId(), SearchCriteria.Op.EQ);
+        ListByGroupId.done();
+
+        ListByPolicyId = createSearchBuilder();
+        ListByPolicyId.and("policyId", ListByPolicyId.entity().getAclPolicyId(), SearchCriteria.Op.EQ);
+        ListByPolicyId.done();
+
+        findByPolicyGroupId = createSearchBuilder();
+        findByPolicyGroupId.and("policyId", findByPolicyGroupId.entity().getAclPolicyId(), SearchCriteria.Op.EQ);
+        findByPolicyGroupId.and("groupId", findByPolicyGroupId.entity().getAclGroupId(), SearchCriteria.Op.EQ);
+        findByPolicyGroupId.done();
+
+        return true;
+    }
+
+    @Override
+    public List<AclGroupPolicyMapVO> listByGroupId(long groupId) {
+        SearchCriteria<AclGroupPolicyMapVO> sc = ListByGroupId.create();
+        sc.setParameters("groupId", groupId);
+        return listBy(sc);
+    }
+
+    @Override
+    public List<AclGroupPolicyMapVO> listByPolicyId(long policyId) {
+        SearchCriteria<AclGroupPolicyMapVO> sc = ListByPolicyId.create();
+        sc.setParameters("policyId", policyId);
+        return listBy(sc);
+    }
+
+    @Override
+    public AclGroupPolicyMapVO findByGroupAndPolicy(long groupId, long policyId) {
+        SearchCriteria<AclGroupPolicyMapVO> sc = findByPolicyGroupId.create();
+        sc.setParameters("policyId", policyId);
+        sc.setParameters("groupId", groupId);
+        return findOneBy(sc);
+    }
+}
\ No newline at end of file

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyDao.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyDao.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyDao.java
new file mode 100644
index 0000000..a61c5de
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyDao.java
@@ -0,0 +1,28 @@
+// 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.server.dao;
+
+import org.apache.cloudstack.iam.api.AclPolicy;
+import org.apache.cloudstack.iam.server.AclPolicyVO;
+
+import com.cloud.utils.db.GenericDao;
+
+public interface AclPolicyDao extends GenericDao<AclPolicyVO, Long> {
+
+    AclPolicy findByName(String policyName);
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyDaoImpl.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyDaoImpl.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyDaoImpl.java
new file mode 100644
index 0000000..a1a81e6
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyDaoImpl.java
@@ -0,0 +1,57 @@
+// 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.server.dao;
+
+import java.util.Map;
+
+import javax.naming.ConfigurationException;
+
+import org.apache.cloudstack.iam.api.AclPolicy;
+import org.apache.cloudstack.iam.server.AclPolicyVO;
+import org.springframework.stereotype.Component;
+
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+@Component
+public class AclPolicyDaoImpl extends GenericDaoBase<AclPolicyVO, Long> implements AclPolicyDao {
+    private SearchBuilder<AclPolicyVO> nameSearch;
+
+    @Override
+    public boolean configure(String name, Map<String, Object> params) throws ConfigurationException {
+        super.configure(name, params);
+
+        nameSearch = createSearchBuilder();
+        nameSearch.and("name", nameSearch.entity().getName(), SearchCriteria.Op.EQ);
+        // nameSearch.and("domainId", nameSearch.entity().getDomainId(),
+        // SearchCriteria.Op.EQ);
+        nameSearch.done();
+
+
+        return true;
+    }
+
+    @Override
+    public AclPolicy findByName(String name) {
+        SearchCriteria<AclPolicyVO> sc = nameSearch.create();
+        sc.setParameters("name", name);
+
+        return findOneBy(sc);
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyPermissionDao.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyPermissionDao.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyPermissionDao.java
new file mode 100644
index 0000000..f2da895
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyPermissionDao.java
@@ -0,0 +1,38 @@
+// 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.server.dao;
+import java.util.List;
+import org.apache.cloudstack.iam.api.AclPolicyPermission.Permission;
+import org.apache.cloudstack.iam.server.AclPolicyPermissionVO;
+
+
+import com.cloud.utils.db.GenericDao;
+
+public interface AclPolicyPermissionDao extends GenericDao<AclPolicyPermissionVO, Long> {
+
+    List<AclPolicyPermissionVO> listByPolicy(long policyId);
+
+    AclPolicyPermissionVO findByPolicyAndEntity(long policyId, String entityType, String scope, Long scopeId,
+            String action, Permission perm);
+
+    List<AclPolicyPermissionVO> listGrantedByActionAndScope(long policyId, String action, String scope);
+
+    List<AclPolicyPermissionVO> listByPolicyActionAndEntity(long policyId, String action, String entityType);
+
+    List<AclPolicyPermissionVO> listByPolicyAccessAndEntity(long id, String accessType, String entityType);
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyPermissionDaoImpl.java
----------------------------------------------------------------------
diff --git a/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyPermissionDaoImpl.java b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyPermissionDaoImpl.java
new file mode 100644
index 0000000..d738e00
--- /dev/null
+++ b/services/iam/server/src/org/apache/cloudstack/iam/server/dao/AclPolicyPermissionDaoImpl.java
@@ -0,0 +1,115 @@
+// 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.server.dao;
+
+import java.util.List;
+import java.util.Map;
+
+import javax.naming.ConfigurationException;
+
+import org.apache.cloudstack.iam.api.AclPolicyPermission.Permission;
+import org.apache.cloudstack.iam.server.AclPolicyPermissionVO;
+
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+public class AclPolicyPermissionDaoImpl extends GenericDaoBase<AclPolicyPermissionVO, Long> implements
+        AclPolicyPermissionDao {
+
+    private SearchBuilder<AclPolicyPermissionVO> policyIdSearch;
+    private SearchBuilder<AclPolicyPermissionVO> fullSearch;
+    private SearchBuilder<AclPolicyPermissionVO> actionScopeSearch;
+
+    @Override
+    public boolean configure(String name, Map<String, Object> params) throws ConfigurationException {
+        super.configure(name, params);
+
+        policyIdSearch = createSearchBuilder();
+        policyIdSearch.and("policyId", policyIdSearch.entity().getAclPolicyId(), SearchCriteria.Op.EQ);
+        policyIdSearch.done();
+
+        fullSearch = createSearchBuilder();
+        fullSearch.and("policyId", fullSearch.entity().getAclPolicyId(), SearchCriteria.Op.EQ);
+        fullSearch.and("entityType", fullSearch.entity().getEntityType(), SearchCriteria.Op.EQ);
+        fullSearch.and("scope", fullSearch.entity().getScope(), SearchCriteria.Op.EQ);
+        fullSearch.and("scopeId", fullSearch.entity().getScopeId(), SearchCriteria.Op.EQ);
+        fullSearch.and("action", fullSearch.entity().getAction(), SearchCriteria.Op.EQ);
+        fullSearch.and("permission", fullSearch.entity().getPermission(), SearchCriteria.Op.EQ);
+        fullSearch.and("accessType", fullSearch.entity().getAccessType(), SearchCriteria.Op.EQ);
+        fullSearch.done();
+
+        actionScopeSearch = createSearchBuilder();
+        actionScopeSearch.and("policyId", actionScopeSearch.entity().getAclPolicyId(), SearchCriteria.Op.EQ);
+        actionScopeSearch.and("scope", actionScopeSearch.entity().getScope(), SearchCriteria.Op.EQ);
+        actionScopeSearch.and("action", actionScopeSearch.entity().getAction(), SearchCriteria.Op.EQ);
+        actionScopeSearch.and("permission", actionScopeSearch.entity().getPermission(), SearchCriteria.Op.EQ);
+        actionScopeSearch.done();
+
+        return true;
+    }
+
+    @Override
+    public List<AclPolicyPermissionVO> listByPolicy(long policyId) {
+        SearchCriteria<AclPolicyPermissionVO> sc = policyIdSearch.create();
+        sc.setParameters("policyId", policyId);
+        return listBy(sc);
+    }
+
+    @Override
+    public AclPolicyPermissionVO findByPolicyAndEntity(long policyId, String entityType, String scope, Long scopeId,
+            String action, Permission perm) {
+        SearchCriteria<AclPolicyPermissionVO> sc = fullSearch.create();
+        sc.setParameters("policyId", policyId);
+        sc.setParameters("entityType", entityType);
+        sc.setParameters("scope", scope);
+        sc.setParameters("scopeId", scopeId);
+        sc.setParameters("action", action);
+        sc.setParameters("permission", perm);
+        return findOneBy(sc);
+    }
+
+    @Override
+    public List<AclPolicyPermissionVO> listGrantedByActionAndScope(long policyId, String action, String scope) {
+        SearchCriteria<AclPolicyPermissionVO> sc = actionScopeSearch.create();
+        sc.setParameters("policyId", policyId);
+        sc.setParameters("action", action);
+        sc.setParameters("scope", scope);
+        sc.setParameters("permission", Permission.Allow);
+        return listBy(sc);
+    }
+
+    @Override
+    public List<AclPolicyPermissionVO> listByPolicyActionAndEntity(long policyId, String action, String entityType) {
+        SearchCriteria<AclPolicyPermissionVO> sc = fullSearch.create();
+        sc.setParameters("policyId", policyId);
+        sc.setParameters("entityType", entityType);
+        sc.setParameters("action", action);
+        return listBy(sc);
+    }
+
+    @Override
+    public List<AclPolicyPermissionVO> listByPolicyAccessAndEntity(long policyId, String accessType,
+            String entityType) {
+        SearchCriteria<AclPolicyPermissionVO> sc = fullSearch.create();
+        sc.setParameters("policyId", policyId);
+        sc.setParameters("entityType", entityType);
+        sc.setParameters("accessType", accessType);
+        return listBy(sc);
+    }
+
+}

http://git-wip-us.apache.org/repos/asf/cloudstack/blob/2543fbe8/services/pom.xml
----------------------------------------------------------------------
diff --git a/services/pom.xml b/services/pom.xml
index c2f7f88..81531df 100644
--- a/services/pom.xml
+++ b/services/pom.xml
@@ -33,5 +33,6 @@
   <modules>
     <module>console-proxy</module>
     <module>secondary-storage</module>
+    <module>iam</module>
   </modules>
 </project>