| | |
| | | # CDDL HEADER END |
| | | # |
| | | # |
| | | # Portions Copyright 2006 Sun Microsystems, Inc. |
| | | # Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | # |
| | | # |
| | | # This file contains a core set of attribute type and objectlass definitions |
| | |
| | | EQUALITY distinguishedNameMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.12 |
| | | SINGLE-VALUE NO-USER-MODIFICATION USAGE directoryOperation |
| | | X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 2.5.21.5 NAME 'attributeTypes' |
| | | EQUALITY objectIdentifierFirstComponentMatch |
| | | attributeTypes: ( 2.5.21.5 NAME 'attributeTypes' EQUALITY caseIgnoreMatch |
| | | SYNTAX 1.3.6.1.4.1.1466.115.121.1.3 USAGE directoryOperation |
| | | X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 2.5.21.6 NAME 'objectClasses' |
| | | EQUALITY objectIdentifierFirstComponentMatch |
| | | attributeTypes: ( 2.5.21.6 NAME 'objectClasses' EQUALITY caseIgnoreMatch |
| | | SYNTAX 1.3.6.1.4.1.1466.115.121.1.37 USAGE directoryOperation |
| | | X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 2.5.21.4 NAME 'matchingRules' |
| | | EQUALITY objectIdentifierFirstComponentMatch |
| | | attributeTypes: ( 2.5.21.4 NAME 'matchingRules' EQUALITY caseIgnoreMatch |
| | | SYNTAX 1.3.6.1.4.1.1466.115.121.1.30 USAGE directoryOperation |
| | | X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 2.5.21.8 NAME 'matchingRuleUse' |
| | | EQUALITY objectIdentifierFirstComponentMatch |
| | | attributeTypes: ( 2.5.21.8 NAME 'matchingRuleUse' EQUALITY caseIgnoreMatch |
| | | SYNTAX 1.3.6.1.4.1.1466.115.121.1.31 USAGE directoryOperation |
| | | X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 1.3.6.1.4.1.1466.101.120.5 NAME 'namingContexts' |
| | |
| | | attributeTypes: ( 1.3.6.1.4.1.1466.101.120.16 NAME 'ldapSyntaxes' |
| | | SYNTAX 1.3.6.1.4.1.1466.115.121.1.54 USAGE directoryOperation |
| | | X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 2.5.21.1 NAME 'dITStructureRules' |
| | | EQUALITY integerFirstComponentMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.17 |
| | | USAGE directoryOperation X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 2.5.21.7 NAME 'nameForms' |
| | | EQUALITY objectIdentifierFirstComponentMatch |
| | | attributeTypes: ( 2.5.21.1 NAME 'dITStructureRules' EQUALITY caseIgnoreMatch |
| | | SYNTAX 1.3.6.1.4.1.1466.115.121.1.17 USAGE directoryOperation |
| | | X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 2.5.21.7 NAME 'nameForms' EQUALITY caseIgnoreMatch |
| | | SYNTAX 1.3.6.1.4.1.1466.115.121.1.35 USAGE directoryOperation |
| | | X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 2.5.21.2 NAME 'dITContentRules' |
| | | EQUALITY objectIdentifierFirstComponentMatch |
| | | attributeTypes: ( 2.5.21.2 NAME 'dITContentRules' EQUALITY caseIgnoreMatch |
| | | SYNTAX 1.3.6.1.4.1.1466.115.121.1.16 USAGE directoryOperation |
| | | X-ORIGIN 'RFC 2252' ) |
| | | attributeTypes: ( 0.9.2342.19200300.100.1.25 NAME 'dc' |
| | |
| | | AUXILIARY X-ORIGIN 'RFC 2252' ) |
| | | objectClasses: ( 2.5.20.1 NAME 'subschema' AUXILIARY MAY ( dITStructureRules $ |
| | | nameForms $ ditContentRules $ objectClasses $ attributeTypes $ matchingRules $ |
| | | matchingRuleUse ) X-ORIGIn 'RFC 2252' ) |
| | | matchingRuleUse ) X-ORIGIN 'RFC 2252' ) |
| | | objectClasses: ( 0.9.2342.19200300.100.4.5 NAME 'account' SUP top STRUCTURAL |
| | | MUST uid MAY ( description $ seeAlso $ l $ o $ ou $ host ) |
| | | X-ORIGIN 'RFC 4524' ) |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.backends; |
| | | |
| | |
| | | import java.io.FileInputStream; |
| | | import java.io.FileOutputStream; |
| | | import java.io.InputStream; |
| | | import java.io.IOException; |
| | | import java.io.OutputStream; |
| | | import java.security.MessageDigest; |
| | | import java.util.ArrayList; |
| | |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.Set; |
| | | import java.util.TreeSet; |
| | | import java.util.zip.Deflater; |
| | | import java.util.zip.ZipEntry; |
| | | import java.util.zip.ZipInputStream; |
| | |
| | | import javax.crypto.CipherOutputStream; |
| | | import javax.crypto.Mac; |
| | | |
| | | import org.opends.server.api.AlertGenerator; |
| | | import org.opends.server.api.Backend; |
| | | import org.opends.server.api.ConfigurableComponent; |
| | | import org.opends.server.api.MatchingRule; |
| | | import org.opends.server.config.BooleanConfigAttribute; |
| | | import org.opends.server.config.ConfigAttribute; |
| | | import org.opends.server.config.ConfigEntry; |
| | |
| | | import org.opends.server.core.SchemaConfigManager; |
| | | import org.opends.server.core.SearchOperation; |
| | | import org.opends.server.schema.AttributeTypeSyntax; |
| | | import org.opends.server.schema.DITContentRuleSyntax; |
| | | import org.opends.server.schema.DITStructureRuleSyntax; |
| | | import org.opends.server.schema.MatchingRuleUseSyntax; |
| | | import org.opends.server.schema.NameFormSyntax; |
| | | import org.opends.server.schema.ObjectClassSyntax; |
| | | import org.opends.server.types.Attribute; |
| | | import org.opends.server.types.AttributeType; |
| | |
| | | import org.opends.server.types.ConfigChangeResult; |
| | | import org.opends.server.types.CryptoManager; |
| | | import org.opends.server.types.DirectoryException; |
| | | import org.opends.server.types.DITContentRule; |
| | | import org.opends.server.types.DITStructureRule; |
| | | import org.opends.server.types.DN; |
| | | import org.opends.server.types.Entry; |
| | | import org.opends.server.types.ErrorLogCategory; |
| | |
| | | import org.opends.server.types.InitializationException; |
| | | import org.opends.server.types.LDIFImportConfig; |
| | | import org.opends.server.types.LDIFExportConfig; |
| | | import org.opends.server.types.MatchingRuleUse; |
| | | import org.opends.server.types.Modification; |
| | | import org.opends.server.types.ModificationType; |
| | | import org.opends.server.types.NameForm; |
| | | import org.opends.server.types.ObjectClass; |
| | | import org.opends.server.types.ObjectClassType; |
| | | import org.opends.server.types.RDN; |
| | | import org.opends.server.types.RestoreConfig; |
| | | import org.opends.server.types.ResultCode; |
| | | import org.opends.server.types.Schema; |
| | | import org.opends.server.types.SchemaFileElement; |
| | | import org.opends.server.types.SearchFilter; |
| | | import org.opends.server.types.SearchScope; |
| | | import org.opends.server.util.DynamicConstants; |
| | | import org.opends.server.util.LDIFReader; |
| | | import org.opends.server.util.LDIFException; |
| | | import org.opends.server.util.LDIFWriter; |
| | | |
| | | import static org.opends.server.config.ConfigConstants.*; |
| | |
| | | */ |
| | | public class SchemaBackend |
| | | extends Backend |
| | | implements ConfigurableComponent |
| | | implements ConfigurableComponent, AlertGenerator |
| | | { |
| | | /** |
| | | * The fully-qualified name of this class for debugging purposes. |
| | |
| | | // elements, nor will we allow modification of any other attributes. Make |
| | | // sure that the included modify operation is acceptable within these |
| | | // constraints. |
| | | List<Modification> mods = modifyOperation.getModifications(); |
| | | ArrayList<Modification> mods = |
| | | new ArrayList<Modification>(modifyOperation.getModifications()); |
| | | if (mods.isEmpty()) |
| | | { |
| | | // There aren't any modifications, so we don't need to do anything. |
| | |
| | | } |
| | | |
| | | Schema newSchema = DirectoryServer.getSchema().duplicate(); |
| | | LinkedList<AttributeType> newAttrTypes = new LinkedList<AttributeType>(); |
| | | LinkedList<ObjectClass> newObjectClasses = new LinkedList<ObjectClass>(); |
| | | TreeSet<String> modifiedSchemaFiles = new TreeSet<String>(); |
| | | LinkedHashSet<SchemaFileElement> dependentElements = |
| | | new LinkedHashSet<SchemaFileElement>(); |
| | | |
| | | int pos = -1; |
| | | for (Modification m : mods) |
| | | { |
| | | pos++; |
| | | |
| | | if (m.isInternal()) |
| | | { |
| | | // We don't need to do anything for internal modifications (e.g., like |
| | |
| | | continue; |
| | | } |
| | | |
| | | |
| | | // Determine the type of modification to perform. We will support add and |
| | | // delete operations in the schema, and we will also support the ability |
| | | // to add a schema element that already exists and treat it as a |
| | | // replacement of that existing element. |
| | | Attribute a = m.getAttribute(); |
| | | AttributeType at = a.getAttributeType(); |
| | | switch (m.getModificationType()) |
| | | { |
| | | case ADD: |
| | | // This is fine, as long as there aren't any conflicts later. |
| | | LinkedHashSet<AttributeValue> values = a.getValues(); |
| | | if (values.isEmpty()) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | if (at.equals(attributeTypesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | AttributeType type; |
| | | try |
| | | { |
| | | type = AttributeTypeSyntax.decodeAttributeType(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_ATTRTYPE; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | addAttributeType(type, newSchema, modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(objectClassesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | ObjectClass oc; |
| | | try |
| | | { |
| | | oc = ObjectClassSyntax.decodeObjectClass(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_OBJECTCLASS; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | addObjectClass(oc, newSchema, modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(nameFormsType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | NameForm nf; |
| | | try |
| | | { |
| | | nf = NameFormSyntax.decodeNameForm(v.getValue(), newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_NAME_FORM; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | addNameForm(nf, newSchema, modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(ditContentRulesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | DITContentRule dcr; |
| | | try |
| | | { |
| | | dcr = DITContentRuleSyntax.decodeDITContentRule(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_DCR; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | addDITContentRule(dcr, newSchema, modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(ditStructureRulesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | DITStructureRule dsr; |
| | | try |
| | | { |
| | | dsr = DITStructureRuleSyntax.decodeDITStructureRule( |
| | | v.getValue(), newSchema, false); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_DSR; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | addDITStructureRule(dsr, newSchema, modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(matchingRuleUsesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | MatchingRuleUse mru; |
| | | try |
| | | { |
| | | mru = MatchingRuleUseSyntax.decodeMatchingRuleUse(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_MR_USE; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | addMatchingRuleUse(mru, newSchema, modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_UNSUPPORTED_ATTRIBUTE_TYPE; |
| | | String message = getMessage(msgID, a.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | |
| | | break; |
| | | |
| | | |
| | | case DELETE: |
| | | // FIXME -- We need to support this. |
| | | int msgID = MSGID_SCHEMA_DELETE_MODTYPE_NOT_SUPPORTED; |
| | | String message = getMessage(msgID); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | values = a.getValues(); |
| | | if (values.isEmpty()) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_DELETE_NO_VALUES; |
| | | String message = getMessage(msgID, a.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | |
| | | case REPLACE: |
| | | // FIXME -- Should we support this? |
| | | case INCREMENT: |
| | | if (at.equals(attributeTypesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | AttributeType type; |
| | | try |
| | | { |
| | | type = AttributeTypeSyntax.decodeAttributeType(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_ATTRTYPE; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | removeAttributeType(type, newSchema, mods, pos, |
| | | modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(objectClassesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | ObjectClass oc; |
| | | try |
| | | { |
| | | oc = ObjectClassSyntax.decodeObjectClass(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_OBJECTCLASS; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | removeObjectClass(oc, newSchema, mods, pos, modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(nameFormsType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | NameForm nf; |
| | | try |
| | | { |
| | | nf = NameFormSyntax.decodeNameForm(v.getValue(), newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_NAME_FORM; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | removeNameForm(nf, newSchema, mods, pos, modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(ditContentRulesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | DITContentRule dcr; |
| | | try |
| | | { |
| | | dcr = DITContentRuleSyntax.decodeDITContentRule(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_DCR; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | removeDITContentRule(dcr, newSchema, mods, pos, |
| | | modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(ditStructureRulesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | DITStructureRule dsr; |
| | | try |
| | | { |
| | | dsr = DITStructureRuleSyntax.decodeDITStructureRule( |
| | | v.getValue(), newSchema, false); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_DSR; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | removeDITStructureRule(dsr, newSchema, mods, pos, |
| | | modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else if (at.equals(matchingRuleUsesType)) |
| | | { |
| | | for (AttributeValue v : values) |
| | | { |
| | | MatchingRuleUse mru; |
| | | try |
| | | { |
| | | mru = MatchingRuleUseSyntax.decodeMatchingRuleUse(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_MR_USE; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | removeMatchingRuleUse(mru, newSchema, mods, pos, |
| | | modifiedSchemaFiles); |
| | | } |
| | | } |
| | | else |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_UNSUPPORTED_ATTRIBUTE_TYPE; |
| | | String message = getMessage(msgID, a.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | |
| | | break; |
| | | |
| | | |
| | | default: |
| | | // FIXME -- Make sure to update this message once we support |
| | | // schema deletes and possibly replace. |
| | | msgID = MSGID_SCHEMA_INVALID_MODIFICATION_TYPE; |
| | | message = getMessage(msgID, m.getModificationType()); |
| | | int msgID = MSGID_SCHEMA_INVALID_MODIFICATION_TYPE; |
| | | String message = getMessage(msgID, m.getModificationType()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // At the present time, we will only allow modification of the |
| | | // attributeTypes and objectClasses attributes. |
| | | Attribute a = m.getAttribute(); |
| | | AttributeType t = a.getAttributeType(); |
| | | if (t.equals(attributeTypesType)) |
| | | { |
| | | for (AttributeValue v : a.getValues()) |
| | | { |
| | | AttributeType newType; |
| | | try |
| | | { |
| | | newType = AttributeTypeSyntax.decodeAttributeType(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_ATTRTYPE; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException(ResultCode.INVALID_ATTRIBUTE_SYNTAX, |
| | | message, msgID, de); |
| | | } |
| | | |
| | | try |
| | | { |
| | | newSchema.registerAttributeType(newType, false); |
| | | newAttrTypes.add(newType); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_ATTRTYPE_ALREADY_EXISTS; |
| | | String message = getMessage(msgID, newType.getNameOrOID(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID, de); |
| | | } |
| | | } |
| | | } |
| | | else if (t.equals(objectClassesType)) |
| | | { |
| | | for (AttributeValue v : a.getValues()) |
| | | { |
| | | ObjectClass newClass; |
| | | try |
| | | { |
| | | newClass = ObjectClassSyntax.decodeObjectClass(v.getValue(), |
| | | newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_OBJECTCLASS; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException(ResultCode.INVALID_ATTRIBUTE_SYNTAX, |
| | | message, msgID, de); |
| | | } |
| | | |
| | | // If there is a superior class, then make sure it is defined. |
| | | ObjectClass superiorClass = newClass.getSuperiorClass(); |
| | | if (superiorClass != null) |
| | | { |
| | | String lowerName = toLowerCase(superiorClass.getNameOrOID()); |
| | | if (! newSchema.hasObjectClass(lowerName)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_UNDEFINED_SUPERIOR_OBJECTCLASS; |
| | | String message = getMessage(msgID, newClass.getNameOrOID(), |
| | | superiorClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | } |
| | | |
| | | // Make sure that all the associated attribute types are defined. |
| | | for (AttributeType at : newClass.getRequiredAttributes()) |
| | | { |
| | | String lowerName = toLowerCase(at.getNameOrOID()); |
| | | if (! newSchema.hasAttributeType(lowerName)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_OC_UNDEFINED_REQUIRED_ATTR; |
| | | String message = getMessage(msgID, newClass.getNameOrOID(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | } |
| | | |
| | | for (AttributeType at : newClass.getOptionalAttributes()) |
| | | { |
| | | String lowerName = toLowerCase(at.getNameOrOID()); |
| | | if (! newSchema.hasAttributeType(lowerName)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_OC_UNDEFINED_OPTIONAL_ATTR; |
| | | String message = getMessage(msgID, newClass.getNameOrOID(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | } |
| | | |
| | | try |
| | | { |
| | | newSchema.registerObjectClass(newClass, false); |
| | | newObjectClasses.add(newClass); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_OBJECTCLASS_ALREADY_EXISTS; |
| | | String message = getMessage(msgID, newClass.getNameOrOID(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID, de); |
| | | } |
| | | } |
| | | } |
| | | else |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_UNSUPPORTED_ATTRIBUTE_TYPE; |
| | | String message = getMessage(msgID, a.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // If we've gotten here, then everything looks OK. Add the new schema |
| | | // elements to the 99-user.ldif file and swing the new schema into place. |
| | | String schemaDirPath = SchemaConfigManager.getSchemaDirectoryPath(); |
| | | File userSchemaFile = new File(schemaDirPath, FILE_USER_SCHEMA_ELEMENTS); |
| | | Entry userSchemaEntry = null; |
| | | |
| | | if (userSchemaFile.exists()) |
| | | { |
| | | // There's already a set of user-defined schema elements, so we'll need to |
| | | // add these new elements to that set. |
| | | LDIFReader ldifReader = null; |
| | | try |
| | | { |
| | | LDIFImportConfig importConfig = |
| | | new LDIFImportConfig(userSchemaFile.getAbsolutePath()); |
| | | ldifReader = new LDIFReader(importConfig); |
| | | |
| | | userSchemaEntry = ldifReader.readEntry(true); |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", e); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_READ_EXISTING_USER_SCHEMA; |
| | | String message = getMessage(msgID, userSchemaFile.getAbsolutePath(), |
| | | stackTraceToSingleLineString(e)); |
| | | throw new DirectoryException(DirectoryServer.getServerErrorResultCode(), |
| | | message, msgID, e); |
| | | } |
| | | finally |
| | | { |
| | | if (ldifReader != null) |
| | | { |
| | | ldifReader.close(); |
| | | } |
| | | } |
| | | } |
| | | |
| | | if (userSchemaEntry == null) |
| | | { |
| | | // This could happen if there was no user schema file or if it was there |
| | | // but didn't have any entries. At any rate, create a new, empty entry. |
| | | userSchemaEntry = createEmptySchemaEntry(); |
| | | } |
| | | |
| | | |
| | | // Add all of the new schema elements to the entry. |
| | | if (! newAttrTypes.isEmpty()) |
| | | { |
| | | LinkedHashSet<AttributeValue> values = |
| | | new LinkedHashSet<AttributeValue>(); |
| | | for (AttributeType t : newAttrTypes) |
| | | { |
| | | StringBuilder buffer = new StringBuilder(); |
| | | t.toString(buffer, false); |
| | | values.add(new AttributeValue(attributeTypesType, buffer.toString())); |
| | | } |
| | | |
| | | Attribute attrTypeAttribute = new Attribute(attributeTypesType, |
| | | ATTR_ATTRIBUTE_TYPES, values); |
| | | LinkedList<AttributeValue> duplicateValues = |
| | | new LinkedList<AttributeValue>(); |
| | | userSchemaEntry.addAttribute(attrTypeAttribute, duplicateValues); |
| | | } |
| | | |
| | | if (! newObjectClasses.isEmpty()) |
| | | { |
| | | LinkedHashSet<AttributeValue> values = |
| | | new LinkedHashSet<AttributeValue>(); |
| | | for (ObjectClass oc : newObjectClasses) |
| | | { |
| | | StringBuilder buffer = new StringBuilder(); |
| | | oc.toString(buffer, false); |
| | | values.add(new AttributeValue(attributeTypesType, buffer.toString())); |
| | | } |
| | | |
| | | Attribute ocAttribute = new Attribute(objectClassesType, |
| | | ATTR_OBJECTCLASSES, values); |
| | | LinkedList<AttributeValue> duplicateValues = |
| | | new LinkedList<AttributeValue>(); |
| | | userSchemaEntry.addAttribute(ocAttribute, duplicateValues); |
| | | } |
| | | |
| | | |
| | | // Swing the new schema into place. |
| | | // If we've gotten here, then everything looks OK. We'll re-write all |
| | | // impacted schema files by first creating them in a temporary location |
| | | // and then replacing the existing schema files with the new versions. |
| | | // If all that goes successfully, then activate the new schema. |
| | | HashMap<String,File> tempSchemaFiles = new HashMap<String,File>(); |
| | | try |
| | | { |
| | | File tempSchemaFile = new File(userSchemaFile.getAbsolutePath() + ".tmp"); |
| | | LDIFExportConfig exportConfig = |
| | | new LDIFExportConfig(tempSchemaFile.getAbsolutePath(), |
| | | ExistingFileBehavior.OVERWRITE); |
| | | |
| | | LDIFWriter writer = null; |
| | | try |
| | | for (String schemaFile : modifiedSchemaFiles) |
| | | { |
| | | writer = new LDIFWriter(exportConfig); |
| | | writer.writeEntry(userSchemaEntry); |
| | | } |
| | | finally |
| | | { |
| | | if (writer != null) |
| | | { |
| | | writer.close(); |
| | | } |
| | | File tempSchemaFile = writeTempSchemaFile(newSchema, schemaFile); |
| | | tempSchemaFiles.put(schemaFile, tempSchemaFile); |
| | | } |
| | | |
| | | File oldSchemaFile = null; |
| | | if (userSchemaFile.exists()) |
| | | { |
| | | oldSchemaFile = new File(userSchemaFile.getAbsolutePath() + ".old"); |
| | | if (oldSchemaFile.exists()) |
| | | { |
| | | oldSchemaFile.delete(); |
| | | } |
| | | |
| | | userSchemaFile.renameTo(oldSchemaFile); |
| | | } |
| | | |
| | | tempSchemaFile.renameTo(userSchemaFile); |
| | | |
| | | if (oldSchemaFile != null) |
| | | { |
| | | oldSchemaFile.delete(); |
| | | } |
| | | |
| | | installSchemaFiles(tempSchemaFiles); |
| | | DirectoryServer.setSchema(newSchema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", de); |
| | | |
| | | throw de; |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | assert debugException(CLASS_NAME, "replaceEntry", e); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_WRITE_NEW_SCHEMA; |
| | | String message = getMessage(msgID, userSchemaFile.getAbsolutePath(), |
| | | stackTraceToSingleLineString(e)); |
| | | String message = getMessage(msgID, stackTraceToSingleLineString(e)); |
| | | throw new DirectoryException(DirectoryServer.getServerErrorResultCode(), |
| | | message, msgID, e); |
| | | } |
| | | finally |
| | | { |
| | | cleanUpTempSchemaFiles(tempSchemaFiles); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required for adding the provided attribute type to |
| | | * the given schema, replacing an existing type if necessary, and ensuring all |
| | | * other metadata is properly updated. |
| | | * |
| | | * @param attributeType The attribute type to add or replace in the |
| | | * server schema. |
| | | * @param schema The schema to which the attribute type should |
| | | * be added. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to add |
| | | * the provided attribute type to the server |
| | | * schema. |
| | | */ |
| | | private void addAttributeType(AttributeType attributeType, Schema schema, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addAttributeType", |
| | | String.valueOf(attributeType), String.valueOf(schema), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // First, see if the specified attribute type already exists. We'll check |
| | | // the OID and all of the names, which means that it's possible there could |
| | | // be more than one match (although if there is, then we'll refuse the |
| | | // operation). |
| | | AttributeType existingType = |
| | | schema.getAttributeType(attributeType.getOID()); |
| | | for (String name : attributeType.getNormalizedNames()) |
| | | { |
| | | AttributeType t = schema.getAttributeType(name); |
| | | if (t == null) |
| | | { |
| | | continue; |
| | | } |
| | | else if (existingType == null) |
| | | { |
| | | existingType = t; |
| | | } |
| | | else if (existingType != t) |
| | | { |
| | | // NOTE: We really do want to use "!=" instead of "! t.equals()" |
| | | // because we want to check whether it's the same object instance, not |
| | | // just a logical equivalent. |
| | | int msgID = MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_ATTRTYPE; |
| | | String message = getMessage(msgID, attributeType.getNameOrOID(), |
| | | existingType.getNameOrOID(), |
| | | t.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the new attribute type doesn't reference an undefined |
| | | // superior attribute type. |
| | | AttributeType superiorType = attributeType.getSuperiorType(); |
| | | if (superiorType != null) |
| | | { |
| | | if (! schema.hasAttributeType(superiorType.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_UNDEFINED_SUPERIOR_ATTRIBUTE_TYPE; |
| | | String message = getMessage(msgID, attributeType.getNameOrOID(), |
| | | superiorType.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // If there is no existing type, then we're adding a new attribute. |
| | | // Otherwise, we're replacing an existing one. |
| | | if (existingType == null) |
| | | { |
| | | schema.registerAttributeType(attributeType, false); |
| | | String schemaFile = attributeType.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | attributeType.setSchemaFile(schemaFile); |
| | | } |
| | | |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | schema.deregisterAttributeType(existingType); |
| | | schema.registerAttributeType(attributeType, false); |
| | | schema.rebuildDependentElements(existingType); |
| | | |
| | | if ((attributeType.getSchemaFile() == null) || |
| | | (attributeType.getSchemaFile().length() == 0)) |
| | | { |
| | | String schemaFile = existingType.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | } |
| | | |
| | | attributeType.setSchemaFile(schemaFile); |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | String newSchemaFile = attributeType.getSchemaFile(); |
| | | String oldSchemaFile = existingType.getSchemaFile(); |
| | | if ((oldSchemaFile == null) || oldSchemaFile.equals(newSchemaFile)) |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | } |
| | | else |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | modifiedSchemaFiles.add(oldSchemaFile); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required to remove the provided attribute type from |
| | | * the server schema, ensuring all other metadata is properly updated. Note |
| | | * that this method will first check to see whether the same attribute type |
| | | * will be later added to the server schema with an updated definition, and if |
| | | * so then the removal will be ignored because the later add will be handled |
| | | * as a replace. If the attribute type will not be replaced with a new |
| | | * definition, then this method will ensure that there are no other schema |
| | | * elements that depend on the attribute type before allowing it to be |
| | | * removed. |
| | | * |
| | | * @param attributeType The attribute type to remove from the server |
| | | * schema. |
| | | * @param schema The schema from which the attribute type |
| | | * should be removed. |
| | | * @param modifications The full set of modifications to be processed |
| | | * against the server schema. |
| | | * @param currentPosition The position of the modification currently |
| | | * being performed. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to remove |
| | | * the provided attribute type from the server |
| | | * schema. |
| | | */ |
| | | private void removeAttributeType(AttributeType attributeType, Schema schema, |
| | | ArrayList<Modification> modifications, |
| | | int currentPosition, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeAttributeType", |
| | | String.valueOf(attributeType), String.valueOf(schema), |
| | | String.valueOf(modifications), |
| | | String.valueOf(currentPosition), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // See if the specified attribute type is actually defined in the server |
| | | // schema. If not, then fail. |
| | | AttributeType removeType = schema.getAttributeType(attributeType.getOID()); |
| | | if ((removeType == null) || (! removeType.equals(attributeType))) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_ATTRIBUTE_TYPE; |
| | | String message = getMessage(msgID, attributeType.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // See if there is another modification later to add the attribute type back |
| | | // into the schema. If so, then it's a replace and we should ignore the |
| | | // remove because adding it back will handle the replace. |
| | | for (int i=currentPosition+1; i < modifications.size(); i++) |
| | | { |
| | | Modification m = modifications.get(i); |
| | | Attribute a = m.getAttribute(); |
| | | |
| | | if ((m.getModificationType() != ModificationType.ADD) || |
| | | (! a.getAttributeType().equals(attributeTypesType))) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | for (AttributeValue v : a.getValues()) |
| | | { |
| | | AttributeType at; |
| | | try |
| | | { |
| | | at = AttributeTypeSyntax.decodeAttributeType(v.getValue(), schema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "removeAttributeType", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_ATTRTYPE; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | if (attributeType.getOID().equals(at.getOID())) |
| | | { |
| | | // We found a match where the attribute type is added back later, so |
| | | // we don't need to do anything else here. |
| | | return; |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the attribute type isn't used as the superior type for |
| | | // any other attributes. |
| | | for (AttributeType at : schema.getAttributeTypes().values()) |
| | | { |
| | | AttributeType superiorType = at.getSuperiorType(); |
| | | if ((superiorType != null) && superiorType.equals(removeType)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_AT_SUPERIOR_TYPE; |
| | | String message = getMessage(msgID, removeType.getNameOrOID(), |
| | | superiorType.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the attribute type isn't used as a required or optional |
| | | // attribute type in any objectclass. |
| | | for (ObjectClass oc : schema.getObjectClasses().values()) |
| | | { |
| | | if (oc.getRequiredAttributes().contains(removeType) || |
| | | oc.getOptionalAttributes().contains(removeType)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_OC; |
| | | String message = getMessage(msgID, removeType.getNameOrOID(), |
| | | oc.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the attribute type isn't used as a required or optional |
| | | // attribute type in any name form. |
| | | for (NameForm nf : schema.getNameFormsByObjectClass().values()) |
| | | { |
| | | if (nf.getRequiredAttributes().contains(removeType) || |
| | | nf.getOptionalAttributes().contains(removeType)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_NF; |
| | | String message = getMessage(msgID, removeType.getNameOrOID(), |
| | | nf.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the attribute type isn't used as a required, optional, or |
| | | // prohibited attribute type in any DIT content rule. |
| | | for (DITContentRule dcr : schema.getDITContentRules().values()) |
| | | { |
| | | if (dcr.getRequiredAttributes().contains(removeType) || |
| | | dcr.getOptionalAttributes().contains(removeType) || |
| | | dcr.getProhibitedAttributes().contains(removeType)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_DCR; |
| | | String message = getMessage(msgID, removeType.getNameOrOID(), |
| | | dcr.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the attribute type isn't referenced by any matching rule |
| | | // use. |
| | | for (MatchingRuleUse mru : schema.getMatchingRuleUses().values()) |
| | | { |
| | | if (mru.getAttributes().contains(removeType)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_MR_USE; |
| | | String message = getMessage(msgID, removeType.getNameOrOID(), |
| | | mru.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // If we've gotten here, then it's OK to remove the attribute type from |
| | | // the schema. |
| | | schema.deregisterAttributeType(removeType); |
| | | String schemaFile = removeType.getSchemaFile(); |
| | | if (schemaFile != null) |
| | | { |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required for adding the provided objectclass to the |
| | | * given schema, replacing an existing class if necessary, and ensuring |
| | | * all other metadata is properly updated. |
| | | * |
| | | * @param objectClass The objectclass to add or replace in the |
| | | * server schema. |
| | | * @param schema The schema to which the objectclass should be |
| | | * added. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to add |
| | | * the provided objectclass to the server schema. |
| | | */ |
| | | private void addObjectClass(ObjectClass objectClass, Schema schema, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addObjectClass", String.valueOf(objectClass), |
| | | String.valueOf(schema), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // First, see if the specified objectclass already exists. We'll check the |
| | | // OID and all of the names, which means that it's possible there could be |
| | | // more than one match (although if there is, then we'll refuse the |
| | | // operation). |
| | | ObjectClass existingClass = |
| | | schema.getObjectClass(objectClass.getOID()); |
| | | for (String name : objectClass.getNormalizedNames()) |
| | | { |
| | | ObjectClass oc = schema.getObjectClass(name); |
| | | if (oc == null) |
| | | { |
| | | continue; |
| | | } |
| | | else if (existingClass == null) |
| | | { |
| | | existingClass = oc; |
| | | } |
| | | else if (existingClass != oc) |
| | | { |
| | | // NOTE: We really do want to use "!=" instead of "! t.equals()" |
| | | // because we want to check whether it's the same object instance, not |
| | | // just a logical equivalent. |
| | | int msgID = MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_OBJECTCLASS; |
| | | String message = getMessage(msgID, objectClass.getNameOrOID(), |
| | | existingClass.getNameOrOID(), |
| | | oc.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the new objectclass doesn't reference an undefined |
| | | // superior class, or an undefined required or optional attribute type. |
| | | ObjectClass superiorClass = objectClass.getSuperiorClass(); |
| | | if (superiorClass != null) |
| | | { |
| | | if (! schema.hasObjectClass(superiorClass.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_UNDEFINED_SUPERIOR_OBJECTCLASS; |
| | | String message = getMessage(msgID, objectClass.getNameOrOID(), |
| | | superiorClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | for (AttributeType at : objectClass.getRequiredAttributes()) |
| | | { |
| | | if (! schema.hasAttributeType(at.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_OC_UNDEFINED_REQUIRED_ATTR; |
| | | String message = getMessage(msgID, objectClass.getNameOrOID(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | for (AttributeType at : objectClass.getOptionalAttributes()) |
| | | { |
| | | if (! schema.hasAttributeType(at.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_OC_UNDEFINED_OPTIONAL_ATTR; |
| | | String message = getMessage(msgID, objectClass.getNameOrOID(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // If there is no existing class, then we're adding a new objectclass. |
| | | // Otherwise, we're replacing an existing one. |
| | | if (existingClass == null) |
| | | { |
| | | schema.registerObjectClass(objectClass, false); |
| | | String schemaFile = objectClass.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | objectClass.setSchemaFile(schemaFile); |
| | | } |
| | | |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | schema.deregisterObjectClass(existingClass); |
| | | schema.registerObjectClass(objectClass, false); |
| | | schema.rebuildDependentElements(existingClass); |
| | | |
| | | if ((objectClass.getSchemaFile() == null) || |
| | | (objectClass.getSchemaFile().length() == 0)) |
| | | { |
| | | String schemaFile = existingClass.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | } |
| | | |
| | | objectClass.setSchemaFile(schemaFile); |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | String newSchemaFile = objectClass.getSchemaFile(); |
| | | String oldSchemaFile = existingClass.getSchemaFile(); |
| | | if ((oldSchemaFile == null) || oldSchemaFile.equals(newSchemaFile)) |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | } |
| | | else |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | modifiedSchemaFiles.add(oldSchemaFile); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required to remove the provided objectclass from the |
| | | * server schema, ensuring all other metadata is properly updated. Note that |
| | | * this method will first check to see whether the same objectclass will be |
| | | * later added to the server schema with an updated definition, and if so then |
| | | * the removal will be ignored because the later add will be handled as a |
| | | * replace. If the objectclass will not be replaced with a new definition, |
| | | * then this method will ensure that there are no other schema elements that |
| | | * depend on the objectclass before allowing it to be removed. |
| | | * |
| | | * @param objectClass The objectclass to remove from the server |
| | | * schema. |
| | | * @param schema The schema from which the objectclass should |
| | | * be removed. |
| | | * @param modifications The full set of modifications to be processed |
| | | * against the server schema. |
| | | * @param currentPosition The position of the modification currently |
| | | * being performed. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to remove |
| | | * the provided objectclass from the server |
| | | * schema. |
| | | */ |
| | | private void removeObjectClass(ObjectClass objectClass, Schema schema, |
| | | ArrayList<Modification> modifications, |
| | | int currentPosition, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeObjectClass", |
| | | String.valueOf(objectClass), String.valueOf(schema), |
| | | String.valueOf(modifications), |
| | | String.valueOf(currentPosition), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // See if the specified objectclass is actually defined in the server |
| | | // schema. If not, then fail. |
| | | ObjectClass removeClass = schema.getObjectClass(objectClass.getOID()); |
| | | if ((removeClass == null) || (! removeClass.equals(objectClass))) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_OBJECTCLASS; |
| | | String message = getMessage(msgID, objectClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // See if there is another modification later to add the objectclass back |
| | | // into the schema. If so, then it's a replace and we should ignore the |
| | | // remove because adding it back will handle the replace. |
| | | for (int i=currentPosition+1; i < modifications.size(); i++) |
| | | { |
| | | Modification m = modifications.get(i); |
| | | Attribute a = m.getAttribute(); |
| | | |
| | | if ((m.getModificationType() != ModificationType.ADD) || |
| | | (! a.getAttributeType().equals(objectClassesType))) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | for (AttributeValue v : a.getValues()) |
| | | { |
| | | ObjectClass oc; |
| | | try |
| | | { |
| | | oc = ObjectClassSyntax.decodeObjectClass(v.getValue(), schema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "removeObjectClass", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_OBJECTCLASS; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | if (objectClass.getOID().equals(oc.getOID())) |
| | | { |
| | | // We found a match where the objectClass is added back later, so we |
| | | // don't need to do anything else here. |
| | | return; |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the objectclass isn't used as the superior class for any |
| | | // other objectclass. |
| | | for (ObjectClass oc : schema.getObjectClasses().values()) |
| | | { |
| | | ObjectClass superiorClass = oc.getSuperiorClass(); |
| | | if ((superiorClass != null) && superiorClass.equals(removeClass)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_OC_SUPERIOR_CLASS; |
| | | String message = getMessage(msgID, removeClass.getNameOrOID(), |
| | | superiorClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the objectclass isn't used as the structural class for |
| | | // any name form. |
| | | NameForm nf = schema.getNameForm(removeClass); |
| | | if (nf != null) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_OC_IN_NF; |
| | | String message = getMessage(msgID, removeClass.getNameOrOID(), |
| | | nf.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // Make sure that the objectclass isn't used as a structural or auxiliary |
| | | // class for any DIT content rule. |
| | | for (DITContentRule dcr : schema.getDITContentRules().values()) |
| | | { |
| | | if (dcr.getStructuralClass().equals(removeClass) || |
| | | dcr.getAuxiliaryClasses().contains(removeClass)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_OC_IN_DCR; |
| | | String message = getMessage(msgID, removeClass.getNameOrOID(), |
| | | dcr.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // If we've gotten here, then it's OK to remove the objectclass from the |
| | | // schema. |
| | | schema.deregisterObjectClass(removeClass); |
| | | String schemaFile = removeClass.getSchemaFile(); |
| | | if (schemaFile != null) |
| | | { |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required for adding the provided name form to the |
| | | * the given schema, replacing an existing name form if necessary, and |
| | | * ensuring all other metadata is properly updated. |
| | | * |
| | | * @param nameForm The name form to add or replace in the server |
| | | * schema. |
| | | * @param schema The schema to which the name form should be |
| | | * added. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to add |
| | | * the provided name form to the server schema. |
| | | */ |
| | | private void addNameForm(NameForm nameForm, Schema schema, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addNameForm", String.valueOf(nameForm), |
| | | String.valueOf(schema), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // First, see if the specified name form already exists. We'll check the |
| | | // OID and all of the names, which means that it's possible there could be |
| | | // more than one match (although if there is, then we'll refuse the |
| | | // operation). |
| | | NameForm existingNF = |
| | | schema.getNameForm(nameForm.getOID()); |
| | | for (String name : nameForm.getNames().keySet()) |
| | | { |
| | | NameForm nf = schema.getNameForm(name); |
| | | if (nf == null) |
| | | { |
| | | continue; |
| | | } |
| | | else if (existingNF == null) |
| | | { |
| | | existingNF = nf; |
| | | } |
| | | else if (existingNF != nf) |
| | | { |
| | | // NOTE: We really do want to use "!=" instead of "! t.equals()" |
| | | // because we want to check whether it's the same object instance, not |
| | | // just a logical equivalent. |
| | | int msgID = MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_NAME_FORM; |
| | | String message = getMessage(msgID, nameForm.getNameOrOID(), |
| | | existingNF.getNameOrOID(), |
| | | nf.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the new name form doesn't reference an undefined |
| | | // structural class, or an undefined required or optional attribute type. |
| | | ObjectClass structuralClass = nameForm.getStructuralClass(); |
| | | if (! schema.hasObjectClass(structuralClass.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_NF_UNDEFINED_STRUCTURAL_OC; |
| | | String message = getMessage(msgID, nameForm.getNameOrOID(), |
| | | structuralClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | if (structuralClass.getObjectClassType() != ObjectClassType.STRUCTURAL) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_NF_OC_NOT_STRUCTURAL; |
| | | String message = getMessage(msgID, nameForm.getNameOrOID(), |
| | | structuralClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | NameForm existingNFForClass = schema.getNameForm(structuralClass); |
| | | if ((existingNFForClass != null) && (existingNFForClass != existingNF)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_STRUCTURAL_OC_CONFLICT_FOR_ADD_NF; |
| | | String message = getMessage(msgID, nameForm.getNameOrOID(), |
| | | structuralClass.getNameOrOID(), |
| | | existingNFForClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | for (AttributeType at : nameForm.getRequiredAttributes()) |
| | | { |
| | | if (! schema.hasAttributeType(at.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_NF_UNDEFINED_REQUIRED_ATTR; |
| | | String message = getMessage(msgID, nameForm.getNameOrOID(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | for (AttributeType at : nameForm.getOptionalAttributes()) |
| | | { |
| | | if (! schema.hasAttributeType(at.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_NF_UNDEFINED_OPTIONAL_ATTR; |
| | | String message = getMessage(msgID, nameForm.getNameOrOID(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // If there is no existing class, then we're adding a new name form. |
| | | // Otherwise, we're replacing an existing one. |
| | | if (existingNF == null) |
| | | { |
| | | schema.registerNameForm(nameForm, false); |
| | | String schemaFile = nameForm.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | nameForm.setSchemaFile(schemaFile); |
| | | } |
| | | |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | schema.deregisterNameForm(existingNF); |
| | | schema.registerNameForm(nameForm, false); |
| | | schema.rebuildDependentElements(existingNF); |
| | | |
| | | if ((nameForm.getSchemaFile() == null) || |
| | | (nameForm.getSchemaFile().length() == 0)) |
| | | { |
| | | String schemaFile = existingNF.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | } |
| | | |
| | | nameForm.setSchemaFile(schemaFile); |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | String newSchemaFile = nameForm.getSchemaFile(); |
| | | String oldSchemaFile = existingNF.getSchemaFile(); |
| | | if ((oldSchemaFile == null) || oldSchemaFile.equals(newSchemaFile)) |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | } |
| | | else |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | modifiedSchemaFiles.add(oldSchemaFile); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required to remove the provided name form from the |
| | | * server schema, ensuring all other metadata is properly updated. Note that |
| | | * this method will first check to see whether the same name form will be |
| | | * later added to the server schema with an updated definition, and if so then |
| | | * the removal will be ignored because the later add will be handled as a |
| | | * replace. If the name form will not be replaced with a new definition, then |
| | | * this method will ensure that there are no other schema elements that depend |
| | | * on the name form before allowing it to be removed. |
| | | * |
| | | * @param nameForm The name form to remove from the server |
| | | * schema. |
| | | * @param schema The schema from which the name form should be |
| | | * be removed. |
| | | * @param modifications The full set of modifications to be processed |
| | | * against the server schema. |
| | | * @param currentPosition The position of the modification currently |
| | | * being performed. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to remove |
| | | * the provided name form from the server schema. |
| | | */ |
| | | private void removeNameForm(NameForm nameForm, Schema schema, |
| | | ArrayList<Modification> modifications, |
| | | int currentPosition, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeNameForm", |
| | | String.valueOf(nameForm), String.valueOf(schema), |
| | | String.valueOf(modifications), |
| | | String.valueOf(currentPosition), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // See if the specified name form is actually defined in the server schema. |
| | | // If not, then fail. |
| | | NameForm removeNF = schema.getNameForm(nameForm.getOID()); |
| | | if ((removeNF == null) || (! removeNF.equals(nameForm))) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_NAME_FORM; |
| | | String message = getMessage(msgID, nameForm.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // See if there is another modification later to add the name form back |
| | | // into the schema. If so, then it's a replace and we should ignore the |
| | | // remove because adding it back will handle the replace. |
| | | for (int i=currentPosition+1; i < modifications.size(); i++) |
| | | { |
| | | Modification m = modifications.get(i); |
| | | Attribute a = m.getAttribute(); |
| | | |
| | | if ((m.getModificationType() != ModificationType.ADD) || |
| | | (! a.getAttributeType().equals(nameFormsType))) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | for (AttributeValue v : a.getValues()) |
| | | { |
| | | NameForm nf; |
| | | try |
| | | { |
| | | nf = NameFormSyntax.decodeNameForm(v.getValue(), schema); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "removeNameForm", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_NAME_FORM; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | if (nameForm.getOID().equals(nf.getOID())) |
| | | { |
| | | // We found a match where the name form is added back later, so we |
| | | // don't need to do anything else here. |
| | | return; |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the name form isn't referenced by any DIT structure |
| | | // rule. |
| | | DITStructureRule dsr = schema.getDITStructureRule(removeNF); |
| | | if (dsr != null) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_NF_IN_DSR; |
| | | String message = getMessage(msgID, removeNF.getNameOrOID(), |
| | | dsr.getNameOrRuleID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // If we've gotten here, then it's OK to remove the name form from the |
| | | // schema. |
| | | schema.deregisterNameForm(removeNF); |
| | | String schemaFile = removeNF.getSchemaFile(); |
| | | if (schemaFile != null) |
| | | { |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required for adding the provided DIT content rule to |
| | | * the given schema, replacing an existing rule if necessary, and ensuring |
| | | * all other metadata is properly updated. |
| | | * |
| | | * @param ditContentRule The DIT content rule to add or replace in the |
| | | * server schema. |
| | | * @param schema The schema to which the DIT content rule |
| | | * should be be added. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to add |
| | | * the provided DIT content rule to the server |
| | | * schema. |
| | | */ |
| | | private void addDITContentRule(DITContentRule ditContentRule, Schema schema, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addDITContentRule", |
| | | String.valueOf(ditContentRule), String.valueOf(schema), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // First, see if the specified DIT content rule already exists. We'll check |
| | | // all of the names, which means that it's possible there could be more than |
| | | // one match (although if there is, then we'll refuse the operation). |
| | | DITContentRule existingDCR = null; |
| | | for (DITContentRule dcr : schema.getDITContentRules().values()) |
| | | { |
| | | for (String name : ditContentRule.getNames().keySet()) |
| | | { |
| | | if (dcr.hasName(name)) |
| | | { |
| | | if (existingDCR == null) |
| | | { |
| | | existingDCR = dcr; |
| | | break; |
| | | } |
| | | else |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_DCR; |
| | | String message = getMessage(msgID, ditContentRule.getName(), |
| | | existingDCR.getName(), |
| | | dcr.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | // Get the structural class for the new DIT content rule and see if there's |
| | | // already an existing rule that is associated with that class. If there |
| | | // is, then it will only be acceptable if it's the DIT content rule that we |
| | | // are replacing (in which case we really do want to use the "!=" operator). |
| | | ObjectClass structuralClass = ditContentRule.getStructuralClass(); |
| | | DITContentRule existingRuleForClass = |
| | | schema.getDITContentRule(structuralClass); |
| | | if ((existingRuleForClass != null) && (existingRuleForClass != existingDCR)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_STRUCTURAL_OC_CONFLICT_FOR_ADD_DCR; |
| | | String message = getMessage(msgID, ditContentRule.getName(), |
| | | structuralClass.getNameOrOID(), |
| | | existingRuleForClass.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // Make sure that the new DIT content rule doesn't reference an undefined |
| | | // structural or auxiliaryclass, or an undefined required, optional, or |
| | | // prohibited attribute type. |
| | | if (! schema.hasObjectClass(structuralClass.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_STRUCTURAL_OC; |
| | | String message = getMessage(msgID, ditContentRule.getName(), |
| | | structuralClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | if (structuralClass.getObjectClassType() != ObjectClassType.STRUCTURAL) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_DCR_OC_NOT_STRUCTURAL; |
| | | String message = getMessage(msgID, ditContentRule.getName(), |
| | | structuralClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | for (ObjectClass oc : ditContentRule.getAuxiliaryClasses()) |
| | | { |
| | | if (! schema.hasObjectClass(oc.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_AUXILIARY_OC; |
| | | String message = getMessage(msgID, ditContentRule.getName(), |
| | | oc.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | for (AttributeType at : ditContentRule.getRequiredAttributes()) |
| | | { |
| | | if (! schema.hasAttributeType(at.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_REQUIRED_ATTR; |
| | | String message = getMessage(msgID, ditContentRule.getName(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | for (AttributeType at : ditContentRule.getOptionalAttributes()) |
| | | { |
| | | if (! schema.hasAttributeType(at.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_OPTIONAL_ATTR; |
| | | String message = getMessage(msgID, ditContentRule.getName(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | for (AttributeType at : ditContentRule.getProhibitedAttributes()) |
| | | { |
| | | if (! schema.hasAttributeType(at.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_PROHIBITED_ATTR; |
| | | String message = getMessage(msgID, ditContentRule.getName(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // If there is no existing rule, then we're adding a new DIT content rule. |
| | | // Otherwise, we're replacing an existing one. |
| | | if (existingDCR == null) |
| | | { |
| | | schema.registerDITContentRule(ditContentRule, false); |
| | | String schemaFile = ditContentRule.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | ditContentRule.setSchemaFile(schemaFile); |
| | | } |
| | | |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | schema.deregisterDITContentRule(existingDCR); |
| | | schema.registerDITContentRule(ditContentRule, false); |
| | | schema.rebuildDependentElements(existingDCR); |
| | | |
| | | if ((ditContentRule.getSchemaFile() == null) || |
| | | (ditContentRule.getSchemaFile().length() == 0)) |
| | | { |
| | | String schemaFile = existingDCR.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | } |
| | | |
| | | ditContentRule.setSchemaFile(schemaFile); |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | String newSchemaFile = ditContentRule.getSchemaFile(); |
| | | String oldSchemaFile = existingDCR.getSchemaFile(); |
| | | if ((oldSchemaFile == null) || oldSchemaFile.equals(newSchemaFile)) |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | } |
| | | else |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | modifiedSchemaFiles.add(oldSchemaFile); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required to remove the provided DIT content rule |
| | | * from the server schema, ensuring all other metadata is properly updated. |
| | | * Note that this method will first check to see whether the same rule will be |
| | | * later added to the server schema with an updated definition, and if so then |
| | | * the removal will be ignored because the later add will be handled as a |
| | | * replace. If the DIT content rule will not be replaced with a new |
| | | * definition, then this method will ensure that there are no other schema |
| | | * elements that depend on the rule before allowing it to be removed. |
| | | * |
| | | * @param ditContentRule The DIT content rule to remove from the server |
| | | * schema. |
| | | * @param schema The schema from which the DIT content rule |
| | | * should be removed. |
| | | * @param modifications The full set of modifications to be processed |
| | | * against the server schema. |
| | | * @param currentPosition The position of the modification currently |
| | | * being performed. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to remove |
| | | * the provided DIT content rule from the server |
| | | * schema. |
| | | */ |
| | | private void removeDITContentRule(DITContentRule ditContentRule, |
| | | Schema schema, |
| | | ArrayList<Modification> modifications, |
| | | int currentPosition, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeDITContentRule", |
| | | String.valueOf(ditContentRule), String.valueOf(schema), |
| | | String.valueOf(modifications), |
| | | String.valueOf(currentPosition), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // See if the specified DIT content rule is actually defined in the server |
| | | // schema. If not, then fail. |
| | | DITContentRule removeDCR = |
| | | schema.getDITContentRule(ditContentRule.getStructuralClass()); |
| | | if ((removeDCR == null) || (! removeDCR.equals(ditContentRule))) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_DCR; |
| | | String message = getMessage(msgID, ditContentRule.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // Since DIT content rules don't have any dependencies, then we don't need |
| | | // to worry about the difference between a remove or a replace. We can |
| | | // just remove the DIT content rule now, and if it is added back later then |
| | | // there still won't be any conflict. |
| | | schema.deregisterDITContentRule(removeDCR); |
| | | String schemaFile = removeDCR.getSchemaFile(); |
| | | if (schemaFile != null) |
| | | { |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required for adding the provided DIT structure rule |
| | | * to the given schema, replacing an existing rule if necessary, and ensuring |
| | | * all other metadata is properly updated. |
| | | * |
| | | * @param ditStructureRule The DIT structure rule to add or replace in |
| | | * the server schema. |
| | | * @param schema The schema to which the DIT structure rule |
| | | * should be be added. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to add |
| | | * the provided DIT structure rule to the server |
| | | * schema. |
| | | */ |
| | | private void addDITStructureRule(DITStructureRule ditStructureRule, |
| | | Schema schema, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addDITStructureRule", |
| | | String.valueOf(ditStructureRule), String.valueOf(schema), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // First, see if the specified DIT structure rule already exists. We'll |
| | | // check the rule ID and all of the names, which means that it's possible |
| | | // there could be more than one match (although if there is, then we'll |
| | | // refuse the operation). |
| | | DITStructureRule existingDSR = |
| | | schema.getDITStructureRule(ditStructureRule.getRuleID()); |
| | | for (DITStructureRule dsr : schema.getDITStructureRulesByID().values()) |
| | | { |
| | | for (String name : ditStructureRule.getNames().keySet()) |
| | | { |
| | | if (dsr.hasName(name)) |
| | | { |
| | | // We really do want to use the "!=" operator here because it's |
| | | // acceptable if we find match for the same object instance. |
| | | if ((existingDSR != null) && (existingDSR != dsr)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_DSR; |
| | | String message = getMessage(msgID, |
| | | ditStructureRule.getNameOrRuleID(), |
| | | existingDSR.getNameOrRuleID(), |
| | | dsr.getNameOrRuleID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | // Get the name form for the new DIT structure rule and see if there's |
| | | // already an existing rule that is associated with that name form. If |
| | | // there is, then it will only be acceptable if it's the DIT structure rule |
| | | // that we are replacing (in which case we really do want to use the "!=" |
| | | // operator). |
| | | NameForm nameForm = ditStructureRule.getNameForm(); |
| | | DITStructureRule existingRuleForNameForm = |
| | | schema.getDITStructureRule(nameForm); |
| | | if ((existingRuleForNameForm != null) && |
| | | (existingRuleForNameForm != existingDSR)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_NAME_FORM_CONFLICT_FOR_ADD_DSR; |
| | | String message = getMessage(msgID, ditStructureRule.getNameOrRuleID(), |
| | | nameForm.getNameOrOID(), |
| | | existingRuleForNameForm.getNameOrRuleID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // Make sure that the new DIT structure rule doesn't reference an undefined |
| | | // name form or superior DIT structure rule. |
| | | if (! schema.hasNameForm(nameForm.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_DSR_UNDEFINED_NAME_FORM; |
| | | String message = getMessage(msgID, ditStructureRule.getNameOrRuleID(), |
| | | nameForm.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // If there is no existing rule, then we're adding a new DIT structure rule. |
| | | // Otherwise, we're replacing an existing one. |
| | | if (existingDSR == null) |
| | | { |
| | | schema.registerDITStructureRule(ditStructureRule, false); |
| | | String schemaFile = ditStructureRule.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | ditStructureRule.setSchemaFile(schemaFile); |
| | | } |
| | | |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | schema.deregisterDITStructureRule(existingDSR); |
| | | schema.registerDITStructureRule(ditStructureRule, false); |
| | | schema.rebuildDependentElements(existingDSR); |
| | | |
| | | if ((ditStructureRule.getSchemaFile() == null) || |
| | | (ditStructureRule.getSchemaFile().length() == 0)) |
| | | { |
| | | String schemaFile = existingDSR.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | } |
| | | |
| | | ditStructureRule.setSchemaFile(schemaFile); |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | String newSchemaFile = ditStructureRule.getSchemaFile(); |
| | | String oldSchemaFile = existingDSR.getSchemaFile(); |
| | | if ((oldSchemaFile == null) || oldSchemaFile.equals(newSchemaFile)) |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | } |
| | | else |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | modifiedSchemaFiles.add(oldSchemaFile); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required to remove the provided DIT structure rule |
| | | * from the server schema, ensuring all other metadata is properly updated. |
| | | * Note that this method will first check to see whether the same rule will be |
| | | * later added to the server schema with an updated definition, and if so then |
| | | * the removal will be ignored because the later add will be handled as a |
| | | * replace. If the DIT structure rule will not be replaced with a new |
| | | * definition, then this method will ensure that there are no other schema |
| | | * elements that depend on the rule before allowing it to be removed. |
| | | * |
| | | * @param ditStructureRule The DIT structure rule to remove from the |
| | | * server schema. |
| | | * @param schema The schema from which the DIT structure rule |
| | | * should be removed. |
| | | * @param modifications The full set of modifications to be processed |
| | | * against the server schema. |
| | | * @param currentPosition The position of the modification currently |
| | | * being performed. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to remove |
| | | * the provided DIT structure rule from the |
| | | * server schema. |
| | | */ |
| | | private void removeDITStructureRule(DITStructureRule ditStructureRule, |
| | | Schema schema, |
| | | ArrayList<Modification> modifications, |
| | | int currentPosition, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeDITStructureRule", |
| | | String.valueOf(ditStructureRule), String.valueOf(schema), |
| | | String.valueOf(modifications), |
| | | String.valueOf(currentPosition), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // See if the specified DIT structure rule is actually defined in the server |
| | | // schema. If not, then fail. |
| | | DITStructureRule removeDSR = |
| | | schema.getDITStructureRule(ditStructureRule.getRuleID()); |
| | | if ((removeDSR == null) || (! removeDSR.equals(ditStructureRule))) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_DSR; |
| | | String message = getMessage(msgID, ditStructureRule.getNameOrRuleID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // See if there is another modification later to add the DIT structure rule |
| | | // back into the schema. If so, then it's a replace and we should ignore |
| | | // the remove because adding it back will handle the replace. |
| | | for (int i=currentPosition+1; i < modifications.size(); i++) |
| | | { |
| | | Modification m = modifications.get(i); |
| | | Attribute a = m.getAttribute(); |
| | | |
| | | if ((m.getModificationType() != ModificationType.ADD) || |
| | | (! a.getAttributeType().equals(ditStructureRulesType))) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | for (AttributeValue v : a.getValues()) |
| | | { |
| | | DITStructureRule dsr; |
| | | try |
| | | { |
| | | dsr = DITStructureRuleSyntax.decodeDITStructureRule( |
| | | v.getValue(), schema, false); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | assert debugException(CLASS_NAME, "removeDITStructureRule", de); |
| | | |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_DECODE_DSR; |
| | | String message = getMessage(msgID, v.getStringValue(), |
| | | de.getErrorMessage()); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID, de); |
| | | } |
| | | |
| | | if (ditStructureRule.getRuleID() == dsr.getRuleID()) |
| | | { |
| | | // We found a match where the DIT structure rule is added back later, |
| | | // so we don't need to do anything else here. |
| | | return; |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | // Make sure that the DIT structure rule isn't the superior for any other |
| | | // DIT structure rule. |
| | | for (DITStructureRule dsr : schema.getDITStructureRulesByID().values()) |
| | | { |
| | | if (dsr.getSuperiorRules().contains(removeDSR)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_DSR_SUPERIOR_RULE; |
| | | String message = getMessage(msgID, removeDSR.getNameOrRuleID(), |
| | | dsr.getNameOrRuleID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // If we've gotten here, then it's OK to remove the DIT structure rule from |
| | | // the schema. |
| | | schema.deregisterDITStructureRule(removeDSR); |
| | | String schemaFile = removeDSR.getSchemaFile(); |
| | | if (schemaFile != null) |
| | | { |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required for adding the provided matching rule use |
| | | * to the given schema, replacing an existing use if necessary, and ensuring |
| | | * all other metadata is properly updated. |
| | | * |
| | | * @param matchingRuleUse The matching rule use to add or replace in the |
| | | * server schema. |
| | | * @param schema The schema to which the matching rule use |
| | | * should be added. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to add |
| | | * the provided matching rule use to the server |
| | | * schema. |
| | | */ |
| | | private void addMatchingRuleUse(MatchingRuleUse matchingRuleUse, |
| | | Schema schema, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addMatchingRuleUse", |
| | | String.valueOf(matchingRuleUse), String.valueOf(schema), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // First, see if the specified matching rule use already exists. We'll |
| | | // check all of the names, which means that it's possible that there could |
| | | // be more than one match (although if there is, then we'll refuse the |
| | | // operation). |
| | | MatchingRuleUse existingMRU = null; |
| | | for (MatchingRuleUse mru : schema.getMatchingRuleUses().values()) |
| | | { |
| | | for (String name : matchingRuleUse.getNames().keySet()) |
| | | { |
| | | if (mru.hasName(name)) |
| | | { |
| | | if (existingMRU == null) |
| | | { |
| | | existingMRU = mru; |
| | | break; |
| | | } |
| | | else |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_MR_USE; |
| | | String message = getMessage(msgID, matchingRuleUse.getName(), |
| | | existingMRU.getName(), mru.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | // Get the matching rule for the new matching rule use and see if there's |
| | | // already an existing matching rule use that is associated with that |
| | | // matching rule. If there is, then it will only be acceptable if it's the |
| | | // matching rule use that we are replacing (in which case we really do want |
| | | // to use the "!=" operator). |
| | | MatchingRule matchingRule = matchingRuleUse.getMatchingRule(); |
| | | MatchingRuleUse existingMRUForRule = |
| | | schema.getMatchingRuleUse(matchingRule); |
| | | if ((existingMRUForRule != null) && (existingMRUForRule != existingMRU)) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_MR_CONFLICT_FOR_ADD_MR_USE; |
| | | String message = getMessage(msgID, matchingRuleUse.getName(), |
| | | matchingRule.getNameOrOID(), |
| | | existingMRUForRule.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // Make sure that the new matching rule use doesn't reference an undefined |
| | | // attribute type. |
| | | for (AttributeType at : matchingRuleUse.getAttributes()) |
| | | { |
| | | if (! schema.hasAttributeType(at.getOID())) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_MRU_UNDEFINED_ATTR; |
| | | String message = getMessage(msgID, matchingRuleUse.getName(), |
| | | at.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | } |
| | | |
| | | |
| | | // If there is no existing matching rule use, then we're adding a new one. |
| | | // Otherwise, we're replacing an existing matching rule use. |
| | | if (existingMRU == null) |
| | | { |
| | | schema.registerMatchingRuleUse(matchingRuleUse, false); |
| | | String schemaFile = matchingRuleUse.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | matchingRuleUse.setSchemaFile(schemaFile); |
| | | } |
| | | |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | schema.deregisterMatchingRuleUse(existingMRU); |
| | | schema.registerMatchingRuleUse(matchingRuleUse, false); |
| | | schema.rebuildDependentElements(existingMRU); |
| | | |
| | | if ((matchingRuleUse.getSchemaFile() == null) || |
| | | (matchingRuleUse.getSchemaFile().length() == 0)) |
| | | { |
| | | String schemaFile = existingMRU.getSchemaFile(); |
| | | if ((schemaFile == null) || (schemaFile.length() == 0)) |
| | | { |
| | | schemaFile = FILE_USER_SCHEMA_ELEMENTS; |
| | | } |
| | | |
| | | matchingRuleUse.setSchemaFile(schemaFile); |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | else |
| | | { |
| | | String newSchemaFile = matchingRuleUse.getSchemaFile(); |
| | | String oldSchemaFile = existingMRU.getSchemaFile(); |
| | | if ((oldSchemaFile == null) || oldSchemaFile.equals(newSchemaFile)) |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | } |
| | | else |
| | | { |
| | | modifiedSchemaFiles.add(newSchemaFile); |
| | | modifiedSchemaFiles.add(oldSchemaFile); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Handles all processing required to remove the provided matching rule use |
| | | * from the server schema, ensuring all other metadata is properly updated. |
| | | * Note that this method will first check to see whether the same matching |
| | | * rule use will be later added to the server schema with an updated |
| | | * definition, and if so then the removal will be ignored because the later |
| | | * add will be handled as a replace. If the matching rule use will not be |
| | | * replaced with a new definition, then this method will ensure that there are |
| | | * no other schema elements that depend on the matching rule use before |
| | | * allowing it to be removed. |
| | | * |
| | | * @param matchingRuleUse The matching rule use to remove from the |
| | | * server schema. |
| | | * @param schema The schema from which the matching rule use |
| | | * should be removed. |
| | | * @param modifications The full set of modifications to be processed |
| | | * against the server schema. |
| | | * @param currentPosition The position of the modification currently |
| | | * being performed. |
| | | * @param modifiedSchemaFiles The names of the schema files containing |
| | | * schema elements that have been updated as part |
| | | * of the schema modification. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to remove |
| | | * the provided matching rule use from the server |
| | | * schema. |
| | | */ |
| | | private void removeMatchingRuleUse(MatchingRuleUse matchingRuleUse, |
| | | Schema schema, |
| | | ArrayList<Modification> modifications, |
| | | int currentPosition, |
| | | Set<String> modifiedSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeMatchingRuleUse", |
| | | String.valueOf(matchingRuleUse), String.valueOf(schema), |
| | | String.valueOf(modifications), |
| | | String.valueOf(currentPosition), |
| | | String.valueOf(modifiedSchemaFiles)); |
| | | |
| | | |
| | | // See if the specified DIT content rule is actually defined in the server |
| | | // schema. If not, then fail. |
| | | MatchingRuleUse removeMRU = |
| | | schema.getMatchingRuleUse(matchingRuleUse.getMatchingRule()); |
| | | if ((removeMRU == null) || (! removeMRU.equals(matchingRuleUse))) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_MR_USE; |
| | | String message = getMessage(msgID, matchingRuleUse.getName()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | |
| | | // Since matching rule uses don't have any dependencies, then we don't need |
| | | // to worry about the difference between a remove or a replace. We can |
| | | // just remove the DIT content rule now, and if it is added back later then |
| | | // there still won't be any conflict. |
| | | schema.deregisterMatchingRuleUse(removeMRU); |
| | | String schemaFile = removeMRU.getSchemaFile(); |
| | | if (schemaFile != null) |
| | | { |
| | | modifiedSchemaFiles.add(schemaFile); |
| | | } |
| | | } |
| | | |
| | | |
| | |
| | | |
| | | |
| | | |
| | | |
| | | /** |
| | | * Writes a temporary version of the specified schema file. |
| | | * |
| | | * @param schema The schema from which to take the definitions to be |
| | | * written. |
| | | * @param schemaFile The name of the schema file to be written. |
| | | * |
| | | * @throws DirectoryException If an unexpected problem occurs while |
| | | * identifying the schema definitions to include |
| | | * in the schema file. |
| | | * |
| | | * @throws IOException If an unexpected error occurs while attempting to |
| | | * write the temporary schema file. |
| | | * |
| | | * @throws LDIFException If an unexpected problem occurs while generating |
| | | * the LDIF representation of the schema entry. |
| | | */ |
| | | private File writeTempSchemaFile(Schema schema, String schemaFile) |
| | | throws DirectoryException, IOException, LDIFException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "writeTempSchemaFile", String.valueOf(schema), |
| | | String.valueOf(schemaFile)); |
| | | |
| | | |
| | | // Start with an empty schema entry. |
| | | Entry schemaEntry = createEmptySchemaEntry(); |
| | | |
| | | |
| | | // Add all of the appropriate attribute types to the schema entry. We need |
| | | // to be careful of the ordering to ensure that any superior types in the |
| | | // same file are written before the subordinate types. |
| | | HashSet<AttributeType> addedTypes = new HashSet<AttributeType>(); |
| | | LinkedHashSet<AttributeValue> values = new LinkedHashSet<AttributeValue>(); |
| | | for (AttributeType at : schema.getAttributeTypes().values()) |
| | | { |
| | | if (schemaFile.equals(at.getSchemaFile())) |
| | | { |
| | | addAttrTypeToSchemaFile(schema, schemaFile, at, values, addedTypes, 0); |
| | | } |
| | | } |
| | | |
| | | if (! values.isEmpty()) |
| | | { |
| | | ArrayList<Attribute> attrList = new ArrayList<Attribute>(1); |
| | | attrList.add(new Attribute(attributeTypesType, |
| | | attributeTypesType.getPrimaryName(), values)); |
| | | schemaEntry.putAttribute(attributeTypesType, attrList); |
| | | } |
| | | |
| | | |
| | | // Add all of the appropriate objectclasses to the schema entry. We need |
| | | // to be careful of the ordering to ensure that any superior classes in the |
| | | // same file are written before the subordinate classes. |
| | | HashSet<ObjectClass> addedClasses = new HashSet<ObjectClass>(); |
| | | values = new LinkedHashSet<AttributeValue>(); |
| | | for (ObjectClass oc : schema.getObjectClasses().values()) |
| | | { |
| | | if (schemaFile.equals(oc.getSchemaFile())) |
| | | { |
| | | addObjectClassToSchemaFile(schema, schemaFile, oc, values, addedClasses, |
| | | 0); |
| | | } |
| | | } |
| | | |
| | | if (! values.isEmpty()) |
| | | { |
| | | ArrayList<Attribute> attrList = new ArrayList<Attribute>(1); |
| | | attrList.add(new Attribute(objectClassesType, |
| | | objectClassesType.getPrimaryName(), values)); |
| | | schemaEntry.putAttribute(objectClassesType, attrList); |
| | | } |
| | | |
| | | |
| | | // Add all of the appropriate name forms to the schema entry. Since there |
| | | // is no hierarchical relationship between name forms, we don't need to |
| | | // worry about ordering. |
| | | values = new LinkedHashSet<AttributeValue>(); |
| | | for (NameForm nf : schema.getNameFormsByObjectClass().values()) |
| | | { |
| | | if (schemaFile.equals(nf.getSchemaFile())) |
| | | { |
| | | values.add(new AttributeValue(nameFormsType, nf.getDefinition())); |
| | | } |
| | | } |
| | | |
| | | if (! values.isEmpty()) |
| | | { |
| | | ArrayList<Attribute> attrList = new ArrayList<Attribute>(1); |
| | | attrList.add(new Attribute(nameFormsType, |
| | | nameFormsType.getPrimaryName(), values)); |
| | | schemaEntry.putAttribute(nameFormsType, attrList); |
| | | } |
| | | |
| | | |
| | | // Add all of the appropriate DIT content rules to the schema entry. Since |
| | | // there is no hierarchical relationship between DIT content rules, we don't |
| | | // need to worry about ordering. |
| | | values = new LinkedHashSet<AttributeValue>(); |
| | | for (DITContentRule dcr : schema.getDITContentRules().values()) |
| | | { |
| | | if (schemaFile.equals(dcr.getSchemaFile())) |
| | | { |
| | | values.add(new AttributeValue(ditContentRulesType, |
| | | dcr.getDefinition())); |
| | | } |
| | | } |
| | | |
| | | if (! values.isEmpty()) |
| | | { |
| | | ArrayList<Attribute> attrList = new ArrayList<Attribute>(1); |
| | | attrList.add(new Attribute(ditContentRulesType, |
| | | ditContentRulesType.getPrimaryName(), values)); |
| | | schemaEntry.putAttribute(ditContentRulesType, attrList); |
| | | } |
| | | |
| | | |
| | | // Add all of the appropriate DIT structure rules to the schema entry. We |
| | | // need to be careful of the ordering to ensure that any superior rules in |
| | | // the same file are written before the subordinate rules. |
| | | HashSet<DITStructureRule> addedDSRs = new HashSet<DITStructureRule>(); |
| | | values = new LinkedHashSet<AttributeValue>(); |
| | | for (DITStructureRule dsr : schema.getDITStructureRulesByID().values()) |
| | | { |
| | | if (schemaFile.equals(dsr.getSchemaFile())) |
| | | { |
| | | addDITStructureRuleToSchemaFile(schema, schemaFile, dsr, values, |
| | | addedDSRs, 0); |
| | | } |
| | | } |
| | | |
| | | if (! values.isEmpty()) |
| | | { |
| | | ArrayList<Attribute> attrList = new ArrayList<Attribute>(1); |
| | | attrList.add(new Attribute(ditStructureRulesType, |
| | | ditStructureRulesType.getPrimaryName(), |
| | | values)); |
| | | schemaEntry.putAttribute(ditStructureRulesType, attrList); |
| | | } |
| | | |
| | | |
| | | // Add all of the appropriate matching rule uses to the schema entry. Since |
| | | // there is no hierarchical relationship between matching rule uses, we |
| | | // don't need to worry about ordering. |
| | | values = new LinkedHashSet<AttributeValue>(); |
| | | for (MatchingRuleUse mru : schema.getMatchingRuleUses().values()) |
| | | { |
| | | if (schemaFile.equals(mru.getSchemaFile())) |
| | | { |
| | | values.add(new AttributeValue(matchingRuleUsesType, |
| | | mru.getDefinition())); |
| | | } |
| | | } |
| | | |
| | | if (! values.isEmpty()) |
| | | { |
| | | ArrayList<Attribute> attrList = new ArrayList<Attribute>(1); |
| | | attrList.add(new Attribute(matchingRuleUsesType, |
| | | matchingRuleUsesType.getPrimaryName(), |
| | | values)); |
| | | schemaEntry.putAttribute(matchingRuleUsesType, attrList); |
| | | } |
| | | |
| | | |
| | | // Create a temporary file to which we can write the schema entry. |
| | | File tempFile = File.createTempFile(schemaFile, "temp"); |
| | | LDIFExportConfig exportConfig = |
| | | new LDIFExportConfig(tempFile.getAbsolutePath(), |
| | | ExistingFileBehavior.OVERWRITE); |
| | | LDIFWriter ldifWriter = new LDIFWriter(exportConfig); |
| | | ldifWriter.writeEntry(schemaEntry); |
| | | ldifWriter.close(); |
| | | |
| | | return tempFile; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the definition for the specified attribute type to the provided set of |
| | | * attribute values, recursively adding superior types as appropriate. |
| | | * |
| | | * @param schema The schema containing the attribute type. |
| | | * @param schemaFile The schema file with which the attribute type is |
| | | * associated. |
| | | * @param attributeType The attribute type whose definition should be added |
| | | * to the value set. |
| | | * @param values The set of values for attribute type definitions |
| | | * already added. |
| | | * @param addedTypes The set of attribute types whose definitions have |
| | | * already been added to the set of values. |
| | | * @param depth A depth counter to use in an attempt to detect |
| | | * circular references. |
| | | */ |
| | | private void addAttrTypeToSchemaFile(Schema schema, String schemaFile, |
| | | AttributeType attributeType, |
| | | LinkedHashSet<AttributeValue> values, |
| | | HashSet<AttributeType> addedTypes, |
| | | int depth) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addAttrTypeToSchemaFile", |
| | | String.valueOf(schema), String.valueOf(schemaFile), |
| | | String.valueOf(attributeType), String.valueOf(values), |
| | | String.valueOf(addedTypes), String.valueOf(depth)); |
| | | |
| | | if (depth > 20) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_CIRCULAR_REFERENCE_AT; |
| | | String message = getMessage(msgID, attributeType.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | if (addedTypes.contains(attributeType)) |
| | | { |
| | | return; |
| | | } |
| | | |
| | | AttributeType superiorType = attributeType.getSuperiorType(); |
| | | if ((superiorType != null) && |
| | | schemaFile.equals(superiorType.getSchemaFile()) && |
| | | (! addedTypes.contains(superiorType))) |
| | | { |
| | | addAttrTypeToSchemaFile(schema, schemaFile, superiorType, values, |
| | | addedTypes, depth+1); |
| | | } |
| | | |
| | | values.add(new AttributeValue(attributeTypesType, |
| | | attributeType.getDefinition())); |
| | | addedTypes.add(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the definition for the specified objectclass to the provided set of |
| | | * attribute values, recursively adding superior classes as appropriate. |
| | | * |
| | | * @param schema The schema containing the objectclass. |
| | | * @param schemaFile The schema file with which the objectclass is |
| | | * associated. |
| | | * @param objectClass The objectclass whose definition should be added to |
| | | * the value set. |
| | | * @param values The set of values for objectclass definitions |
| | | * already added. |
| | | * @param addedClasses The set of objectclasses whose definitions have |
| | | * already been added to the set of values. |
| | | * @param depth A depth counter to use in an attempt to detect |
| | | * circular references. |
| | | */ |
| | | private void addObjectClassToSchemaFile(Schema schema, String schemaFile, |
| | | ObjectClass objectClass, |
| | | LinkedHashSet<AttributeValue> values, |
| | | HashSet<ObjectClass> addedClasses, |
| | | int depth) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addObjectClassToSchemaFile", |
| | | String.valueOf(schema), String.valueOf(schemaFile), |
| | | String.valueOf(objectClass), String.valueOf(values), |
| | | String.valueOf(addedClasses), String.valueOf(depth)); |
| | | |
| | | if (depth > 20) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_CIRCULAR_REFERENCE_OC; |
| | | String message = getMessage(msgID, objectClass.getNameOrOID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | if (addedClasses.contains(objectClass)) |
| | | { |
| | | return; |
| | | } |
| | | |
| | | ObjectClass superiorClass = objectClass.getSuperiorClass(); |
| | | if ((superiorClass != null) && |
| | | schemaFile.equals(superiorClass.getSchemaFile()) && |
| | | (! addedClasses.contains(superiorClass))) |
| | | { |
| | | addObjectClassToSchemaFile(schema, schemaFile, superiorClass, values, |
| | | addedClasses, depth+1); |
| | | } |
| | | |
| | | values.add(new AttributeValue(objectClassesType, |
| | | objectClass.getDefinition())); |
| | | addedClasses.add(objectClass); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the definition for the specified DIT structure rule to the provided |
| | | * set of attribute values, recursively adding superior rules as appropriate. |
| | | * |
| | | * @param schema The schema containing the DIT structure rule. |
| | | * @param schemaFile The schema file with which the DIT structure rule |
| | | * is associated. |
| | | * @param ditStructureRule The DIT structure rule whose definition should be |
| | | * added to the value set. |
| | | * @param values The set of values for DIT structure rule |
| | | * definitions already added. |
| | | * @param addedDSRs The set of DIT structure rules whose definitions |
| | | * have already been added added to the set of |
| | | * values. |
| | | * @param depth A depth counter to use in an attempt to detect |
| | | * circular references. |
| | | */ |
| | | private void addDITStructureRuleToSchemaFile(Schema schema, String schemaFile, |
| | | DITStructureRule ditStructureRule, |
| | | LinkedHashSet<AttributeValue> values, |
| | | HashSet<DITStructureRule> addedDSRs, int depth) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addDITStructureRuleToSchemaFile", |
| | | String.valueOf(schema), String.valueOf(schemaFile), |
| | | String.valueOf(ditStructureRule), String.valueOf(values), |
| | | String.valueOf(addedDSRs), String.valueOf(depth)); |
| | | |
| | | if (depth > 20) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_CIRCULAR_REFERENCE_DSR; |
| | | String message = getMessage(msgID, ditStructureRule.getNameOrRuleID()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, message, |
| | | msgID); |
| | | } |
| | | |
| | | if (addedDSRs.contains(ditStructureRule)) |
| | | { |
| | | return; |
| | | } |
| | | |
| | | for (DITStructureRule dsr : ditStructureRule.getSuperiorRules()) |
| | | { |
| | | if (schemaFile.equals(dsr.getSchemaFile()) && (! addedDSRs.contains(dsr))) |
| | | { |
| | | addDITStructureRuleToSchemaFile(schema, schemaFile, dsr, values, |
| | | addedDSRs, depth+1); |
| | | } |
| | | } |
| | | |
| | | values.add(new AttributeValue(ditStructureRulesType, |
| | | ditStructureRule.getDefinition())); |
| | | addedDSRs.add(ditStructureRule); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Moves the specified temporary schema files in place of the active versions. |
| | | * If an error occurs in the process, then this method will attempt to restore |
| | | * the original schema files if possible. |
| | | * |
| | | * @param tempSchemaFiles The set of temporary schema files to be activated. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting to |
| | | * install the temporary schema files. |
| | | */ |
| | | private void installSchemaFiles(HashMap<String,File> tempSchemaFiles) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "installSchemaFiles", |
| | | String.valueOf(tempSchemaFiles)); |
| | | |
| | | |
| | | // Create lists that will hold the three types of files we'll be dealing |
| | | // with (the temporary files that will be installed, the installed schema |
| | | // files, and the previously-installed schema files). |
| | | ArrayList<File> installedFileList = new ArrayList<File>(); |
| | | ArrayList<File> tempFileList = new ArrayList<File>(); |
| | | ArrayList<File> origFileList = new ArrayList<File>(); |
| | | |
| | | File schemaDir = new File(SchemaConfigManager.getSchemaDirectoryPath()); |
| | | |
| | | for (String name : tempSchemaFiles.keySet()) |
| | | { |
| | | installedFileList.add(new File(schemaDir, name)); |
| | | tempFileList.add(tempSchemaFiles.get(name)); |
| | | origFileList.add(new File(schemaDir, name + ".orig")); |
| | | } |
| | | |
| | | |
| | | // If there are any old ".orig" files laying around from a previous |
| | | // attempt, then try to clean them up. |
| | | for (File f : origFileList) |
| | | { |
| | | if (f.exists()) |
| | | { |
| | | f.delete(); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Copy all of the currently-installed files with a ".orig" extension. If |
| | | // this fails, then try to clean up the copies. |
| | | try |
| | | { |
| | | for (int i=0; i < installedFileList.size(); i++) |
| | | { |
| | | File installedFile = installedFileList.get(i); |
| | | File origFile = origFileList.get(i); |
| | | |
| | | if (installedFile.exists()) |
| | | { |
| | | copyFile(installedFile, origFile); |
| | | } |
| | | } |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | assert debugException(CLASS_NAME, "installSchemaFiles", e); |
| | | |
| | | boolean allCleaned = true; |
| | | for (File f : origFileList) |
| | | { |
| | | try |
| | | { |
| | | if (f.exists()) |
| | | { |
| | | if (! f.delete()) |
| | | { |
| | | allCleaned = false; |
| | | } |
| | | } |
| | | } |
| | | catch (Exception e2) |
| | | { |
| | | assert debugException(CLASS_NAME, "installSchemaFiles", e2); |
| | | |
| | | allCleaned = false; |
| | | } |
| | | } |
| | | |
| | | if (allCleaned) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_WRITE_ORIG_FILES_CLEANED; |
| | | String message = getMessage(msgID, stackTraceToSingleLineString(e)); |
| | | throw new DirectoryException(DirectoryServer.getServerErrorResultCode(), |
| | | message, msgID, e); |
| | | } |
| | | else |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_WRITE_ORIG_FILES_NOT_CLEANED; |
| | | String message = getMessage(msgID, stackTraceToSingleLineString(e)); |
| | | |
| | | DirectoryServer.sendAlertNotification(this, |
| | | ALERT_TYPE_CANNOT_COPY_SCHEMA_FILES, msgID, |
| | | message); |
| | | |
| | | throw new DirectoryException(DirectoryServer.getServerErrorResultCode(), |
| | | message, msgID, e); |
| | | } |
| | | } |
| | | |
| | | |
| | | // Try to copy all of the temporary files into place over the installed |
| | | // files. If this fails, then try to restore the originals. |
| | | try |
| | | { |
| | | for (int i=0; i < installedFileList.size(); i++) |
| | | { |
| | | File installedFile = installedFileList.get(i); |
| | | File tempFile = tempFileList.get(i); |
| | | copyFile(tempFile, installedFile); |
| | | } |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | assert debugException(CLASS_NAME, "installSchemaFiles", e); |
| | | |
| | | for (File f : installedFileList) |
| | | { |
| | | try |
| | | { |
| | | if (f.exists()) |
| | | { |
| | | f.delete(); |
| | | } |
| | | } |
| | | catch (Exception e2) |
| | | { |
| | | assert debugException(CLASS_NAME, "installSchemaFiles", e2); |
| | | } |
| | | } |
| | | |
| | | boolean allRestored = true; |
| | | for (int i=0; i < installedFileList.size(); i++) |
| | | { |
| | | File installedFile = installedFileList.get(i); |
| | | File origFile = origFileList.get(i); |
| | | |
| | | try |
| | | { |
| | | if (origFile.exists()) |
| | | { |
| | | if (! origFile.renameTo(installedFile)) |
| | | { |
| | | allRestored = false; |
| | | } |
| | | } |
| | | } |
| | | catch (Exception e2) |
| | | { |
| | | assert debugException(CLASS_NAME, "installSchemaFiles", e2); |
| | | |
| | | allRestored = false; |
| | | } |
| | | } |
| | | |
| | | if (allRestored) |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_WRITE_NEW_FILES_RESTORED; |
| | | String message = getMessage(msgID, stackTraceToSingleLineString(e)); |
| | | throw new DirectoryException(DirectoryServer.getServerErrorResultCode(), |
| | | message, msgID, e); |
| | | } |
| | | else |
| | | { |
| | | int msgID = MSGID_SCHEMA_MODIFY_CANNOT_WRITE_NEW_FILES_NOT_RESTORED; |
| | | String message = getMessage(msgID, stackTraceToSingleLineString(e)); |
| | | |
| | | DirectoryServer.sendAlertNotification(this, |
| | | ALERT_TYPE_CANNOT_WRITE_NEW_SCHEMA_FILES, msgID, |
| | | message); |
| | | |
| | | throw new DirectoryException(DirectoryServer.getServerErrorResultCode(), |
| | | message, msgID, e); |
| | | } |
| | | } |
| | | |
| | | |
| | | // At this point, we're committed to the schema change, so we can't throw |
| | | // any more exceptions, but all we have left is to clean up the original and |
| | | // temporary files. |
| | | for (File f : origFileList) |
| | | { |
| | | try |
| | | { |
| | | if (f.exists()) |
| | | { |
| | | f.delete(); |
| | | } |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | assert debugException(CLASS_NAME, "installSchemaFiles", e); |
| | | } |
| | | } |
| | | |
| | | for (File f : tempFileList) |
| | | { |
| | | try |
| | | { |
| | | if (f.exists()) |
| | | { |
| | | f.delete(); |
| | | } |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | assert debugException(CLASS_NAME, "installSchemaFiles", e); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a copy of the specified file. |
| | | * |
| | | * @param from The source file to be copied. |
| | | * @param to The destination file to be created. |
| | | * |
| | | * @throws IOException If a problem occurs. |
| | | */ |
| | | private void copyFile(File from, File to) |
| | | throws IOException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "copyFile", String.valueOf(from), |
| | | String.valueOf(to)); |
| | | |
| | | byte[] buffer = new byte[4096]; |
| | | FileInputStream inputStream = null; |
| | | FileOutputStream outputStream = null; |
| | | try |
| | | { |
| | | inputStream = new FileInputStream(from); |
| | | outputStream = new FileOutputStream(to, false); |
| | | |
| | | int bytesRead = inputStream.read(buffer); |
| | | while (bytesRead > 0) |
| | | { |
| | | outputStream.write(buffer, 0, bytesRead); |
| | | bytesRead = inputStream.read(buffer); |
| | | } |
| | | } |
| | | finally |
| | | { |
| | | if (inputStream != null) |
| | | { |
| | | try |
| | | { |
| | | inputStream.close(); |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | assert debugException(CLASS_NAME, "copyFile", e); |
| | | } |
| | | } |
| | | |
| | | if (outputStream != null) |
| | | { |
| | | outputStream.close(); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Performs any necessary cleanup in an attempt to delete any temporary schema |
| | | * files that may have been left over after trying to install the new schema. |
| | | * |
| | | * @param tempSchemaFiles The set of temporary schema files that have been |
| | | * created and are candidates for cleanup. |
| | | */ |
| | | private void cleanUpTempSchemaFiles(HashMap<String,File> tempSchemaFiles) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "cleanUpTempSchemaFiles", |
| | | String.valueOf(tempSchemaFiles)); |
| | | |
| | | if ((tempSchemaFiles == null) || tempSchemaFiles.isEmpty()) |
| | | { |
| | | return; |
| | | } |
| | | |
| | | for (File f : tempSchemaFiles.values()) |
| | | { |
| | | try |
| | | { |
| | | if (f.exists()) |
| | | { |
| | | f.delete(); |
| | | } |
| | | } |
| | | catch (Exception e) |
| | | { |
| | | assert debugException(CLASS_NAME, "cleanUpTempSchemaFiles", e); |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Moves and/or renames the provided entry in this backend, altering any |
| | | * subordinate entries as necessary. This must ensure that an entry already |
| | |
| | | |
| | | this.showAllAttributes = showAllAttributes; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the DN of the configuration entry with which this alert generator |
| | | * is associated. |
| | | * |
| | | * @return The DN of the configuration entry with which this alert generator |
| | | * is associated. |
| | | */ |
| | | public DN getComponentEntryDN() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getComponentEntryDN"); |
| | | |
| | | return configEntryDN; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the fully-qualified name of the Java class for this alert |
| | | * generator implementation. |
| | | * |
| | | * @return The fully-qualified name of the Java class for this alert |
| | | * generator implementation. |
| | | */ |
| | | public String getClassName() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getClassName"); |
| | | |
| | | return CLASS_NAME; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves information about the set of alerts that this generator may |
| | | * produce. The map returned should be between the notification type for a |
| | | * particular notification and the human-readable description for that |
| | | * notification. This alert generator must not generate any alerts with types |
| | | * that are not contained in this list. |
| | | * |
| | | * @return Information about the set of alerts that this generator may |
| | | * produce. |
| | | */ |
| | | public LinkedHashMap<String,String> getAlerts() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getAlerts"); |
| | | |
| | | LinkedHashMap<String,String> alerts = new LinkedHashMap<String,String>(); |
| | | |
| | | alerts.put(ALERT_TYPE_CANNOT_COPY_SCHEMA_FILES, |
| | | ALERT_DESCRIPTION_CANNOT_COPY_SCHEMA_FILES); |
| | | alerts.put(ALERT_TYPE_CANNOT_WRITE_NEW_SCHEMA_FILES, |
| | | ALERT_DESCRIPTION_CANNOT_WRITE_NEW_SCHEMA_FILES); |
| | | |
| | | return alerts; |
| | | } |
| | | } |
| | | |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.core; |
| | | |
| | |
| | | directoryServer.schema.getObjectClass(TOP_OBJECTCLASS_NAME); |
| | | if (objectClass == null) |
| | | { |
| | | objectClass = new ObjectClass(TOP_OBJECTCLASS_NAME, Collections |
| | | .singleton(TOP_OBJECTCLASS_NAME), TOP_OBJECTCLASS_OID, |
| | | TOP_OBJECTCLASS_DESCRIPTION, null, null, null, |
| | | ObjectClassType.ABSTRACT, false, null); |
| | | String definition = |
| | | "( 2.5.6.0 NAME 'top' ABSTRACT MUST objectClass " + |
| | | "X-ORIGIN 'RFC 2256' )"; |
| | | |
| | | objectClass = new ObjectClass(definition, TOP_OBJECTCLASS_NAME, |
| | | Collections.singleton(TOP_OBJECTCLASS_NAME), |
| | | TOP_OBJECTCLASS_OID, |
| | | TOP_OBJECTCLASS_DESCRIPTION, null, null, |
| | | null, ObjectClassType.ABSTRACT, false, |
| | | null); |
| | | } |
| | | |
| | | return objectClass; |
| | |
| | | ObjectClass objectClass = directoryServer.schema.getObjectClass(lowerName); |
| | | if (objectClass == null) |
| | | { |
| | | objectClass = new ObjectClass(name, |
| | | Collections.singleton(name), lowerName, null, |
| | | getTopObjectClass(), null, null, ObjectClassType.ABSTRACT, |
| | | false, null); |
| | | String oid = lowerName + "-oid"; |
| | | String definition = "( " + oid + " NAME '" + name + "' ABSTRACT )"; |
| | | |
| | | objectClass = new ObjectClass(definition, name, |
| | | Collections.singleton(name), oid, null, |
| | | getTopObjectClass(), null, null, |
| | | ObjectClassType.ABSTRACT, false, null); |
| | | } |
| | | |
| | | return objectClass; |
| | |
| | | } |
| | | } |
| | | |
| | | String definition = |
| | | "( 2.5.4.0 NAME 'objectClass' EQUALITY objectIdentifierMatch " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.38 X-ORIGIN 'RFC 2256' )"; |
| | | |
| | | directoryServer.objectClassAttributeType = |
| | | new AttributeType("objectClass", |
| | | new AttributeType(definition, "objectClass", |
| | | Collections.singleton("objectClass"), |
| | | OBJECTCLASS_ATTRIBUTE_TYPE_OID, null, null, |
| | | oidSyntax, AttributeUsage.USER_APPLICATIONS, |
| | |
| | | String.valueOf(name)); |
| | | |
| | | |
| | | String lowerName = toLowerCase(name); |
| | | return new AttributeType(name, Collections.singleton(name), |
| | | lowerName, null, null, syntax, |
| | | String oid = toLowerCase(name) + "-oid"; |
| | | String definition = "( " + oid + " NAME '" + name + "' SYNTAX " + |
| | | syntax.getOID() + " )"; |
| | | |
| | | return new AttributeType(definition, name, Collections.singleton(name), |
| | | oid, null, null, syntax, |
| | | AttributeUsage.USER_APPLICATIONS, false, false, |
| | | false, false); |
| | | } |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.core; |
| | | |
| | |
| | | DITStructureRule dsr; |
| | | try |
| | | { |
| | | dsr = dsrSyntax.decodeDITStructureRule(v.getValue(), schema); |
| | | dsr = dsrSyntax.decodeDITStructureRule(v.getValue(), schema, |
| | | false); |
| | | dsr.getExtraProperties().remove(SCHEMA_PROPERTY_FILENAME); |
| | | dsr.setSchemaFile(schemaFile); |
| | | } |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.messages; |
| | | |
| | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an error occurs while |
| | | * trying to write an updated schema file. This takes two arguments, which |
| | | * are the path to the schema file and a string representation of the |
| | | * exception that was caught. |
| | | * trying to write an updated schema file. This takes a single argument, |
| | | * which is a string representation of the exception that was caught. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CANNOT_WRITE_NEW_SCHEMA = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 222; |
| | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an error occurs while |
| | | * attempting to decode a new name form. This takes two arguments, which |
| | | * are the name form string and a message explaining the problem that |
| | | * occurred. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CANNOT_DECODE_NAME_FORM = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 223; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an error occurs while |
| | | * attempting to decode a new DIT content rule. This takes two arguments, |
| | | * which are the DIT content rule string and a message explaining the problem |
| | | * that occurred. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CANNOT_DECODE_DCR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 224; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an error occurs while |
| | | * attempting to decode a new DIT structure rule. This takes two arguments, |
| | | * which are the DIT structure rule string and a message explaining the |
| | | * problem that occurred. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CANNOT_DECODE_DSR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 225; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an error occurs while |
| | | * attempting to decode a new matching rule use. This takes two arguments, |
| | | * which are the matching rule use string and a message explaining the problem |
| | | * that occurred. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CANNOT_DECODE_MR_USE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 226; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * remove all values for a given attribute type. This takes a single |
| | | * argument, which is the name of that attribute type. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_DELETE_NO_VALUES = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 227; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new attribute type that conflicts with multiple existing attribute |
| | | * types. This takes three arguments, which are the name or OID of the new |
| | | * attribute type, and the name or OID of the two attribute types that were |
| | | * found to conflict with the new type. |
| | | */ |
| | | public static final int |
| | | MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_ATTRTYPE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 228; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new attribute type that references an undefined superior attribute |
| | | * type. This takes two arguments, which are the name or OID of the new |
| | | * attribute type and the name or OID of the superior attribute type. |
| | | */ |
| | | public static final int |
| | | MSGID_SCHEMA_MODIFY_UNDEFINED_SUPERIOR_ATTRIBUTE_TYPE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 229; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new objectclas that conflicts with multiple existing objectclasses. |
| | | * This takes three arguments, which are the name or OID of the new |
| | | * objectclass, and the name or OID of the two objectclasses that were found |
| | | * to conflict with the new objectclass. |
| | | */ |
| | | public static final int |
| | | MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_OBJECTCLASS = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 230; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new name form that conflicts with multiple existing name forms. This |
| | | * takes three arguments, which are the name or OID of the new name form, and |
| | | * the name or OID of the two name forms that were found to conflict with the |
| | | * new name form. |
| | | */ |
| | | public static final int |
| | | MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_NAME_FORM = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 231; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new name form that references an undefined structural objectclass. |
| | | * This takes two arguments, which are the name or OID of the new name form |
| | | * and the name or OID of the undefined objectclass. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_NF_UNDEFINED_STRUCTURAL_OC = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 232; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new name form that references an undefined required attribute type. |
| | | * This takes two arguments, which are the name or OID of the new name form |
| | | * and the name or OID of the undefined attribute type. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_NF_UNDEFINED_REQUIRED_ATTR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 233; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new name form that references an undefined optional attribute type. |
| | | * This takes two arguments, which are the name or OID of the new name form |
| | | * and the name or OID of the undefined attribute type. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_NF_UNDEFINED_OPTIONAL_ATTR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 234; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT content rule that conflicts with multiple existing DIT |
| | | * content rules. This takes three arguments, which are the name of the new |
| | | * DIT content rule, and the names of the two DIT content rules that were |
| | | * found to conflict with the new DIT content rule. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_DCR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 235; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT content rule that references a structural objectclass which |
| | | * is already referenced by an existing DIT copntent rule. This takes three |
| | | * arguments, which are the name of the new DIT content rule, the name or OID |
| | | * of the structural objectclass, and the name of the conflicting DIT content |
| | | * rule. |
| | | */ |
| | | public static final int |
| | | MSGID_SCHEMA_MODIFY_STRUCTURAL_OC_CONFLICT_FOR_ADD_DCR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 236; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT content rule that references a structural objectclass which |
| | | * is not defined in the server schema. This takes two arguments, which are |
| | | * the name of the new DIT content rule and the name or OID of the undefined |
| | | * objectclass. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_STRUCTURAL_OC = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 237; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT content rule that references an auxiliary objectclass which |
| | | * is not defined in the server schema. This takes two arguments, which are |
| | | * the name of the new DIT content rule and the name or OID of the undefined |
| | | * objectclass. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_AUXILIARY_OC = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 238; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT content rule that references a required attribute type |
| | | * which is not defined in the server schema. This takes two arguments, which |
| | | * are the name of the new DIT content rule and the name or OID of the |
| | | * undefined attribute type. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_REQUIRED_ATTR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 239; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT content rule that references an optional attribute type |
| | | * which is not defined in the server schema. This takes two arguments, which |
| | | * are the name of the new DIT content rule and the name or OID of the |
| | | * undefined attribute type. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_OPTIONAL_ATTR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 240; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT content rule that references a prohibited attribute type |
| | | * which is not defined in the server schema. This takes two arguments, which |
| | | * are the name of the new DIT content rule and the name or OID of the |
| | | * undefined attribute type. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_PROHIBITED_ATTR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 241; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT structure rule that conflicts with multiple existing DIT |
| | | * structure rules. This takes three arguments, which are the name or rule ID |
| | | * of the new DIT structure rule, and the names or rule IDs of the two DIT |
| | | * structure rules that were found to conflict with the new DIT structure |
| | | * rule. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_DSR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 242; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT structure rule that references a name form that is already |
| | | * referenced by another DIT structure rule. This takes three arguemnts, |
| | | * which are the name or rule ID of the new DIT structure rule, the name or |
| | | * OID of the name form, and the name or rule ID of the conflicting DIT |
| | | * structure rule. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_NAME_FORM_CONFLICT_FOR_ADD_DSR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 243; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT structure rule that references a name form that is not |
| | | * defined in the server schema. This takes two arguments, which are the name |
| | | * or rule ID of the new DIT structure rule and the name or OID of the |
| | | * undefined name form. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_DSR_UNDEFINED_NAME_FORM = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 244; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new matching rule use that conflicts with multiple existing matching |
| | | * rule uses. This takes three arguments, which are the name of the new |
| | | * matching rule use, and the names of the two matching rule uses that were |
| | | * found to conflict with the new matching rule use. |
| | | */ |
| | | public static final int |
| | | MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_MR_USE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 245; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new matching rule use that references a matching rule that is already |
| | | * associated with another matching rule use. This takes three arguments, |
| | | * which are the name of the new matching rule use, the name or OID of the |
| | | * matching rule, and the name of the conflicting matching rule use. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_MR_CONFLICT_FOR_ADD_MR_USE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 246; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new matching rule use that references an attribute type that is not |
| | | * defined in the server schema. This takes two arguments, which are the |
| | | * name of the new matching rule use and the name or OID of the undefined |
| | | * attribute type. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_MRU_UNDEFINED_ATTR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 247; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if a circular reference |
| | | * is detected in the superior chain for an attribute type. This takes a |
| | | * single argument, which is the name or OID of the attribute type. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CIRCULAR_REFERENCE_AT = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 248; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if a circular reference |
| | | * is detected in the superior chain for an objectclass. This takes a single |
| | | * argument, which is the name or OID of the objectclass. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CIRCULAR_REFERENCE_OC = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 249; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if a circular reference |
| | | * is detected in the superior chain for a DIT structure rule. This takes a |
| | | * single argument, which is the name or rule ID of the DIT structure rule. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CIRCULAR_REFERENCE_DSR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 250; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an error occurs while |
| | | * trying to create copies of the current schema files, but the server was |
| | | * able to properly clean up after itself. This takes a single argument, |
| | | * which is a string representation of the exception that was caught. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CANNOT_WRITE_ORIG_FILES_CLEANED = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 251; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an error occurs while |
| | | * trying to create copies of the current schema files, and the server was |
| | | * not able to properly clean up after itself. This takes a single argument, |
| | | * which is a string representation of the exception that was caught. |
| | | */ |
| | | public static final int |
| | | MSGID_SCHEMA_MODIFY_CANNOT_WRITE_ORIG_FILES_NOT_CLEANED = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 252; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an error occurs while |
| | | * trying to write the new schema files, but the server was able to properly |
| | | * clean up after itself. This takes a single argument, which is a string |
| | | * representation of the exception that was caught. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_CANNOT_WRITE_NEW_FILES_RESTORED = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 253; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an error occurs while |
| | | * trying to write the new schema files, and the server was not able to |
| | | * properly clean up after itself. This takes a single argument, which is a |
| | | * string representation of the exception that was caught. |
| | | */ |
| | | public static final int |
| | | MSGID_SCHEMA_MODIFY_CANNOT_WRITE_NEW_FILES_NOT_RESTORED = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 254; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an attribute type from the schema fails because there is no such attribute |
| | | * type defined. This takes a single argument, which is the name or OID of |
| | | * the attribute type to remove. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_ATTRIBUTE_TYPE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 255; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an attribute type from the schema fails because it is the superior type for |
| | | * another attribute type. This takes two arguments, which are the name or |
| | | * OID of the attribute type to remove, and the name or OID of the subordinate |
| | | * attribute type. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_AT_SUPERIOR_TYPE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 256; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an attribute type from the schema fails because the attribute type is |
| | | * referenced by an objectclass. This takes two arguments, which are the name |
| | | * or OID of the attribute type and the name or OID of the objectclass. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_OC = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 257; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an attribute type from the schema fails because the attribute type is |
| | | * referenced by a name form. This takes two arguments, which are the name or |
| | | * OID of the attribute type and the name or OID of the name form. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_NF = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 258; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an attribute type from the schema fails because the attribute type is |
| | | * referenced by a DIT content rule. This takes two arguments, which are the |
| | | * name or OID of the attribute type and the name of the DIT content rule. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_DCR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 259; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an attribute type from the schema fails because the attribute type is |
| | | * referenced by a matching rule use. This takes two arguments, which are the |
| | | * name or OID of the attribute type and the name of the matching rule use. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_MR_USE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 260; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an objectclass from the schema fails because there is no such objectclass |
| | | * defined. This takes a single argument, which is the name or OID of the |
| | | * objectclass to remove. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_OBJECTCLASS = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 261; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an objectclass from the schema fails because it is the superior class for |
| | | * another objectclass. This takes two arguments, which are the name or OID |
| | | * of the objectclass to remove, and the name or OID of the subordinate |
| | | * objectclass. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_OC_SUPERIOR_CLASS = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 262; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an objectclass from the schema fails because the objectclass is referenced |
| | | * by a name form. This takes two arguments, which are the name or OID of the |
| | | * objectclass and the name or OID of the name form. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_OC_IN_NF = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 263; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * an objectclass from the schema fails because the objectclass is referenced |
| | | * by a DIT content rule. This takes two arguments, which are the name or OID |
| | | * of the objectclass and the name of the DIT content rule. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_OC_IN_DCR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 264; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * a name form from the schema fails because there is no such name form |
| | | * defined. This takes a single argument, which is the name or OID of the |
| | | * name form to remove. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_NAME_FORM = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 265; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * a name form from the schema fails because the name form is referenced by a |
| | | * DIT structure rule. This takes two arguments, which are the name or OID |
| | | * of the name form and the name or rule ID of the DIT structure rule. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_NF_IN_DSR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 266; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * a DIT content rule from the schema fails because there is no such DIT |
| | | * content rule defined. This takes a single argument, which is the name of |
| | | * the DIT content rule to remove. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_DCR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 267; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * a DIT structure rule from the schema fails because there is no such DIT |
| | | * structure rule defined. This takes a single argument, which is the name or |
| | | * rule ID of the DIT structure rule to remove. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_DSR = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 268; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * a DIT structure rule from the schema fails because it is the superior rule |
| | | * for another DIT structure rule. This takes two arguments, which are the |
| | | * name or rule ID of the DIT structure rule to remove, and the name or rule |
| | | * ID of the subordinate rule. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_DSR_SUPERIOR_RULE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 269; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt to remove |
| | | * a matching rule use from the schema fails because there is no such matching |
| | | * rule use defined. This takes a single argument, which is the name of the |
| | | * matching rule use to remove. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_MR_USE = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 270; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new name form that references an objectclass that is not structural. |
| | | * This takes two arguments, which are the name or OID of the new name form |
| | | * and the name or OID of the objectclass. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_NF_OC_NOT_STRUCTURAL = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 271; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new DIT content rule that references an objectclass that is not |
| | | * structural. This takes two arguments, which are the name of the new DIT |
| | | * content rule and the name or OID of the objectclass. |
| | | */ |
| | | public static final int MSGID_SCHEMA_MODIFY_DCR_OC_NOT_STRUCTURAL = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 272; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if an attempt is made to |
| | | * add a new name form that references a structural objectclass which is |
| | | * already referenced by an existing name form. This takes three arguments, |
| | | * which are the name or OID of the new name form, the name or OID of the |
| | | * structural objectclass, and the name or OID of the conflicting name form. |
| | | */ |
| | | public static final int |
| | | MSGID_SCHEMA_MODIFY_STRUCTURAL_OC_CONFLICT_FOR_ADD_NF = |
| | | CATEGORY_MASK_BACKEND | SEVERITY_MASK_MILD_ERROR | 273; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Associates a set of generic messages with the message IDs defined in this |
| | | * class. |
| | | */ |
| | |
| | | registerMessage(MSGID_SCHEMA_DELETE_MODTYPE_NOT_SUPPORTED, |
| | | "The schema backend does not currently support removing " + |
| | | "existing schema elements."); |
| | | // FIXME -- Change the below message once we support removing schema |
| | | // elements. |
| | | registerMessage(MSGID_SCHEMA_INVALID_MODIFICATION_TYPE, |
| | | "The schema backend does not support the %s modification " + |
| | | "type. It is currently only possible to add new schema " + |
| | | "elements."); |
| | | "type."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_UNSUPPORTED_ATTRIBUTE_TYPE, |
| | | "The schema backend does not support the modification of " + |
| | | "the %s attribute type. Only attribute types, object " + |
| | |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_DECODE_OBJECTCLASS, |
| | | "An error occurred while attempting to decode the object " + |
| | | "class \"%s\": %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_DECODE_NAME_FORM, |
| | | "An error occurred while attempting to decode the name " + |
| | | "form \"%s\": %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_DECODE_DCR, |
| | | "An error occurred while attempting to decode the DIT " + |
| | | "content rule \"%s\": %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_DECODE_DSR, |
| | | "An error occurred while attempting to decode the DIT " + |
| | | "structure rule \"%s\": %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_DECODE_MR_USE, |
| | | "An error occurred while attempting to decode the " + |
| | | "matching rule use \"%s\": %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_DELETE_NO_VALUES, |
| | | "The server will not allow removing all values for the " + |
| | | "%s attribute type in the server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_UNDEFINED_SUPERIOR_OBJECTCLASS, |
| | | "Unable to add objectclass %s because its superior " + |
| | | "class of %s is not defined in the server schema."); |
| | |
| | | "of schema file %s: %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_WRITE_NEW_SCHEMA, |
| | | "An error occurred while attepting to write the updated " + |
| | | "schema file %s: %s."); |
| | | "schema: %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_DN_NOT_SUPPORTED, |
| | | "Unwilling to rename entry \"%s\" because modify DN " + |
| | | "operations are not supported in the schema backend."); |
| | |
| | | "An error occurred while attempting to update the backup " + |
| | | "descriptor file %s with information about the schema " + |
| | | "backup: %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_ATTRTYPE, |
| | | "Unable to add attribute type %s because it conflicts " + |
| | | "with multiple existing attribute types (%s and " + |
| | | "%s)."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_UNDEFINED_SUPERIOR_ATTRIBUTE_TYPE, |
| | | "Unable to add attribute type %s because it references " + |
| | | "superior attribute type %s which is not defined in the " + |
| | | "server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_OBJECTCLASS, |
| | | "Unable to add objectclass %s because it conflicts with " + |
| | | "multiple existing objectclasses (%s and %s)."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_NAME_FORM, |
| | | "Unable to add name form %s because it conflicts with " + |
| | | "multiple existing name forms (%s and %s)."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_NF_UNDEFINED_STRUCTURAL_OC, |
| | | "Unable to add name form %s because it references " + |
| | | "structural objectclass %s which is not defined in the " + |
| | | "server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_NF_OC_NOT_STRUCTURAL, |
| | | "Unable to add name form %s because it references " + |
| | | "objectclass %s which is defined in the server schema " + |
| | | "but is not a structural objectclass."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_STRUCTURAL_OC_CONFLICT_FOR_ADD_NF, |
| | | "Unable to add name form %s because it references " + |
| | | "structural objectclass %s which is already associated " + |
| | | "with another name form %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_NF_UNDEFINED_REQUIRED_ATTR, |
| | | "Unable to add name form %s because it references " + |
| | | "required attribute type %s which is not defined in the " + |
| | | "server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_NF_UNDEFINED_OPTIONAL_ATTR, |
| | | "Unable to add name form %s because it references " + |
| | | "optional attribute type %s which is not defined in the " + |
| | | "server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_DCR, |
| | | "Unable to add DIT content rule %s because it conflicts " + |
| | | "with multiple existing DIT content rules (%s and %s)."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_STRUCTURAL_OC_CONFLICT_FOR_ADD_DCR, |
| | | "Unable to add DIT content rule %s because it " + |
| | | "references structural objectclass %s which is already " + |
| | | "associated with another DIT content rule %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_STRUCTURAL_OC, |
| | | "Unable to add DIT content rule %s because it " + |
| | | "references structural objectclass %s which is not " + |
| | | "defined in the server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_DCR_OC_NOT_STRUCTURAL, |
| | | "Unable to add DIT content rule %s because it " + |
| | | "references structural objectclass %s which is defined " + |
| | | "in the server schema but is not structural."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_AUXILIARY_OC, |
| | | "Unable to add DIT content rule %s because it " + |
| | | "references auxiliary objectclass %s which is not " + |
| | | "defined in the server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_REQUIRED_ATTR, |
| | | "Unable to add DIT content rule %s because it " + |
| | | "references required attribute type %s which is not " + |
| | | "defined in the server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_OPTIONAL_ATTR, |
| | | "Unable to add DIT content rule %s because it " + |
| | | "references optional attribute type %s which is not " + |
| | | "defined in the server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_DCR_UNDEFINED_PROHIBITED_ATTR, |
| | | "Unable to add DIT content rule %s because it " + |
| | | "references prohibited attribute type %s which is not " + |
| | | "defined in the server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_DSR, |
| | | "Unable to add DIT structure rule %s because it " + |
| | | "conflicts with multiple existing DIT structure rules " + |
| | | "(%s and %s)."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_NAME_FORM_CONFLICT_FOR_ADD_DSR, |
| | | "Unable to add DIT structure rule %s because it " + |
| | | "references name form %s which is already associated " + |
| | | "with another DIT structure rule %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_DSR_UNDEFINED_NAME_FORM, |
| | | "Unable to add DIT structure rule %s because it " + |
| | | "references name form %s which is not defined in the " + |
| | | "server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_MULTIPLE_CONFLICTS_FOR_ADD_MR_USE, |
| | | "Unable to add matching rule use %s because it " + |
| | | "conflicts with multiple existing matching rule uses " + |
| | | "(%s and %s)."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_MR_CONFLICT_FOR_ADD_MR_USE, |
| | | "Unable to add matching rule use %s because it " + |
| | | "references matching rule %s which is already associated " + |
| | | "with another matching rule use %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_MRU_UNDEFINED_ATTR, |
| | | "Unable to add matching rule use %s because it " + |
| | | "references attribute type %s which is not defined in " + |
| | | "the server schema."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CIRCULAR_REFERENCE_AT, |
| | | "Circular reference detected for attribute type %s in " + |
| | | "which the superior type chain references the " + |
| | | "attribute type itself."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CIRCULAR_REFERENCE_OC, |
| | | "Circular reference detected for objectclass %s in which " + |
| | | "the superior class chain references the objectclass " + |
| | | "itself."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CIRCULAR_REFERENCE_DSR, |
| | | "Circular reference detected for DIT structure rule %s " + |
| | | "in which the superior rule chain references the DIT " + |
| | | "structure rule itself."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_WRITE_ORIG_FILES_CLEANED, |
| | | "An error occurred while attempting to create copies " + |
| | | "of the existing schema files before applying the " + |
| | | "updates: %s. The server was able to restore the " + |
| | | "original schema configuration, so no additional " + |
| | | "cleanup should be required."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_WRITE_ORIG_FILES_NOT_CLEANED, |
| | | "An error occurred while attempting to create copies " + |
| | | "of the existing schema files before applying the " + |
| | | "updates: %s. A problem also occurred when attempting " + |
| | | "to restore the original schema configuration, so the " + |
| | | "server may be left in an inconsistent state and could " + |
| | | "require manual cleanup."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_WRITE_NEW_FILES_RESTORED, |
| | | "An error occurred while attempting to write new " + |
| | | "versions of the server schema files: %s. The server " + |
| | | "was able to restore the original schema configuration, " + |
| | | "so no additional cleanup should be required."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_CANNOT_WRITE_NEW_FILES_NOT_RESTORED, |
| | | "An error occrred while attempting to write new " + |
| | | "versions of the server schema files: %s. A problem " + |
| | | "also occured when attempting to restore the original " + |
| | | "schema configuration, so the server may be left in an " + |
| | | "inconsistent state and could require manual cleanup."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_ATTRIBUTE_TYPE, |
| | | "Unable to remove attribute type %s from the server " + |
| | | "schema because no such attribute type is defined."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_AT_SUPERIOR_TYPE, |
| | | "Unable to remove attribute type %s from the server " + |
| | | "schema because it is referenced as the superior type " + |
| | | "for attribute type %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_OC, |
| | | "Unable to remove attribute type %s from the server " + |
| | | "schema because it is referenced as a required or " + |
| | | "optional attribute type in objectclass %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_NF, |
| | | "Unable to remove attribute type %s from the server " + |
| | | "schema because it is referenced as a required or " + |
| | | "optional attribute type in name form %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_DCR, |
| | | "Unable to remove attribute type %s from the server " + |
| | | "schema because it is referenced as a required, " + |
| | | "optional, or prohibited attribute type in DIT content " + |
| | | "rule %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_AT_IN_MR_USE, |
| | | "Unable to remove attribute type %s from the server " + |
| | | "schema because it is referenced by matching rule use %s"); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_OBJECTCLASS, |
| | | "Unable to remove objectclass %s from the server schema " + |
| | | "because no such objectclass is defined."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_OC_SUPERIOR_CLASS, |
| | | "Unable to remove objectclass %s from the server schema " + |
| | | "because it is referenced as the superior class for " + |
| | | "objectclass %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_OC_IN_NF, |
| | | "Unable to remove objectclass %s from the server schema " + |
| | | "because it is referenced as the structural class for " + |
| | | "name form %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_OC_IN_DCR, |
| | | "Unable to remove objectclass %s from the server schema " + |
| | | "because it is referenced as a structural or auxiliary " + |
| | | "class for DIT content rule %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_NAME_FORM, |
| | | "Unable to remove name form %s from the server schema " + |
| | | "because no such name form is defined."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_NF_IN_DSR, |
| | | "Unable to remove name form %s from the server schema " + |
| | | "because it is referenced by DIT structure rule %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_DCR, |
| | | "Unable to remove DIT content rule %s from the server " + |
| | | "schema because no such DIT content rule is defined."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_DSR, |
| | | "Unable to remove DIT structure rule %s from the server " + |
| | | "schema because no such DIT structure rule is defined."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_DSR_SUPERIOR_RULE, |
| | | "Unable to remove DIT structure rule %s from the server " + |
| | | "schema because it is referenced as a superior rule for " + |
| | | "DIT structure rule %s."); |
| | | registerMessage(MSGID_SCHEMA_MODIFY_REMOVE_NO_SUCH_MR_USE, |
| | | "Unable to remove matching rule use %s from the server " + |
| | | "schema because no such matching rule use is defined."); |
| | | |
| | | |
| | | registerMessage(MSGID_SCHEMA_RESTORE_NO_SUCH_BACKUP, |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.messages; |
| | | |
| | |
| | | CATEGORY_MASK_CORE | SEVERITY_MASK_SEVERE_WARNING | 578; |
| | | |
| | | |
| | | /** |
| | | * The message ID for the message that will be used if a circular reference is |
| | | * detected when attempting to rebuild schema element dependencies. This |
| | | * takes a single argument, which is the definition string for the schema |
| | | * element that triggered the circular reference error. |
| | | */ |
| | | public static final int MSGID_SCHEMA_CIRCULAR_DEPENDENCY_REFERENCE = |
| | | CATEGORY_MASK_CORE | SEVERITY_MASK_MILD_ERROR | 579; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Associates a set of generic messages with the message IDs defined |
| | |
| | | "Unable to register name form %s with the server schema " + |
| | | "because its name %s conflicts with the name for an " + |
| | | "existing name form %s."); |
| | | registerMessage(MSGID_SCHEMA_CIRCULAR_DEPENDENCY_REFERENCE, |
| | | "Unable to update the schema element with definition " + |
| | | "\"%s\" because a circular reference was identified " + |
| | | "when attempting to rebuild other schema elements " + |
| | | "dependent upon it."); |
| | | |
| | | |
| | | registerMessage(MSGID_ADD_OP_INVALID_SYNTAX, |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.plugins; |
| | | |
| | |
| | | false); |
| | | if (at == null) |
| | | { |
| | | at = new AttributeType(ENTRYUUID, Collections.singleton(ENTRYUUID), |
| | | ENTRYUUID, null, null, |
| | | DirectoryConfig.getDefaultAttributeSyntax(), |
| | | String definition = |
| | | "( 1.3.6.1.1.16.4 NAME 'entryUUID' DESC 'UUID of the entry' " + |
| | | "EQUALITY uuidMatch ORDERING uuidOrderingMatch " + |
| | | "SYNTAX 1.3.6.1.1.16.1 SINGLE-VALUE NO-USER-MODIFICATION " + |
| | | "USAGE directoryOperation X-ORIGIN 'RFC 4530' )"; |
| | | |
| | | at = new AttributeType(definition, ENTRYUUID, |
| | | Collections.singleton(ENTRYUUID), ENTRYUUID, null, |
| | | null, DirectoryConfig.getDefaultAttributeSyntax(), |
| | | AttributeUsage.DIRECTORY_OPERATION, false, true, |
| | | false, true); |
| | | } |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.schema; |
| | | |
| | |
| | | } |
| | | |
| | | |
| | | return new AttributeType(primaryName, typeNames, oid, description, |
| | | superiorType, syntax, approximateMatchingRule, |
| | | equalityMatchingRule, orderingMatchingRule, |
| | | substringMatchingRule, attributeUsage, |
| | | isCollective, isNoUserModification, isObsolete, |
| | | isSingleValue, extraProperties); |
| | | return new AttributeType(value.stringValue(), primaryName, typeNames, oid, |
| | | description, superiorType, syntax, |
| | | approximateMatchingRule, equalityMatchingRule, |
| | | orderingMatchingRule, substringMatchingRule, |
| | | attributeUsage, isCollective, isNoUserModification, |
| | | isObsolete, isSingleValue, extraProperties); |
| | | } |
| | | |
| | | |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.schema; |
| | | |
| | | |
| | | |
| | | import java.util.LinkedHashMap; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.concurrent.ConcurrentHashMap; |
| | | import java.util.concurrent.CopyOnWriteArrayList; |
| | | import java.util.concurrent.CopyOnWriteArraySet; |
| | | import java.util.List; |
| | | |
| | | import org.opends.server.api.ApproximateMatchingRule; |
| | | import org.opends.server.api.AttributeSyntax; |
| | |
| | | // out what it is and how to treat what comes after it, then repeat until |
| | | // we get to the end of the value. But before we start, set default values |
| | | // for everything else we might need to know. |
| | | ConcurrentHashMap<String,String> names = |
| | | new ConcurrentHashMap<String,String>(); |
| | | LinkedHashMap<String,String> names = new LinkedHashMap<String,String>(); |
| | | String description = null; |
| | | boolean isObsolete = false; |
| | | CopyOnWriteArraySet<ObjectClass> auxiliaryClasses = |
| | | new CopyOnWriteArraySet<ObjectClass>(); |
| | | CopyOnWriteArraySet<AttributeType> requiredAttributes = |
| | | new CopyOnWriteArraySet<AttributeType>(); |
| | | CopyOnWriteArraySet<AttributeType> optionalAttributes = |
| | | new CopyOnWriteArraySet<AttributeType>(); |
| | | CopyOnWriteArraySet<AttributeType> prohibitedAttributes = |
| | | new CopyOnWriteArraySet<AttributeType>(); |
| | | ConcurrentHashMap<String,CopyOnWriteArrayList<String>> extraProperties = |
| | | new ConcurrentHashMap<String,CopyOnWriteArrayList<String>>(); |
| | | LinkedHashSet<ObjectClass> auxiliaryClasses = |
| | | new LinkedHashSet<ObjectClass>(); |
| | | LinkedHashSet<AttributeType> requiredAttributes = |
| | | new LinkedHashSet<AttributeType>(); |
| | | LinkedHashSet<AttributeType> optionalAttributes = |
| | | new LinkedHashSet<AttributeType>(); |
| | | LinkedHashSet<AttributeType> prohibitedAttributes = |
| | | new LinkedHashSet<AttributeType>(); |
| | | LinkedHashMap<String,List<String>> extraProperties = |
| | | new LinkedHashMap<String,List<String>>(); |
| | | |
| | | |
| | | while (true) |
| | |
| | | // either a single value in single quotes or an open parenthesis |
| | | // followed by one or more values in single quotes separated by spaces |
| | | // followed by a close parenthesis. |
| | | CopyOnWriteArrayList<String> valueList = |
| | | new CopyOnWriteArrayList<String>(); |
| | | LinkedList<String> valueList = new LinkedList<String>(); |
| | | pos = readExtraParameterValues(valueStr, valueList, pos); |
| | | extraProperties.put(tokenName, valueList); |
| | | } |
| | | } |
| | | |
| | | |
| | | return new DITContentRule(structuralClass, names, description, |
| | | auxiliaryClasses, requiredAttributes, |
| | | return new DITContentRule(value.stringValue(), structuralClass, names, |
| | | description, auxiliaryClasses, requiredAttributes, |
| | | optionalAttributes, prohibitedAttributes, |
| | | isObsolete, extraProperties); |
| | | } |
| | |
| | | * the value. |
| | | */ |
| | | private static int readExtraParameterValues(String valueStr, |
| | | CopyOnWriteArrayList<String> valueList, int startPos) |
| | | List<String> valueList, |
| | | int startPos) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "readExtraParameterValues", |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.schema; |
| | | |
| | | |
| | | |
| | | import java.util.LinkedHashMap; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.concurrent.ConcurrentHashMap; |
| | | import java.util.concurrent.CopyOnWriteArrayList; |
| | | import java.util.concurrent.CopyOnWriteArraySet; |
| | | import java.util.List; |
| | | |
| | | import org.opends.server.api.ApproximateMatchingRule; |
| | | import org.opends.server.api.AttributeSyntax; |
| | |
| | | // acceptable. |
| | | try |
| | | { |
| | | decodeDITStructureRule(value, DirectoryServer.getSchema()); |
| | | decodeDITStructureRule(value, DirectoryServer.getSchema(), true); |
| | | return true; |
| | | } |
| | | catch (DirectoryException de) |
| | |
| | | * should not be in order to allow the desired capitalization to be |
| | | * preserved). |
| | | * |
| | | * @param value The ASN.1 octet string containing the value to decode (it |
| | | * does not need to be normalized). |
| | | * @param schema The schema to use to resolve references to other schema |
| | | * elements. |
| | | * @param value The ASN.1 octet string containing the value |
| | | * to decode (it does not need to be |
| | | * normalized). |
| | | * @param schema The schema to use to resolve references to |
| | | * other schema elements. |
| | | * @param allowUnknownElements Indicates whether to allow values that |
| | | * reference a name form and/or superior rules |
| | | * which are not defined in the server schema. |
| | | * This should only be true when called by |
| | | * {@code valueIsAcceptable}. |
| | | * |
| | | * @return The decoded DIT structure rule definition. |
| | | * |
| | |
| | | * DIT structure rule definition. |
| | | */ |
| | | public static DITStructureRule decodeDITStructureRule(ByteString value, |
| | | Schema schema) |
| | | Schema schema, |
| | | boolean allowUnknownElements) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "decodeDITStructureRule", |
| | |
| | | // out what it is and how to treat what comes after it, then repeat until |
| | | // we get to the end of the value. But before we start, set default values |
| | | // for everything else we might need to know. |
| | | ConcurrentHashMap<String,String> names = |
| | | new ConcurrentHashMap<String,String>(); |
| | | LinkedHashMap<String,String> names = new LinkedHashMap<String,String>(); |
| | | String description = null; |
| | | boolean isObsolete = false; |
| | | NameForm nameForm = null; |
| | | CopyOnWriteArraySet<DITStructureRule> superiorRules = null; |
| | | ConcurrentHashMap<String,CopyOnWriteArrayList<String>> extraProperties = |
| | | new ConcurrentHashMap<String,CopyOnWriteArrayList<String>>(); |
| | | boolean nameFormGiven = false; |
| | | LinkedHashSet<DITStructureRule> superiorRules = null; |
| | | LinkedHashMap<String,List<String>> extraProperties = |
| | | new LinkedHashMap<String,List<String>>(); |
| | | |
| | | |
| | | while (true) |
| | |
| | | StringBuilder woidBuffer = new StringBuilder(); |
| | | pos = readWOID(lowerStr, woidBuffer, pos); |
| | | |
| | | nameFormGiven = true; |
| | | nameForm = schema.getNameForm(woidBuffer.toString()); |
| | | if (nameForm == null) |
| | | if ((nameForm == null) && (! allowUnknownElements)) |
| | | { |
| | | int msgID = MSGID_ATTR_SYNTAX_DSR_UNKNOWN_NAME_FORM; |
| | | String message = getMessage(msgID, valueStr, woidBuffer.toString()); |
| | |
| | | schema.getDITStructureRule(supRuleID); |
| | | if (superiorRule == null) |
| | | { |
| | | int msgID = MSGID_ATTR_SYNTAX_DSR_UNKNOWN_RULE_ID; |
| | | String message = getMessage(msgID, valueStr, supRuleID); |
| | | throw new DirectoryException(ResultCode.INVALID_ATTRIBUTE_SYNTAX, |
| | | message, msgID); |
| | | if (! allowUnknownElements) |
| | | { |
| | | int msgID = MSGID_ATTR_SYNTAX_DSR_UNKNOWN_RULE_ID; |
| | | String message = getMessage(msgID, valueStr, supRuleID); |
| | | throw new DirectoryException( |
| | | ResultCode.INVALID_ATTRIBUTE_SYNTAX, message, |
| | | msgID); |
| | | } |
| | | } |
| | | else |
| | | { |
| | |
| | | DITStructureRule superiorRule = schema.getDITStructureRule(supRuleID); |
| | | if (superiorRule == null) |
| | | { |
| | | int msgID = MSGID_ATTR_SYNTAX_DSR_UNKNOWN_RULE_ID; |
| | | String message = getMessage(msgID, valueStr, supRuleID); |
| | | throw new DirectoryException(ResultCode.INVALID_ATTRIBUTE_SYNTAX, |
| | | message, msgID); |
| | | if (! allowUnknownElements) |
| | | { |
| | | int msgID = MSGID_ATTR_SYNTAX_DSR_UNKNOWN_RULE_ID; |
| | | String message = getMessage(msgID, valueStr, supRuleID); |
| | | throw new DirectoryException(ResultCode.INVALID_ATTRIBUTE_SYNTAX, |
| | | message, msgID); |
| | | } |
| | | } |
| | | else |
| | | { |
| | |
| | | } |
| | | } |
| | | |
| | | superiorRules = new CopyOnWriteArraySet<DITStructureRule>(superiorList); |
| | | superiorRules = new LinkedHashSet<DITStructureRule>(superiorList); |
| | | } |
| | | else |
| | | { |
| | |
| | | // either a single value in single quotes or an open parenthesis |
| | | // followed by one or more values in single quotes separated by spaces |
| | | // followed by a close parenthesis. |
| | | CopyOnWriteArrayList<String> valueList = |
| | | new CopyOnWriteArrayList<String>(); |
| | | LinkedList<String> valueList = |
| | | new LinkedList<String>(); |
| | | pos = readExtraParameterValues(valueStr, valueList, pos); |
| | | extraProperties.put(tokenName, valueList); |
| | | } |
| | | } |
| | | |
| | | |
| | | if (nameForm == null) |
| | | if ((nameForm == null) && (! nameFormGiven)) |
| | | { |
| | | int msgID = MSGID_ATTR_SYNTAX_DSR_NO_NAME_FORM; |
| | | String message = getMessage(msgID, valueStr); |
| | |
| | | } |
| | | |
| | | |
| | | return new DITStructureRule(names, ruleID, description, isObsolete, |
| | | nameForm, superiorRules, extraProperties); |
| | | return new DITStructureRule(value.stringValue(), names, ruleID, description, |
| | | isObsolete, nameForm, superiorRules, |
| | | extraProperties); |
| | | } |
| | | |
| | | |
| | |
| | | * the value. |
| | | */ |
| | | private static int readExtraParameterValues(String valueStr, |
| | | CopyOnWriteArrayList<String> valueList, int startPos) |
| | | List<String> valueList, int startPos) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "readExtraParameterValues", |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.schema; |
| | | |
| | | |
| | | |
| | | import java.util.*; |
| | | import java.util.concurrent.*; |
| | | import java.util.LinkedHashMap; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | |
| | | import org.opends.server.api.ApproximateMatchingRule; |
| | | import org.opends.server.api.AttributeSyntax; |
| | |
| | | // out what it is and how to treat what comes after it, then repeat until |
| | | // we get to the end of the value. But before we start, set default values |
| | | // for everything else we might need to know. |
| | | ConcurrentHashMap<String,String> names = |
| | | new ConcurrentHashMap<String,String>(); |
| | | LinkedHashMap<String,String> names = new LinkedHashMap<String,String>(); |
| | | String description = null; |
| | | boolean isObsolete = false; |
| | | CopyOnWriteArraySet<AttributeType> attributes = null; |
| | | ConcurrentHashMap<String,CopyOnWriteArrayList<String>> extraProperties = |
| | | new ConcurrentHashMap<String,CopyOnWriteArrayList<String>>(); |
| | | LinkedHashSet<AttributeType> attributes = null; |
| | | LinkedHashMap<String,List<String>> extraProperties = |
| | | new LinkedHashMap<String,List<String>>(); |
| | | |
| | | while (true) |
| | | { |
| | |
| | | attrs.add(attr); |
| | | } |
| | | |
| | | attributes = new CopyOnWriteArraySet<AttributeType>(attrs); |
| | | attributes = new LinkedHashSet<AttributeType>(attrs); |
| | | } |
| | | else |
| | | { |
| | |
| | | // either a single value in single quotes or an open parenthesis |
| | | // followed by one or more values in single quotes separated by spaces |
| | | // followed by a close parenthesis. |
| | | CopyOnWriteArrayList<String> valueList = |
| | | new CopyOnWriteArrayList<String>(); |
| | | LinkedList<String> valueList = new LinkedList<String>(); |
| | | pos = readExtraParameterValues(valueStr, valueList, pos); |
| | | extraProperties.put(tokenName, valueList); |
| | | } |
| | |
| | | } |
| | | |
| | | |
| | | return new MatchingRuleUse(matchingRule, names, description, isObsolete, |
| | | attributes, extraProperties); |
| | | return new MatchingRuleUse(value.stringValue(), matchingRule, names, |
| | | description, isObsolete, attributes, |
| | | extraProperties); |
| | | } |
| | | |
| | | |
| | |
| | | * the value. |
| | | */ |
| | | private static int readExtraParameterValues(String valueStr, |
| | | CopyOnWriteArrayList<String> valueList, int startPos) |
| | | List<String> valueList, int startPos) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "readExtraParameterValues", |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.schema; |
| | | |
| | | |
| | | |
| | | import java.util.LinkedHashMap; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.concurrent.ConcurrentHashMap; |
| | | import java.util.concurrent.CopyOnWriteArrayList; |
| | | import java.util.concurrent.CopyOnWriteArraySet; |
| | | import java.util.List; |
| | | |
| | | import org.opends.server.api.ApproximateMatchingRule; |
| | | import org.opends.server.api.AttributeSyntax; |
| | |
| | | // out what it is and how to treat what comes after it, then repeat until |
| | | // we get to the end of the value. But before we start, set default values |
| | | // for everything else we might need to know. |
| | | ConcurrentHashMap<String,String> names = |
| | | new ConcurrentHashMap<String,String>(); |
| | | LinkedHashMap<String,String> names = new LinkedHashMap<String,String>(); |
| | | String description = null; |
| | | boolean isObsolete = false; |
| | | ObjectClass structuralClass = null; |
| | | CopyOnWriteArraySet<AttributeType> requiredAttributes = |
| | | new CopyOnWriteArraySet<AttributeType>(); |
| | | CopyOnWriteArraySet<AttributeType> optionalAttributes = |
| | | new CopyOnWriteArraySet<AttributeType>(); |
| | | ConcurrentHashMap<String,CopyOnWriteArrayList<String>> extraProperties = |
| | | new ConcurrentHashMap<String,CopyOnWriteArrayList<String>>(); |
| | | LinkedHashSet<AttributeType> requiredAttributes = |
| | | new LinkedHashSet<AttributeType>(); |
| | | LinkedHashSet<AttributeType> optionalAttributes = |
| | | new LinkedHashSet<AttributeType>(); |
| | | LinkedHashMap<String,List<String>> extraProperties = |
| | | new LinkedHashMap<String,List<String>>(); |
| | | |
| | | |
| | | while (true) |
| | |
| | | // either a single value in single quotes or an open parenthesis |
| | | // followed by one or more values in single quotes separated by spaces |
| | | // followed by a close parenthesis. |
| | | CopyOnWriteArrayList<String> valueList = |
| | | new CopyOnWriteArrayList<String>(); |
| | | LinkedList<String> valueList = new LinkedList<String>(); |
| | | pos = readExtraParameterValues(valueStr, valueList, pos); |
| | | extraProperties.put(tokenName, valueList); |
| | | } |
| | |
| | | } |
| | | |
| | | |
| | | return new NameForm(names, oid, description, isObsolete, structuralClass, |
| | | requiredAttributes, optionalAttributes, |
| | | extraProperties); |
| | | return new NameForm(value.stringValue(), names, oid, description, |
| | | isObsolete, structuralClass, requiredAttributes, |
| | | optionalAttributes, extraProperties); |
| | | } |
| | | |
| | | |
| | |
| | | * the value. |
| | | */ |
| | | private static int readExtraParameterValues(String valueStr, |
| | | CopyOnWriteArrayList<String> valueList, int startPos) |
| | | List<String> valueList, int startPos) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "readExtraParameterValues", |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.schema; |
| | | |
| | |
| | | } |
| | | |
| | | |
| | | return new ObjectClass(primaryName, names, oid, description, superiorClass, |
| | | requiredAttributes, optionalAttributes, |
| | | objectClassType, isObsolete, extraProperties); |
| | | return new ObjectClass(value.stringValue(), primaryName, names, oid, |
| | | description, superiorClass, requiredAttributes, |
| | | optionalAttributes, objectClassType, isObsolete, |
| | | extraProperties); |
| | | } |
| | | |
| | | |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | |
| | | import java.util.Collection; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | | |
| | | import org.opends.server.api.ApproximateMatchingRule; |
| | | import org.opends.server.api.AttributeSyntax; |
| | | import org.opends.server.api.EqualityMatchingRule; |
| | | import org.opends.server.api.OrderingMatchingRule; |
| | | import org.opends.server.api.SubstringMatchingRule; |
| | | import org.opends.server.core.DirectoryServer; |
| | | import org.opends.server.schema.AttributeTypeSyntax; |
| | | |
| | | import static org.opends.server.loggers.Debug.*; |
| | | import static org.opends.server.messages.CoreMessages.*; |
| | | import static org.opends.server.messages.MessageHandler.*; |
| | | import static org.opends.server.util.ServerConstants.*; |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | |
| | | |
| | |
| | | * ordering will be preserved when the associated fields are accessed |
| | | * via their getters or via the {@link #toString()} methods. |
| | | */ |
| | | public final class AttributeType extends CommonSchemaElements |
| | | public final class AttributeType |
| | | extends CommonSchemaElements |
| | | implements SchemaFileElement |
| | | { |
| | | /** |
| | | * The fully-qualified name of this class for debugging purposes. |
| | |
| | | // The ordering matching rule for this attribute type. |
| | | private final OrderingMatchingRule orderingMatchingRule; |
| | | |
| | | // The definition string used to create this attribute type. |
| | | private final String definition; |
| | | |
| | | // The substring matching rule for this attribute type. |
| | | private final SubstringMatchingRule substringMatchingRule; |
| | | |
| | |
| | | * from the set of <code>names</code> will be used as the primary |
| | | * name. |
| | | * |
| | | * @param definition |
| | | * The definition string used to create this attribute |
| | | * type. It must not be {@code null}. |
| | | * @param primaryName |
| | | * The primary name for this attribute type, or |
| | | * <code>null</code> if there is no primary name. |
| | |
| | | * The full set of names for this attribute type, or |
| | | * <code>null</code> if there are no names. |
| | | * @param oid |
| | | * The OID for this attribute type (must not be |
| | | * <code>null</code>). |
| | | * The OID for this attribute type. It must not be |
| | | * {@code null}. |
| | | * @param description |
| | | * The description for the attribute type, or |
| | | * <code>null</code> if there is no description. |
| | |
| | | * Indicates whether this attribute type is declared |
| | | * "single-value". |
| | | */ |
| | | public AttributeType(String primaryName, |
| | | public AttributeType(String definition, String primaryName, |
| | | Collection<String> typeNames, |
| | | String oid, String description, |
| | | AttributeType superiorType, |
| | |
| | | boolean isNoUserModification, |
| | | boolean isObsolete, boolean isSingleValue) |
| | | { |
| | | this(primaryName, typeNames, oid, description, |
| | | this(definition, primaryName, typeNames, oid, description, |
| | | superiorType, syntax, null, null, null, |
| | | null, attributeUsage, isCollective, |
| | | isNoUserModification, isObsolete, isSingleValue, null); |
| | |
| | | * from the set of <code>names</code> will be used as the primary |
| | | * name. |
| | | * |
| | | * @param definition |
| | | * The definition string used to create this attribute |
| | | * type. It must not be {@code null}. |
| | | * @param primaryName |
| | | * The primary name for this attribute type, or |
| | | * <code>null</code> if there is no primary name. |
| | |
| | | * The full set of names for this attribute type, or |
| | | * <code>null</code> if there are no names. |
| | | * @param oid |
| | | * The OID for this attribute type (must not be |
| | | * <code>null</code>). |
| | | * The OID for this attribute type. It must not be |
| | | * {@code null}. |
| | | * @param description |
| | | * The description for the attribute type, or |
| | | * <code>null</code> if there is no description. |
| | |
| | | * @param extraProperties |
| | | * A set of extra properties for this attribute type, or |
| | | * <code>null</code> if there are no extra properties. |
| | | * @throws NullPointerException |
| | | * If the provided OID was <code>null</code>. |
| | | */ |
| | | public AttributeType(String primaryName, |
| | | public AttributeType(String definition, String primaryName, |
| | | Collection<String> typeNames, |
| | | String oid, String description, |
| | | AttributeType superiorType, |
| | |
| | | boolean isNoUserModification, |
| | | boolean isObsolete, boolean isSingleValue, |
| | | Map<String,List<String>> extraProperties) |
| | | throws NullPointerException |
| | | { |
| | | super(primaryName, typeNames, oid, description, isObsolete, |
| | | extraProperties); |
| | | |
| | | assert debugConstructor(CLASS_NAME,String.valueOf(primaryName), |
| | | assert debugConstructor(CLASS_NAME, |
| | | String.valueOf(definition), |
| | | String.valueOf(primaryName), |
| | | String.valueOf(typeNames), |
| | | String.valueOf(oid), |
| | | String.valueOf(description), |
| | |
| | | String.valueOf(isSingleValue), |
| | | String.valueOf(extraProperties)); |
| | | |
| | | ensureNotNull(definition, oid); |
| | | |
| | | this.definition = definition; |
| | | this.superiorType = superiorType; |
| | | this.isCollective = isCollective; |
| | | this.isNoUserModification = isNoUserModification; |
| | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the definition string used to create this attribute |
| | | * type. |
| | | * |
| | | * @return The definition string used to create this attribute |
| | | * type. |
| | | */ |
| | | public String getDefinition() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getDefinition"); |
| | | |
| | | return definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new instance of this attribute type based on the |
| | | * definition string. It will also preserve other state information |
| | | * associated with this attribute type that is not included in the |
| | | * definition string (e.g., the name of the schema file with which |
| | | * it is associated). |
| | | * |
| | | * @return The new instance of this attribute type based on the |
| | | * definition string. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting |
| | | * to create a new attribute type |
| | | * instance from the definition string. |
| | | */ |
| | | public AttributeType recreateFromDefinition() |
| | | throws DirectoryException |
| | | { |
| | | ByteString value = ByteStringFactory.create(definition); |
| | | Schema schema = DirectoryServer.getSchema(); |
| | | |
| | | AttributeType at = |
| | | AttributeTypeSyntax.decodeAttributeType(value, schema); |
| | | at.setSchemaFile(getSchemaFile()); |
| | | |
| | | return at; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the superior type for this attribute type. |
| | | * |
| | | * @return The superior type for this attribute type, or |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | |
| | | import static org.opends.server.loggers.Debug.debugEnter; |
| | | import static org.opends.server.util.ServerConstants.*; |
| | | import static org.opends.server.util.StaticUtils.toLowerCase; |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | import java.util.Iterator; |
| | | import java.util.LinkedList; |
| | | import java.util.LinkedHashMap; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | |
| | | * Where ordered sets of names, or extra properties are provided, the |
| | | * ordering will be preserved when the associated fields are accessed |
| | | * via their getters or via the {@link #toString()} methods. |
| | | * <p> |
| | | * Note that these schema elements are not completely immutable, as |
| | | * the set of extra properties for the schema element may be altered |
| | | * after the element is created. Among other things, this allows the |
| | | * associated schema file to be edited so that an element created over |
| | | * protocol may be associated with a particular schema file. |
| | | */ |
| | | public abstract class CommonSchemaElements { |
| | | /** |
| | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the path to the schema file that contains the |
| | | * Retrieves the name of the schema file that contains the |
| | | * definition for this schema definition. |
| | | * |
| | | * @return The path to the schema file that contains the definition |
| | | * @return The name of the schema file that contains the definition |
| | | * for this schema definition, or <code>null</code> if it |
| | | * is not known or if it is not stored in any schema file. |
| | | */ |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the name of the schema file that contains the |
| | | * definition for this schema element. If a schema file is already |
| | | * defined in the set of extra properties, then it will be |
| | | * overwritten. If the provided schema file value is {@code null}, |
| | | * then any existing schema file definition will be removed. |
| | | * |
| | | * @param schemaFile The name of the schema file that contains the |
| | | * definition for this schema element. |
| | | */ |
| | | public final void setSchemaFile(String schemaFile) { |
| | | assert debugEnter(CLASS_NAME, "setSchemaFile", |
| | | String.valueOf(schemaFile)); |
| | | |
| | | setExtraProperty(SCHEMA_PROPERTY_FILENAME, schemaFile); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the description for this schema definition. |
| | | * |
| | | * @return The description for this schema definition, or |
| | |
| | | |
| | | |
| | | /** |
| | | * Sets the value for an "extra" property for this schema element. |
| | | * If a property already exists with the specified name, then it |
| | | * will be overwritten. If the value is {@code null}, then any |
| | | * existing property with the given name will be removed. |
| | | * |
| | | * @param name The name for the "extra" property. It must not be |
| | | * {@code null}. |
| | | * @param value The value for the "extra" property. If it is |
| | | * {@code null}, then any existing definition will be |
| | | * removed. |
| | | */ |
| | | public final void setExtraProperty(String name, String value) { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(value)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if (value == null) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> values = new LinkedList<String>(); |
| | | values.add(value); |
| | | |
| | | extraProperties.put(name, values); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Sets the values for an "extra" property for this schema element. |
| | | * If a property already exists with the specified name, then it |
| | | * will be overwritten. If the set of values is {@code null} or |
| | | * empty, then any existing property with the given name will be |
| | | * removed. |
| | | * |
| | | * @param name The name for the "extra" property. It must not |
| | | * be {@code null}. |
| | | * @param values The set of values for the "extra" property. If |
| | | * it is {@code null} or empty, then any existing |
| | | * definition will be removed. |
| | | */ |
| | | public final void setExtraProperty(String name, |
| | | List<String> values) { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(values)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> valuesCopy = new LinkedList<String>(values); |
| | | extraProperties.put(name, valuesCopy); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided object is equal to this attribute |
| | | * type. The object will be considered equal if it is an attribute |
| | | * type with the same OID as the current type. |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | | |
| | | |
| | | import java.util.Iterator; |
| | | import java.util.concurrent.ConcurrentHashMap; |
| | | import java.util.concurrent.CopyOnWriteArrayList; |
| | | import java.util.concurrent.CopyOnWriteArraySet; |
| | | import java.util.LinkedHashMap; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | | import java.util.Set; |
| | | |
| | | import org.opends.server.schema.DITContentRuleSyntax; |
| | | |
| | | import static org.opends.server.loggers.Debug.*; |
| | | import static org.opends.server.loggers.Error.*; |
| | |
| | | import static org.opends.server.messages.MessageHandler.*; |
| | | import static org.opends.server.util.ServerConstants.*; |
| | | import static org.opends.server.util.StaticUtils.*; |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | |
| | | |
| | |
| | | * given structural objectclass, and also indicates which auxiliary |
| | | * classes that may be included in the entry. |
| | | */ |
| | | public class DITContentRule |
| | | public final class DITContentRule |
| | | implements SchemaFileElement |
| | | { |
| | | /** |
| | | * The fully-qualified name of this class for debugging purposes. |
| | |
| | | |
| | | |
| | | // Indicates whether this content rule is declared "obsolete". |
| | | private boolean isObsolete; |
| | | private final boolean isObsolete; |
| | | |
| | | // The set of additional name-value pairs associated with this |
| | | // content rule definition. |
| | | private ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | extraProperties; |
| | | private final Map<String,List<String>> extraProperties; |
| | | |
| | | // The set of names for this DIT content rule, in a mapping between |
| | | // the all-lowercase form and the user-defined form. |
| | | private ConcurrentHashMap<String,String> names; |
| | | private final Map<String,String> names; |
| | | |
| | | // The structural objectclass for this DIT content rule. |
| | | private final ObjectClass structuralClass; |
| | | |
| | | // The set of auxiliary objectclasses that entries with this content |
| | | // rule may contain, in a mapping between the objectclass and the |
| | | // user-defined name for that class. |
| | | private CopyOnWriteArraySet<ObjectClass> auxiliaryClasses; |
| | | private final Set<ObjectClass> auxiliaryClasses; |
| | | |
| | | // The set of optional attribute types for this DIT content rule. |
| | | private CopyOnWriteArraySet<AttributeType> optionalAttributes; |
| | | private final Set<AttributeType> optionalAttributes; |
| | | |
| | | // The set of prohibited attribute types for this DIT content rule. |
| | | private CopyOnWriteArraySet<AttributeType> prohibitedAttributes; |
| | | private final Set<AttributeType> prohibitedAttributes; |
| | | |
| | | // The set of required attribute types for this DIT content rule. |
| | | private CopyOnWriteArraySet<AttributeType> requiredAttributes; |
| | | private final Set<AttributeType> requiredAttributes; |
| | | |
| | | // The structural objectclass for this DIT content rule. |
| | | private ObjectClass structuralClass; |
| | | // The definition string used to create this DIT content rule. |
| | | private final String definition; |
| | | |
| | | // The description for this attribute type. |
| | | private String description; |
| | | |
| | | // The path to the schema file that contains this DIT content rule |
| | | // definition. |
| | | private String schemaFile; |
| | | // The description for this DIT content rule. |
| | | private final String description; |
| | | |
| | | |
| | | |
| | |
| | | * Creates a new DIT content rule definition with the provided |
| | | * information. |
| | | * |
| | | * @param definition The definition string used to |
| | | * create this DIT content rule. It |
| | | * must not be {@code null}. |
| | | * @param structuralClass The structural objectclass for this |
| | | * DIT content rule. |
| | | * DIT content rule. It must not be |
| | | * {@code null}. |
| | | * @param names The set of names that may be used |
| | | * to reference this DIT content rule. |
| | | * @param description The description for this DIT |
| | |
| | | * @param extraProperties A set of extra properties for this |
| | | * DIT content rule. |
| | | */ |
| | | public DITContentRule(ObjectClass structuralClass, |
| | | ConcurrentHashMap<String,String> names, |
| | | String description, |
| | | CopyOnWriteArraySet<ObjectClass> auxiliaryClasses, |
| | | CopyOnWriteArraySet<AttributeType> requiredAttributes, |
| | | CopyOnWriteArraySet<AttributeType> optionalAttributes, |
| | | CopyOnWriteArraySet<AttributeType> prohibitedAttributes, |
| | | boolean isObsolete, |
| | | ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | extraProperties) |
| | | public DITContentRule(String definition, |
| | | ObjectClass structuralClass, |
| | | Map<String,String> names, String description, |
| | | Set<ObjectClass> auxiliaryClasses, |
| | | Set<AttributeType> requiredAttributes, |
| | | Set<AttributeType> optionalAttributes, |
| | | Set<AttributeType> prohibitedAttributes, |
| | | boolean isObsolete, |
| | | Map<String,List<String>> extraProperties) |
| | | { |
| | | assert debugConstructor(CLASS_NAME, |
| | | new String[] |
| | | { |
| | | String.valueOf(structuralClass), |
| | | String.valueOf(names), |
| | | String.valueOf(description), |
| | | String.valueOf(auxiliaryClasses), |
| | | String.valueOf(requiredAttributes), |
| | | String.valueOf(optionalAttributes), |
| | | String.valueOf(prohibitedAttributes), |
| | | String.valueOf(isObsolete), |
| | | String.valueOf(extraProperties) |
| | | }); |
| | | assert debugConstructor(CLASS_NAME, String.valueOf(definition), |
| | | String.valueOf(structuralClass), |
| | | String.valueOf(names), |
| | | String.valueOf(description), |
| | | String.valueOf(auxiliaryClasses), |
| | | String.valueOf(requiredAttributes), |
| | | String.valueOf(optionalAttributes), |
| | | String.valueOf(prohibitedAttributes), |
| | | String.valueOf(isObsolete), |
| | | String.valueOf(extraProperties)); |
| | | |
| | | this.structuralClass = structuralClass; |
| | | this.names = names; |
| | | this.description = description; |
| | | this.auxiliaryClasses = auxiliaryClasses; |
| | | this.requiredAttributes = requiredAttributes; |
| | | this.optionalAttributes = optionalAttributes; |
| | | this.prohibitedAttributes = prohibitedAttributes; |
| | | this.isObsolete = isObsolete; |
| | | this.schemaFile = null; |
| | | this.extraProperties = extraProperties; |
| | | ensureNotNull(definition, structuralClass); |
| | | |
| | | this.definition = definition; |
| | | this.structuralClass = structuralClass; |
| | | this.description = description; |
| | | this.isObsolete = isObsolete; |
| | | |
| | | if ((names == null) || names.isEmpty()) |
| | | { |
| | | this.names = new LinkedHashMap<String,String>(0); |
| | | } |
| | | else |
| | | { |
| | | this.names = new LinkedHashMap<String,String>(names); |
| | | } |
| | | |
| | | if ((auxiliaryClasses == null) || auxiliaryClasses.isEmpty()) |
| | | { |
| | | this.auxiliaryClasses = new LinkedHashSet<ObjectClass>(0); |
| | | } |
| | | else |
| | | { |
| | | this.auxiliaryClasses = |
| | | new LinkedHashSet<ObjectClass>(auxiliaryClasses); |
| | | } |
| | | |
| | | if ((requiredAttributes == null) || requiredAttributes.isEmpty()) |
| | | { |
| | | this.requiredAttributes = new LinkedHashSet<AttributeType>(0); |
| | | } |
| | | else |
| | | { |
| | | this.requiredAttributes = |
| | | new LinkedHashSet<AttributeType>(requiredAttributes); |
| | | } |
| | | |
| | | if ((optionalAttributes == null) || optionalAttributes.isEmpty()) |
| | | { |
| | | this.optionalAttributes = new LinkedHashSet<AttributeType>(0); |
| | | } |
| | | else |
| | | { |
| | | this.optionalAttributes = |
| | | new LinkedHashSet<AttributeType>(optionalAttributes); |
| | | } |
| | | |
| | | if ((prohibitedAttributes == null) || |
| | | prohibitedAttributes.isEmpty()) |
| | | { |
| | | this.prohibitedAttributes = new LinkedHashSet<AttributeType>(0); |
| | | } |
| | | else |
| | | { |
| | | this.prohibitedAttributes = |
| | | new LinkedHashSet<AttributeType>(prohibitedAttributes); |
| | | } |
| | | |
| | | if ((extraProperties == null) || extraProperties.isEmpty()) |
| | | { |
| | | this.extraProperties = |
| | | new LinkedHashMap<String,List<String>>(0); |
| | | } |
| | | else |
| | | { |
| | | this.extraProperties = |
| | | new LinkedHashMap<String,List<String>>(extraProperties); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the definition string used to create this DIT content |
| | | * rule. |
| | | * |
| | | * @return The definition string used to create this DIT content |
| | | * rule. |
| | | */ |
| | | public String getDefinition() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getDefinition"); |
| | | |
| | | return definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new instance of this DIT content rule based on the |
| | | * definition string. It will also preserve other state information |
| | | * associated with this DIT content rule that is not included in the |
| | | * definition string (e.g., the name of the schema file with which |
| | | * it is associated). |
| | | * |
| | | * @return The new instance of this DIT content rule based on the |
| | | * definition string. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting |
| | | * to create a new DIT content rule |
| | | * instance from the definition string. |
| | | */ |
| | | public DITContentRule recreateFromDefinition() |
| | | throws DirectoryException |
| | | { |
| | | ByteString value = ByteStringFactory.create(definition); |
| | | Schema schema = DirectoryConfig.getSchema(); |
| | | |
| | | DITContentRule dcr = |
| | | DITContentRuleSyntax.decodeDITContentRule(value, schema); |
| | | dcr.setSchemaFile(getSchemaFile()); |
| | | |
| | | return dcr; |
| | | } |
| | | |
| | | |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the structural objectclass for this DIT content rule. |
| | | * |
| | | * @param structuralClass The structural objectclass for this DIT |
| | | * content rule. |
| | | */ |
| | | public void setStructuralClass(ObjectClass structuralClass) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setStructuralClass", |
| | | String.valueOf(structuralClass)); |
| | | |
| | | this.structuralClass = structuralClass; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the set of names that may be used to reference this DIT |
| | | * content rule. The returned object will be a mapping between each |
| | | * name in all lowercase characters and that name in a user-defined |
| | |
| | | * @return The set of names that may be used to reference this DIT |
| | | * content rule. |
| | | */ |
| | | public ConcurrentHashMap<String,String> getNames() |
| | | public Map<String,String> getNames() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getNames"); |
| | | |
| | |
| | | * rule. |
| | | * |
| | | * @return The primary name to use to reference this DIT content |
| | | * rule, or <CODE>null</CODE> if there is none. |
| | | * rule, or {@code null} if there is none. |
| | | */ |
| | | public String getName() |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of names that may be used to reference this DIT |
| | | * content rule. The provided set must provide a mapping between |
| | | * each name in all lowercase characters and that name in a |
| | | * user-defined form (which may include mixed capitalization). |
| | | * |
| | | * @param names The set of names that may be used to reference |
| | | * this DIT content rule. |
| | | */ |
| | | public void setNames(ConcurrentHashMap<String,String> names) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setNames", String.valueOf(names)); |
| | | |
| | | this.names = names; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided lowercase name may be used to |
| | | * reference this DIT content rule. |
| | | * |
| | | * @param lowerName The name for which to make the determination, |
| | | * in all lowercase characters. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided lowercase name may be |
| | | * used to reference this DIT content rule, or |
| | | * <CODE>false</CODE> if not. |
| | | * @return {@code true} if the provided lowercase name may be used |
| | | * to reference this DIT content rule, or {@code false} if |
| | | * not. |
| | | */ |
| | | public boolean hasName(String lowerName) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided name to the set of names that may be used to |
| | | * reference this DIT content rule. |
| | | * |
| | | * @param name The name to add to the set of names that may be |
| | | * used to reference this DIT content rule. |
| | | */ |
| | | public void addName(String name) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addName", String.valueOf(name)); |
| | | |
| | | String lowerName = toLowerCase(name); |
| | | names.put(lowerName, name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided lowercase name from the set of names that |
| | | * may be used to reference this DIT content rule. |
| | | * |
| | | * @param lowerName The name to remove from the set of names that |
| | | * may be used to reference this DIT content |
| | | * rule, in all lowercase characters. |
| | | */ |
| | | public void removeName(String lowerName) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeName", |
| | | String.valueOf(lowerName)); |
| | | |
| | | names.remove(lowerName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the path to the schema file that contains the |
| | | * Retrieves the name of the schema file that contains the |
| | | * definition for this DIT content rule. |
| | | * |
| | | * @return The path to the schema file that contains the definition |
| | | * for this DIT content rule, or <CODE>null</CODE> if it is |
| | | * not known or if it is not stored in any schema file. |
| | | * @return The name of the schema file that contains the definition |
| | | * for this DIT content rule, or {@code null} if it is not |
| | | * known or if it is not stored in any schema file. |
| | | */ |
| | | public String getSchemaFile() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getSchemaFile"); |
| | | |
| | | return schemaFile; |
| | | List<String> values = |
| | | extraProperties.get(SCHEMA_PROPERTY_FILENAME); |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | return null; |
| | | } |
| | | |
| | | return values.get(0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specifies the path to the schema file that contains the |
| | | * Specifies the name of the schema file that contains the |
| | | * definition for this DIT content rule. |
| | | * |
| | | * @param schemaFile The path to the schema file that contains the |
| | | * @param schemaFile The name of the schema file that contains the |
| | | * definition for this DIT content rule. |
| | | */ |
| | | public void setSchemaFile(String schemaFile) |
| | |
| | | assert debugEnter(CLASS_NAME, "setSchemaFile", |
| | | String.valueOf(schemaFile)); |
| | | |
| | | this.schemaFile = schemaFile; |
| | | setExtraProperty(SCHEMA_PROPERTY_FILENAME, schemaFile); |
| | | } |
| | | |
| | | |
| | |
| | | * Retrieves the description for this DIT content rule. |
| | | * |
| | | * @return The description for this DIT content rule, or |
| | | * <CODE>null</CODE> if there is none. |
| | | * {@code null} if there is none. |
| | | */ |
| | | public String getDescription() |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the description for this DIT content rule. |
| | | * |
| | | * @param description The description for this DIT content rule. |
| | | */ |
| | | public void setDescription(String description) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setDescription", |
| | | String.valueOf(description)); |
| | | |
| | | this.description = description; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the set of auxiliary objectclasses that may be used for |
| | | * entries associated with this DIT content rule. |
| | | * |
| | | * @return The set of auxiliary objectclasses that may be used for |
| | | * entries associated with this DIT content rule. |
| | | */ |
| | | public CopyOnWriteArraySet<ObjectClass> getAuxiliaryClasses() |
| | | public Set<ObjectClass> getAuxiliaryClasses() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getAuxiliaryClasses"); |
| | | |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of auxiliary objectclasses that may be used for |
| | | * entries associated with this DIT content rule. |
| | | * |
| | | * @param auxiliaryClasses The set of auxiliary objectclasses that |
| | | * may be used for entries associated with |
| | | * this DIT content rule. |
| | | */ |
| | | public void setAuxiliaryClasses( |
| | | CopyOnWriteArraySet<ObjectClass> auxiliaryClasses) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setAuxiliaryClasses", |
| | | String.valueOf(auxiliaryClasses)); |
| | | |
| | | this.auxiliaryClasses = auxiliaryClasses; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the specified auxiliary objectclass to this DIT content |
| | | * rule. |
| | | * |
| | | * @param auxiliaryClass The auxiliary class to add to this DIT |
| | | * content rule. |
| | | */ |
| | | public void addAuxiliaryClass(ObjectClass auxiliaryClass) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addAuxiliaryClass", |
| | | String.valueOf(auxiliaryClass)); |
| | | |
| | | auxiliaryClasses.add(auxiliaryClass); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the specified auxiliary objectclass from this DIT content |
| | | * rule. |
| | | * |
| | | * @param auxiliaryClass The auxiliary class to remove from this |
| | | * DIT content rule. |
| | | */ |
| | | public void removeAuxiliaryClass(ObjectClass auxiliaryClass) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeAuxiliaryClass", |
| | | String.valueOf(auxiliaryClass)); |
| | | |
| | | auxiliaryClasses.remove(auxiliaryClass); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided auxiliary objectclass is allowed |
| | | * for use by this DIT content rule. |
| | | * |
| | | * @param auxiliaryClass The auxiliary objectclass for which to |
| | | * make the determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided auxiliary objectclass |
| | | * is allowed for use by this DIT content rule, or |
| | | * <CODE>false</CODE> if not. |
| | | * @return {@code true} if the provided auxiliary objectclass is |
| | | * allowed for use by this DIT content rule, or |
| | | * {@code false} if not. |
| | | */ |
| | | public boolean isAllowedAuxiliaryClass(ObjectClass auxiliaryClass) |
| | | { |
| | |
| | | * @return The set of required attributes for this DIT content |
| | | * rule. |
| | | */ |
| | | public CopyOnWriteArraySet<AttributeType> getRequiredAttributes() |
| | | public Set<AttributeType> getRequiredAttributes() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getRequiredAttributes"); |
| | | |
| | |
| | | * @param attributeType The attribute type for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided attribute type is |
| | | * required by this DIT content rule, or <CODE>false</CODE> |
| | | * if not. |
| | | * @return {@code true} if the provided attribute type is required |
| | | * by this DIT content rule, or {@code false} if not. |
| | | */ |
| | | public boolean isRequired(AttributeType attributeType) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of required attributes for this DIT content |
| | | * rule. |
| | | * |
| | | * @param requiredAttributes The set of required attributes for |
| | | * this DIT content rule. |
| | | */ |
| | | public void setRequiredAttributes(CopyOnWriteArraySet<AttributeType> |
| | | requiredAttributes) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setRequiredAttributes", |
| | | String.valueOf(requiredAttributes)); |
| | | |
| | | this.requiredAttributes = requiredAttributes; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided attribute to the set of required attributes for |
| | | * this DIT content rule. |
| | | * |
| | | * @param attributeType The attribute type to add to the set of |
| | | * required attributes for this DIT content |
| | | * rule. |
| | | */ |
| | | public void addRequiredAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addRequiredAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | requiredAttributes.add(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided attribute from the set of required |
| | | * attributes for this DIT content rule. |
| | | * |
| | | * @param attributeType The attribute type to remove from the set |
| | | * of required attributes for this DIT |
| | | * content rule. |
| | | */ |
| | | public void removeRequiredAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeRequiredAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | requiredAttributes.remove(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the set of optional attributes for this DIT content |
| | | * rule. |
| | | * |
| | | * @return The set of optional attributes for this DIT content |
| | | * rule. |
| | | */ |
| | | public CopyOnWriteArraySet<AttributeType> getOptionalAttributes() |
| | | public Set<AttributeType> getOptionalAttributes() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getOptionalAttributes"); |
| | | |
| | |
| | | * @param attributeType The attribute type for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided attribute type is |
| | | * optional for this DIT content rule, or |
| | | * <CODE>false</CODE> if not. |
| | | * @return {@code true} if the provided attribute type is optional |
| | | * for this DIT content rule, or {@code false} if not. |
| | | */ |
| | | public boolean isOptional(AttributeType attributeType) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of optional attributes for this DIT content |
| | | * rule. |
| | | * |
| | | * @param optionalAttributes The set of optional attributes for |
| | | * this DIT content rule. |
| | | */ |
| | | public void setOptionalAttributes(CopyOnWriteArraySet<AttributeType> |
| | | optionalAttributes) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setOptionalAttributes", |
| | | String.valueOf(optionalAttributes)); |
| | | |
| | | this.optionalAttributes = optionalAttributes; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided attribute to the set of optional attributes for |
| | | * this DIT content rule. |
| | | * |
| | | * @param attributeType The attribute type to add to the set of |
| | | * optional attributes for this DIT content |
| | | * rule. |
| | | */ |
| | | public void addOptionalAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addOptionalAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | optionalAttributes.add(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided attribute from the set of optional |
| | | * attributes for this DIT content rule. |
| | | * |
| | | * @param attributeType The attribute type to remove from the set |
| | | * of optional attributes for this DIT |
| | | * content rule. |
| | | */ |
| | | public void removeOptionalAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeOptionalAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | optionalAttributes.remove(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided attribute type is in the list of |
| | | * required or optional attributes for this DIT content rule. |
| | | * |
| | | * @param attributeType The attribute type for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided attribute type is |
| | | * required or allowed for this DIT content rule, or |
| | | * <CODE>false</CODE> if it is not. |
| | | * @return {@code true} if the provided attribute type is required |
| | | * or allowed for this DIT content rule, or {@code false} |
| | | * if it is not. |
| | | */ |
| | | public boolean isRequiredOrOptional(AttributeType attributeType) |
| | | { |
| | |
| | | * allowed for an objectclass will be |
| | | * acceptable. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided attribute type is |
| | | * required or allowed for this DIT content rule, or |
| | | * <CODE>false</CODE> if it is not. |
| | | * @return {@code true} if the provided attribute type is required |
| | | * or allowed for this DIT content rule, or {@code false} |
| | | * if it is not. |
| | | */ |
| | | public boolean isRequiredOrOptional(AttributeType attributeType, |
| | | boolean acceptEmpty) |
| | |
| | | * @return The set of prohibited attributes for this DIT content |
| | | * rule. |
| | | */ |
| | | public CopyOnWriteArraySet<AttributeType> getProhibitedAttributes() |
| | | public Set<AttributeType> getProhibitedAttributes() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getProhibitedAttributes"); |
| | | |
| | |
| | | * @param attributeType The attribute type for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided attribute type is |
| | | * prohibited for this DIT content rule, or |
| | | * <CODE>false</CODE> if not. |
| | | * @return {@code true} if the provided attribute type is |
| | | * prohibited for this DIT content rule, or {@code false} |
| | | * if not. |
| | | */ |
| | | public boolean isProhibited(AttributeType attributeType) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of prohibited attributes for this DIT content |
| | | * rule. |
| | | * |
| | | * @param prohibitedAttributes The set of prohibited attributes |
| | | * for this DIT content rule. |
| | | */ |
| | | public void setProhibitedAttributes( |
| | | CopyOnWriteArraySet<AttributeType> |
| | | prohibitedAttributes) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setProhibitedAttributes", |
| | | String.valueOf(prohibitedAttributes)); |
| | | |
| | | this.prohibitedAttributes = prohibitedAttributes; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided attribute to the set of prohibited attributes |
| | | * for this DIT content rule. |
| | | * |
| | | * @param attributeType The attribute type to add to the set of |
| | | * prohibited attributes for this DIT |
| | | * content rule. |
| | | */ |
| | | public void addProhibitedAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addProhibitedAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | prohibitedAttributes.add(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided attribute from the set of prohibited |
| | | * attributes for this DIT content rule. |
| | | * |
| | | * @param attributeType The attribute type to remove from the set |
| | | * of prohibited attributes for this DIT |
| | | * content rule. |
| | | */ |
| | | public void removeProhibitedAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeProhibitedAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | prohibitedAttributes.remove(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether this DIT content rule is declared "obsolete". |
| | | * |
| | | * @return <CODE>true</CODE> if this DIT content rule is declared |
| | | * "obsolete", or <CODE>false</CODE> if it is not. |
| | | * @return {@code true} if this DIT content rule is declared |
| | | * "obsolete", or {@code false} if it is not. |
| | | */ |
| | | public boolean isObsolete() |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies whether this DIT content rule is declared "obsolete". |
| | | * |
| | | * @param isObsolete Specifies whether this DIT content rule is |
| | | * declared "obsolete". |
| | | */ |
| | | public void setObsolete(boolean isObsolete) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setObsolete", |
| | | String.valueOf(isObsolete)); |
| | | |
| | | this.isObsolete = isObsolete; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves a mapping between the names of any extra non-standard |
| | | * properties that may be associated with this DIT content rule and |
| | | * the value for that property. The caller may alter the contents |
| | | * of this mapping. |
| | | * the value for that property. |
| | | * |
| | | * @return A mapping between the names of any extra non-standard |
| | | * properties that may be associated with this DIT content |
| | | * rule and the value for that property. |
| | | */ |
| | | public ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | getExtraProperties() |
| | | public Map<String,List<String>> getExtraProperties() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getExtraProperties"); |
| | | |
| | |
| | | * to retrieve the value. |
| | | * |
| | | * @return The value of the specified "extra" property for this DIT |
| | | * content rule, or <CODE>null</CODE> if no such property |
| | | * is defined. |
| | | * content rule, or {@code null} if no such property is |
| | | * defined. |
| | | */ |
| | | public CopyOnWriteArrayList<String> |
| | | getExtraProperty(String propertyName) |
| | | public List<String> getExtraProperty(String propertyName) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getExtraProperty", |
| | | String.valueOf(propertyName)); |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the provided "extra" property for this DIT content |
| | | * rule. |
| | | * |
| | | * @param name The name for the "extra" property. It must not be |
| | | * {@code null}. |
| | | * @param value The value for the "extra" property, or |
| | | * {@code null} if the property is to be removed. |
| | | */ |
| | | public void setExtraProperty(String name, String value) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(value)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if (value == null) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> values = new LinkedList<String>(); |
| | | values.add(value); |
| | | |
| | | extraProperties.put(name, values); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specifies the provided "extra" property for this DIT content |
| | | * rule. |
| | | * |
| | | * @param name The name for the "extra" property. It must not |
| | | * be {@code null}. |
| | | * @param values The set of value for the "extra" property, or |
| | | * {@code null} if the property is to be removed. |
| | | */ |
| | | public void setExtraProperty(String name, List<String> values) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(values)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> valuesCopy = new LinkedList<String>(values); |
| | | extraProperties.put(name, valuesCopy); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided object is equal to this DIT |
| | | * content rule. The object will be considered equal if it is a DIT |
| | | * content rule for the same structural objectclass and the same |
| | |
| | | * |
| | | * @param o The object for which to make the determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided object is equal to |
| | | * this DIT content rule, or <CODE>false</CODE> if not. |
| | | * @return {@code true} if the provided object is equal to |
| | | * this DIT content rule, or {@code false} if not. |
| | | */ |
| | | public boolean equals(Object o) |
| | | { |
| | |
| | | { |
| | | for (String property : extraProperties.keySet()) |
| | | { |
| | | CopyOnWriteArrayList<String> valueList = |
| | | extraProperties.get(property); |
| | | if ((! includeFileElement) && |
| | | property.equals(SCHEMA_PROPERTY_FILENAME)) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | List<String> valueList = extraProperties.get(property); |
| | | |
| | | buffer.append(" "); |
| | | buffer.append(property); |
| | |
| | | } |
| | | } |
| | | |
| | | if (includeFileElement && (schemaFile != null) && |
| | | (! extraProperties.containsKey(SCHEMA_PROPERTY_FILENAME))) |
| | | { |
| | | buffer.append(" "); |
| | | buffer.append(SCHEMA_PROPERTY_FILENAME); |
| | | buffer.append(" '"); |
| | | buffer.append(schemaFile); |
| | | buffer.append("'"); |
| | | } |
| | | |
| | | buffer.append(" )"); |
| | | } |
| | | } |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | | |
| | | |
| | | import java.util.Iterator; |
| | | import java.util.concurrent.ConcurrentHashMap; |
| | | import java.util.concurrent.CopyOnWriteArrayList; |
| | | import java.util.concurrent.CopyOnWriteArraySet; |
| | | import java.util.LinkedHashMap; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | | import java.util.Set; |
| | | |
| | | import org.opends.server.schema.DITStructureRuleSyntax; |
| | | |
| | | import static org.opends.server.loggers.Debug.*; |
| | | import static org.opends.server.loggers.Error.*; |
| | |
| | | import static org.opends.server.messages.MessageHandler.*; |
| | | import static org.opends.server.util.ServerConstants.*; |
| | | import static org.opends.server.util.StaticUtils.*; |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | |
| | | |
| | |
| | | * This class defines a DIT structure rule, which is used to indicate |
| | | * the types of children that entries may have. |
| | | */ |
| | | public class DITStructureRule |
| | | public final class DITStructureRule |
| | | implements SchemaFileElement |
| | | { |
| | | /** |
| | | * The fully-qualified name of this class for debugging purposes. |
| | |
| | | |
| | | |
| | | // Indicates whether this DIT structure rule is declared "obsolete". |
| | | private boolean isObsolete; |
| | | private final boolean isObsolete; |
| | | |
| | | // The rule ID for this DIT structure rule. |
| | | private final int ruleID; |
| | | |
| | | // The name form for this DIT structure rule. |
| | | private final NameForm nameForm; |
| | | |
| | | // The set of additional name-value pairs associated with this DIT |
| | | // structure rule. |
| | | private ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | extraProperties; |
| | | private final Map<String,List<String>> extraProperties; |
| | | |
| | | // The set of names for this DIT structure rule, in a mapping |
| | | // between the all-lowercase form and the user-defined form. |
| | | private ConcurrentHashMap<String,String> names; |
| | | private final Map<String,String> names; |
| | | |
| | | // The set of superior DIT structure rules. |
| | | private CopyOnWriteArraySet<DITStructureRule> superiorRules; |
| | | private final Set<DITStructureRule> superiorRules; |
| | | |
| | | // The rule ID for this DIT structure rule. |
| | | private int ruleID; |
| | | |
| | | // The name form for this DIT structure rule. |
| | | private NameForm nameForm; |
| | | // The definition string for this DIT structure rule. |
| | | private final String definition; |
| | | |
| | | // The description for this DIT structure rule. |
| | | private String description; |
| | | |
| | | // The path to the schema file that contains this DIT structure rule |
| | | // definition. |
| | | private String schemaFile; |
| | | private final String description; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new DIT structure rule with the provided information. |
| | | * |
| | | * @param definition The definition string used to create |
| | | * this DIT structure rule. It must not be |
| | | * {@code null}. |
| | | * @param names The set of names for this DIT structure |
| | | * rule, mapping the lowercase names to the |
| | | * user-defined values. |
| | |
| | | * @param extraProperties The set of "extra" properties associated |
| | | * with this DIT structure rules. |
| | | */ |
| | | public DITStructureRule(ConcurrentHashMap<String,String> names, |
| | | int ruleID, String description, boolean isObsolete, |
| | | NameForm nameForm, |
| | | CopyOnWriteArraySet<DITStructureRule> superiorRules, |
| | | ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | extraProperties) |
| | | public DITStructureRule(String definition, Map<String,String> names, |
| | | int ruleID, String description, |
| | | boolean isObsolete, NameForm nameForm, |
| | | Set<DITStructureRule> superiorRules, |
| | | Map<String,List<String>> extraProperties) |
| | | { |
| | | assert debugConstructor(CLASS_NAME, |
| | | new String[] |
| | | { |
| | | String.valueOf(names), |
| | | String.valueOf(ruleID), |
| | | String.valueOf(description), |
| | | String.valueOf(isObsolete), |
| | | String.valueOf(nameForm), |
| | | String.valueOf(superiorRules), |
| | | String.valueOf(extraProperties) |
| | | }); |
| | | assert debugConstructor(CLASS_NAME, String.valueOf(definition), |
| | | String.valueOf(names), |
| | | String.valueOf(ruleID), |
| | | String.valueOf(description), |
| | | String.valueOf(isObsolete), |
| | | String.valueOf(nameForm), |
| | | String.valueOf(superiorRules), |
| | | String.valueOf(extraProperties)); |
| | | |
| | | this.names = names; |
| | | this.ruleID = ruleID; |
| | | this.description = description; |
| | | this.isObsolete = isObsolete; |
| | | this.nameForm = nameForm; |
| | | this.superiorRules = superiorRules; |
| | | this.schemaFile = null; |
| | | this.extraProperties = extraProperties; |
| | | ensureNotNull(definition); |
| | | |
| | | this.definition = definition; |
| | | this.ruleID = ruleID; |
| | | this.description = description; |
| | | this.isObsolete = isObsolete; |
| | | this.nameForm = nameForm; |
| | | |
| | | if ((names == null) || names.isEmpty()) |
| | | { |
| | | this.names = new LinkedHashMap<String,String>(0); |
| | | } |
| | | else |
| | | { |
| | | this.names = new LinkedHashMap<String,String>(names); |
| | | } |
| | | |
| | | if ((superiorRules == null) || superiorRules.isEmpty()) |
| | | { |
| | | this.superiorRules = new LinkedHashSet<DITStructureRule>(0); |
| | | } |
| | | else |
| | | { |
| | | this.superiorRules = |
| | | new LinkedHashSet<DITStructureRule>(superiorRules); |
| | | } |
| | | |
| | | if ((extraProperties == null) || extraProperties.isEmpty()) |
| | | { |
| | | this.extraProperties = |
| | | new LinkedHashMap<String,List<String>>(0); |
| | | } |
| | | else |
| | | { |
| | | this.extraProperties = |
| | | new LinkedHashMap<String,List<String>>(extraProperties); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the definition string used to create this DIT structure |
| | | * rule. |
| | | * |
| | | * @return The definition string used to create this DIT structure |
| | | * rule. |
| | | */ |
| | | public String getDefinition() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getDefinition"); |
| | | |
| | | return definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new instance of this DIT structure rule based on the |
| | | * definition string. It will also preserve other state information |
| | | * associated with this DIT structure rule that is not included in |
| | | * the definition string (e.g., the name of the schema file with |
| | | * which it is associated). |
| | | * |
| | | * @return The new instance of this DIT structure rule based on the |
| | | * definition string. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting |
| | | * to create a new DIT structure rule |
| | | * instance from the definition string. |
| | | */ |
| | | public DITStructureRule recreateFromDefinition() |
| | | throws DirectoryException |
| | | { |
| | | ByteString value = ByteStringFactory.create(definition); |
| | | Schema schema = DirectoryConfig.getSchema(); |
| | | |
| | | DITStructureRule dsr = |
| | | DITStructureRuleSyntax.decodeDITStructureRule(value, schema, |
| | | false); |
| | | dsr.setSchemaFile(getSchemaFile()); |
| | | |
| | | return dsr; |
| | | } |
| | | |
| | | |
| | |
| | | * @return The set of names that may be used to reference this DIT |
| | | * structure rule. |
| | | */ |
| | | public ConcurrentHashMap<String,String> getNames() |
| | | public Map<String,String> getNames() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getNames"); |
| | | |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of names that may be used to reference this DIT |
| | | * structure rule. The provided set must contain a mapping between |
| | | * each name in all lowercase characters and the name in a |
| | | * user-defined form (which may include mixed capitalization). |
| | | * |
| | | * @param names The set of names that may be used to reference |
| | | * this attribute type. |
| | | */ |
| | | public void setNames(ConcurrentHashMap<String,String> names) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setNames", String.valueOf(names)); |
| | | |
| | | this.names = names; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether this DIT structure rule has the specified name. |
| | | * |
| | | * @param lowerName The lowercase name for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the specified name is assigned to |
| | | * this DIT structure rule, or <CODE>false</CODE> if not. |
| | | * @return {@code true} if the specified name is assigned to this |
| | | * DIT structure rule, or {@code false} if not. |
| | | */ |
| | | public boolean hasName(String lowerName) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Adds the specified name to the set of names for this DIT |
| | | * structure rule. |
| | | * |
| | | * @param name The name to add to the set of names for this DIT |
| | | * structure rule. |
| | | */ |
| | | public void addName(String name) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addName", String.valueOf(name)); |
| | | |
| | | String lowerName = toLowerCase(name); |
| | | names.put(lowerName, name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the specified name from the set of names for this DIT |
| | | * structure rule. This will have no effect if the specified name |
| | | * is not associated with this attribute type. |
| | | * |
| | | * @param lowerName The lowercase name to remove from the set of |
| | | * names for this DIT structure rule. |
| | | */ |
| | | public void removeName(String lowerName) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeName", |
| | | String.valueOf(lowerName)); |
| | | |
| | | names.remove(lowerName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the rule ID for this DIT structure rule. |
| | | * |
| | | * @return The rule ID for this DIT structure rule. |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the rule ID for this DIT structure rule. |
| | | * |
| | | * @param ruleID The rule ID for this DIT structure rule. |
| | | */ |
| | | public void setRuleID(int ruleID) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setRuleID", |
| | | String.valueOf(ruleID)); |
| | | |
| | | this.ruleID = ruleID; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the name or rule ID for this DIT structure rule. If it |
| | | * has one or more names, then the primary name will be returned. |
| | | * If it does not have any names, then the rule ID will be returned. |
| | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether this DIT structure rule has the specified name |
| | | * or rule ID. |
| | | * |
| | | * @param lowerValue The lowercase value for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided value matches the rule |
| | | * ID or one of the names assigned to this DIT structure |
| | | * rule, or <CODE>false</CODE> if not. |
| | | */ |
| | | public boolean hasNameOrOID(String lowerValue) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "hasNameOrOID", |
| | | String.valueOf(lowerValue)); |
| | | |
| | | if (names.containsKey(lowerValue)) |
| | | { |
| | | return true; |
| | | } |
| | | |
| | | return lowerValue.equals(String.valueOf(ruleID)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the path to the schema file that contains the |
| | | * definition for this DIT structure rule. |
| | | * |
| | | * @return The path to the schema file that contains the definition |
| | | * for this DIT structure rule, or <CODE>null</CODE> if it |
| | | * for this DIT structure rule, or {@code null} if it |
| | | * is not known or if it is not stored in any schema file. |
| | | */ |
| | | public String getSchemaFile() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getSchemaFile"); |
| | | |
| | | return schemaFile; |
| | | List<String> values = |
| | | extraProperties.get(SCHEMA_PROPERTY_FILENAME); |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | return null; |
| | | } |
| | | |
| | | return values.get(0); |
| | | } |
| | | |
| | | |
| | |
| | | assert debugEnter(CLASS_NAME, "setSchemaFile", |
| | | String.valueOf(schemaFile)); |
| | | |
| | | this.schemaFile = schemaFile; |
| | | setExtraProperty(SCHEMA_PROPERTY_FILENAME, schemaFile); |
| | | } |
| | | |
| | | |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the description for this DIT structure rule. |
| | | * |
| | | * @param description The description for this DIT structure rule. |
| | | */ |
| | | public void setDescription(String description) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setDescription", description); |
| | | |
| | | this.description = description; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the name form for this DIT structure rule. |
| | | * |
| | | * @return The name form for this DIT structure rule. |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the name form for this DIT structure rule. |
| | | * |
| | | * @param nameForm The name form for this DIT structure rule. |
| | | */ |
| | | public void setNameForm(NameForm nameForm) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setNameForm", |
| | | String.valueOf(nameForm)); |
| | | |
| | | this.nameForm = nameForm; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the structural objectclass for the name form with which |
| | | * this DIT structure rule is associated. |
| | | * |
| | |
| | | * |
| | | * @return The set of superior rules for this DIT structure rule. |
| | | */ |
| | | public CopyOnWriteArraySet<DITStructureRule> getSuperiorRules() |
| | | public Set<DITStructureRule> getSuperiorRules() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getSuperiorRules"); |
| | | |
| | |
| | | * Indicates whether this DIT structure rule has one or more |
| | | * superior rules. |
| | | * |
| | | * @return <CODE>true</CODE> if this DIT structure rule has one or |
| | | * more superior rules, or <CODE>false</CODE> if not. |
| | | * @return {@code true} if this DIT structure rule has one or more |
| | | * superior rules, or {@code false} if not. |
| | | */ |
| | | public boolean hasSuperiorRules() |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of superior rules for this DIT structure rule. |
| | | * |
| | | * @param superiorRules The set of superior rules for this DIT |
| | | * structure rule. |
| | | */ |
| | | public void setSuperiorRules(CopyOnWriteArraySet<DITStructureRule> |
| | | superiorRules) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setSuperiorRules", |
| | | String.valueOf(superiorRules)); |
| | | |
| | | this.superiorRules = superiorRules; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided rule as a superior rule for this DIT structure |
| | | * rule. |
| | | * |
| | | * @param superiorRule The superior rule to add to this DIT |
| | | * structure rule. |
| | | */ |
| | | public void addSuperiorRule(DITStructureRule superiorRule) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addSuperiorRule", |
| | | String.valueOf(superiorRule)); |
| | | |
| | | superiorRules.add(superiorRule); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided rule as a superior rule for this DIT |
| | | * structure rule. It will have no effect if the provided rule is |
| | | * not a superior rule for this DIT structure rule. |
| | | * |
| | | * @param superiorRule The superior rule to remove from this DIT |
| | | * structure rule. |
| | | */ |
| | | public void removeSuperiorRule(DITStructureRule superiorRule) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeSuperiorRule", |
| | | String.valueOf(superiorRule)); |
| | | |
| | | superiorRules.remove(superiorRule); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether this DIT structure rule is declared "obsolete". |
| | | * |
| | | * @return <CODE>true</CODE> if this DIT structure rule is declared |
| | | * "obsolete", or <CODE>false</CODE> if not. |
| | | * @return {@code true} if this DIT structure rule is declared |
| | | * "obsolete", or {@code false} if not. |
| | | */ |
| | | public boolean isObsolete() |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies whether this DIT structure rule is declared "obsolete". |
| | | * |
| | | * @param isObsolete Specifies whether this DIT structure rule is |
| | | * declared "obsolete". |
| | | */ |
| | | public void setObsolete(boolean isObsolete) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setObsolete", |
| | | String.valueOf(isObsolete)); |
| | | |
| | | this.isObsolete = isObsolete; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves a mapping between the names of any extra non-standard |
| | | * properties that may be associated with this DIT structure rule |
| | | * and the value for that property. The caller may alter the |
| | | * contents of this mapping. |
| | | * and the value for that property. |
| | | * |
| | | * @return A mapping between the names of any extra non-standard |
| | | * properties that may be associated with this DIT |
| | | * structure rule and the value for that property. |
| | | */ |
| | | public ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | getExtraProperties() |
| | | public Map<String,List<String>> getExtraProperties() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getExtraProperties"); |
| | | |
| | |
| | | * to retrieve the value. |
| | | * |
| | | * @return The value of the specified "extra" property for this DIT |
| | | * structure rule, or <CODE>null</CODE> if no such property |
| | | * is defined. |
| | | * structure rule, or {@code null} if no such property is |
| | | * defined. |
| | | */ |
| | | public CopyOnWriteArrayList<String> |
| | | getExtraProperty(String propertyName) |
| | | public List<String> getExtraProperty(String propertyName) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getExtraProperty", |
| | | String.valueOf(propertyName)); |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the provided "extra" property for this DIT structure |
| | | * rule. |
| | | * |
| | | * @param name The name for the "extra" property. It must not be |
| | | * {@code null}. |
| | | * @param value The value for the "extra" property, or |
| | | * {@code null} if the property is to be removed. |
| | | */ |
| | | public void setExtraProperty(String name, String value) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(value)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if (value == null) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> values = new LinkedList<String>(); |
| | | values.add(value); |
| | | |
| | | extraProperties.put(name, values); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specifies the provided "extra" property for this DIT structure |
| | | * rule. |
| | | * |
| | | * @param name The name for the "extra" property. It must not |
| | | * be {@code null}. |
| | | * @param values The set of value for the "extra" property, or |
| | | * {@code null} if the property is to be removed. |
| | | */ |
| | | public void setExtraProperty(String name, List<String> values) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(values)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> valuesCopy = new LinkedList<String>(values); |
| | | extraProperties.put(name, valuesCopy); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided object is equal to this DIT |
| | | * structure rule. The object will be considered equal if it is a |
| | | * DIT structure rule with the same OID as the current type. |
| | | * |
| | | * @param o The object for which to make the determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided object is equal to |
| | | * this attribute, or <CODE>false</CODE> if not. |
| | | * @return {@code true} if the provided object is equal to this |
| | | * attribute, or {@code false} if not. |
| | | */ |
| | | public boolean equals(Object o) |
| | | { |
| | |
| | | { |
| | | for (String property : extraProperties.keySet()) |
| | | { |
| | | CopyOnWriteArrayList<String> valueList = |
| | | extraProperties.get(property); |
| | | if ((! includeFileElement) && |
| | | property.equals(SCHEMA_PROPERTY_FILENAME)) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | List<String> valueList = extraProperties.get(property); |
| | | |
| | | buffer.append(" "); |
| | | buffer.append(property); |
| | |
| | | } |
| | | } |
| | | |
| | | if (includeFileElement && (schemaFile != null) && |
| | | (! extraProperties.containsKey(SCHEMA_PROPERTY_FILENAME))) |
| | | { |
| | | buffer.append(" "); |
| | | buffer.append(SCHEMA_PROPERTY_FILENAME); |
| | | buffer.append(" '"); |
| | | buffer.append(schemaFile); |
| | | buffer.append("'"); |
| | | } |
| | | |
| | | buffer.append(" )"); |
| | | } |
| | | } |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | | |
| | | |
| | | import java.util.Iterator; |
| | | import java.util.concurrent.ConcurrentHashMap; |
| | | import java.util.concurrent.CopyOnWriteArrayList; |
| | | import java.util.concurrent.CopyOnWriteArraySet; |
| | | import java.util.LinkedHashMap; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | | import java.util.Set; |
| | | |
| | | import org.opends.server.api.MatchingRule; |
| | | import org.opends.server.schema.MatchingRuleUseSyntax; |
| | | |
| | | import static org.opends.server.loggers.Debug.*; |
| | | import static org.opends.server.util.ServerConstants.*; |
| | | import static org.opends.server.util.StaticUtils.*; |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | |
| | | |
| | |
| | | * the set of attribute types that may be used for a given matching |
| | | * rule. |
| | | */ |
| | | public class MatchingRuleUse |
| | | public final class MatchingRuleUse |
| | | implements SchemaFileElement |
| | | { |
| | | /** |
| | | * The fully-qualified name of this class for debugging purposes. |
| | |
| | | |
| | | |
| | | // Indicates whether this matching rule use is declared "obsolete". |
| | | private boolean isObsolete; |
| | | private final boolean isObsolete; |
| | | |
| | | // The set of additional name-value pairs associated with this |
| | | // matching rule use definition. |
| | | private final Map<String,List<String>> extraProperties; |
| | | |
| | | // The set of names that may be used to refer to this matching rule |
| | | // use, mapped between their all-lowercase representations and the |
| | | // user-defined representations. |
| | | private ConcurrentHashMap<String,String> names; |
| | | |
| | | // The set of attribute types with which this matching rule use is |
| | | // associated. |
| | | private CopyOnWriteArraySet<AttributeType> attributes; |
| | | |
| | | // The set of additional name-value pairs associated with this |
| | | // matching rule use definition. |
| | | private ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | extraProperties; |
| | | private final Map<String,String> names; |
| | | |
| | | // The matching rule with which this matching rule use is |
| | | // associated. |
| | | private MatchingRule matchingRule; |
| | | private final MatchingRule matchingRule; |
| | | |
| | | // The set of attribute types with which this matching rule use is |
| | | // associated. |
| | | private final Set<AttributeType> attributes; |
| | | |
| | | // The definition string used to create this matching rule use. |
| | | private final String definition; |
| | | |
| | | // The description for this matching rule use. |
| | | private String description; |
| | | |
| | | // The path to the schema file that contains this matching rule use |
| | | // definition. |
| | | private String schemaFile; |
| | | private final String description; |
| | | |
| | | |
| | | |
| | |
| | | * Creates a new matching rule use definition with the provided |
| | | * information. |
| | | * |
| | | * @param definition The definition string used to create |
| | | * this matching rule use. It must not be |
| | | * {@code null}. |
| | | * @param matchingRule The matching rule for this matching rule |
| | | * use. |
| | | * use. It must not be {@code null}. |
| | | * @param names The set of names for this matching rule |
| | | * use. |
| | | * @param description The description for this matching rule |
| | |
| | | * @param extraProperties A set of "extra" properties that may be |
| | | * associated with this matching rule use. |
| | | */ |
| | | public MatchingRuleUse(MatchingRule matchingRule, |
| | | ConcurrentHashMap<String,String> names, |
| | | String description, boolean isObsolete, |
| | | CopyOnWriteArraySet<AttributeType> attributes, |
| | | ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | extraProperties) |
| | | public MatchingRuleUse(String definition, MatchingRule matchingRule, |
| | | Map<String,String> names, String description, |
| | | boolean isObsolete, |
| | | Set<AttributeType> attributes, |
| | | Map<String,List<String>> extraProperties) |
| | | { |
| | | assert debugConstructor(CLASS_NAME, |
| | | new String[] |
| | | { |
| | | String.valueOf(matchingRule), |
| | | String.valueOf(names), |
| | | String.valueOf(description), |
| | | String.valueOf(isObsolete), |
| | | String.valueOf(attributes), |
| | | String.valueOf(extraProperties) |
| | | }); |
| | | assert debugConstructor(CLASS_NAME, String.valueOf(definition), |
| | | String.valueOf(matchingRule), |
| | | String.valueOf(names), |
| | | String.valueOf(description), |
| | | String.valueOf(isObsolete), |
| | | String.valueOf(attributes), |
| | | String.valueOf(extraProperties)); |
| | | |
| | | ensureNotNull(definition, matchingRule); |
| | | |
| | | this.definition = definition; |
| | | this.matchingRule = matchingRule; |
| | | this.description = description; |
| | | this.isObsolete = isObsolete; |
| | | |
| | | if ((names == null) || names.isEmpty()) |
| | | { |
| | | this.names = new LinkedHashMap<String,String>(0); |
| | | } |
| | | else |
| | | { |
| | | this.names = new LinkedHashMap<String,String>(names); |
| | | } |
| | | |
| | | if ((attributes == null) || attributes.isEmpty()) |
| | | { |
| | | this.attributes = new LinkedHashSet<AttributeType>(0); |
| | | } |
| | | else |
| | | { |
| | | this.attributes = new LinkedHashSet<AttributeType>(attributes); |
| | | } |
| | | |
| | | if ((extraProperties == null) || extraProperties.isEmpty()) |
| | | { |
| | | this.extraProperties = |
| | | new LinkedHashMap<String,List<String>>(0); |
| | | } |
| | | else |
| | | { |
| | | this.extraProperties = |
| | | new LinkedHashMap<String,List<String>>(extraProperties); |
| | | } |
| | | } |
| | | |
| | | |
| | | this.matchingRule = matchingRule; |
| | | this.names = names; |
| | | this.description = description; |
| | | this.isObsolete = isObsolete; |
| | | this.attributes = attributes; |
| | | this.schemaFile = null; |
| | | this.extraProperties = extraProperties; |
| | | |
| | | /** |
| | | * Retrieves the definition string used to create this matching rule |
| | | * use. |
| | | * |
| | | * @return The definition string used to create this matching rule |
| | | * use. |
| | | */ |
| | | public String getDefinition() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getDefinition"); |
| | | |
| | | return definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new instance of this matching rule use based on the |
| | | * definition string. It will also preserve other state information |
| | | * associated with this matching rule use that is not included in |
| | | * the definition string (e.g., the name of the schema file with |
| | | * which it is associated). |
| | | * |
| | | * @return The new instance of this matching rule use based on the |
| | | * definition string. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting |
| | | * to create a new matching rule use |
| | | * instance from the definition string. |
| | | */ |
| | | public MatchingRuleUse recreateFromDefinition() |
| | | throws DirectoryException |
| | | { |
| | | ByteString value = ByteStringFactory.create(definition); |
| | | Schema schema = DirectoryConfig.getSchema(); |
| | | |
| | | MatchingRuleUse mru = |
| | | MatchingRuleUseSyntax.decodeMatchingRuleUse(value, schema); |
| | | mru.setSchemaFile(getSchemaFile()); |
| | | |
| | | return mru; |
| | | } |
| | | |
| | | |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the matching rule for this matching rule use. |
| | | * |
| | | * @param matchingRule The matching rule for this matching rule |
| | | * use. |
| | | */ |
| | | public void setMatchingRule(MatchingRule matchingRule) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setMatchingRule", |
| | | String.valueOf(matchingRule)); |
| | | |
| | | this.matchingRule = matchingRule; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the set of names for this matching rule use. The |
| | | * mapping will be between the names in all lowercase form and the |
| | | * names in the user-defined form. |
| | | * |
| | | * @return The set of names for this matching rule use. |
| | | */ |
| | | public ConcurrentHashMap<String,String> getNames() |
| | | public Map<String,String> getNames() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getNames"); |
| | | |
| | |
| | | * rule use. |
| | | * |
| | | * @return The primary name to use when referencing this matching |
| | | * rule use, or <CODE>null</CODE> if there is none. |
| | | * rule use, or {@code null} if there is none. |
| | | */ |
| | | public String getName() |
| | | { |
| | |
| | | * @param lowerName The name for which to make the determination, |
| | | * formatted in all lowercase characters. |
| | | * |
| | | * @return <CODE>true</CODE> if this matching rule use has the |
| | | * specified name, or <CODE>false</CODE> if not. |
| | | * @return {@code true} if this matching rule use has the specified |
| | | * name, or {@code false} if not. |
| | | */ |
| | | public boolean hasName(String lowerName) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of names for this matching rule use as a |
| | | * mapping between the names in all lowercase form and the names in |
| | | * the user-defined form. |
| | | * |
| | | * @param names The set of names for this matching rule use. |
| | | */ |
| | | public void setNames(ConcurrentHashMap<String,String> names) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setNames", String.valueOf(names)); |
| | | |
| | | this.names = names; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided name to the set of names for this matching rule |
| | | * use. |
| | | * |
| | | * @param name The name to add to the set of names for this |
| | | * matching rule use. |
| | | */ |
| | | public void addName(String name) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addName", String.valueOf(name)); |
| | | |
| | | names.put(toLowerCase(name), name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided name from the set of names for this matching |
| | | * rule use. This will have no effect if the specified name is not |
| | | * associated with this matching rule use. |
| | | * |
| | | * @param lowerName The name to remove from the set of names for |
| | | * this matching rule use, in all lowercase |
| | | * characters. |
| | | */ |
| | | public void removeName(String lowerName) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeName", |
| | | String.valueOf(lowerName)); |
| | | |
| | | names.remove(lowerName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the path to the schema file that contains the |
| | | * definition for this matching rule use. |
| | | * |
| | | * @return The path to the schema file that contains the definition |
| | | * for this matching rule use, or <CODE>null</CODE> if it |
| | | * is not known or if it is not stored in any schema file. |
| | | * for this matching rule use, or {@code null} if it is not |
| | | * known or if it is not stored in any schema file. |
| | | */ |
| | | public String getSchemaFile() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getSchemaFile"); |
| | | |
| | | return schemaFile; |
| | | List<String> values = |
| | | extraProperties.get(SCHEMA_PROPERTY_FILENAME); |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | return null; |
| | | } |
| | | |
| | | return values.get(0); |
| | | } |
| | | |
| | | |
| | |
| | | assert debugEnter(CLASS_NAME, "setSchemaFile", |
| | | String.valueOf(schemaFile)); |
| | | |
| | | this.schemaFile = schemaFile; |
| | | setExtraProperty(SCHEMA_PROPERTY_FILENAME, schemaFile); |
| | | } |
| | | |
| | | |
| | |
| | | * Retrieves the description for this matching rule use. |
| | | * |
| | | * @return The description for this matching rule use, or |
| | | * <CODE>null</CODE> if there is none. |
| | | * {@code null} if there is none. |
| | | */ |
| | | public String getDescription() |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the description for this matching rule use. |
| | | * |
| | | * @param description The description for this matching rule use. |
| | | */ |
| | | public void setDescription(String description) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setDescription", |
| | | String.valueOf(description)); |
| | | |
| | | this.description = description; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether this matching rule use is declared "obsolete". |
| | | * |
| | | * @return <CODE>true</CODE> if this matching rule use is declared |
| | | * "obsolete", or <CODE>false</CODE> if it is not. |
| | | * @return {@code true} if this matching rule use is declared |
| | | * "obsolete", or {@code false} if it is not. |
| | | */ |
| | | public boolean isObsolete() |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies whether this matching rule use is declared "obsolete". |
| | | * |
| | | * @param isObsolete Specifies whether this matching rule use is |
| | | * declared "obsolete". |
| | | */ |
| | | public void setObsolete(boolean isObsolete) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setObsolete", |
| | | String.valueOf(isObsolete)); |
| | | |
| | | this.isObsolete = isObsolete; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the set of attributes associated with this matching |
| | | * rule use. |
| | | * |
| | | * @return The set of attributes associated with this matching |
| | | * rule use. |
| | | */ |
| | | public CopyOnWriteArraySet<AttributeType> getAttributes() |
| | | public Set<AttributeType> getAttributes() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getAttributes"); |
| | | |
| | |
| | | * @param attributeType The attribute type for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided attribute type is |
| | | * referenced by this matching rule use, or |
| | | * <CODE>false</CODE> if it is not. |
| | | * @return {@code true} if the provided attribute type is |
| | | * referenced by this matching rule use, or {@code false} |
| | | * if it is not. |
| | | */ |
| | | public boolean appliesToAttribute(AttributeType attributeType) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of attributes for this matching rule use. |
| | | * |
| | | * @param attributes The set of attributes for this matching rule |
| | | * use. |
| | | */ |
| | | public void setAttributes( |
| | | CopyOnWriteArraySet<AttributeType> attributes) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setAttributes", |
| | | String.valueOf(attributes)); |
| | | |
| | | this.attributes = attributes; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided attribute type to the set of attributes for |
| | | * this matching rule use. This will have no effect if the provided |
| | | * attribute type is already associated with this matching rule use. |
| | | * |
| | | * @param attributeType The attribute type to add to the set of |
| | | * attributes for this matching rule use. |
| | | */ |
| | | public void addAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | attributes.add(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided attribute type from the set of attributes |
| | | * for this matching rule use. This will have no effect if the |
| | | * provided attribute type is not associated with this matching rule |
| | | * use. |
| | | * |
| | | * @param attributeType The attribute type to remove from the set |
| | | * of attributes for this matching rule use. |
| | | */ |
| | | public void removeAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | attributes.remove(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves a mapping between the names of any extra non-standard |
| | | * properties that may be associated with this matching rule use and |
| | | * the value for that property. The caller may alter the contents |
| | | * of this mapping. |
| | | * the value for that property. |
| | | * |
| | | * @return A mapping between the names of any extra non-standard |
| | | * properties that may be associated with this matching |
| | | * rule use and the value for that property. |
| | | */ |
| | | public ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | getExtraProperties() |
| | | public Map<String,List<String>> getExtraProperties() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getExtraProperties"); |
| | | |
| | |
| | | * to retrieve the value. |
| | | * |
| | | * @return The value of the specified "extra" property for this |
| | | * matching rule use, or <CODE>null</CODE> if no such |
| | | * property is defined. |
| | | * matching rule use, or {@code null} if no such property |
| | | * is defined. |
| | | */ |
| | | public CopyOnWriteArrayList<String> |
| | | getExtraProperty(String propertyName) |
| | | public List<String> getExtraProperty(String propertyName) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getExtraProperty", |
| | | String.valueOf(propertyName)); |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the provided "extra" property for this matching rule |
| | | * use. |
| | | * |
| | | * @param name The name for the "extra" property. It must not be |
| | | * {@code null}. |
| | | * @param value The value for the "extra" property, or |
| | | * {@code null} if the property is to be removed. |
| | | */ |
| | | public void setExtraProperty(String name, String value) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(value)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if (value == null) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> values = new LinkedList<String>(); |
| | | values.add(value); |
| | | |
| | | extraProperties.put(name, values); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specifies the provided "extra" property for this matching rule |
| | | * use. |
| | | * |
| | | * @param name The name for the "extra" property. It must not |
| | | * be {@code null}. |
| | | * @param values The set of value for the "extra" property, or |
| | | * {@code null} if the property is to be removed. |
| | | */ |
| | | public void setExtraProperty(String name, List<String> values) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(values)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> valuesCopy = new LinkedList<String>(values); |
| | | extraProperties.put(name, valuesCopy); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided object is equal to this matching |
| | | * rule use. The object will be considered equal if it is a |
| | | * matching rule use with the same matching rule. |
| | | * |
| | | * @param o The object for which to make the determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided object is equal to |
| | | * this matching rule use, or <CODE>false</CODE> if not. |
| | | * @return {@code true} if the provided object is equal to this |
| | | * matching rule use, or {@code false} if not. |
| | | */ |
| | | public boolean equals(Object o) |
| | | { |
| | |
| | | { |
| | | for (String property : extraProperties.keySet()) |
| | | { |
| | | CopyOnWriteArrayList<String> valueList = |
| | | extraProperties.get(property); |
| | | if ((! includeFileElement) && |
| | | property.equals(SCHEMA_PROPERTY_FILENAME)) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | List<String> valueList = extraProperties.get(property); |
| | | |
| | | buffer.append(" "); |
| | | buffer.append(property); |
| | |
| | | } |
| | | } |
| | | |
| | | if (includeFileElement && (schemaFile != null) && |
| | | (! extraProperties.containsKey(SCHEMA_PROPERTY_FILENAME))) |
| | | { |
| | | buffer.append(" "); |
| | | buffer.append(SCHEMA_PROPERTY_FILENAME); |
| | | buffer.append(" '"); |
| | | buffer.append(schemaFile); |
| | | buffer.append("'"); |
| | | } |
| | | |
| | | buffer.append(" )"); |
| | | } |
| | | } |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | | |
| | | |
| | | import java.util.Iterator; |
| | | import java.util.concurrent.ConcurrentHashMap; |
| | | import java.util.concurrent.CopyOnWriteArrayList; |
| | | import java.util.concurrent.CopyOnWriteArraySet; |
| | | import java.util.LinkedHashMap; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.LinkedList; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | | import java.util.Set; |
| | | |
| | | import org.opends.server.schema.NameFormSyntax; |
| | | |
| | | import static org.opends.server.loggers.Debug.*; |
| | | import static org.opends.server.util.ServerConstants.*; |
| | | import static org.opends.server.util.StaticUtils.*; |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | |
| | | |
| | |
| | | * and/or may be used in the RDN of an entry with a given structural |
| | | * objectclass. |
| | | */ |
| | | public class NameForm |
| | | public final class NameForm |
| | | implements SchemaFileElement |
| | | { |
| | | /** |
| | | * The fully-qualified name of this class for debugging purposes. |
| | |
| | | |
| | | |
| | | // Indicates whether this name form is declared "obsolete". |
| | | private boolean isObsolete; |
| | | private final boolean isObsolete; |
| | | |
| | | // The set of additional name-value pairs associated with this name |
| | | // form definition. |
| | | private ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | extraProperties; |
| | | private final Map<String,List<String>> extraProperties; |
| | | |
| | | // The mapping between the lowercase names and the user-provided |
| | | // names for this name form. |
| | | private ConcurrentHashMap<String,String> names; |
| | | |
| | | // The set of optional attribute types for this name form. |
| | | private CopyOnWriteArraySet<AttributeType> optionalAttributes; |
| | | |
| | | // The set of required attribute types for this name form. |
| | | private CopyOnWriteArraySet<AttributeType> requiredAttributes; |
| | | private final Map<String,String> names; |
| | | |
| | | // The reference to the structural objectclass for this name form. |
| | | private ObjectClass structuralClass; |
| | | private final ObjectClass structuralClass; |
| | | |
| | | // The set of optional attribute types for this name form. |
| | | private final Set<AttributeType> optionalAttributes; |
| | | |
| | | // The set of required attribute types for this name form. |
| | | private final Set<AttributeType> requiredAttributes; |
| | | |
| | | // The definition string used to create this name form. |
| | | private final String definition; |
| | | |
| | | // The description for this name form. |
| | | private String description; |
| | | private final String description; |
| | | |
| | | // The OID for this name form. |
| | | private String oid; |
| | | |
| | | // The path to the schema file that contains the definition for this |
| | | // name form. |
| | | private String schemaFile; |
| | | private final String oid; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new name form definition with the provided information. |
| | | * |
| | | * @param definition The definition string used to create |
| | | * this name form. It must not be |
| | | * {@code null}. |
| | | * @param names The set of names that may be used to |
| | | * reference this name form. |
| | | * @param oid The OID for this name form. |
| | | * @param oid The OID for this name form. It must |
| | | * not be {@code null}. |
| | | * @param description The description for this name form. |
| | | * @param isObsolete Indicates whether this name form is |
| | | * declared "obsolete". |
| | | * @param structuralClass The structural objectclass with which |
| | | * this name form is associated. |
| | | * this name form is associated. It |
| | | * must not be {@code null}. |
| | | * @param requiredAttributes The set of required attribute types |
| | | * for this name form. |
| | | * @param optionalAttributes The set of optional attribute types |
| | |
| | | * @param extraProperties A set of extra properties for this |
| | | * name form. |
| | | */ |
| | | public NameForm(ConcurrentHashMap<String,String> names, String oid, |
| | | String description, boolean isObsolete, |
| | | ObjectClass structuralClass, |
| | | CopyOnWriteArraySet<AttributeType> requiredAttributes, |
| | | CopyOnWriteArraySet<AttributeType> optionalAttributes, |
| | | ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | extraProperties) |
| | | public NameForm(String definition, Map<String,String> names, |
| | | String oid, String description, boolean isObsolete, |
| | | ObjectClass structuralClass, |
| | | Set<AttributeType> requiredAttributes, |
| | | Set<AttributeType> optionalAttributes, |
| | | Map<String,List<String>> extraProperties) |
| | | { |
| | | assert debugConstructor(CLASS_NAME, |
| | | new String[] |
| | | { |
| | | String.valueOf(names), |
| | | String.valueOf(oid), |
| | | String.valueOf(description), |
| | | String.valueOf(isObsolete), |
| | | String.valueOf(structuralClass), |
| | | String.valueOf(requiredAttributes), |
| | | String.valueOf(optionalAttributes), |
| | | String.valueOf(extraProperties) |
| | | }); |
| | | assert debugConstructor(CLASS_NAME, String.valueOf(definition), |
| | | String.valueOf(names), |
| | | String.valueOf(oid), |
| | | String.valueOf(description), |
| | | String.valueOf(isObsolete), |
| | | String.valueOf(structuralClass), |
| | | String.valueOf(requiredAttributes), |
| | | String.valueOf(optionalAttributes), |
| | | String.valueOf(extraProperties)); |
| | | |
| | | this.names = names; |
| | | this.oid = oid; |
| | | this.description = description; |
| | | this.isObsolete = isObsolete; |
| | | this.structuralClass = structuralClass; |
| | | this.requiredAttributes = requiredAttributes; |
| | | this.optionalAttributes = optionalAttributes; |
| | | this.schemaFile = null; |
| | | this.extraProperties = extraProperties; |
| | | ensureNotNull(definition, oid, structuralClass); |
| | | |
| | | this.definition = definition; |
| | | this.oid = oid; |
| | | this.description = description; |
| | | this.isObsolete = isObsolete; |
| | | this.structuralClass = structuralClass; |
| | | |
| | | if ((names == null) || names.isEmpty()) |
| | | { |
| | | this.names = new LinkedHashMap<String,String>(0); |
| | | } |
| | | else |
| | | { |
| | | this.names = new LinkedHashMap<String,String>(names); |
| | | } |
| | | |
| | | if ((requiredAttributes == null) || requiredAttributes.isEmpty()) |
| | | { |
| | | this.requiredAttributes = new LinkedHashSet<AttributeType>(0); |
| | | } |
| | | else |
| | | { |
| | | this.requiredAttributes = |
| | | new LinkedHashSet<AttributeType>(requiredAttributes); |
| | | } |
| | | |
| | | if ((optionalAttributes == null) || optionalAttributes.isEmpty()) |
| | | { |
| | | this.optionalAttributes = new LinkedHashSet<AttributeType>(0); |
| | | } |
| | | else |
| | | { |
| | | this.optionalAttributes = |
| | | new LinkedHashSet<AttributeType>(optionalAttributes); |
| | | } |
| | | |
| | | if ((extraProperties == null) || extraProperties.isEmpty()) |
| | | { |
| | | this.extraProperties = |
| | | new LinkedHashMap<String,List<String>>(0); |
| | | } |
| | | else |
| | | { |
| | | this.extraProperties = |
| | | new LinkedHashMap<String,List<String>>(extraProperties); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the definition string used to create this name form. |
| | | * |
| | | * @return The definition string used to create this name form. |
| | | */ |
| | | public String getDefinition() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getDefinition"); |
| | | |
| | | return definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new instance of this name form based on the definition |
| | | * string. It will also preserve other state information associated |
| | | * with this name form that is not included in the definition string |
| | | * (e.g., the name of the schema file with which it is associated). |
| | | * |
| | | * @return The new instance of this name form based on the |
| | | * definition string. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting |
| | | * to create a new name form instance |
| | | * from the definition string. |
| | | */ |
| | | public NameForm recreateFromDefinition() |
| | | throws DirectoryException |
| | | { |
| | | ByteString value = ByteStringFactory.create(definition); |
| | | Schema schema = DirectoryConfig.getSchema(); |
| | | |
| | | NameForm nf = NameFormSyntax.decodeNameForm(value, schema); |
| | | nf.setSchemaFile(getSchemaFile()); |
| | | |
| | | return nf; |
| | | } |
| | | |
| | | |
| | |
| | | * @return The set of names that may be used to reference this |
| | | * name form. |
| | | */ |
| | | public ConcurrentHashMap<String,String> getNames() |
| | | public Map<String,String> getNames() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getNames"); |
| | | |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of names that may be used to reference this |
| | | * name form. The provided set must provide a mapping between each |
| | | * name in all lowercase characters and that name in a user-defined |
| | | * form (which may include mixed capitalization). |
| | | * |
| | | * @param names The set of names that may be used to reference |
| | | * this name form. |
| | | */ |
| | | public void setNames(ConcurrentHashMap<String,String> names) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setNames", String.valueOf(names)); |
| | | |
| | | this.names = names; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided lowercase name may be used to |
| | | * reference this name form. |
| | | * |
| | | * @param lowerName The name for which to make the determination, |
| | | * in all lowercase characters. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided lowercase name may be |
| | | * used to reference this name form, or <CODE>false</CODE> |
| | | * if not. |
| | | * @return {@code true} if the provided lowercase name may be used |
| | | * to reference this name form, or {@code false} if not. |
| | | */ |
| | | public boolean hasName(String lowerName) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided name to the set of names that may be used to |
| | | * reference this name form. |
| | | * |
| | | * @param name The name to add to the set of names that may be |
| | | * used to reference this name form. |
| | | */ |
| | | public void addName(String name) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addName", String.valueOf(name)); |
| | | |
| | | String lowerName = toLowerCase(name); |
| | | names.put(lowerName, name); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided lowercase name from the set of names that |
| | | * may be used to reference this name form. |
| | | * |
| | | * @param lowerName The name to remove from the set of names that |
| | | * may be used to reference this name form, in |
| | | * all lowercase characters. |
| | | */ |
| | | public void removeName(String lowerName) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeName", |
| | | String.valueOf(lowerName)); |
| | | |
| | | names.remove(lowerName); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the OID for this name form. |
| | | * |
| | | * @return The OID for this name form. |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the OID for this name form. |
| | | * |
| | | * @param oid The OID for this name form. |
| | | */ |
| | | public void setOID(String oid) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setOID", String.valueOf(oid)); |
| | | |
| | | this.oid = oid; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the name or OID that should be used to reference this |
| | | * name form. If at least one name is defined, then the first will |
| | | * be returned. Otherwise, the OID will be returned. |
| | |
| | | * @param lowerValue The value, in all lowercase characters, that |
| | | * may be used to make the determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided lowercase value is one |
| | | * of the names or the OID of this name form, or |
| | | * <CODE>false</CODE> if it is not. |
| | | * @return {@code true} if the provided lowercase value is one of |
| | | * the names or the OID of this name form, or {@code false} |
| | | * if it is not. |
| | | */ |
| | | public boolean hasNameOrOID(String lowerValue) |
| | | { |
| | |
| | | * definition for this name form. |
| | | * |
| | | * @return The path to the schema file that contains the definition |
| | | * for this name form, or <CODE>null</CODE> if it is not |
| | | * known or if it is not stored in any schema file. |
| | | * for this name form, or {@code null} if it is not known |
| | | * or if it is not stored in any schema file. |
| | | */ |
| | | public String getSchemaFile() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getSchemaFile"); |
| | | |
| | | return schemaFile; |
| | | List<String> values = |
| | | extraProperties.get(SCHEMA_PROPERTY_FILENAME); |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | return null; |
| | | } |
| | | |
| | | return values.get(0); |
| | | } |
| | | |
| | | |
| | |
| | | assert debugEnter(CLASS_NAME, "setSchemaFile", |
| | | String.valueOf(schemaFile)); |
| | | |
| | | this.schemaFile = schemaFile; |
| | | setExtraProperty(SCHEMA_PROPERTY_FILENAME, schemaFile); |
| | | } |
| | | |
| | | |
| | |
| | | /** |
| | | * Retrieves the description for this name form. |
| | | * |
| | | * @return The description for this name form, or <CODE>null</CODE> |
| | | * if there is none. |
| | | * @return The description for this name form, or {@code true} if |
| | | * there is none. |
| | | */ |
| | | public String getDescription() |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the description for this name form. |
| | | * |
| | | * @param description The description for this name form. |
| | | */ |
| | | public void setDescription(String description) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setDescription", |
| | | String.valueOf(description)); |
| | | |
| | | this.description = description; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the reference to the structural objectclass for this |
| | | * name form. |
| | | * |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the structural objectclass for this name form. |
| | | * |
| | | * @param structuralClass The structural objectclass for this name |
| | | * form. |
| | | */ |
| | | public void setStructuralClass(ObjectClass structuralClass) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setStructuralClass", |
| | | String.valueOf(structuralClass)); |
| | | |
| | | this.structuralClass = structuralClass; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the set of required attributes for this name form. |
| | | * |
| | | * @return The set of required attributes for this name form. |
| | | */ |
| | | public CopyOnWriteArraySet<AttributeType> getRequiredAttributes() |
| | | public Set<AttributeType> getRequiredAttributes() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getRequiredAttributes"); |
| | | |
| | |
| | | * @param attributeType The attribute type for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided attribute type is |
| | | * required by this name form, or <CODE>false</CODE> if |
| | | * not. |
| | | * @return {@code true} if the provided attribute type is required |
| | | * by this name form, or {@code false} if not. |
| | | */ |
| | | public boolean isRequired(AttributeType attributeType) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of required attributes for this name form. |
| | | * |
| | | * @param requiredAttributes The set of required attributes for |
| | | * this name form. |
| | | */ |
| | | public void setRequiredAttributes(CopyOnWriteArraySet<AttributeType> |
| | | requiredAttributes) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setRequiredAttributes", |
| | | String.valueOf(requiredAttributes)); |
| | | |
| | | this.requiredAttributes = requiredAttributes; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided attribute to the set of required attributes for |
| | | * this name form. |
| | | * |
| | | * @param attributeType The attribute type to add to the set of |
| | | * required attributes for this name form. |
| | | */ |
| | | public void addRequiredAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addRequiredAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | requiredAttributes.add(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided attribute from the set of required |
| | | * attributes for this name form. |
| | | * |
| | | * @param attributeType The attribute type to remove from the set |
| | | * of required attributes for this name form. |
| | | */ |
| | | public void removeRequiredAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeRequiredAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | requiredAttributes.remove(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the set of optional attributes for this name form. |
| | | * |
| | | * @return The set of optional attributes for this name form. |
| | | */ |
| | | public CopyOnWriteArraySet<AttributeType> getOptionalAttributes() |
| | | public Set<AttributeType> getOptionalAttributes() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getOptionalAttributes"); |
| | | |
| | |
| | | * @param attributeType The attribute type for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided attribute type is |
| | | * optional for this name form, or <CODE>false</CODE> if |
| | | * not. |
| | | * @return {@code true} if the provided attribute type is optional |
| | | * for this name form, or {@code false} if not. |
| | | */ |
| | | public boolean isOptional(AttributeType attributeType) |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the set of optional attributes for this name form. |
| | | * |
| | | * @param optionalAttributes The set of optional attributes for |
| | | * this name form. |
| | | */ |
| | | public void setOptionalAttributes(CopyOnWriteArraySet<AttributeType> |
| | | optionalAttributes) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setOptionalAttributes", |
| | | String.valueOf(optionalAttributes)); |
| | | |
| | | this.optionalAttributes = optionalAttributes; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Adds the provided attribute to the set of optional attributes for |
| | | * this name form. |
| | | * |
| | | * @param attributeType The attribute type to add to the set of |
| | | * optional attributes for this name form. |
| | | */ |
| | | public void addOptionalAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "addOptionalAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | optionalAttributes.add(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Removes the provided attribute from the set of optional |
| | | * attributes for this name form. |
| | | * |
| | | * @param attributeType The attribute type to remove from the set |
| | | * optional attributes for this name form. |
| | | */ |
| | | public void removeOptionalAttribute(AttributeType attributeType) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "removeOptionalAttribute", |
| | | String.valueOf(attributeType)); |
| | | |
| | | optionalAttributes.remove(attributeType); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided attribute type is in the list of |
| | | * required or optional attributes for this name form. |
| | | * |
| | | * @param attributeType The attribute type for which to make the |
| | | * determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided attribute type is |
| | | * required or allowed for this name form, or |
| | | * <CODE>false</CODE> if it is not. |
| | | * @return {@code true} if the provided attribute type is required |
| | | * or optional for this name form, or {@code false} if it |
| | | * is not. |
| | | */ |
| | | public boolean isRequiredOrOptional(AttributeType attributeType) |
| | | { |
| | |
| | | /** |
| | | * Indicates whether this name form is declared "obsolete". |
| | | * |
| | | * @return <CODE>true</CODE> if this name form is declared |
| | | * "obsolete", or <CODE>false</CODE> if it is not. |
| | | * @return {@code true} if this name form is declared |
| | | * "obsolete", or {@code false} if it is not. |
| | | */ |
| | | public boolean isObsolete() |
| | | { |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies whether this name form is declared "obsolete". |
| | | * |
| | | * @param isObsolete Specifies whether this name form is declared |
| | | * "obsolete". |
| | | */ |
| | | public void setObsolete(boolean isObsolete) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setObsolete", |
| | | String.valueOf(isObsolete)); |
| | | |
| | | this.isObsolete = isObsolete; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves a mapping between the names of any extra non-standard |
| | | * properties that may be associated with this name form and the |
| | | * value for that property. The caller may alter the contents of |
| | | * this mapping. |
| | | * value for that property. |
| | | * |
| | | * @return A mapping between the names of any extra non-standard |
| | | * properties that may be associated with this name form |
| | | * and the value for that property. |
| | | */ |
| | | public ConcurrentHashMap<String,CopyOnWriteArrayList<String>> |
| | | getExtraProperties() |
| | | public Map<String,List<String>> getExtraProperties() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getExtraProperties"); |
| | | |
| | |
| | | * to retrieve the value. |
| | | * |
| | | * @return The value of the specified "extra" property for this |
| | | * name form, or <CODE>null</CODE> if no such property is |
| | | * name form, or {@code null} if no such property is |
| | | * defined. |
| | | */ |
| | | public CopyOnWriteArrayList<String> |
| | | getExtraProperty(String propertyName) |
| | | public List<String> getExtraProperty(String propertyName) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getExtraProperty", |
| | | String.valueOf(propertyName)); |
| | |
| | | |
| | | |
| | | /** |
| | | * Specifies the provided "extra" property for this name form. |
| | | * |
| | | * @param name The name for the "extra" property. It must not be |
| | | * {@code null}. |
| | | * @param value The value for the "extra" property, or |
| | | * {@code null} if the property is to be removed. |
| | | */ |
| | | public void setExtraProperty(String name, String value) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(value)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if (value == null) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> values = new LinkedList<String>(); |
| | | values.add(value); |
| | | |
| | | extraProperties.put(name, values); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specifies the provided "extra" property for this name form. |
| | | * |
| | | * @param name The name for the "extra" property. It must not |
| | | * be {@code null}. |
| | | * @param values The set of value for the "extra" property, or |
| | | * {@code null} if the property is to be removed. |
| | | */ |
| | | public void setExtraProperty(String name, List<String> values) |
| | | { |
| | | assert debugEnter(CLASS_NAME, "setExtraProperty", |
| | | String.valueOf(name), String.valueOf(values)); |
| | | |
| | | ensureNotNull(name); |
| | | |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | extraProperties.remove(name); |
| | | } |
| | | else |
| | | { |
| | | LinkedList<String> valuesCopy = new LinkedList<String>(values); |
| | | extraProperties.put(name, valuesCopy); |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the provided object is equal to this name form. |
| | | * The object will be considered equal if it is a name form with the |
| | | * same OID as the current name form. |
| | | * |
| | | * @param o The object for which to make the determination. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided object is equal to |
| | | * this name form, or <CODE>false</CODE> if not. |
| | | * @return {@code true} if the provided object is equal to this |
| | | * name form, or {@code true} if not. |
| | | */ |
| | | public boolean equals(Object o) |
| | | { |
| | |
| | | { |
| | | for (String property : extraProperties.keySet()) |
| | | { |
| | | CopyOnWriteArrayList<String> valueList = |
| | | extraProperties.get(property); |
| | | if ((! includeFileElement) && |
| | | property.equals(SCHEMA_PROPERTY_FILENAME)) |
| | | { |
| | | continue; |
| | | } |
| | | |
| | | List<String> valueList = extraProperties.get(property); |
| | | |
| | | buffer.append(" "); |
| | | buffer.append(property); |
| | |
| | | } |
| | | } |
| | | |
| | | if (includeFileElement && (schemaFile != null) && |
| | | (! extraProperties.containsKey(SCHEMA_PROPERTY_FILENAME))) |
| | | { |
| | | buffer.append(" "); |
| | | buffer.append(SCHEMA_PROPERTY_FILENAME); |
| | | buffer.append(" '"); |
| | | buffer.append(schemaFile); |
| | | buffer.append("'"); |
| | | } |
| | | |
| | | buffer.append(" )"); |
| | | } |
| | | } |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | | |
| | | |
| | | import static org.opends.server.loggers.Debug.debugConstructor; |
| | | import static org.opends.server.loggers.Debug.debugEnter; |
| | | import static org.opends.server.util.ServerConstants.*; |
| | | |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | import java.util.HashSet; |
| | |
| | | import java.util.Map; |
| | | import java.util.Set; |
| | | |
| | | import org.opends.server.schema.ObjectClassSyntax; |
| | | |
| | | import static org.opends.server.loggers.Debug.debugConstructor; |
| | | import static org.opends.server.loggers.Debug.debugEnter; |
| | | import static org.opends.server.util.ServerConstants.*; |
| | | import static org.opends.server.util.Validator.*; |
| | | |
| | | |
| | | |
| | | /** |
| | |
| | | * fields are accessed via their getters or via the |
| | | * {@link #toString()} methods. |
| | | */ |
| | | public final class ObjectClass extends CommonSchemaElements { |
| | | public final class ObjectClass |
| | | extends CommonSchemaElements |
| | | implements SchemaFileElement |
| | | { |
| | | /** |
| | | * The fully-qualified name of this class for debugging purposes. |
| | | */ |
| | |
| | | // contain any attribute. |
| | | private final boolean isExtensibleObject; |
| | | |
| | | // The definition string used to create this objectclass. |
| | | private final String definition; |
| | | |
| | | |
| | | |
| | | /** |
| | |
| | | * from the set of <code>names</code> will be used as the primary |
| | | * name. |
| | | * |
| | | * @param definition |
| | | * The definition string used to create this objectclass. |
| | | * It must not be {@code null}. |
| | | * @param primaryName |
| | | * The primary name for this objectclass, or |
| | | * <code>null</code> if there is no primary name. |
| | | * {@code null} if there is no primary name. |
| | | * @param names |
| | | * The set of names that may be used to reference this |
| | | * objectclass, or <code>null</code> if there are no |
| | | * name. |
| | | * objectclass. |
| | | * @param oid |
| | | * The OID for this objectclass (must not be |
| | | * <code>null</code>). |
| | | * The OID for this objectclass. It must not be |
| | | * {@code null}. |
| | | * @param description |
| | | * The description for this objectclass, or |
| | | * <code>null</code> if there is no description. |
| | | * The description for this objectclass, or {@code null} if |
| | | * there is no description. |
| | | * @param superiorClass |
| | | * The superior class for this objectclass, or |
| | | * <code>null</code> if there is no superior object |
| | | * classes. |
| | | * The superior class for this objectclass, or {@code null} |
| | | * if there is no superior object class. |
| | | * @param requiredAttributes |
| | | * The set of required attribute types for this |
| | | * objectclass, or <code>null</code> if there are no |
| | | * required attribute types. |
| | | * objectclass. |
| | | * @param optionalAttributes |
| | | * The set of optional attribute types for this |
| | | * objectclass, or <code>null</code> if there are no |
| | | * optional attribute types. |
| | | * objectclass. |
| | | * @param objectClassType |
| | | * The objectclass type for this objectclass, or |
| | | * <code>null</code> to default to structural. |
| | | * {@code null} to default to structural. |
| | | * @param isObsolete |
| | | * Indicates whether this objectclass is declared |
| | | * "obsolete". |
| | | * @param extraProperties |
| | | * A set of extra properties for this objectclass, or |
| | | * <code>null</code> if there are no extra properties. |
| | | * @throws NullPointerException |
| | | * If the <code>oid</code> is <code>null</code>. |
| | | * A set of extra properties for this objectclass. |
| | | */ |
| | | public ObjectClass(String primaryName, Collection<String> names, |
| | | String oid, String description, ObjectClass superiorClass, |
| | | Set<AttributeType> requiredAttributes, |
| | | Set<AttributeType> optionalAttributes, |
| | | ObjectClassType objectClassType, boolean isObsolete, |
| | | Map<String, List<String>> extraProperties) |
| | | throws NullPointerException { |
| | | |
| | | public ObjectClass(String definition, String primaryName, |
| | | Collection<String> names, String oid, |
| | | String description, ObjectClass superiorClass, |
| | | Set<AttributeType> requiredAttributes, |
| | | Set<AttributeType> optionalAttributes, |
| | | ObjectClassType objectClassType, |
| | | boolean isObsolete, |
| | | Map<String, List<String>> extraProperties) |
| | | { |
| | | super(primaryName, names, oid, description, isObsolete, |
| | | extraProperties); |
| | | |
| | | assert debugConstructor(CLASS_NAME, String.valueOf(primaryName), |
| | | String.valueOf(names), String.valueOf(oid), String |
| | | .valueOf(description), String.valueOf(superiorClass), |
| | | String.valueOf(requiredAttributes), String |
| | | .valueOf(optionalAttributes), String |
| | | .valueOf(objectClassType), String.valueOf(isObsolete), |
| | | String.valueOf(extraProperties)); |
| | | String.valueOf(names), |
| | | String.valueOf(oid), |
| | | String.valueOf(description), |
| | | String.valueOf(superiorClass), |
| | | String.valueOf(requiredAttributes), |
| | | String.valueOf(optionalAttributes), |
| | | String.valueOf(objectClassType), |
| | | String.valueOf(isObsolete), |
| | | String.valueOf(extraProperties)); |
| | | |
| | | ensureNotNull(definition, oid); |
| | | |
| | | this.definition = definition; |
| | | this.superiorClass = superiorClass; |
| | | |
| | | // Set flag indicating whether or not this object class allows any |
| | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the definition string used to create this objectclass. |
| | | * |
| | | * @return The definition string used to create this objectclass. |
| | | */ |
| | | public String getDefinition() |
| | | { |
| | | assert debugEnter(CLASS_NAME, "getDefinition"); |
| | | |
| | | return definition; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new instance of this objectclass based on the |
| | | * definition string. It will also preserve other state information |
| | | * associated with this objectclass that is not included in the |
| | | * definition string (e.g., the name of the schema file with which |
| | | * it is associated). |
| | | * |
| | | * @return The new instance of this objectclass based on the |
| | | * definition string. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting |
| | | * to create a new objectclass instance |
| | | * from the definition string. |
| | | */ |
| | | public ObjectClass recreateFromDefinition() |
| | | throws DirectoryException |
| | | { |
| | | ByteString value = ByteStringFactory.create(definition); |
| | | Schema schema = DirectoryConfig.getSchema(); |
| | | |
| | | ObjectClass oc = ObjectClassSyntax.decodeObjectClass(value, |
| | | schema); |
| | | oc.setSchemaFile(getSchemaFile()); |
| | | |
| | | return oc; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the reference to the superior class for this |
| | | * objectclass. |
| | | * |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = attributeType.toString(); |
| | | String valueString = attributeType.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = attributeType.toString(); |
| | | String valueString = attributeType.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = objectClass.toString(); |
| | | String valueString = objectClass.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = objectClass.toString(); |
| | | String valueString = objectClass.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = matchingRuleUse.toString(); |
| | | String valueString = matchingRuleUse.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = matchingRuleUse.toString(); |
| | | String valueString = matchingRuleUse.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = ditContentRule.toString(); |
| | | String valueString = ditContentRule.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = ditContentRule.toString(); |
| | | String valueString = ditContentRule.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = ditStructureRule.toString(); |
| | | String valueString = ditStructureRule.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = ditStructureRule.toString(); |
| | | String valueString = ditStructureRule.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = nameForm.toString(); |
| | | String valueString = nameForm.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | // rather than the attribute type because otherwise it would use |
| | | // a very expensive matching rule (OID first component match) |
| | | // that would kill performance. |
| | | String valueString = nameForm.toString(); |
| | | String valueString = nameForm.getDefinition(); |
| | | ASN1OctetString rawValue = new ASN1OctetString(valueString); |
| | | ASN1OctetString normValue = |
| | | new ASN1OctetString(toLowerCase(valueString)); |
| | |
| | | |
| | | |
| | | /** |
| | | * Recursively rebuilds all schema elements that are dependent upon |
| | | * the provided element. This must be invoked whenever an existing |
| | | * schema element is modified in order to ensure that any elements |
| | | * that depend on it should also be recreated to reflect the change. |
| | | * <BR><BR> |
| | | * The following conditions create dependencies between schema |
| | | * elements: |
| | | * <UL> |
| | | * <LI>If an attribute type references a superior attribute type, |
| | | * then it is dependent upon that superior attribute |
| | | * type.</LI> |
| | | * <LI>If an objectclass requires or allows an attribute type, |
| | | * then it is dependent upon that attribute type.</LI> |
| | | * <LI>If a name form requires or allows an attribute type in the |
| | | * RDN, then it is dependent upon that attribute type.</LI> |
| | | * <LI>If a DIT content rule requires, allows, or forbids the use |
| | | * of an attribute type, then it is dependent upon that |
| | | * attribute type.</LI> |
| | | * <LI>If a matching rule use references an attribute type, then |
| | | * it is dependent upon that attribute type.</LI> |
| | | * <LI>If an objectclass references a superior objectclass, then |
| | | * it is dependent upon that superior objectclass.</LI> |
| | | * <LI>If a name form references a structural objectclass, then it |
| | | * is dependent upon that objectclass.</LI> |
| | | * <LI>If a DIT content rule references a structural or auxiliary |
| | | * objectclass, then it is dependent upon that |
| | | * objectclass.</LI> |
| | | * <LI>If a DIT structure rule references a name form, then it is |
| | | * dependent upon that name form.</LI> |
| | | * <LI>If a DIT structure rule references a superior DIT structure |
| | | * rule, then it is dependent upon that superior DIT structure |
| | | * rule.</LI> |
| | | * </UL> |
| | | * |
| | | * @param element The element for which to recursively rebuild all |
| | | * dependent elements. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while rebuilding |
| | | * any of the schema elements. |
| | | */ |
| | | public final void rebuildDependentElements( |
| | | SchemaFileElement element) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "rebuildDependentElements", |
| | | String.valueOf(element)); |
| | | |
| | | try |
| | | { |
| | | rebuildDependentElements(element, 0); |
| | | } |
| | | catch (DirectoryException de) |
| | | { |
| | | // If we got an error as a result of a circular reference, then |
| | | // we want to make sure that the schema element we call out is |
| | | // the one that is at the root of the problem. |
| | | if (de.getErrorMessageID() == |
| | | MSGID_SCHEMA_CIRCULAR_DEPENDENCY_REFERENCE) |
| | | { |
| | | int msgID = MSGID_SCHEMA_CIRCULAR_DEPENDENCY_REFERENCE; |
| | | String message = getMessage(msgID, element.getDefinition()); |
| | | throw new DirectoryException(de.getResultCode(), message, |
| | | msgID, de); |
| | | } |
| | | |
| | | |
| | | // It wasn't a circular reference error, so just re-throw the |
| | | // exception. |
| | | throw de; |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Recursively rebuilds all schema elements that are dependent upon |
| | | * the provided element, increasing the depth for each level of |
| | | * recursion to protect against errors due to circular references. |
| | | * |
| | | * @param element The element for which to recursively rebuild all |
| | | * dependent elements. |
| | | * @param depth The current recursion depth. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while rebuilding |
| | | * any of the schema elements. |
| | | */ |
| | | private final void rebuildDependentElements( |
| | | SchemaFileElement element, int depth) |
| | | throws DirectoryException |
| | | { |
| | | assert debugEnter(CLASS_NAME, "rebuildDependentElements", |
| | | String.valueOf(element), String.valueOf(depth)); |
| | | |
| | | if (depth > 20) |
| | | { |
| | | // FIXME -- Is this an appropriate maximum depth for detecting |
| | | // circular references? |
| | | int msgID = MSGID_SCHEMA_CIRCULAR_DEPENDENCY_REFERENCE; |
| | | String message = getMessage(msgID, element.getDefinition()); |
| | | throw new DirectoryException(ResultCode.UNWILLING_TO_PERFORM, |
| | | message, msgID); |
| | | } |
| | | |
| | | |
| | | // Figure out what type of element we're dealing with and make the |
| | | // appropriate determinations for that element. |
| | | if (element instanceof AttributeType) |
| | | { |
| | | AttributeType t = (AttributeType) element; |
| | | |
| | | for (AttributeType at : attributeTypes.values()) |
| | | { |
| | | if ((at.getSuperiorType() != null) && |
| | | at.getSuperiorType().equals(t)) |
| | | { |
| | | AttributeType newAT = at.recreateFromDefinition(); |
| | | deregisterAttributeType(at); |
| | | registerAttributeType(newAT, true); |
| | | rebuildDependentElements(at, depth+1); |
| | | } |
| | | } |
| | | |
| | | for (ObjectClass oc : objectClasses.values()) |
| | | { |
| | | if (oc.getRequiredAttributes().contains(t) || |
| | | oc.getOptionalAttributes().contains(t)) |
| | | { |
| | | ObjectClass newOC = oc.recreateFromDefinition(); |
| | | deregisterObjectClass(oc); |
| | | registerObjectClass(newOC, true); |
| | | rebuildDependentElements(oc, depth+1); |
| | | } |
| | | } |
| | | |
| | | for (NameForm nf : nameFormsByOC.values()) |
| | | { |
| | | if (nf.getRequiredAttributes().contains(t) || |
| | | nf.getOptionalAttributes().contains(t)) |
| | | { |
| | | NameForm newNF = nf.recreateFromDefinition(); |
| | | deregisterNameForm(nf); |
| | | registerNameForm(newNF, true); |
| | | rebuildDependentElements(nf, depth+1); |
| | | } |
| | | } |
| | | |
| | | for (DITContentRule dcr : ditContentRules.values()) |
| | | { |
| | | if (dcr.getRequiredAttributes().contains(t) || |
| | | dcr.getOptionalAttributes().contains(t) || |
| | | dcr.getProhibitedAttributes().contains(t)) |
| | | { |
| | | DITContentRule newDCR = dcr.recreateFromDefinition(); |
| | | deregisterDITContentRule(dcr); |
| | | registerDITContentRule(newDCR, true); |
| | | rebuildDependentElements(dcr, depth+1); |
| | | } |
| | | } |
| | | |
| | | for (MatchingRuleUse mru : matchingRuleUses.values()) |
| | | { |
| | | if (mru.getAttributes().contains(t)) |
| | | { |
| | | MatchingRuleUse newMRU = mru.recreateFromDefinition(); |
| | | deregisterMatchingRuleUse(mru); |
| | | registerMatchingRuleUse(newMRU, true); |
| | | rebuildDependentElements(mru, depth+1); |
| | | } |
| | | } |
| | | } |
| | | else if (element instanceof ObjectClass) |
| | | { |
| | | ObjectClass c = (ObjectClass) element; |
| | | |
| | | for (ObjectClass oc : objectClasses.values()) |
| | | { |
| | | if ((oc.getSuperiorClass() != null) && |
| | | oc.getSuperiorClass().equals(c)) |
| | | { |
| | | ObjectClass newOC = oc.recreateFromDefinition(); |
| | | deregisterObjectClass(oc); |
| | | registerObjectClass(newOC, true); |
| | | rebuildDependentElements(oc, depth+1); |
| | | } |
| | | } |
| | | |
| | | NameForm nf = nameFormsByOC.get(c); |
| | | if (nf != null) |
| | | { |
| | | NameForm newNF = nf.recreateFromDefinition(); |
| | | deregisterNameForm(nf); |
| | | registerNameForm(newNF, true); |
| | | rebuildDependentElements(nf, depth+1); |
| | | } |
| | | |
| | | for (DITContentRule dcr : ditContentRules.values()) |
| | | { |
| | | if (dcr.getStructuralClass().equals(c) || |
| | | dcr.getAuxiliaryClasses().contains(c)) |
| | | { |
| | | DITContentRule newDCR = dcr.recreateFromDefinition(); |
| | | deregisterDITContentRule(dcr); |
| | | registerDITContentRule(newDCR, true); |
| | | rebuildDependentElements(dcr, depth+1); |
| | | } |
| | | } |
| | | } |
| | | else if (element instanceof NameForm) |
| | | { |
| | | NameForm n = (NameForm) element; |
| | | DITStructureRule dsr = ditStructureRulesByNameForm.get(n); |
| | | if (dsr != null) |
| | | { |
| | | DITStructureRule newDSR = dsr.recreateFromDefinition(); |
| | | deregisterDITStructureRule(dsr); |
| | | registerDITStructureRule(newDSR, true); |
| | | rebuildDependentElements(dsr, depth+1); |
| | | } |
| | | } |
| | | else if (element instanceof DITStructureRule) |
| | | { |
| | | DITStructureRule d = (DITStructureRule) element; |
| | | for (DITStructureRule dsr : ditStructureRulesByID.values()) |
| | | { |
| | | if (dsr.getSuperiorRules().contains(d)) |
| | | { |
| | | DITStructureRule newDSR = dsr.recreateFromDefinition(); |
| | | deregisterDITStructureRule(dsr); |
| | | registerDITStructureRule(newDSR, true); |
| | | rebuildDependentElements(dsr, depth+1); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new <CODE>Schema</CODE> object that is a duplicate of |
| | | * this one. It elements may be added and removed from the |
| | | * duplicate without impacting this version. |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying * information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This interface defines a set of methods that must be provided by a |
| | | * schema file element, which is a schema element that is loaded from |
| | | * a schema configuration file. |
| | | * <BR><BR> |
| | | * Note that this interface is not meant to be implemented by |
| | | * third-party code, and only the following classes should be |
| | | * considered schema file elements: |
| | | * <UL> |
| | | * <LI>{@code org.opends.server.types.AttributeType}</LI> |
| | | * <LI>{@code org.opends.server.types.ObjectClass}</LI> |
| | | * <LI>{@code org.opends.server.types.NameForm}</LI> |
| | | * <LI>{@code org.opends.server.types.DITContentRule}</LI> |
| | | * <LI>{@code org.opends.server.types.DITStructureRule}</LI> |
| | | * <LI>{@code org.opends.server.types.MatchingRuleUse}</LI> |
| | | * </UL> |
| | | */ |
| | | public interface SchemaFileElement |
| | | { |
| | | /** |
| | | * Retrieves the name of the schema file in which this element is |
| | | * defined. |
| | | * |
| | | * @return The name of the schema file in which this element is |
| | | * defined, or {@code null} if it is not known or this |
| | | * element is not defined in any schema file. |
| | | */ |
| | | public String getSchemaFile(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Specifies the name of the schema file in which this element is |
| | | * defined. |
| | | * |
| | | * @param schemaFile The name of the schema file in which this |
| | | * element is defined, or {@code null} if it is |
| | | * not defined in any schema file. |
| | | */ |
| | | public void setSchemaFile(String schemaFile); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the definition string that is used to represent this |
| | | * element in the schema configuration file. |
| | | * |
| | | * @return The definition string that should be used to represent |
| | | * this element in the schema configuration file. |
| | | */ |
| | | public String getDefinition(); |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new instance of this schema element based on the |
| | | * definition from the schema file. The new instance should also |
| | | * be created with all appropriate state information that may not |
| | | * be directly represented in the schema definition (e.g., the name |
| | | * of the schema file containing the definition). |
| | | * <BR><BR> |
| | | * Whenever an existing schema file element is modified with the |
| | | * server online, this method will be invoked to recreate any |
| | | * schema elements that might have been dependent upon the |
| | | * modified element. |
| | | * |
| | | * @return A new instance of this schema element based on the |
| | | * definition. |
| | | * |
| | | * @throws DirectoryException If a problem occurs while attempting |
| | | * to create the new instance of this |
| | | * schema element. |
| | | */ |
| | | public SchemaFileElement recreateFromDefinition() |
| | | throws DirectoryException; |
| | | } |
| | | |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.util; |
| | | |
| | |
| | | |
| | | |
| | | /** |
| | | * The description for the alert type that will be used for the alert |
| | | * notification generated if a problem occurs while creating copies of the |
| | | * existing schema configuration files and a problem occurs that leaves the |
| | | * schema configuration in a potentially inconsistent state. |
| | | */ |
| | | public static final String ALERT_DESCRIPTION_CANNOT_COPY_SCHEMA_FILES = |
| | | "This alert type will be used to notify administrators if a problem " + |
| | | "occurs while attempting to create copies of the existing schema " + |
| | | "configuration files before making a schema update, and the schema " + |
| | | "configuration is left in a potentially inconsistent state."; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The alert type string that will be used for the alert notification |
| | | * generated if a problem occurs while creating copies of the existing schema |
| | | * files in a manner that may leave the schema configuration inconsistent. |
| | | */ |
| | | public static final String ALERT_TYPE_CANNOT_COPY_SCHEMA_FILES = |
| | | "org.opends.server.CannotCopySchemaFiles"; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The description for the alert type that will be used for the alert |
| | | * notification generated if a problem occurs while writing new versions of |
| | | * the server schema configuration files and a problem occurs that leaves the |
| | | * schema configuration in a potentially inconsistent state. |
| | | */ |
| | | public static final String ALERT_DESCRIPTION_CANNOT_WRITE_NEW_SCHEMA_FILES = |
| | | "This alert type will be used to notify administrators if a problem " + |
| | | "occurs while attempting to write new verisons of the server schema " + |
| | | "configuration files, and the schema configuration is left in a " + |
| | | "potentially inconsistent state."; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The alert type string that will be used for the alert notification |
| | | * generated if a problem occurs while writing new versions of the server |
| | | * schema files in a manner that may leave the schema configuration |
| | | * inconsistent. |
| | | */ |
| | | public static final String ALERT_TYPE_CANNOT_WRITE_NEW_SCHEMA_FILES = |
| | | "org.opends.server.CannotWriteNewSchemaFiles"; |
| | | |
| | | |
| | | |
| | | /** |
| | | * The name of the default password storage scheme that will be used for new |
| | | * passwords. |
| | | */ |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.backends; |
| | | |
| | | |
| | | |
| | | import java.io.File; |
| | | import java.util.LinkedHashMap; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.List; |
| | | |
| | |
| | | import org.testng.annotations.Test; |
| | | |
| | | import org.opends.server.TestCaseUtils; |
| | | import org.opends.server.config.ConfigEntry; |
| | | import org.opends.server.config.ConfigException; |
| | | import org.opends.server.core.AddOperation; |
| | | import org.opends.server.core.DeleteOperation; |
| | | import org.opends.server.core.DirectoryServer; |
| | | import org.opends.server.core.ModifyOperation; |
| | | import org.opends.server.core.ModifyDNOperation; |
| | | import org.opends.server.core.SchemaConfigManager; |
| | | import org.opends.server.protocols.internal.InternalClientConnection; |
| | | import org.opends.server.protocols.internal.InternalSearchOperation; |
| | | import org.opends.server.tools.LDAPModify; |
| | |
| | | import org.opends.server.types.AttributeValue; |
| | | import org.opends.server.types.ByteStringFactory; |
| | | import org.opends.server.types.DirectoryException; |
| | | import org.opends.server.types.DITContentRule; |
| | | import org.opends.server.types.DN; |
| | | import org.opends.server.types.Entry; |
| | | import org.opends.server.types.ExistingFileBehavior; |
| | | import org.opends.server.types.InitializationException; |
| | | import org.opends.server.types.LDIFExportConfig; |
| | | import org.opends.server.types.LDIFImportConfig; |
| | | import org.opends.server.types.MatchingRuleUse; |
| | | import org.opends.server.types.Modification; |
| | | import org.opends.server.types.ModificationType; |
| | | import org.opends.server.types.ObjectClass; |
| | | import org.opends.server.types.RDN; |
| | | import org.opends.server.types.ResultCode; |
| | | import org.opends.server.types.SearchFilter; |
| | |
| | | |
| | | |
| | | /** |
| | | * Tests the {@code initializeBackend} method by providing a null |
| | | * configuration entry. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test(expectedExceptions = { ConfigException.class, |
| | | InitializationException.class }) |
| | | public void testInitializeWithNullEntry() |
| | | throws Exception |
| | | { |
| | | SchemaBackend schemaBackend = new SchemaBackend(); |
| | | schemaBackend.initializeBackend(null, new DN[0]); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the {@code isLocal} method to ensure that it is considered local. |
| | | */ |
| | | @Test() |
| | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * attribute type that is not allowed to be altered. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddUnsupportedAttr() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClass", |
| | | "objectClass: extensibleObject"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * attribute type that is not allowed to be altered. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveUnsupportedAttr() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: objectClass", |
| | | "objectClass: subschema", |
| | | "-", |
| | | "add: objectClass", |
| | | "objectClass: extensibleObject"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove all |
| | | * attribute type definitions. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveAllAttributeTypes() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: attributeTypes"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to replace all |
| | | * attribute types. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testReplaceAllAttributeTypes() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "replace: attributeTypes"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * attribute type with a valid syntax and that isn't already defined. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( 1.3.6.1.4.1.26027.1.999.4 NAME " + |
| | | "'testAddAttributeTypeSuccessful' SYNTAX " + |
| | | "1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN " + |
| | | "'SchemaBackendTestCase' )"); |
| | | "attributeTypes: ( 1.3.6.1.4.1.26027.1.999.4 " + |
| | | "NAME 'testAddAttributeTypeSuccessful' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testaddattributetypesuccessful"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testaddattributetypesuccessfulnooid-oid NAME " + |
| | | "'testAddAttributeTypeSuccessfulNoOID' SYNTAX " + |
| | | "1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN " + |
| | | "'SchemaBackendTestCase' )"); |
| | | "attributeTypes: ( testaddattributetypesuccessfulnooid-oid " + |
| | | "NAME 'testAddAttributeTypeSuccessfulNoOID' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testaddattributetypesuccessfulnooid"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * attribute type to a specific schema file. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | public void testAddAttributeTypeToAltSchemaFile() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testaddattributetypetoaltschemafile-oid " + |
| | | "NAME 'testAddAttributeTypeToAltSchemaFile' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' " + |
| | | "X-SCHEMA-FILE '98-schema-test-attrtype.ldif' )"); |
| | | |
| | | String attrName = "testaddattributetypetoaltschemafile"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | File schemaFile = new File(SchemaConfigManager.getSchemaDirectoryPath(), |
| | | "98-schema-test-attrtype.ldif"); |
| | | assertFalse(schemaFile.exists()); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | assertTrue(schemaFile.exists()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * attribute type in a manner that replaces an existing definition. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddAttributeTypeSuccessfulReplace() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testaddattributetypesuccessfulreplace-oid " + |
| | | "NAME 'testAddAttributeTypeSuccessfulReplace' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testaddattributetypesuccessfulreplace-oid " + |
| | | "NAME 'testAddAttributeTypeSuccessfulReplace' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testaddattributetypesuccessfulreplace"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to replace an |
| | | * attribute type definition in a custom schema file. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | public void testReplaceAttributeTypeInAltSchemaFile() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testreplaceattributetypeinaltschemafile-oid " + |
| | | "NAME 'testReplaceAttributeTypeInAltSchemaFile' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' " + |
| | | "X-SCHEMA-FILE '98-schema-test-replaceattrtype.ldif' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testreplaceattributetypeinaltschemafile-oid " + |
| | | "NAME 'testReplaceAttributeTypeInAltSchemaFile' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testreplaceattributetypeinaltschemafile"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | File schemaFile = new File(SchemaConfigManager.getSchemaDirectoryPath(), |
| | | "98-schema-test-replaceattrtype.ldif"); |
| | | assertFalse(schemaFile.exists()); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | assertTrue(schemaFile.exists()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * attribute type definition that can't be parsed. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * attribute type that conflicts with multiple existing types. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddAttributeTypeMultipleConflicts() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testaddattributetypemultipleconflicts-oid NAME " + |
| | | "( 'testAddAttributeTypeMultipleConflicts' 'cn' 'uid' ) SYNTAX " + |
| | | "1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN " + |
| | | "'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * attribute type that references an undefined superior attribute type. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddAttributeTypeUndefinedSuperior() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testaddattributetypeundefinedsuperior-oid NAME " + |
| | | "'testAddAttributeTypeUndefinedSuperior' SUP undefined SYNTAX " + |
| | | "1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN " + |
| | | "'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * attribute type that is defined in the server schema and does not have any |
| | | * dependencies. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveAttributeTypeSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( 1.3.6.1.4.1.26027.1.999.6 NAME " + |
| | | "'testRemoveAttributeTypeSuccessful' SYNTAX " + |
| | | "1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN " + |
| | | "'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: attributeTypes", |
| | | "attributeTypes: ( 1.3.6.1.4.1.26027.1.999.6 NAME " + |
| | | "'testRemoveAttributeTypeSuccessful' SYNTAX " + |
| | | "1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN " + |
| | | "'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testremoveattributetypesuccessful"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * attribute type and add it back in the same modification. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveThenAddAttributeTypeSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testremovethenaddattributetypesuccessful-oid " + |
| | | "NAME 'testRemoveThenAddAttributeTypeSuccessful' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: attributeTypes", |
| | | "attributeTypes: ( testremovethenaddattributetypesuccessful-oid " + |
| | | "NAME 'testRemoveThenAddAttributeTypeSuccessful' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testremovethenaddattributetypesuccessful-oid " + |
| | | "NAME 'testRemoveThenAddAttributeTypeSuccessful' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testremoveattributetypesuccessful"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * attribute type that is not defined in the server schema. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveAttributeTypeUndefined() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: attributeTypes", |
| | | "attributeTypes: ( testremoveattributetypeundefined-oid " + |
| | | "NAME 'testRemoveAttributeTypeUndefined' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testremoveattributetypeundefined"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * attribute type that is referenced as the superior type for another |
| | | * attribute type. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveSuperiorAttributeType() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: attributeTypes", |
| | | "attributeTypes: ( 2.5.4.41 NAME 'name' EQUALITY caseIgnoreMatch " + |
| | | "SUBSTR caseIgnoreSubstringsMatch " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15{32768} " + |
| | | "X-ORIGIN 'RFC 2256' )"); |
| | | |
| | | String attrName = "name"; |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * attribute type that is referenced by an existing objectclass. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveAttributeTypeReferencedByObjectClass() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: attributeTypes", |
| | | "attributeTypes: ( 0.9.2342.19200300.100.1.1 NAME 'uid' " + |
| | | "EQUALITY caseIgnoreMatch SUBSTR caseIgnoreSubstringsMatch " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15{256} " + |
| | | "X-ORIGIN 'RFC 1274' )"); |
| | | |
| | | String attrName = "uid"; |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * attribute type that is referenced by an existing name form. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveAttributeTypeReferencedByNameForm() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testremoveattributetypereferencedbynf-oid " + |
| | | "NAME 'testRemoveAttributeTypeReferencedByNF' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremoveattributetypereferencedbynfoc-oid " + |
| | | "NAME 'testRemoveAttributeTypeReferencedByNFOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testremoveattributetypereferencedbynfnf-oid " + |
| | | "NAME 'testRemoveAttributeTypeReferencedByNFNF' " + |
| | | "OC testRemoveAttributeTypeReferencedByNFOC " + |
| | | "MUST testRemoveAttributeTypeReferencedByNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: attributeTypes", |
| | | "attributeTypes: ( testremoveattributetypereferencedbynf-oid " + |
| | | "NAME 'testRemoveAttributeTypeReferencedByNF' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testremoveattributetypereferencedbynf"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * attribute type that is referenced by an existing DIT content rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveAttributeTypeReferencedByDCR() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testremoveattributetypereferencedbydcr-oid " + |
| | | "NAME 'testRemoveAttributeTypeReferencedByDCR' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremoveattributetypereferencedbydcroc-oid " + |
| | | "NAME 'testRemoveAttributeTypeReferencedByDCROC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testremoveattributetypereferencedbydcroc-oid " + |
| | | "NAME 'testRemoveAttributeTypeReferencedByDCRDCR' " + |
| | | "MAY testRemoveAttributeTypeReferencedByDCR " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: attributeTypes", |
| | | "attributeTypes: ( testremoveattributetypereferencedbydcr-oid " + |
| | | "NAME 'testRemoveAttributeTypeReferencedByDCR' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testremoveattributetypereferencedbydcr"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * attribute type that is referenced by an existing matching rule use. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveAttributeTypeReferencedByMRU() |
| | | throws Exception |
| | | { |
| | | SchemaTestMatchingRule matchingRule = |
| | | new SchemaTestMatchingRule("testRemoveATRefByMRUMatch", |
| | | "1.3.6.1.4.1.26027.1.999.17"); |
| | | DirectoryServer.registerMatchingRule(matchingRule, false); |
| | | |
| | | |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: attributeTypes", |
| | | "attributeTypes: ( testremoveatrefbymruat-oid " + |
| | | "NAME 'testRemoveATRefByMRUAT' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.17 " + |
| | | "NAME 'testRemoveATRefByMRUMRU' APPLIES testRemoveATRefByMRUAT " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: attributeTypes", |
| | | "attributeTypes: ( testremoveatrefbymruat-oid " + |
| | | "NAME 'testRemoveATRefByMRUAT' " + |
| | | "SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String attrName = "testremoveatrefbymruat"; |
| | | assertFalse(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | |
| | | MatchingRuleUse mru = |
| | | DirectoryServer.getSchema().getMatchingRuleUse(matchingRule); |
| | | assertNotNull(mru); |
| | | assertTrue(mru.hasName("testremoveatrefbymrumru")); |
| | | |
| | | assertTrue(DirectoryServer.getSchema().hasAttributeType(attrName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * objectclass that doesn't already exist, that has a valid superior class, |
| | | * and for which all attributes contained in it are already defined. |
| | | * |
| | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * objectclass to a specific schema file. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddObjectClassToAltSchemaFile() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddobjectclasstoaltschemafile-oid NAME " + |
| | | "'testAddObjectClassToAltSchemaFile' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase' " + |
| | | "X-SCHEMA-FILE '98-schema-test-oc.ldif' )"); |
| | | |
| | | String ocName = "testaddobjectclasstoaltschemafile"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | File schemaFile = new File(SchemaConfigManager.getSchemaDirectoryPath(), |
| | | "98-schema-test-oc.ldif"); |
| | | assertFalse(schemaFile.exists()); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | assertTrue(schemaFile.exists()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * objectclass that already exists (i.e., a replace) |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddObjectClassSuccessfulReplace() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddobjectclasssuccessfulreplace-oid " + |
| | | "NAME 'testAddObjectClassSuccessfulReplace' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddobjectclasssuccessfulreplace-oid " + |
| | | "NAME 'testAddObjectClassSuccessfulReplace' SUP top STRUCTURAL " + |
| | | "MUST cn MAY description X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String ocName = "testaddobjectclasssuccessfulreplace"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * objectclass that conflicts with multiple existing objectclasses. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddObjectClassMultipleConflicts() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddobjectclassmultipleconflicts-oid " + |
| | | "NAME ( 'testAddObjectClassMultipleConflicts' 'person' " + |
| | | "'device' ) SUP top STRUCTURAL MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String ocName = "testaddobjectclassmultipleconflicts"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * existing objectclass definition and then add it back in the same operation |
| | | * with a different definition. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveThenAddAddObjectClassSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremovethenaddobjectclasssuccessful-oid " + |
| | | "NAME 'testRemoveThenAddObjectClassSuccessful' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: objectClasses", |
| | | "objectClasses: ( testremovethenaddobjectclasssuccessful-oid " + |
| | | "NAME 'testRemoveThenAddObjectClassSuccessful' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremovethenaddobjectclasssuccessful-oid " + |
| | | "NAME 'testRemoveThenAddObjectClassSuccessful' SUP top " + |
| | | "STRUCTURAL MUST cn MAY description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String ocName = "testremovethenaddobjectclasssuccessful"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * objectclass definition that can't be parsed. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * objectclass that exists and for which there are no dependencies. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveObjectClassSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( 1.3.6.1.4.1.26027.1.999.7 NAME " + |
| | | "'testRemoveObjectClassSuccessful' SUP top STRUCTURAL MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: objectClasses", |
| | | "objectClasses: ( 1.3.6.1.4.1.26027.1.999.7 NAME " + |
| | | "'testRemoveObjectClassSuccessful' SUP top STRUCTURAL MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String ocName = "testremoveobjectclasssuccessful"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * objectclass that is the superior class for another objectclass. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveSuperiorObjectClass() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: objectClasses", |
| | | "objectClasses: ( 2.5.6.6 NAME 'person' SUP top STRUCTURAL " + |
| | | "MUST ( sn $ cn ) MAY ( userPassword $ telephoneNumber $ " + |
| | | "seeAlso $ description ) X-ORIGIN 'RFC 2256' )"); |
| | | |
| | | String ocName = "person"; |
| | | assertTrue(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertTrue(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * objectclass that is referenced by an existing name form. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveObjectClassReferencedByNameForm() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremoveobjectclassreferencedbynf-oid " + |
| | | "NAME 'testRemoveObjectClassReferencedByNF' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testremoveattributetypereferencedbynfnf-oid " + |
| | | "NAME 'testRemoveObjectClassReferencedByNFNF' " + |
| | | "OC testRemoveObjectClassReferencedByNF MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: objectClasses", |
| | | "objectClasses: ( testremoveobjectclassreferencedbynf-oid " + |
| | | "NAME 'testRemoveObjectClassReferencedByNF' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')"); |
| | | |
| | | String ocName = "testremoveobjectclassreferencedbynf"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertTrue(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * objectclass that is referenced by an existing DIT content rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveObjectClassReferencedByDCR() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremoveobjectclassreferencedbydcr-oid " + |
| | | "NAME 'testRemoveObjectClassReferencedByDCR' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testremoveobjectclassreferencedbydcr-oid " + |
| | | "NAME 'testRemoveObjectClassReferencedByDCRDCR' " + |
| | | "MAY description X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: objectClasses", |
| | | "objectClasses: ( testremoveobjectclassreferencedbydcr-oid " + |
| | | "NAME 'testRemoveObjectClassReferencedByDCR' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')"); |
| | | |
| | | String ocName = "testremoveobjectclassreferencedbydcr"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertTrue(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new name |
| | | * form that doesn't already exist. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddNameFormSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddnameformsuccessfuloc-oid " + |
| | | "NAME 'testAddNameFormSuccessfulOC' SUP top STRUCTURAL MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( 1.3.6.1.4.1.26027.1.999.8 " + |
| | | "NAME 'testAddNameFormSuccessful' " + |
| | | "OC testAddNameFormSuccessfulOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String nameFormName = "testaddnameformsuccessful"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new name |
| | | * form that doesn't already exist to an alternate schema file. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddNameFormToAltSchemaFile() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddnameformtoaltschemafileoc-oid " + |
| | | "NAME 'testAddNameFormToAltSchemaFileOC' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testaddnameformtoaltschemafile-oid " + |
| | | "NAME 'testAddNameFormToAltSchemaFile' " + |
| | | "OC testAddNameFormToAltSchemaFileOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' " + |
| | | "X-SCHEMA-FILE '98-schema-test-nameform.ldif' )"); |
| | | |
| | | String nameFormName = "testaddnameformtoaltschemafile"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | File schemaFile = new File(SchemaConfigManager.getSchemaDirectoryPath(), |
| | | "98-schema-test-nameform.ldif"); |
| | | assertFalse(schemaFile.exists()); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | assertTrue(schemaFile.exists()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new name |
| | | * form that references a required attribute type not defined in the server |
| | | * schema. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddNameFormWithUndefinedReqAT() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddnameformwithundefinedreqatoc-oid " + |
| | | "NAME 'testAddNameFormWithUndefinedReqATOC' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testaddnameformwithundefinereqdat-oid " + |
| | | "NAME 'testAddNameFormWithUndefinedReqAT' " + |
| | | "OC testAddNameFormWithUndefinedReqATOC MUST xxxundefinedxxx " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String nameFormName = "testaddnameformwithundefinedreqat"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new name |
| | | * form that references an optional attribute type not defined in the server |
| | | * schema. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddNameFormWithUndefinedOptAT() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddnameformwithundefinedoptatoc-oid " + |
| | | "NAME 'testAddNameFormWithUndefinedOptATOC' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testaddnameformwithundefineoptdat-oid " + |
| | | "NAME 'testAddNameFormWithUndefinedOptAT' " + |
| | | "OC testAddNameFormWithUndefinedOptATOC MUST cn " + |
| | | "MAY xxxundefinedxxx X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String nameFormName = "testaddnameformwithundefinedoptat"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new name |
| | | * form whose structural objectclass is not defined in the server schema. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddNameFormWithUndefinedOC() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: nameForms", |
| | | "nameForms: ( testaddnameformwithundefinedoc-oid " + |
| | | "NAME 'testAddNameFormWithUndefinedOC' " + |
| | | "OC xxxundefinedxxx MUST cn X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String nameFormName = "testaddnameformwithundefinedoc"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new name |
| | | * form whose objectclass auxiliary rather than structural. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddNameFormWithAuxiliaryOC() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddnameformwithauxiliaryococ-oid " + |
| | | "NAME 'testAddNameFormWithAuxiliaryOCOC' SUP top AUXILIARY " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testaddnameformwithauxiliaryoc-oid " + |
| | | "NAME 'testAddNameFormWithAuxiliaryOC' " + |
| | | "OC testAddNameFormWithAuxiliaryOCOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String nameFormName = "testaddnameformwithauxiliaryoc"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new name |
| | | * form that references a structural objectclass already referenced by another |
| | | * name form. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddNameFormOCConflict() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddnameformocconflictoc-oid " + |
| | | "NAME 'testAddNameFormOCConflictOC' SUP top STRUCTURAL MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testaddnameformocconflict-oid " + |
| | | "NAME 'testAddNameFormOCConflict' " + |
| | | "OC testAddNameFormOCConflictOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: nameForms", |
| | | "nameForms: ( testaddnameformocconflict2-oid " + |
| | | "NAME 'testAddNameFormOCConflict2' " + |
| | | "OC testAddNameFormOCConflictOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String nameFormName = "testaddnameformocconflict2"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * existing name form. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveNameFormSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremovenameformsuccessfuloc-oid " + |
| | | "NAME 'testRemoveNameFormSuccessfulOC' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( 1.3.6.1.4.1.26027.1.999.9 " + |
| | | "NAME 'testRemoveNameFormSuccessful' " + |
| | | "OC testRemoveNameFormSuccessfulOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: nameForms", |
| | | "nameForms: ( 1.3.6.1.4.1.26027.1.999.9 " + |
| | | "NAME 'testRemoveNameFormSuccessful' " + |
| | | "OC testRemoveNameFormSuccessfulOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String nameFormName = "testremovenameformsuccessful"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * existing name form and then add it back in the same operation. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveThenAddNameFormSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremovethenaddnameformsuccessfuloc-oid " + |
| | | "NAME 'testRemoveThenAddNameFormSuccessfulOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testremovethenaddnameformsuccessful-oid " + |
| | | "NAME 'testRemoveThenAddNameFormSuccessful' " + |
| | | "OC testRemoveThenAddNameFormSuccessfulOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: nameForms", |
| | | "nameForms: ( testremovethenaddnameformsuccessful-oid " + |
| | | "NAME 'testRemoveThenAddNameFormSuccessful' " + |
| | | "OC testRemoveThenAddNameFormSuccessfulOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testremovethenaddnameformsuccessful-oid " + |
| | | "NAME 'testRemoveThenAddNameFormSuccessful' " + |
| | | "OC testRemoveThenAddNameFormSuccessfulOC MUST cn MAY sn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String nameFormName = "testremovethenaddnameformsuccessful"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove a name |
| | | * form that is referenced by a DIT structure rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveNameFormReferencedByDSR() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremovenameformreferencedbydsroc-oid " + |
| | | "NAME 'testRemoveNameFormReferencedByDSROC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testremovenameformreferencedbydsrnf-oid " + |
| | | "NAME 'testRemoveNameFormReferencedByDSRNF' " + |
| | | "OC testRemoveNameFormReferencedByDSROC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999009 " + |
| | | "NAME 'testRemoveNameFormReferencedByDSRDSR' " + |
| | | "FORM testRemoveNameFormReferencedByDSRNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: nameForms", |
| | | "nameForms: ( testremovenameformreferencedbydsrnf-oid " + |
| | | "NAME 'testRemoveNameFormReferencedByDSRNF' " + |
| | | "OC testRemoveNameFormReferencedByDSROC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | String nameFormName = "testremovenameformreferencedbydsrnf"; |
| | | assertFalse(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertTrue(DirectoryServer.getSchema().hasNameForm(nameFormName)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new DIT |
| | | * content rule that doesn't already exist. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITContentRuleSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddditcontentrulesuccessfuloc-oid " + |
| | | "NAME 'testAddDITContentRuleSuccessfulOC' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testaddditcontentrulesuccessfuloc-oid " + |
| | | "NAME 'testAddDITContentRuleSuccessful' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | String ocName = "testaddditcontentrulesuccessfuloc"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | ObjectClass oc = DirectoryServer.getSchema().getObjectClass(ocName); |
| | | assertNotNull(oc); |
| | | |
| | | DITContentRule dcr = DirectoryServer.getSchema().getDITContentRule(oc); |
| | | assertNotNull(dcr); |
| | | assertTrue(dcr.hasName("testaddditcontentrulesuccessful")); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to replace an |
| | | * existing DIT content rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testReplaceDITContentRuleSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testreplaceditcontentrulesuccessfuloc-oid " + |
| | | "NAME 'testReplaceDITContentRuleSuccessfulOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testreplaceditcontentrulesuccessfuloc-oid " + |
| | | "NAME 'testReplaceDITContentRuleSuccessful' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testreplaceditcontentrulesuccessfuloc-oid " + |
| | | "NAME 'testReplaceDITContentRuleSuccessful' MAY sn " + |
| | | "NOT description X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | String ocName = "testreplaceditcontentrulesuccessfuloc"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | ObjectClass oc = DirectoryServer.getSchema().getObjectClass(ocName); |
| | | assertNotNull(oc); |
| | | |
| | | DITContentRule dcr = DirectoryServer.getSchema().getDITContentRule(oc); |
| | | assertNotNull(dcr); |
| | | assertTrue(dcr.hasName("testreplaceditcontentrulesuccessful")); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new DIT |
| | | * content rule to an alternate schema file. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITContentRuleToAltSchemaFile() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testadddcrtoaltschemafileoc-oid " + |
| | | "NAME 'testAddDCRToAltSchemaFileOC' SUP top STRUCTURAL " + |
| | | "MUST cn X-SCHEMA-FILE '98-schema-test-dcr.ldif' " + |
| | | "X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testadddcrtoaltschemafileoc-oid " + |
| | | "NAME 'testAddDCRToAltSchemaFile' NOT description " + |
| | | "X-SCHEMA-FILE '98-schema-test-dcr.ldif' " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | String ocName = "testadddcrtoaltschemafileoc"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | File schemaFile = new File(SchemaConfigManager.getSchemaDirectoryPath(), |
| | | "98-schema-test-dcr.ldif"); |
| | | assertFalse(schemaFile.exists()); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | ObjectClass oc = DirectoryServer.getSchema().getObjectClass(ocName); |
| | | assertNotNull(oc); |
| | | |
| | | DITContentRule dcr = DirectoryServer.getSchema().getDITContentRule(oc); |
| | | assertNotNull(dcr); |
| | | assertTrue(dcr.hasName("testadddcrtoaltschemafile")); |
| | | |
| | | assertTrue(schemaFile.exists()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * existing DIT content rule and add it back in the same operation. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveThenAddDITContentRule() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremovethenaddditcontentruleoc-oid " + |
| | | "NAME 'testRemoveThenAddDITContentRuleOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testremovethenaddditcontentruleoc-oid " + |
| | | "NAME 'testRemoveThenAddDITContentRule' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: ditContentRules", |
| | | "ditContentRules: ( testremovethenaddditcontentruleoc-oid " + |
| | | "NAME 'testRemoveThenAddDITContentRule' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testremovethenaddditcontentruleoc-oid " + |
| | | "NAME 'testRemoveThenAddDITContentRule' MAY sn " + |
| | | "NOT description X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | String ocName = "testremovethenaddditcontentruleoc"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | ObjectClass oc = DirectoryServer.getSchema().getObjectClass(ocName); |
| | | assertNotNull(oc); |
| | | |
| | | DITContentRule dcr = DirectoryServer.getSchema().getDITContentRule(oc); |
| | | assertNotNull(dcr); |
| | | assertTrue(dcr.hasName("testremovethenaddditcontentrule")); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new DIT |
| | | * content rule whose structural objectclass is not defined in the schema. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITContentRuleUndefinedOC() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( xxxundefinedxxx-oid " + |
| | | "NAME 'testAddDITContentRuleUndefinedOC' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new DIT |
| | | * content rule whose structural objectclass is not actually structural. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITContentRuleAuxiliaryOC() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddditcontentruleauxiliaryococ-oid " + |
| | | "NAME 'testAddDITContentRuleAuxiliaryOCOC' SUP top AUXILIARY " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testaddditcontentruleauxiliaryococ-oid " + |
| | | "NAME 'testAddDITContentRuleAuxiliaryOC' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new DIT |
| | | * content rule whose structural objectclass is already referenced by an |
| | | * existing DIT content rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITContentRuleConflictingOC() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddditcontentruleconflictingococ-oid " + |
| | | "NAME 'testAddDITContentRuleConflictingOCOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testaddditcontentruleconflictingococ-oid " + |
| | | "NAME 'testAddDITContentRuleConflictingOC' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testaddditcontentruleconflictingococ-oid " + |
| | | "NAME 'testAddDITContentRuleConflictingOC2' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new DIT |
| | | * content rule with an undefined auxiliary objectclass. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITContentRuleUndefinedAuxOC() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddditcontentruleundefinedauxococ-oid " + |
| | | "NAME 'testAddDITContentRuleUndefinedAuxOCOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testaddditcontentruleundefinedauxococ-oid " + |
| | | "NAME 'testAddDITContentRuleUndefinedAuxOC' " + |
| | | "AUX xxxundefinedxxx X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new DIT |
| | | * content rule that references an undefined required attribute type. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITContentRuleUndefinedReqAT() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddditcontentruleundefinedreqatoc-oid " + |
| | | "NAME 'testAddDITContentRuleAuxiliaryOCOC' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testaddditcontentruleundefinedreqatoc-oid " + |
| | | "NAME 'testAddDITContentRuleUndefinedReqAT' " + |
| | | "MUST xxxundefinedxxx X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new DIT |
| | | * content rule that references an undefined optional attribute type. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITContentRuleUndefinedOptAT() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddditcontentruleundefinedoptatoc-oid " + |
| | | "NAME 'testAddDITContentRuleAuxiliaryOCOC' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testaddditcontentruleundefinedoptatoc-oid " + |
| | | "NAME 'testAddDITContentRuleUndefinedOptAT' " + |
| | | "MAY xxxundefinedxxx X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new DIT |
| | | * content rule that references an undefined prohibited attribute type. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITContentRuleUndefinedNotAT() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddditcontentruleundefinednotatoc-oid " + |
| | | "NAME 'testAddDITContentRuleAuxiliaryOCOC' SUP top STRUCTURAL " + |
| | | "MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testaddditcontentruleundefinednotatoc-oid " + |
| | | "NAME 'testAddDITContentRuleUndefinedNotAT' " + |
| | | "NOT xxxundefinedxxx X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * existing DIT content rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveDITContentRuleSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremoveditcontentrulesuccessfuloc-oid " + |
| | | "NAME 'testRemoveDITContentRuleSuccessfulOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: ditContentRules", |
| | | "ditContentRules: ( testremoveditcontentrulesuccessfuloc-oid " + |
| | | "NAME 'testRemoveDITContentRuleSuccessful' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: ditContentRules", |
| | | "ditContentRules: ( testremoveditcontentrulesuccessfuloc-oid " + |
| | | "NAME 'testRemoveDITContentRuleSuccessful' NOT description " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | String ocName = "testremoveditcontentrulesuccessfuloc"; |
| | | assertFalse(DirectoryServer.getSchema().hasObjectClass(ocName)); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | ObjectClass oc = DirectoryServer.getSchema().getObjectClass(ocName); |
| | | assertNotNull(oc); |
| | | |
| | | DITContentRule dcr = DirectoryServer.getSchema().getDITContentRule(oc); |
| | | assertNull(dcr); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * DIT structure rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITStructureRuleSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddditstructurerulesuccessfuloc-oid " + |
| | | "NAME 'testAddDITStructureRuleSuccessfulOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testaddditstructurerulesuccessfulnf-oid " + |
| | | "NAME 'testAddDITStructureRuleSuccessfulNF' " + |
| | | "OC testAddDITStructureRuleSuccessfulOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999001 " + |
| | | "NAME 'testAddDITStructureRuleSuccessful' " + |
| | | "FORM testAddDITStructureRuleSuccessfulNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | int ruleID = 999001; |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to replace an |
| | | * existing DIT structure rule definition. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testReplaceDITStructureRuleSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testreplaceditstructurerulesuccessfuloc-oid " + |
| | | "NAME 'testReplaceDITStructureRuleSuccessfulOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testreplaceditstructurerulesuccessfulnf-oid " + |
| | | "NAME 'testReplaceDITStructureRuleSuccessfulNF' " + |
| | | "OC testReplaceDITStructureRuleSuccessfulOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999002 " + |
| | | "NAME 'testReplaceDITStructureRuleSuccessful' " + |
| | | "FORM testReplaceDITStructureRuleSuccessfulNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999002 " + |
| | | "NAME 'testReplaceDITStructureRuleSuccessful' " + |
| | | "DESC 'Testing the replacement of an existing DSR' " + |
| | | "FORM testReplaceDITStructureRuleSuccessfulNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | int ruleID = 999002; |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * DIT structure rule to an alternate schema file. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITStructureRuleToAltSchemaFile() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testaddditstructureruletoaltschemafileoc-oid " + |
| | | "NAME 'testAddDITStructureRuleToAltSchemaFileOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-SCHEMA-FILE '98-schema-test-dsr.ldif' " + |
| | | "X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testaddditstructureruletoaltschemafilenf-oid " + |
| | | "NAME 'testAddDITStructureRuleToAltSchemaFileNF' " + |
| | | "OC testAddDITStructureRuleToAltSchemaFileOC MUST cn " + |
| | | "X-SCHEMA-FILE '98-schema-test-dsr.ldif' " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999010 " + |
| | | "NAME 'testAddDITStructureRuleToAltSchemaFile' " + |
| | | "FORM testAddDITStructureRuleToAltSchemaFileNF " + |
| | | "X-SCHEMA-FILE '98-schema-test-dsr.ldif' " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | int ruleID = 999010; |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | File schemaFile = new File(SchemaConfigManager.getSchemaDirectoryPath(), |
| | | "98-schema-test-dsr.ldif"); |
| | | assertFalse(schemaFile.exists()); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | assertTrue(schemaFile.exists()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * existing DIT structure rule definition and add it back in the same |
| | | * operation. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveAndAddDITStructureRuleSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremoveandaddditstructurerulesuccessfuloc-oid " + |
| | | "NAME 'testRemoveAndAddDITStructureRuleSuccessfulOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testremoveandaddditstructurerulesuccessfulnf-oid " + |
| | | "NAME 'testRemoveAndAddDITStructureRuleSuccessfulNF' " + |
| | | "OC testRemoveAndAddDITStructureRuleSuccessfulOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999003 " + |
| | | "NAME 'testRemoveAndAddDITStructureRuleSuccessful' " + |
| | | "FORM testRemoveAndAddDITStructureRuleSuccessfulNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: ditStructureRules", |
| | | "ditStructureRules: ( 999003 " + |
| | | "NAME 'testRemoveAndAddDITStructureRuleSuccessful' " + |
| | | "FORM testRemoveAndAddDITStructureRuleSuccessfulNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999003 " + |
| | | "NAME 'testRemoveAndAddDITStructureRuleSuccessful' " + |
| | | "DESC 'Testing removing and re-adding an existing DSR' " + |
| | | "FORM testRemoveAndAddDITStructureRuleSuccessfulNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | int ruleID = 999003; |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertTrue(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * DIT structure rule with an undefined name form. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITStructureRuleUndefinedNameForm() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999004 " + |
| | | "NAME 'testAddDITStructureRuleUndefinedNameForm' " + |
| | | "FORM xxxundefinedxxx " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | int ruleID = 999004; |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * DIT structure rule that references an undefined superior rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddDITStructureRuleUndefinedSuperior() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testadddsrundefinedsuperioroc-oid " + |
| | | "NAME 'testAddDSRUndefinedSuperiorOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testadddsrundefinedsuperiornf-oid " + |
| | | "NAME 'testAddDSRUndefinedSuperiorNF' " + |
| | | "OC testAddDSRUndefinedSuperiorOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999005 " + |
| | | "NAME 'testAddDSRUndefinedSuperior' " + |
| | | "FORM testAddDSRUndefinedSuperiorNF SUP 999000 " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | int ruleID = 999005; |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * existing DIT structure rule definition. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveDITStructureRuleSuccessful() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremoveditstructurerulesuccessfuloc-oid " + |
| | | "NAME 'testRemoveDITStructureRuleSuccessfulOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testremoveditstructurerulesuccessfulnf-oid " + |
| | | "NAME 'testRemoveDITStructureRuleSuccessfulNF' " + |
| | | "OC testRemoveDITStructureRuleSuccessfulOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999006 " + |
| | | "NAME 'testRemoveDITStructureRuleSuccessful' " + |
| | | "FORM testRemoveDITStructureRuleSuccessfulNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: ditStructureRules", |
| | | "ditStructureRules: ( 999006 " + |
| | | "NAME 'testRemoveDITStructureRuleSuccessful' " + |
| | | "FORM testRemoveDITStructureRuleSuccessfulNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | int ruleID = 999006; |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * existing DIT structure rule definition which is the superior rule for |
| | | * another DIT structure rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveSuperiorDITStructureRule() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: objectClasses", |
| | | "objectClasses: ( testremovesuperiorditstructureruleoc-oid " + |
| | | "NAME 'testRemoveSuperiorDITStructureRuleOC' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "objectClasses: ( testremovesuperiorditstructureruleoc2-oid " + |
| | | "NAME 'testRemoveSuperiorDITStructureRuleOC2' SUP top " + |
| | | "STRUCTURAL MUST cn X-ORIGIN 'SchemaBackendTestCase')", |
| | | "-", |
| | | "add: nameForms", |
| | | "nameForms: ( testremovesuperiorditstructurerulenf-oid " + |
| | | "NAME 'testRemoveSuperiorDITStructureRuleNF' " + |
| | | "OC testRemoveSuperiorDITStructureRuleOC MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "nameForms: ( testremovesuperiorditstructurerulenf2-oid " + |
| | | "NAME 'testRemoveSuperiorDITStructureRuleNF2' " + |
| | | "OC testRemoveSuperiorDITStructureRuleOC2 MUST cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: ditStructureRules", |
| | | "ditStructureRules: ( 999007 " + |
| | | "NAME 'testRemoveSuperiorDITStructureRule' " + |
| | | "FORM testRemoveSuperiorDITStructureRuleNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "ditStructureRules: ( 999008 " + |
| | | "NAME 'testRemoveSuperiorDITStructureRule2' " + |
| | | "FORM testRemoveSuperiorDITStructureRuleNF2 SUP 999007 " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: ditStructureRules", |
| | | "ditStructureRules: ( 999007 " + |
| | | "NAME 'testRemoveSuperiorDITStructureRule' " + |
| | | "FORM testRemoveSuperiorDITStructureRuleNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | int ruleID = 999007; |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | assertTrue(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | |
| | | |
| | | path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: ditStructureRules", |
| | | "ditStructureRules: ( 999008 " + |
| | | "NAME 'testRemoveSuperiorDITStructureRule2' " + |
| | | "FORM testRemoveSuperiorDITStructureRuleNF2 SUP 999007 " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "ditStructureRules: ( 999007 " + |
| | | "NAME 'testRemoveSuperiorDITStructureRule' " + |
| | | "FORM testRemoveSuperiorDITStructureRuleNF " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | args = new String[] |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | assertFalse(DirectoryServer.getSchema().hasDITStructureRule(ruleID)); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * matching rule use that doesn't already exist. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddMatchingRuleUseSuccessful() |
| | | throws Exception |
| | | { |
| | | SchemaTestMatchingRule matchingRule = |
| | | new SchemaTestMatchingRule("testAddMRUSuccessfulMatch", |
| | | "1.3.6.1.4.1.26027.1.999.10"); |
| | | DirectoryServer.registerMatchingRule(matchingRule, false); |
| | | |
| | | |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.10 " + |
| | | "NAME 'testAddMRUSuccessful' APPLIES cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | assertFalse(DirectoryServer.getSchema().hasMatchingRuleUse(matchingRule)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | MatchingRuleUse mru = |
| | | DirectoryServer.getSchema().getMatchingRuleUse(matchingRule); |
| | | assertNotNull(mru); |
| | | assertTrue(mru.hasName("testaddmrusuccessful")); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * matching rule to an alternate schema file. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddMatchingRuleUseToAltSchemaFile() |
| | | throws Exception |
| | | { |
| | | SchemaTestMatchingRule matchingRule = |
| | | new SchemaTestMatchingRule("testAddMRUToAltSchemaFileMatch", |
| | | "1.3.6.1.4.1.26027.1.999.18"); |
| | | DirectoryServer.registerMatchingRule(matchingRule, false); |
| | | |
| | | |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.18 " + |
| | | "NAME 'testAddMRUToAltSchemaFile' APPLIES cn " + |
| | | "X-SCHEMA-FILE '98-schema-test-mru.ldif' " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | assertFalse(DirectoryServer.getSchema().hasMatchingRuleUse(matchingRule)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | File schemaFile = new File(SchemaConfigManager.getSchemaDirectoryPath(), |
| | | "98-schema-test-mru.ldif"); |
| | | assertFalse(schemaFile.exists()); |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | MatchingRuleUse mru = |
| | | DirectoryServer.getSchema().getMatchingRuleUse(matchingRule); |
| | | assertNotNull(mru); |
| | | assertTrue(mru.hasName("testaddmrutoaltschemafile")); |
| | | |
| | | assertTrue(schemaFile.exists()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to replace an |
| | | * existing matching rule use. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testReplaceMatchingRuleUseSuccessful() |
| | | throws Exception |
| | | { |
| | | SchemaTestMatchingRule matchingRule = |
| | | new SchemaTestMatchingRule("testReplaceMRUSuccessfulMatch", |
| | | "1.3.6.1.4.1.26027.1.999.11"); |
| | | DirectoryServer.registerMatchingRule(matchingRule, false); |
| | | |
| | | |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.11 " + |
| | | "NAME 'testReplaceMRUSuccessful' APPLIES cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.11 " + |
| | | "NAME 'testReplaceMRUSuccessful' APPLIES ( cn $ sn ) " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | assertFalse(DirectoryServer.getSchema().hasMatchingRuleUse(matchingRule)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | MatchingRuleUse mru = |
| | | DirectoryServer.getSchema().getMatchingRuleUse(matchingRule); |
| | | assertNotNull(mru); |
| | | assertTrue(mru.hasName("testreplacemrusuccessful")); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove and |
| | | * re-add an existing matching rule use in the same operation. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveAndAddMatchingRuleUse() |
| | | throws Exception |
| | | { |
| | | SchemaTestMatchingRule matchingRule = |
| | | new SchemaTestMatchingRule("testRemoveAndAddMRUMatch", |
| | | "1.3.6.1.4.1.26027.1.999.12"); |
| | | DirectoryServer.registerMatchingRule(matchingRule, false); |
| | | |
| | | |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.12 " + |
| | | "NAME 'testRemoveAndAddMRU' APPLIES cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.12 " + |
| | | "NAME 'testRemoveAndAddMRU' APPLIES cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "-", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.12 " + |
| | | "NAME 'testRemoveAndAddMRU' APPLIES ( cn $ sn ) " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | assertFalse(DirectoryServer.getSchema().hasMatchingRuleUse(matchingRule)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | MatchingRuleUse mru = |
| | | DirectoryServer.getSchema().getMatchingRuleUse(matchingRule); |
| | | assertNotNull(mru); |
| | | assertTrue(mru.hasName("testremoveandaddmru")); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a matching |
| | | * rule use that references the same matching rule as another matching rule |
| | | * use. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddMatchingRuleUseMRConflict() |
| | | throws Exception |
| | | { |
| | | SchemaTestMatchingRule matchingRule = |
| | | new SchemaTestMatchingRule("testAddMRUMRConflictMatch", |
| | | "1.3.6.1.4.1.26027.1.999.14"); |
| | | DirectoryServer.registerMatchingRule(matchingRule, false); |
| | | |
| | | |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.14 " + |
| | | "NAME 'testAddMRUMRConflict' APPLIES cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.14 " + |
| | | "NAME 'testAddMRUMRConflict2' APPLIES sn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | assertFalse(DirectoryServer.getSchema().hasMatchingRuleUse(matchingRule)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | |
| | | MatchingRuleUse mru = |
| | | DirectoryServer.getSchema().getMatchingRuleUse(matchingRule); |
| | | assertNotNull(mru); |
| | | assertTrue(mru.hasName("testaddmrumrconflict")); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * matching rule use that references an undefined matching rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddMatchingRuleUseMRUndefined() |
| | | throws Exception |
| | | { |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.15 " + |
| | | "NAME 'testAddMRUMRUndefined' APPLIES cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to add a new |
| | | * matching rule use that references an undefined attribute type. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testAddMatchingRuleUseAttributeTypeUndefined() |
| | | throws Exception |
| | | { |
| | | SchemaTestMatchingRule matchingRule = |
| | | new SchemaTestMatchingRule("testAddMRUATUndefinedMatch", |
| | | "1.3.6.1.4.1.26027.1.999.16"); |
| | | DirectoryServer.registerMatchingRule(matchingRule, false); |
| | | |
| | | |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.16 " + |
| | | "NAME 'testAddMatchingRuleUseATUndefined' " + |
| | | "APPLIES xxxundefinedxxx " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | assertFalse(DirectoryServer.getSchema().hasMatchingRuleUse(matchingRule)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertFalse(LDAPModify.mainModify(args, false, null, null) == 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the behavior of the schema backend when attempting to remove an |
| | | * existing matching rule use. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testRemoveMatchingRuleUseSuccessful() |
| | | throws Exception |
| | | { |
| | | SchemaTestMatchingRule matchingRule = |
| | | new SchemaTestMatchingRule("testRemoveMRUSuccessfulMatch", |
| | | "1.3.6.1.4.1.26027.1.999.13"); |
| | | DirectoryServer.registerMatchingRule(matchingRule, false); |
| | | |
| | | |
| | | String path = TestCaseUtils.createTempFile( |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "add: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.13 " + |
| | | "NAME 'testRemoveMRUSuccessful' APPLIES cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )", |
| | | "", |
| | | "dn: cn=schema", |
| | | "changetype: modify", |
| | | "delete: matchingRuleUse", |
| | | "matchingRuleUse: ( 1.3.6.1.4.1.26027.1.999.13 " + |
| | | "NAME 'testRemoveMRUSuccessful' APPLIES cn " + |
| | | "X-ORIGIN 'SchemaBackendTestCase' )"); |
| | | |
| | | assertFalse(DirectoryServer.getSchema().hasMatchingRuleUse(matchingRule)); |
| | | |
| | | String[] args = |
| | | { |
| | | "-h", "127.0.0.1", |
| | | "-p", String.valueOf(TestCaseUtils.getServerLdapPort()), |
| | | "-D", "cn=Directory Manager", |
| | | "-w", "password", |
| | | "-f", path |
| | | }; |
| | | |
| | | assertEquals(LDAPModify.mainModify(args, false, null, System.err), 0); |
| | | |
| | | MatchingRuleUse mru = |
| | | DirectoryServer.getSchema().getMatchingRuleUse(matchingRule); |
| | | assertNull(mru); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the {@code exportLDIF} method with a valid configuration. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testExportLDIF() |
| | | throws Exception |
| | | { |
| | | DN configEntryDN = |
| | | DN.decode("ds-cfg-backend-id=schema,cn=Backends,cn=config"); |
| | | DN[] baseDNs = { DN.decode("cn=schema") }; |
| | | |
| | | ConfigEntry configEntry = |
| | | DirectoryServer.getConfigHandler().getConfigEntry(configEntryDN); |
| | | |
| | | File tempFile = File.createTempFile("schema", "testExportLDIF"); |
| | | tempFile.deleteOnExit(); |
| | | LDIFExportConfig exportConfig = |
| | | new LDIFExportConfig(tempFile.getAbsolutePath(), |
| | | ExistingFileBehavior.OVERWRITE); |
| | | |
| | | schemaBackend.exportLDIF(configEntry, baseDNs, exportConfig); |
| | | |
| | | assertTrue(tempFile.exists()); |
| | | assertTrue(tempFile.length() > 0); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the {@code importLDIF} method to ensure that it throws an exception. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test(expectedExceptions = { DirectoryException.class }) |
| | | public void testImportLDIF() |
| | | throws Exception |
| | | { |
| | | DN configEntryDN = |
| | | DN.decode("ds-cfg-backend-id=schema,cn=Backends,cn=config"); |
| | | DN[] baseDNs = { DN.decode("cn=schema") }; |
| | | |
| | | ConfigEntry configEntry = |
| | | DirectoryServer.getConfigHandler().getConfigEntry(configEntryDN); |
| | | |
| | | File tempFile = File.createTempFile("schema", "testImportLDIF"); |
| | | tempFile.deleteOnExit(); |
| | | |
| | | LDIFImportConfig importConfig = |
| | | new LDIFImportConfig(tempFile.getAbsolutePath()); |
| | | |
| | | schemaBackend.importLDIF(configEntry, baseDNs, importConfig); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the {@code getComponentEntryDN} method. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | @Test() |
| | | public void testGetComponentEntryDN() |
| | | throws Exception |
| | | { |
| | | DN configEntryDN = |
| | | DN.decode("ds-cfg-backend-id=schema,cn=Backends,cn=config"); |
| | | assertEquals(schemaBackend.getComponentEntryDN(), configEntryDN); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the {@code getClassName} method. |
| | | */ |
| | | @Test() |
| | | public void testGetClassName() |
| | | { |
| | | assertEquals(schemaBackend.getClassName(), SchemaBackend.class.getName()); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Tests the {@code getAlerts} method. |
| | | */ |
| | | @Test() |
| | | public void testGetAlerts() |
| | | { |
| | | LinkedHashMap<String,String> alerts = schemaBackend.getAlerts(); |
| | | assertNotNull(alerts); |
| | | assertFalse(alerts.isEmpty()); |
| | | } |
| | | } |
| | | |
| New file |
| | |
| | | /* |
| | | * CDDL HEADER START |
| | | * |
| | | * The contents of this file are subject to the terms of the |
| | | * Common Development and Distribution License, Version 1.0 only |
| | | * (the "License"). You may not use this file except in compliance |
| | | * with the License. |
| | | * |
| | | * You can obtain a copy of the license at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE |
| | | * or https://OpenDS.dev.java.net/OpenDS.LICENSE. |
| | | * See the License for the specific language governing permissions |
| | | * and limitations under the License. |
| | | * |
| | | * When distributing Covered Code, include this CDDL HEADER in each |
| | | * file and include the License file at |
| | | * trunk/opends/resource/legal-notices/OpenDS.LICENSE. If applicable, |
| | | * add the following below this CDDL HEADER, with the fields enclosed |
| | | * by brackets "[]" replaced with your own identifying * information: |
| | | * Portions Copyright [yyyy] [name of copyright owner] |
| | | * |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.backends; |
| | | |
| | | |
| | | |
| | | import org.opends.server.api.EqualityMatchingRule; |
| | | import org.opends.server.config.ConfigEntry; |
| | | import org.opends.server.config.ConfigException; |
| | | import org.opends.server.schema.CaseIgnoreEqualityMatchingRule; |
| | | import org.opends.server.types.ByteString; |
| | | import org.opends.server.types.DirectoryException; |
| | | import org.opends.server.types.InitializationException; |
| | | |
| | | |
| | | |
| | | /** |
| | | * This class implements an equality matching rule that is intended for testing |
| | | * purposes within the server (e.g., in conjunction with matching rule uses). |
| | | * For all practical purposes, it behaves like the standard caseIgnoreMatch |
| | | * matching rule. |
| | | */ |
| | | public class SchemaTestMatchingRule |
| | | extends EqualityMatchingRule |
| | | { |
| | | // The matching rule that will do all the real work behind the scenes. |
| | | private CaseIgnoreEqualityMatchingRule caseIgnoreMatchingRule; |
| | | |
| | | // The name for this matching rule. |
| | | private String name; |
| | | |
| | | // The OID for this matching rule. |
| | | private String oid; |
| | | |
| | | |
| | | |
| | | /** |
| | | * Creates a new instance of this matching rule with the provided information. |
| | | * |
| | | * @param name The name to use for this matching rule. |
| | | * @param oid The OID to use for this matching rule. |
| | | * |
| | | * @throws Exception If an unexpected problem occurs. |
| | | */ |
| | | public SchemaTestMatchingRule(String name, String oid) |
| | | throws Exception |
| | | { |
| | | super(); |
| | | |
| | | this.name = name; |
| | | this.oid = oid; |
| | | |
| | | caseIgnoreMatchingRule = new CaseIgnoreEqualityMatchingRule(); |
| | | caseIgnoreMatchingRule.initializeMatchingRule(null); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Initializes this matching rule based on the information in the provided |
| | | * configuration entry. |
| | | * |
| | | * @param configEntry The configuration entry that contains the information |
| | | * to use to initialize this matching rule. |
| | | * |
| | | * @throws ConfigException If an unrecoverable problem arises in the |
| | | * process of performing the initialization. |
| | | * |
| | | * @throws InitializationException If a problem that is not |
| | | * configuration-related occurs during |
| | | * initialization. |
| | | */ |
| | | public void initializeMatchingRule(ConfigEntry configEntry) |
| | | throws ConfigException, InitializationException |
| | | { |
| | | // No initialization is required. |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the common name for this matching rule. |
| | | * |
| | | * @return The common name for this matching rule, or <CODE>null</CODE> if |
| | | * it does not have a name. |
| | | */ |
| | | public String getName() |
| | | { |
| | | return name; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the OID for this matching rule. |
| | | * |
| | | * @return The OID for this matching rule. |
| | | */ |
| | | public String getOID() |
| | | { |
| | | return oid; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the description for this matching rule. |
| | | * |
| | | * @return The description for this matching rule, or <CODE>null</CODE> if |
| | | * there is none. |
| | | */ |
| | | public String getDescription() |
| | | { |
| | | return null; |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the OID of the syntax with which this matching rule is |
| | | * associated. |
| | | * |
| | | * @return The OID of the syntax with which this matching rule is associated. |
| | | */ |
| | | public String getSyntaxOID() |
| | | { |
| | | return caseIgnoreMatchingRule.getSyntaxOID(); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Retrieves the normalized form of the provided value, which is best suited |
| | | * for efficiently performing matching operations on that value. |
| | | * |
| | | * @param value The value to be normalized. |
| | | * |
| | | * @return The normalized version of the provided value. |
| | | * |
| | | * @throws DirectoryException If the provided value is invalid according to |
| | | * the associated attribute syntax. |
| | | */ |
| | | public ByteString normalizeValue(ByteString value) |
| | | throws DirectoryException |
| | | { |
| | | return caseIgnoreMatchingRule.normalizeValue(value); |
| | | } |
| | | |
| | | |
| | | |
| | | /** |
| | | * Indicates whether the two provided normalized values are equal to each |
| | | * other. |
| | | * |
| | | * @param value1 The normalized form of the first value to compare. |
| | | * @param value2 The normalized form of the second value to compare. |
| | | * |
| | | * @return <CODE>true</CODE> if the provided values are equal, or |
| | | * <CODE>false</CODE> if not. |
| | | */ |
| | | public boolean areEqual(ByteString value1, ByteString value2) |
| | | { |
| | | return caseIgnoreMatchingRule.areEqual(value1, value2); |
| | | } |
| | | } |
| | | |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | | |
| | | |
| | | import java.util.Collection; |
| | | import java.util.Iterator; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | | |
| | |
| | | protected AttributeType buildInstance(String primaryName, |
| | | Collection<String> names, String oid, String description, |
| | | boolean isObsolete, Map<String, List<String>> extraProperties) { |
| | | return new AttributeType(primaryName, names, oid, description, |
| | | superiorType, syntax, approximateMatchingRule, |
| | | equalityMatchingRule, orderingMatchingRule, |
| | | substringMatchingRule, attributeUsage, isCollective, |
| | | isNoUserModification, isObsolete, isSingleValue, |
| | | extraProperties); |
| | | |
| | | StringBuilder definition = new StringBuilder(); |
| | | definition.append("( "); |
| | | definition.append(oid); |
| | | |
| | | LinkedHashSet<String> nameSet = new LinkedHashSet<String>(); |
| | | if (primaryName != null) |
| | | { |
| | | nameSet.add(primaryName); |
| | | } |
| | | |
| | | if (names != null) |
| | | { |
| | | for (String name : names) |
| | | { |
| | | nameSet.add(name); |
| | | } |
| | | } |
| | | |
| | | if (! nameSet.isEmpty()) |
| | | { |
| | | if (nameSet.size() == 1) |
| | | { |
| | | definition.append(" NAME '"); |
| | | definition.append(nameSet.iterator().next()); |
| | | definition.append("'"); |
| | | } |
| | | else |
| | | { |
| | | Iterator<String> iterator = nameSet.iterator(); |
| | | |
| | | definition.append(" NAME ( '"); |
| | | definition.append(iterator.next()); |
| | | |
| | | while (iterator.hasNext()) |
| | | { |
| | | definition.append("' '"); |
| | | definition.append(iterator.next()); |
| | | } |
| | | |
| | | definition.append("' )"); |
| | | } |
| | | } |
| | | |
| | | if (description != null) |
| | | { |
| | | definition.append(" DESC '"); |
| | | definition.append(description); |
| | | definition.append("'"); |
| | | } |
| | | |
| | | if (isObsolete) |
| | | { |
| | | definition.append(" OBSOLETE"); |
| | | } |
| | | |
| | | if (superiorType != null) |
| | | { |
| | | definition.append(" SUP "); |
| | | definition.append(superiorType.getNameOrOID()); |
| | | } |
| | | |
| | | if (equalityMatchingRule != null) |
| | | { |
| | | definition.append(" EQUALITY "); |
| | | definition.append(equalityMatchingRule.getNameOrOID()); |
| | | } |
| | | |
| | | if (orderingMatchingRule != null) |
| | | { |
| | | definition.append(" ORDERING "); |
| | | definition.append(orderingMatchingRule.getNameOrOID()); |
| | | } |
| | | |
| | | if (substringMatchingRule != null) |
| | | { |
| | | definition.append(" SUBSTR "); |
| | | definition.append(substringMatchingRule.getNameOrOID()); |
| | | } |
| | | |
| | | if (syntax != null) |
| | | { |
| | | definition.append(" SYNTAX "); |
| | | definition.append(syntax.getOID()); |
| | | } |
| | | |
| | | if (isSingleValue) |
| | | { |
| | | definition.append(" SINGLE-VALUE"); |
| | | } |
| | | |
| | | if (isCollective) |
| | | { |
| | | definition.append(" COLLECTIVE"); |
| | | } |
| | | |
| | | if (isNoUserModification) |
| | | { |
| | | definition.append(" NO-USER-MODIFICATIOn"); |
| | | } |
| | | |
| | | if (attributeUsage != null) |
| | | { |
| | | definition.append(" USAGE "); |
| | | definition.append(attributeUsage.toString()); |
| | | } |
| | | |
| | | if (extraProperties != null) |
| | | { |
| | | for (String property : extraProperties.keySet()) |
| | | { |
| | | List<String> values = extraProperties.get(property); |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | continue; |
| | | } |
| | | else if (values.size() == 1) |
| | | { |
| | | definition.append(" "); |
| | | definition.append(property); |
| | | definition.append(" '"); |
| | | definition.append(values.get(0)); |
| | | definition.append("'"); |
| | | } |
| | | else |
| | | { |
| | | definition.append(" "); |
| | | definition.append(property); |
| | | definition.append(" ("); |
| | | for (String value : values) |
| | | { |
| | | definition.append(" '"); |
| | | definition.append(value); |
| | | definition.append("'"); |
| | | } |
| | | |
| | | definition.append(" )"); |
| | | } |
| | | } |
| | | } |
| | | |
| | | definition.append(" )"); |
| | | |
| | | |
| | | return new AttributeType(definition.toString(), primaryName, names, oid, |
| | | description, superiorType, syntax, |
| | | approximateMatchingRule, equalityMatchingRule, |
| | | orderingMatchingRule, substringMatchingRule, |
| | | attributeUsage, isCollective, |
| | | isNoUserModification, isObsolete, isSingleValue, |
| | | extraProperties); |
| | | } |
| | | |
| | | |
| | |
| | | */ |
| | | @Test(expectedExceptions = NullPointerException.class) |
| | | public void testSimpleConstructorNPE() throws Exception { |
| | | new AttributeType(null, null, null, null, null, null, null, |
| | | new AttributeType(null, null, null, null, null, null, null, null, |
| | | false, false, false, false); |
| | | } |
| | | |
| | |
| | | */ |
| | | @Test(expectedExceptions = NullPointerException.class) |
| | | public void testComplexConstructorNPE() throws Exception { |
| | | new AttributeType(null, null, null, null, null, null, null, null, |
| | | new AttributeType(null, null, null, null, null, null, null, null, null, |
| | | null, null, null, false, false, false, false, null); |
| | | } |
| | | |
| | |
| | | */ |
| | | @Test |
| | | public void testComplexConstructorDefault() throws Exception { |
| | | AttributeType type = new AttributeType(null, null, "1.2.3", null, |
| | | AttributeType type = new AttributeType("", null, null, "1.2.3", null, |
| | | null, null, null, null, null, null, null, false, false, |
| | | false, false, null); |
| | | |
| | |
| | | * CDDL HEADER END |
| | | * |
| | | * |
| | | * Portions Copyright 2006 Sun Microsystems, Inc. |
| | | * Portions Copyright 2006-2007 Sun Microsystems, Inc. |
| | | */ |
| | | package org.opends.server.types; |
| | | |
| | |
| | | import java.util.Arrays; |
| | | import java.util.Collection; |
| | | import java.util.Collections; |
| | | import java.util.Iterator; |
| | | import java.util.LinkedHashSet; |
| | | import java.util.List; |
| | | import java.util.Map; |
| | |
| | | protected ObjectClass buildInstance(String primaryName, |
| | | Collection<String> names, String oid, String description, |
| | | boolean isObsolete, Map<String, List<String>> extraProperties) { |
| | | return new ObjectClass(primaryName, names, oid, description, |
| | | superior, requiredAttributeTypes, optionalAttributeTypes, |
| | | objectClassType, isObsolete, extraProperties); |
| | | |
| | | StringBuilder definition = new StringBuilder(); |
| | | definition.append("( "); |
| | | definition.append(oid); |
| | | |
| | | LinkedHashSet<String> nameSet = new LinkedHashSet<String>(); |
| | | if (primaryName != null) |
| | | { |
| | | nameSet.add(primaryName); |
| | | } |
| | | |
| | | if (names != null) |
| | | { |
| | | for (String name : names) |
| | | { |
| | | nameSet.add(name); |
| | | } |
| | | } |
| | | |
| | | if (! nameSet.isEmpty()) |
| | | { |
| | | if (nameSet.size() == 1) |
| | | { |
| | | definition.append(" NAME '"); |
| | | definition.append(nameSet.iterator().next()); |
| | | definition.append("'"); |
| | | } |
| | | else |
| | | { |
| | | Iterator<String> iterator = nameSet.iterator(); |
| | | |
| | | definition.append(" NAME ( '"); |
| | | definition.append(iterator.next()); |
| | | |
| | | while (iterator.hasNext()) |
| | | { |
| | | definition.append("' '"); |
| | | definition.append(iterator.next()); |
| | | } |
| | | |
| | | definition.append("' )"); |
| | | } |
| | | } |
| | | |
| | | if (description != null) |
| | | { |
| | | definition.append(" DESC '"); |
| | | definition.append(description); |
| | | definition.append("'"); |
| | | } |
| | | |
| | | if (isObsolete) |
| | | { |
| | | definition.append(" OBSOLETE"); |
| | | } |
| | | |
| | | if (superior != null) |
| | | { |
| | | definition.append(" SUP "); |
| | | definition.append(superior.getNameOrOID()); |
| | | } |
| | | |
| | | if (objectClassType != null) |
| | | { |
| | | definition.append(" "); |
| | | definition.append(objectClassType.toString()); |
| | | } |
| | | |
| | | if ((requiredAttributeTypes != null) && |
| | | (! requiredAttributeTypes.isEmpty())) |
| | | { |
| | | if (requiredAttributeTypes.size() == 1) |
| | | { |
| | | definition.append(" MUST "); |
| | | definition.append( |
| | | requiredAttributeTypes.iterator().next().getNameOrOID()); |
| | | } |
| | | else |
| | | { |
| | | Iterator<AttributeType> iterator = requiredAttributeTypes.iterator(); |
| | | |
| | | definition.append(" MUST ( "); |
| | | definition.append(iterator.next().getNameOrOID()); |
| | | while (iterator.hasNext()) |
| | | { |
| | | definition.append(" $ "); |
| | | definition.append(iterator.next().getNameOrOID()); |
| | | } |
| | | definition.append(" )"); |
| | | } |
| | | } |
| | | |
| | | if ((optionalAttributeTypes != null) && |
| | | (! optionalAttributeTypes.isEmpty())) |
| | | { |
| | | if (optionalAttributeTypes.size() == 1) |
| | | { |
| | | definition.append(" MUST "); |
| | | definition.append( |
| | | optionalAttributeTypes.iterator().next().getNameOrOID()); |
| | | } |
| | | else |
| | | { |
| | | Iterator<AttributeType> iterator = optionalAttributeTypes.iterator(); |
| | | |
| | | definition.append(" MUST ( "); |
| | | definition.append(iterator.next().getNameOrOID()); |
| | | while (iterator.hasNext()) |
| | | { |
| | | definition.append(" $ "); |
| | | definition.append(iterator.next().getNameOrOID()); |
| | | } |
| | | definition.append(" )"); |
| | | } |
| | | } |
| | | |
| | | if (extraProperties != null) |
| | | { |
| | | for (String property : extraProperties.keySet()) |
| | | { |
| | | List<String> values = extraProperties.get(property); |
| | | if ((values == null) || values.isEmpty()) |
| | | { |
| | | continue; |
| | | } |
| | | else if (values.size() == 1) |
| | | { |
| | | definition.append(" "); |
| | | definition.append(property); |
| | | definition.append(" '"); |
| | | definition.append(values.get(0)); |
| | | definition.append("'"); |
| | | } |
| | | else |
| | | { |
| | | definition.append(" "); |
| | | definition.append(property); |
| | | definition.append(" ("); |
| | | for (String value : values) |
| | | { |
| | | definition.append(" '"); |
| | | definition.append(value); |
| | | definition.append("'"); |
| | | } |
| | | |
| | | definition.append(" )"); |
| | | } |
| | | } |
| | | } |
| | | |
| | | definition.append(" )"); |
| | | |
| | | |
| | | return new ObjectClass(definition.toString(), primaryName, names, oid, |
| | | description, superior, requiredAttributeTypes, |
| | | optionalAttributeTypes, objectClassType, |
| | | isObsolete, extraProperties); |
| | | } |
| | | |
| | | |
| | |
| | | Set<AttributeType> emptySet = Collections.emptySet(); |
| | | Map<String, List<String>> emptyMap = Collections.emptyMap(); |
| | | |
| | | new ObjectClass("test", Collections.singleton("test"), null, |
| | | new ObjectClass(null, "test", Collections.singleton("test"), null, |
| | | "description", DirectoryServer.getTopObjectClass(), emptySet, |
| | | emptySet, ObjectClassType.STRUCTURAL, false, emptyMap); |
| | | } |
| | |
| | | */ |
| | | @Test |
| | | public void testConstructorDefault() throws Exception { |
| | | ObjectClass type = new ObjectClass(null, null, "1.2.3", null, |
| | | String definition = "( 1.2.3 )"; |
| | | ObjectClass type = new ObjectClass(definition, null, null, "1.2.3", null, |
| | | null, null, null, null, false, null); |
| | | |
| | | Assert.assertNull(type.getPrimaryName()); |