The Roles Database is MIT's central system for storing and disseminating authorization information. It currently stores authorizations for hundreds of business functions within dozens of applications, and new functions are being added each year. Maintenance of authorizations is distributed to departmental administrators (who control access to their department's resources) and to central offices responsible for HR, financial, student records, and other resources.
ISDA has developed a Web Service providing real-time access for looking up authorizations in the Roles Database. The Web Service is described in detail later in this document, but first, let's cover some of the basics of the Roles Database.
Authorizations in the Roles Database have the form:
Authorization = Person + Function + QualifierThe Person is the person who has the Authorization to do some sort of business transaction. The Function represents the business transaction. The Qualifier is the organizational, financial, or other unit within which the Person is is Authorized to perform the Function. When an Authorization is created (by a person with appropriate authority), the authorization-creator picks a Person, a Function, and a Qualifier from pre-existing lists.
Consider, for example, the following hypothetical authorization:
In this example, the person JOEUSER (identified by his username) has an authorization to perform the function "View Employee Records" within the category HR, but only applying to records related to organizational unit 10000429 (Biology). In this particular hypothetical case, the particular Function requires that the Qualifier Type must be an 8-digit org unit; other Functions would require different types of Qualifiers such as financial units, academic course numbers, etc..
Person Function Qualifier Category Function Name JOEUSER HR View Employee Records 10000429 (Biology)
There are several hierarchies of Qualifiers within the Roles Database, one for each Qualifier Type. Most of the Qualifier heirarchies are updated automatically each night in the Roles Database from sources of financial, HR, EHS, or other data at MIT. Other Qualifier hierarchies can be maintained manually via a web-based UI.
When an Authorization is created, the Qualifier may be a "leaf" level, or a "node" in a hierarchy, in which case the Authorization applies to all Qualifiers that are a child, grandchild, etc. of the specified node. In the above example, the Qualifier could have been specified as "10000030 Science Area", and the Authorization would have applied not only to Biology, but also to Mathematics, Physics, and all other units under the School of Science. An Authorization can be "direct" (i.e., it was explicitly created in the Roles Database), or "implied" (i.e., it is implied by an Authorization created for an object at a higher level in the hierarchy).
Qualifiers can be identified by a Qualifier Code (usually the common code used throughout MIT) or the Qualifier ID (a unique number within the Roles Database that has no meaning in other systems at MIT).
There is a special Qualifier "NULL". Some business Functions do not need a Qualifier. This would be the case where the business transaction to be performed is all-or-nothing and is not limited to an organizational or financial area. In these cases, Authorizations would have a Qualifier identified by the Qualifier Code "NULL".
Within the Roles Database, a Person is identified by his/her Kerberos principal at MIT. In the future, the "Person" field may be broadened to represent a broader set of Agents, including people in the broader MIT community who do not have an MIT Kerberos principal, servers, groups, etc.. There are some limited definitions of "pseudo-usernames" within the Roles Database representing servers, but this is an ad-hoc mechanism that needs to be replaced with a more generic way of representing diverse people, servers, and other agents. For now, authorizations can only be created for people at MIT who have an MIT Kerberos principal, and a few "pseudo-users" representing servers.
A Function is an object that represents a role or authority to perform some sort of business transaction, such as viewing data, spending money, accepting a student's application, etc.. Functions are grouped into Function Categories, or application areas, such as HR (Human Resources), PAYR (Payroll), EHS (Environment, Health and Safety), UADM (Undergraduate Admissions), etc.. A Function Category is identified by a 2-4 character code. A Function can be identified by either (1) its Function Category and Function Name or (2) its unique Function ID number.
Within an Authorization, in addition to the main fields of Person, Function, and Qualifier, there are also some minor fields that optionally specify a date range for the Authorization, and flags indicating whether the person can "do" the function specified in the Authorization, grant the Authorization to others or both.
There are currently 2 exposed APIs for the ROLES web service. These APIs are
There is an authentication step and up to two levels of authorization checking when the Web Service is used.
Examples will illustrate a simple and more complex case of authorization checking for the Roles Web Server.
Thus, there is only one level of authorization checking -- the application server looks up the authority of its end users. The Undergraduate Admissions server, once it has connected and has been authenticated with the WS Server, is identified with the pseudo-username 'UA$SERV'. It is allowed to run Roles Web Services to look up authorizations only within the Function Category 'UADM'. This is controlled via an Authorization in the Roles Database for pseudo-user UA$SERV, function 'RUN ROLES SERVICE PROCEDURES' and qualifier "CATUADM (Category UADM)". Thus, the Undergraduate Admissions server is allowed to look up authorizations in the UADM category but not in other categories such as HR, PAYR, EHS, etc..
In this case, the Room Access application server would need to authenticate with the Web Service. Once authenticated, one of its features will be to decide whether to let an individual into a given room. When it does this, it will call the Web Service to look up the individual's authorization to enter the room. The pseudo-username MKEY$SRV will need an authorization to 'RUN ROLES SERVICE PROCEDURES' for qualifier "CATMKEY (Category MKEY)", allowing the application server to look up authorizations within the category MKEY.
The Room Access application server will also allow administrators to look up people's authorizations within the Roles Database for entering rooms. In this case the application server will serve as a proxy for an end user, passing the end user's lookup request about authorizations to the Roles Database, which will return information about who is authorized to enter a given room. The application server will fill in a parameter in its Web Service call to tell the WS server the username of the end user. Thus, there will be two levels of authorization checking: (a) the application server (identified by MKEY$SRV) will need "RUN ROLES SERVICE PROCEDURES" authorization for the appropriate category of authorizations (MKEY), and (b) the end user, identified by his/her Kerberos username, will need "VIEW AUTH BY CATEGORY" authorization for the appropriate category of authorizations (again, MKEY).
The isUserAuthoried API returns a Boolean true if the user is authorized for the category, function and qualifier parameters or a Boolean false if the user is not authorized.
syntax:
public boolean isUserAuthorized(
String kerberos_principal,
String category,
String function,
String qualifier,
String proxy_user)
throws rolesException
Parameters:
kerberos_principal:
[in] string which contains the kerberos principal name for the user whose
authorizations are to be looked up. This is a required parameter.
category:
[in] string which contains the ROLES category code (e.g., HR, PAYR, UADM)
function:
[in] string which contains the Roles function name. This is a required parameter.
qualifier:
[in] string which contains the Roles qualifier code. This is a required parameter.
proxy_user:
[in] in cases where the application server is acting as a proxy for an
end user to look up authorizations for others, this string will contain
the kerberos principal of the user who wants to look up authorizations
for others. This parameter is not yet implemented and must be set to
the empty string (""). This is a required parameter.
Return value:
This API will return a boolean true if the user specified in the kerberos_principal parameter is authorized to perform the given Function (within the given Category) for the given Qualifier that were specified in the category, function and qualifier parameters. If the user is not authorized for the given Function (within the given Category) and Qualifier, a boolean false will be returned.
public rolesAuthorization[] listAuthorizationsByPerson(
String kerberos_principal,
String category,
boolean isActive,
boolean willExpand,
String proxy_user)
throws rolesException
Parameters:
kerberos_principal:
[in] string which contains the kerberos principal name for the user. This is a required parameter.
category:
[in] string which contains the ROLES category code. This is a required parameter.
function:
[in] string which contains the Roles function name. This is a required parameter.
isActive:
[in] boolean true or false. Set to true if the user is marked as active in ROLES, otherwise set to false. This is a required parameter.
willExpand:
[in] Boolean true or false. Setting this value to true, this API will return all implied and explicit authorizations for the specified user. Setting this value to false, this API will return only the explicit authorizations for the specified user. This is a required parameter.
proxy_user:
[in] in cases where the application server is acting as a proxy for an
end user to look up authorizations for others, this string will contain
the kerberos principal of the user who wants to look up authorizations
for others. This parameter is not yet implemented and must be set to
the empty string (""). This is a required parameter.
Return value:
This API will return array of authorizations for the user specified in the kerberos_principal parameter. This array is an array of Java Beans as described in the following pages.
If no authorizations are found for the user, a null will be returned.
The rolesAuthorization class below describes the elements of the array that is returned by the listAuthorizationsByPerson API.
public class rolesAuthorization implements java.io.Serializable {
private String category;
private String qualifier;
private String qualifierCode;
private String function;
private String name;
public rolesAuthorization()
{
}
public String getCategory()
{
return category;
}
public void setCategory(String uCategory)
{
category = uCategory;
}
public String getQualifier()
{
return qualifier;
}
public void setQualifier(String uQualifier)
{
qualifier = uQualifier;
}
public String getFunction()
{
return function;
}
public String getQualifierCode()
{
return qualifierCode;
}
public void setQualifierCode(String uQualifierCode)
{
qualifierCode = uQualifierCode;
}
public void setFunction(String uFunction)
{
function = uFunction;
}
public String getName()
{
return name;
}
public void setName(String uName)
{
name = uName;
}
public String toString()
{
String s = "Name: ";
if (name != null)
s += name;
s += "\n Category: ";
if (category != null)
s += category;
s += "\n Qualifier: ";
if (qualifier != null)
s += qualifier;
s += "\n Function: ";
if (function != null)
s += function;
return s;
}
}
Code samples
The following code snippets illustrate how to implement the client side calls to the ROLES web service. All the marshalling code that is required talk to the web service can be generated from the web service WSDL. Once generated, the marshalling code can be found in the rolesService_pkg package.
For the isUserAuthorized API:
Public String getUserAuthorization(
String UserName,
String Category,
String Function,
String Qualifier)
{
try
{
RolesServiceLocator sl = new RolesServiceLocator();
String ServiceName = sl.getrolesAddress();
Roles service = sl.getroles();
boolean rResponse = service.isUserAuthorized(
UserName,
Category,
Function,
Qualifier,
"");
}
catch(Exception e)
{
return(e.getMessage());
}
if (rResponse == true)
return("authorized")
return("not authorized");
}
For the listAuthorizationsByPerson API:
public String listUserAuthorization(
String UserName,
String Category,
boolean bisActive,
boolean bwillExpand)
{
RolesAuthorization rResponse[] = null;
StringBuffer sb = new StringBuffer();
try
{
RolesServiceLocator sl = new RolesServiceLocator();
String ServiceName = sl.getrolesAddress();
Roles service = sl.getroles();
rResponse = service.listAuthorizationsByPerson(UserName, Catagory,
bisActive, bwillExpand, "");
catch(Exception e)
{
sb.append(e.getMessage());
return(sb.toString());
}
if (rResponse == null)
return ("");
for (int i = 0; i < rResponse.length; i++)
{
sb.append("<BR>\r\n");
sb.append("Name: " + rResponse[i].getName());
sb.append("<BR>\r\n");
sb.append(" Category: " +
rResponse[i].getCategory());
sb.append("<BR>\r\n");
sb.append(" Qualifier: " +
rResponse[i].getQualifier());
sb.append("<BR>\r\n");
sb.append(" QualifierCode: " +
rResponse[i].getQualifierCode());
sb.append("<BR>\r\n");
sb.append(" Function: " +
rResponse[i].getFunction());
sb.append("<BR>\r\n");
}
return(sb.toString);
}