Previous | Next | Trail Map | Tips for LDAP Users | Schema

Object Class Definitions

All LDAP entries in the directory are typed. That is, each entry belongs to object classes that identify the type of data represented by the entry. The object class specifies the mandatory and optional attributes that can be associated with an entry of that class.

The object classes for all objects in the directory form a class hierarchy. The classes "top" and "alias" are at the root of the hierarchy. For example, the "organizationalPerson" object class is a subclass of the "Person" object class, which in turn is a subclass of "top". When you create a new LDAP entry, you must always specify all the object classes to which the new entry belongs. Because many directories do not support object class subclassing, you should always include all the superclasses of the entry. For example, for an "organizationalPerson" object, you should have "organizationalPerson", "person", and "top" in its list of object classes.

There are three types of object classes:

In the schema tree, the name "ClassDefinition" is bound to a flat context containing DirContext(in the API reference documentation) objects representing object class definitions in the schema. For example, if a directory supports a "person" object class, the "ClassDefinition" context will have a binding with name "person" that is bound to a DirContext object.

Each object in the "ClassDefinition" context has the following mandatory and optional attributes:
 

Attribute Identifier Attribute Value Description
NUMERICOID (mandatory) unique identifier (OID)
NAME object class's name
DESC object class's description
OBSOLETE "true" if obsolete; "false" or absent otherwise
SUP names of superior object classes from which this object class is derived
ABSTRACT "true" if object class is abstract; "false" or absent otherwise
STRUCTURAL "true" if object class is structural; "false" or absent otherwise
AUXILIARY "true" if object class is auxiliary; "false" or absent otherwise
MUST a list of type names of attributes that must be present
MAY a list of type names of attributes that may be present

These attributes correspond to the definition of "ObjectClassDescription" in RFC 2252. All the attribute values are represented by the java.lang.String class. Some directories do not publish all of the schema data. For example, the Netscape Directory Server 4.1 does not publish whether an object class is abstract, structural, or auxiliary. In such cases, the schema objects do not completely describe the object classes definitions.

Retrieving the Schema of an Object Class

To retrieve the schema object of an object class, you look for it in the schema tree. For example, you can obtain the schema object representing the "person" object class by using the following code:
// Get the schema tree root
DirContext schema = ctx.getSchema("");

// Get schema object for "person"
DirContext personSchema = (DirContext)schema.lookup("ClassDefinition/person");
If you get the attributes of the "personSchema" schema object, you will see:
NUMERICOID: 2.5.6.6
NAME: person 
MAY:  description, seealso, telephonenumber, userpassword
MUST: objectclass, sn, cn 
DESC: Standard ObjectClass 
SUP: top

In addition to using lookup(), you can use methods such as list()(in the API reference documentation) or search()(in the API reference documentation) to retrieve schema objects from the schema tree.

Getting an Entry's Object Classes

Given a DirContext object representing an LDAP entry, you can get that entry's object classes by invoking DirContext.getSchemaClassDefinition()(in the API reference documentation) on it. Here's an example that enumerates the object class definitions for the entry cn=Ted Geisel, ou=People. getSchemaClassDefinition() returns a context containing the entry's object class definitions. Using this context, you can look up an individual definition, search for a definition, enumerate all definitions, or perform other DirContext operations.

// Create the initial context
DirContext ctx = new InitialDirContext(env);

// Get context containing class definitions for cn=Ted Geisel entry
DirContext tedClasses = ctx.getSchemaClassDefinition("cn=Ted Geisel, ou=People");

// Enumerate class definitions
NamingEnumeration enum = tedClasses.search("", null);
while (enum.hasMore()) {
    System.out.println(enum.next());
}


Note: JNDI 1.2 is incompatible with JNDI 1.1 with respect to this method. JNDI 1.1's specification of getSchemaClassDefinition() says that the service provider should return any one of an object's object class definitions. This specification is inadequate, because an object usually has multiple object classes and the application might require knowledge about any of those object classes. When using JNDI 1.1 to get an entry's object class schema objects, you should retrieve the entry's "objectclass" attribute and then use the attribute values returned to look up the corresponding schema objects. Here's an example:
Attributes attrs = 
    ctx.getAttributes("cn=Ted Geisel, ou=People", new String[]{"objectclass"});
