8.6 Implementing a Role-Based Access Control System

In a ClearCase environment, where users perform different roles, you may want to restrict access to certain ClearCase operations based on role. This section shows a trigger definition and script that implement a role-based access control system.

The following mktrtype command creates a preoperation trigger type called role_restrictions. The trigger type fires when a user attempts to make a baseline, stream, or activity.

cleartool mktrtype -nc -ucmobject -all -preop mkstream,mkbl,mkactivity \
-execunix "perl /net/jupiter/triggers/role_restrictions.pl" \
-execwin "ccperl \\pluto\disk1\triggers\role_restrictions.pl" \
role_restrictions@\my_pvob

Preoperation Trigger Script

The following preoperation trigger script maps users to the following roles:

The script maps the mkactivity, mkbl, and mkstream operations to the roles that are permitted to perform them. For example, only users designated as project managers or integrators can make a baseline.

The script uses the CLEARCASE_USER environment variable to retrieve the user's name, the CLEARCASE_OP_KIND environment variable to identify the operation the user attempts to perform, and the CLEARCASE_POP_KIND environment variable to identify the parent operation. If the parent operation is deliver or rebase, the script does not check permissions.

use strict;

sub has_permission
{
my ($user,$op,$pop,$proj) = @_;

#When performing a composite operation like 'deliver' or 'rebase',
#we don't need to check permissions on the individual sub-operations
#that make up the composite.

return 1 if($pop eq 'deliver_start' || $pop eq 'rebase_start' ||
($pop eq 'deliver_complete' || $pop eq 'rebase_complete' ||
($pop eq 'deliver_cancel' || $pop eq 'rebase_cancel');

# Which roles can perform what operations?
# Note that these maps could be stored in a ClearCase attribute
# on each project instead of hard-coded here in the trigger script
# to give true per-project control.

my %map_op_to_roles = (
mkactivity => [ "projectmgr", "integrator", "developer" ],
mkbl => [ "projectmgr", "integrator" ],
mkstream => [ "projectmgr", "integrator", "developer" ],
);

# Which users belong to what roles?

my %map_role_to_users = (
projectmgr => [ "kate" ],
integrator => [ "kate", "mike" ],
developer => [ "kate", "mike", "jones" ],
);

# Does user belong to any of the roles that can perform this operation?

my ($role,$tmp_user);

for $role (@{ $map_op_to_roles{$op} }) {
for $tmp_user (@{ $map_role_to_users{$role} }) {
if ($tmp_user eq $user) {
return 1;
}
}
}

return 0;
}

sub Main
{
my $user = $ENV{CLEARCASE_USER};
my $proj = $ENV{CLEARCASE_PROJECT};
my $op = $ENV{CLEARCASE_OP_KIND};
my $pop = $ENV{CLEARCASE_POP_KIND};

my $perm = has_permission($user, $op, $proj);

printf("$user %s permission to perform '$op' in project $proj\n",
$perm ? "has" : "does NOT have");

exit($perm ? 0 : 1);
}

Main();