Skip to content

Commit 190cf8b

Browse files
author
Rene Glover
committed
initial commit for multi-role and oidc support
1 parent b0d74fe commit 190cf8b

178 files changed

Lines changed: 44332 additions & 18806 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.gitignore

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -100,6 +100,14 @@ unittest
100100
venv
101101
waf-*
102102

103+
# Developer environment (generated by make init)
104+
developer/db.properties
105+
developer/log4j-cloud.xml
106+
developer/logs/
107+
developer/.server.pid
108+
developer/.ui.pid
109+
.github/copilot-instructions.md
110+
103111
# this ignores _all files starting with '.'. Don't do that!
104112
#.*
105113

Makefile

Lines changed: 616 additions & 0 deletions
Large diffs are not rendered by default.

api/src/main/java/com/cloud/event/EventTypes.java

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,9 @@
1919
import java.util.HashMap;
2020
import java.util.Map;
2121

22+
import org.apache.cloudstack.acl.ProjectRoleClaimBinding;
2223
import org.apache.cloudstack.acl.Role;
24+
import org.apache.cloudstack.acl.RoleClaimBinding;
2325
import org.apache.cloudstack.acl.RolePermission;
2426
import org.apache.cloudstack.affinity.AffinityGroup;
2527
import org.apache.cloudstack.annotation.Annotation;
@@ -254,9 +256,24 @@ public class EventTypes {
254256
public static final String EVENT_ROLE_IMPORT = "ROLE.IMPORT";
255257
public static final String EVENT_ROLE_ENABLE = "ROLE.ENABLE";
256258
public static final String EVENT_ROLE_DISABLE = "ROLE.DISABLE";
259+
260+
// OIDC Provider events
261+
public static final String EVENT_OIDC_PROVIDER_CREATE = "OIDC.PROVIDER.CREATE";
262+
public static final String EVENT_OIDC_PROVIDER_UPDATE = "OIDC.PROVIDER.UPDATE";
263+
public static final String EVENT_OIDC_PROVIDER_DELETE = "OIDC.PROVIDER.DELETE";
264+
public static final String EVENT_OIDC_PROVIDER_ENABLE = "OIDC.PROVIDER.ENABLE";
265+
public static final String EVENT_OIDC_PROVIDER_DISABLE = "OIDC.PROVIDER.DISABLE";
266+
public static final String EVENT_OIDC_PROVIDER_TEST = "OIDC.PROVIDER.TEST";
257267
public static final String EVENT_ROLE_PERMISSION_CREATE = "ROLE.PERMISSION.CREATE";
258268
public static final String EVENT_ROLE_PERMISSION_UPDATE = "ROLE.PERMISSION.UPDATE";
259269
public static final String EVENT_ROLE_PERMISSION_DELETE = "ROLE.PERMISSION.DELETE";
270+
public static final String EVENT_ROLE_CLAIM_BINDING_CREATE = "ROLE.CLAIM.BINDING.CREATE";
271+
public static final String EVENT_ROLE_CLAIM_BINDING_DELETE = "ROLE.CLAIM.BINDING.DELETE";
272+
public static final String EVENT_ACCOUNT_ROLE_ASSIGN = "ACCOUNT.ROLE.ASSIGN";
273+
public static final String EVENT_ACCOUNT_ROLE_UNASSIGN = "ACCOUNT.ROLE.UNASSIGN";
274+
// Role-perspective events (for audit tracking by role)
275+
public static final String EVENT_ROLE_ACCOUNT_ASSIGN = "ROLE.ACCOUNT.ASSIGN";
276+
public static final String EVENT_ROLE_ACCOUNT_UNASSIGN = "ROLE.ACCOUNT.UNASSIGN";
260277

261278
// Project Role events
262279
public static final String EVENT_PROJECT_ROLE_CREATE = "PROJECT.ROLE.CREATE";
@@ -265,6 +282,11 @@ public class EventTypes {
265282
public static final String EVENT_PROJECT_ROLE_PERMISSION_CREATE = "PROJECT.ROLE.PERMISSION.CREATE";
266283
public static final String EVENT_PROJECT_ROLE_PERMISSION_UPDATE = "PROJECT.ROLE.PERMISSION.UPDATE";
267284
public static final String EVENT_PROJECT_ROLE_PERMISSION_DELETE = "PROJECT.ROLE.PERMISSION.DELETE";
285+
public static final String EVENT_PROJECT_ROLE_CLAIM_BINDING_CREATE = "PROJECT.ROLE.CLAIM.BINDING.CREATE";
286+
public static final String EVENT_PROJECT_ROLE_CLAIM_BINDING_DELETE = "PROJECT.ROLE.CLAIM.BINDING.DELETE";
287+
// Project role assignment events (account-perspective for audit tracking)
288+
public static final String EVENT_PROJECT_ACCOUNT_ROLE_ASSIGN = "PROJECT.ACCOUNT.ROLE.ASSIGN";
289+
public static final String EVENT_PROJECT_ACCOUNT_ROLE_UNASSIGN = "PROJECT.ACCOUNT.ROLE.UNASSIGN";
268290

269291
// CA events
270292
public static final String EVENT_CA_CERTIFICATE_ISSUE = "CA.CERTIFICATE.ISSUE";
@@ -963,6 +985,13 @@ public class EventTypes {
963985
entityEventDetails.put(EVENT_ROLE_PERMISSION_CREATE, RolePermission.class);
964986
entityEventDetails.put(EVENT_ROLE_PERMISSION_UPDATE, RolePermission.class);
965987
entityEventDetails.put(EVENT_ROLE_PERMISSION_DELETE, RolePermission.class);
988+
entityEventDetails.put(EVENT_ROLE_CLAIM_BINDING_CREATE, RoleClaimBinding.class);
989+
entityEventDetails.put(EVENT_ROLE_CLAIM_BINDING_DELETE, RoleClaimBinding.class);
990+
entityEventDetails.put(EVENT_ACCOUNT_ROLE_ASSIGN, Account.class);
991+
entityEventDetails.put(EVENT_ACCOUNT_ROLE_UNASSIGN, Account.class);
992+
// Role-perspective events (for audit tracking by role)
993+
entityEventDetails.put(EVENT_ROLE_ACCOUNT_ASSIGN, Role.class);
994+
entityEventDetails.put(EVENT_ROLE_ACCOUNT_UNASSIGN, Role.class);
966995

967996
// Account events
968997
entityEventDetails.put(EVENT_ACCOUNT_ENABLE, Account.class);
@@ -1175,6 +1204,11 @@ public class EventTypes {
11751204
entityEventDetails.put(EVENT_PROJECT_INVITATION_UPDATE, Project.class);
11761205
entityEventDetails.put(EVENT_PROJECT_INVITATION_REMOVE, Project.class);
11771206
entityEventDetails.put(EVENT_PROJECT_ACCOUNT_REMOVE, Project.class);
1207+
entityEventDetails.put(EVENT_PROJECT_ROLE_CLAIM_BINDING_CREATE, ProjectRoleClaimBinding.class);
1208+
entityEventDetails.put(EVENT_PROJECT_ROLE_CLAIM_BINDING_DELETE, ProjectRoleClaimBinding.class);
1209+
// Project role assignment events (account-perspective for audit tracking)
1210+
entityEventDetails.put(EVENT_PROJECT_ACCOUNT_ROLE_ASSIGN, Account.class);
1211+
entityEventDetails.put(EVENT_PROJECT_ACCOUNT_ROLE_UNASSIGN, Account.class);
11781212

11791213
// Network as a Service
11801214
entityEventDetails.put(EVENT_NETWORK_ELEMENT_CONFIGURE, Network.class);

api/src/main/java/com/cloud/projects/ProjectAccount.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -32,4 +32,6 @@ public enum Role {
3232
Role getAccountRole();
3333

3434
long getProjectAccountId();
35+
36+
Long getAssignedBy();
3537
}

api/src/main/java/com/cloud/projects/ProjectService.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,8 @@ public interface ProjectService {
6868

6969
ProjectAccount assignAccountToProject(Project project, long accountId, Role accountRole, Long userId, Long projectRoleId);
7070

71+
ProjectAccount assignAccountToProject(Project project, long accountId, Role accountRole, Long userId, Long projectRoleId, Long assignedBy);
72+
7173
Account getProjectOwner(long projectId);
7274

7375
List<Long> getProjectOwners(long projectId);
Lines changed: 107 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,107 @@
1+
// Licensed to the Apache Software Foundation (ASF) under one
2+
// or more contributor license agreements. See the NOTICE file
3+
// distributed with this work for additional information
4+
// regarding copyright ownership. The ASF licenses this file
5+
// to you under the Apache License, Version 2.0 (the
6+
// "License"); you may not use this file except in compliance
7+
// with the License. You may obtain a copy of the License at
8+
//
9+
// http://www.apache.org/licenses/LICENSE-2.0
10+
//
11+
// Unless required by applicable law or agreed to in writing,
12+
// software distributed under the License is distributed on an
13+
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14+
// KIND, either express or implied. See the License for the
15+
// specific language governing permissions and limitations
16+
// under the License.
17+
18+
package org.apache.cloudstack.acl;
19+
20+
import org.apache.cloudstack.acl.RolePermissionEntity.Permission;
21+
22+
import java.util.ArrayList;
23+
import java.util.List;
24+
25+
/**
26+
* Represents an effective permission with lineage information showing
27+
* which roles contributed to the final permission state.
28+
*/
29+
public class EffectivePermission {
30+
31+
private String rule;
32+
private Permission permission;
33+
private List<RoleSource> sourceRoles;
34+
private List<RoleSource> overriddenRoles;
35+
36+
public EffectivePermission(String rule, Permission permission) {
37+
this.rule = rule;
38+
this.permission = permission;
39+
this.sourceRoles = new ArrayList<>();
40+
this.overriddenRoles = new ArrayList<>();
41+
}
42+
43+
public String getRule() {
44+
return rule;
45+
}
46+
47+
public void setRule(String rule) {
48+
this.rule = rule;
49+
}
50+
51+
public Permission getPermission() {
52+
return permission;
53+
}
54+
55+
public void setPermission(Permission permission) {
56+
this.permission = permission;
57+
}
58+
59+
public List<RoleSource> getSourceRoles() {
60+
return sourceRoles;
61+
}
62+
63+
public void addSourceRole(RoleSource source) {
64+
this.sourceRoles.add(source);
65+
}
66+
67+
public List<RoleSource> getOverriddenRoles() {
68+
return overriddenRoles;
69+
}
70+
71+
public void addOverriddenRole(RoleSource source) {
72+
this.overriddenRoles.add(source);
73+
}
74+
75+
/**
76+
* Represents a role that contributed to the effective permission
77+
*/
78+
public static class RoleSource {
79+
private long roleId;
80+
private String roleName;
81+
private Permission permission;
82+
private boolean isPrimaryRole;
83+
84+
public RoleSource(long roleId, String roleName, Permission permission, boolean isPrimaryRole) {
85+
this.roleId = roleId;
86+
this.roleName = roleName;
87+
this.permission = permission;
88+
this.isPrimaryRole = isPrimaryRole;
89+
}
90+
91+
public long getRoleId() {
92+
return roleId;
93+
}
94+
95+
public String getRoleName() {
96+
return roleName;
97+
}
98+
99+
public Permission getPermission() {
100+
return permission;
101+
}
102+
103+
public boolean isPrimaryRole() {
104+
return isPrimaryRole;
105+
}
106+
}
107+
}

api/src/main/java/org/apache/cloudstack/acl/ProjectRole.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,17 @@
2020
import org.apache.cloudstack.api.Identity;
2121
import org.apache.cloudstack.api.InternalIdentity;
2222

23+
import com.cloud.projects.ProjectAccount;
24+
2325
public interface ProjectRole extends RoleEntity, InternalIdentity, Identity {
2426

2527
Long getProjectId();
28+
29+
/**
30+
* Gets the project account type (Admin/Regular) associated with this role.
31+
* When this role is assigned to an account in a project, this type determines
32+
* the account's project membership type.
33+
* @return the project account type, defaults to Regular if not set
34+
*/
35+
ProjectAccount.Role getType();
2636
}
Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
// Licensed to the Apache Software Foundation (ASF) under one
2+
// or more contributor license agreements. See the NOTICE file
3+
// distributed with this work for additional information
4+
// regarding copyright ownership. The ASF licenses this file
5+
// to you under the Apache License, Version 2.0 (the
6+
// "License"); you may not use this file except in compliance
7+
// with the License. You may obtain a copy of the License at
8+
//
9+
// http://www.apache.org/licenses/LICENSE-2.0
10+
//
11+
// Unless required by applicable law or agreed to in writing,
12+
// software distributed under the License is distributed on an
13+
// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14+
// KIND, either express or implied. See the License for the
15+
// specific language governing permissions and limitations
16+
// under the License.
17+
18+
package org.apache.cloudstack.acl;
19+
20+
import java.util.Date;
21+
22+
import org.apache.cloudstack.api.Identity;
23+
24+
public interface ProjectRoleClaimBinding extends Identity {
25+
26+
long getId();
27+
28+
String getUuid();
29+
30+
long getProjectRoleId();
31+
32+
RoleClaimBinding.ClaimType getClaimType();
33+
34+
String getClaimValue();
35+
36+
Date getCreated();
37+
38+
Date getRemoved();
39+
40+
Long getCreatedBy();
41+
42+
Long getRemovedBy();
43+
}

api/src/main/java/org/apache/cloudstack/acl/ProjectRoleService.java

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,8 @@
2222
import org.apache.cloudstack.api.command.admin.acl.project.CreateProjectRolePermissionCmd;
2323
import org.apache.cloudstack.acl.RolePermissionEntity.Permission;
2424

25+
import com.cloud.projects.ProjectAccount;
26+
2527
public interface ProjectRoleService {
2628
/**
2729
* Creates a Project role in a Project to be mapped to a user/ account (all users of an account)
@@ -32,6 +34,16 @@ public interface ProjectRoleService {
3234
*/
3335
ProjectRole createProjectRole(Long projectId, String name, String description);
3436

37+
/**
38+
* Creates a Project role in a Project to be mapped to a user/ account (all users of an account)
39+
* @param projectId ID of the project where the project role is to be created
40+
* @param name Name of the project role
41+
* @param description description provided for the project role
42+
* @param type the project account type (Admin/Regular) for accounts assigned to this role
43+
* @return the Instance of the project role created
44+
*/
45+
ProjectRole createProjectRole(Long projectId, String name, String description, ProjectAccount.Role type);
46+
3547
/**
3648
* Updates a Project role created
3749
* @param role Project role reference to be updated
@@ -42,6 +54,17 @@ public interface ProjectRoleService {
4254
*/
4355
ProjectRole updateProjectRole(ProjectRole role, Long projectId, String name, String description);
4456

57+
/**
58+
* Updates a Project role created
59+
* @param role Project role reference to be updated
60+
* @param projectId ID of the project where the Project role exists
61+
* @param name new name to be given to the project role
62+
* @param description description for the project role
63+
* @param type the project account type (Admin/Regular) for accounts assigned to this role
64+
* @return the updated instance of the project role
65+
*/
66+
ProjectRole updateProjectRole(ProjectRole role, Long projectId, String name, String description, ProjectAccount.Role type);
67+
4568
/**
4669
*
4770
* @param projectId ID of the project in which the project role is to be searched for
@@ -116,4 +139,10 @@ public interface ProjectRoleService {
116139
*/
117140
List<ProjectRolePermission> findAllProjectRolePermissions(Long projectId, Long projectRoleId);
118141

142+
ProjectRoleClaimBinding createProjectRoleClaimBinding(long projectRoleId, RoleClaimBinding.ClaimType claimType, String claimValue);
143+
144+
boolean deleteProjectRoleClaimBinding(long id);
145+
146+
List<ProjectRoleClaimBinding> listProjectRoleClaimBindings(long projectRoleId);
147+
119148
}

api/src/main/java/org/apache/cloudstack/acl/Role.java

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,4 +35,10 @@ public String toString(){
3535
boolean isDefault();
3636
boolean isPublicRole();
3737
State getState();
38+
39+
/**
40+
* Returns the domain ID for domain-scoped roles.
41+
* @return the domain ID if this role is domain-scoped, null if global
42+
*/
43+
Long getDomainId();
3844
}

0 commit comments

Comments
 (0)