Attribute attr = attrs.get("objectclass");
NamingEnumeration ocs = attr.getAll();
while (ocs.hasMore()) {
     DirContext oc = 
	(DirContext)schema.lookup("ClassDefinition/"+ (String)ocs.next());
     ...
}

Adding a new Object Class


Before you go on: In order to update the schema, you must authenticate as the directory administrator. This is the name that you supplied to the directory setup program when you first configured the directory. For example, if you configured "cn=Directory Manager" as the administrator, you need to do something like this when creating the initial context:
env.put(Context.SECURITY_PRINCIPAL, "cn=Directory Manager");
env.put(Context.SECURITY_CREDENTIALS, "secret99");

Netscape 4.0 Bugs: The Netscape Directory Server 4.0 and earlier releases do not support schema entries that comply with RFC 2252. Specifically, contrary to RFC 2252, the Netscape server requires OIDs (such as those for SUP and SYNTAX) be delimited by single quotes and MUST/MAY lists be enclosed by parentheses. By default, the LDAP service provider produces schema entries that are compliant with RFC 2252 but not acceptable to the Netscape server. In order to produce schema entries that are acceptable to the Netscape 4.0 server, you must add the following to the environment properties before creating the initial context:

env.put("com.sun.jndi.ldap.netscape.schemaBugs", "true");
Netscape 4.1 Bugs: The Netscape Directory Server 4.1 has fixed some of the schema handling problems found in the 4.0 server, so you should not use the "com.sun.jndi.ldap.netscape.schemaBugs" property with 4.1. However, the 4.1 server still requires that MUST/MAY lists be enclosed by parentheses. Sun's LDAP provider uses a quoted item instead of a parenthetical list for single-item MUST/MAY specifications. To work around this problem, if you are modifying or creating an object class definition that contains a single MUST/MAY item, add a superfluous value, such as "objectclass", to the MUST/MAY attribute.
Adding a new object class to the schema is like adding a new entry to the directory, because the schema tree and schema objects are DirContext objects. Here's an example that adds a new object class to the schema. It first declares the attributes that describe the new object class, and then adds the object class definition to the schema by using DirContext.createSubcontext()(in the API reference documentation) .
// Specify attributes for schema object
Attributes attrs = new BasicAttributes(true); // ignore case
attrs.put("NUMERICOID", "1.3.6.1.4.1.42.2.27.4.2.3.1.1.1");
attrs.put("NAME", "fooObjectClass");
attrs.put("DESC", "for JNDITutorial example only");
attrs.put("SUP", "top");
attrs.put("STRUCTURAL", "true");
Attribute must = new BasicAttribute("MUST", "cn");
must.add("objectclass");
attrs.put(must);

// Get the schema tree root
DirContext schema = ctx.getSchema("");

// Add new schema object for "fooObjectClass"
DirContext newClass = schema.createSubcontext("ClassDefinition/fooObjectClass", attrs);

Modifying an Object Class

You cannot modify an existing object class. You must first delete the existing object class definition, and then add the updated version.

Deleting an Object Class


Before you go on: See Adding a New Object Class for notes regarding updating the schema.
Deleting an existing object class from the schema is like deleting an entry from the directory. Here's an example that removes the object class "fooObjectClass" from the schema by using DirContext.destroySubcontext()(in the API reference documentation) :
// Get the schema tree root
DirContext schema = ctx.getSchema("");

// Remove the schema object for "fooObjectClass"
schema.destroySubcontext("ClassDefinition/fooObjectClass");
Some servers might not let you delete an object class that's being used by entries in the directory. You might be able to get around this restriction by turning off schema-checking.


Previous | Next | Trail Map | Tips for LDAP Users | Schema