From 4b31a35ca148d08a0c89ebbcbb51edeb3ba411b9 Mon Sep 17 00:00:00 2001
From: neil_a_wilson <neil_a_wilson@localhost>
Date: Thu, 25 Jan 2007 01:59:52 +0000
Subject: [PATCH] Make a number of updates to schema processing, all of which fall under the umbrella of issue #1163. The individual issues addressed include:
---
opendj-sdk/opends/src/server/org/opends/server/schema/ObjectClassSyntax.java | 326 +++++++++++++++++++++++++++++++++--------------------
1 files changed, 202 insertions(+), 124 deletions(-)
diff --git a/opendj-sdk/opends/src/server/org/opends/server/schema/ObjectClassSyntax.java b/opendj-sdk/opends/src/server/org/opends/server/schema/ObjectClassSyntax.java
index 627ccfb..557b4bb 100644
--- a/opendj-sdk/opends/src/server/org/opends/server/schema/ObjectClassSyntax.java
+++ b/opendj-sdk/opends/src/server/org/opends/server/schema/ObjectClassSyntax.java
@@ -46,18 +46,17 @@
import org.opends.server.types.AttributeType;
import org.opends.server.types.ByteString;
import org.opends.server.types.DirectoryException;
-import org.opends.server.types.ErrorLogCategory;
-import org.opends.server.types.ErrorLogSeverity;
+import org.opends.server.types.InitializationException;
import org.opends.server.types.ObjectClass;
import org.opends.server.types.ObjectClassType;
import org.opends.server.types.ResultCode;
import org.opends.server.types.Schema;
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.messages.SchemaMessages.*;
import static org.opends.server.schema.SchemaConstants.*;
+import static org.opends.server.util.ServerConstants.*;
import static org.opends.server.util.StaticUtils.*;
@@ -105,17 +104,10 @@
/**
- * Initializes this attribute syntax based on the information in the provided
- * configuration entry.
- *
- * @param configEntry The configuration entry that contains the information
- * to use to initialize this attribute syntax.
- *
- * @throws ConfigException If an unrecoverable problem arises in the
- * process of performing the initialization.
+ * {@inheritDoc}
*/
public void initializeSyntax(ConfigEntry configEntry)
- throws ConfigException
+ throws ConfigException, InitializationException
{
assert debugEnter(CLASS_NAME, "initializeSyntax",
String.valueOf(configEntry));
@@ -124,36 +116,37 @@
DirectoryServer.getEqualityMatchingRule(EMR_CASE_IGNORE_OID);
if (defaultEqualityMatchingRule == null)
{
- logError(ErrorLogCategory.SCHEMA, ErrorLogSeverity.SEVERE_ERROR,
- MSGID_ATTR_SYNTAX_UNKNOWN_EQUALITY_MATCHING_RULE,
- EMR_CASE_IGNORE_OID, SYNTAX_OBJECTCLASS_NAME);
+ int msgID = MSGID_ATTR_SYNTAX_UNKNOWN_EQUALITY_MATCHING_RULE;
+ String message = getMessage(msgID, EMR_CASE_IGNORE_OID,
+ SYNTAX_OBJECTCLASS_NAME);
+ throw new InitializationException(msgID, message);
}
defaultOrderingMatchingRule =
DirectoryServer.getOrderingMatchingRule(OMR_CASE_IGNORE_OID);
if (defaultOrderingMatchingRule == null)
{
- logError(ErrorLogCategory.SCHEMA, ErrorLogSeverity.SEVERE_ERROR,
- MSGID_ATTR_SYNTAX_UNKNOWN_ORDERING_MATCHING_RULE,
- OMR_CASE_IGNORE_OID, SYNTAX_OBJECTCLASS_NAME);
+ int msgID = MSGID_ATTR_SYNTAX_UNKNOWN_ORDERING_MATCHING_RULE;
+ String message = getMessage(msgID, OMR_CASE_IGNORE_OID,
+ SYNTAX_OBJECTCLASS_NAME);
+ throw new InitializationException(msgID, message);
}
defaultSubstringMatchingRule =
DirectoryServer.getSubstringMatchingRule(SMR_CASE_IGNORE_OID);
if (defaultSubstringMatchingRule == null)
{
- logError(ErrorLogCategory.SCHEMA, ErrorLogSeverity.SEVERE_ERROR,
- MSGID_ATTR_SYNTAX_UNKNOWN_SUBSTRING_MATCHING_RULE,
- SMR_CASE_IGNORE_OID, SYNTAX_OBJECTCLASS_NAME);
+ int msgID = MSGID_ATTR_SYNTAX_UNKNOWN_SUBSTRING_MATCHING_RULE;
+ String message = getMessage(msgID, SMR_CASE_IGNORE_OID,
+ SYNTAX_OBJECTCLASS_NAME);
+ throw new InitializationException(msgID, message);
}
}
/**
- * Retrieves the common name for this attribute syntax.
- *
- * @return The common name for this attribute syntax.
+ * {@inheritDoc}
*/
public String getSyntaxName()
{
@@ -165,9 +158,7 @@
/**
- * Retrieves the OID for this attribute syntax.
- *
- * @return The OID for this attribute syntax.
+ * {@inheritDoc}
*/
public String getOID()
{
@@ -179,9 +170,7 @@
/**
- * Retrieves a description for this attribute syntax.
- *
- * @return A description for this attribute syntax.
+ * {@inheritDoc}
*/
public String getDescription()
{
@@ -193,12 +182,7 @@
/**
- * Retrieves the default equality matching rule that will be used for
- * attributes with this syntax.
- *
- * @return The default equality matching rule that will be used for
- * attributes with this syntax, or <CODE>null</CODE> if equality
- * matches will not be allowed for this type by default.
+ * {@inheritDoc}
*/
public EqualityMatchingRule getEqualityMatchingRule()
{
@@ -210,12 +194,7 @@
/**
- * Retrieves the default ordering matching rule that will be used for
- * attributes with this syntax.
- *
- * @return The default ordering matching rule that will be used for
- * attributes with this syntax, or <CODE>null</CODE> if ordering
- * matches will not be allowed for this type by default.
+ * {@inheritDoc}
*/
public OrderingMatchingRule getOrderingMatchingRule()
{
@@ -227,12 +206,7 @@
/**
- * Retrieves the default substring matching rule that will be used for
- * attributes with this syntax.
- *
- * @return The default substring matching rule that will be used for
- * attributes with this syntax, or <CODE>null</CODE> if substring
- * matches will not be allowed for this type by default.
+ * {@inheritDoc}
*/
public SubstringMatchingRule getSubstringMatchingRule()
{
@@ -244,12 +218,7 @@
/**
- * Retrieves the default approximate matching rule that will be used for
- * attributes with this syntax.
- *
- * @return The default approximate matching rule that will be used for
- * attributes with this syntax, or <CODE>null</CODE> if approximate
- * matches will not be allowed for this type by default.
+ * {@inheritDoc}
*/
public ApproximateMatchingRule getApproximateMatchingRule()
{
@@ -262,16 +231,7 @@
/**
- * Indicates whether the provided value is acceptable for use in an attribute
- * with this syntax. If it is not, then the reason may be appended to the
- * provided buffer.
- *
- * @param value The value for which to make the determination.
- * @param invalidReason The buffer to which the invalid reason should be
- * appended.
- *
- * @return <CODE>true</CODE> if the provided value is acceptable for use with
- * this syntax, or <CODE>false</CODE> if not.
+ * {@inheritDoc}
*/
public boolean valueIsAcceptable(ByteString value,
StringBuilder invalidReason)
@@ -284,7 +244,7 @@
// acceptable.
try
{
- decodeObjectClass(value, DirectoryServer.getSchema());
+ decodeObjectClass(value, DirectoryServer.getSchema(), true);
return true;
}
catch (DirectoryException de)
@@ -304,17 +264,25 @@
* octet string value does not need to be normalized (and in fact, it 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 superior class or required or
+ * optional attribute types which are not
+ * defined in the server schema. This should
+ * only be true when called by
+ * {@code valueIsAcceptable}.
*
* @return The decoded objectclass definition.
*
* @throws DirectoryException If the provided value cannot be decoded as an
* objectclass definition.
*/
- public static ObjectClass decodeObjectClass(ByteString value, Schema schema)
+ public static ObjectClass decodeObjectClass(ByteString value, Schema schema,
+ boolean allowUnknownElements)
throws DirectoryException
{
assert debugEnter(CLASS_NAME, "decodeObjectClass", String.valueOf(value));
@@ -593,17 +561,21 @@
superiorClass = schema.getObjectClass(woidBuffer.toString());
if (superiorClass == null)
{
- // This is bad because we don't know what the superior objectclass
- // is so we can't base this objectclass on it. Log a message and
- // just create a default empty superior class.
- int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_SUPERIOR_CLASS;
- String message = getMessage(msgID, String.valueOf(oid),
- String.valueOf(woidBuffer));
- logError(ErrorLogCategory.SCHEMA, ErrorLogSeverity.SEVERE_WARNING,
- message, msgID);
-
- superiorClass =
- DirectoryServer.getDefaultObjectClass(woidBuffer.toString());
+ if (allowUnknownElements)
+ {
+ superiorClass =
+ DirectoryServer.getDefaultObjectClass(woidBuffer.toString());
+ }
+ else
+ {
+ // This is bad because we don't know what the superior objectclass
+ // is so we can't base this objectclass on it.
+ int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_SUPERIOR_CLASS;
+ String message = getMessage(msgID, String.valueOf(oid),
+ String.valueOf(woidBuffer));
+ throw new DirectoryException(ResultCode.CONSTRAINT_VIOLATION,
+ message, msgID);
+ }
}
@@ -652,17 +624,20 @@
AttributeType attr = schema.getAttributeType(woidBuffer.toString());
if (attr == null)
{
- // This isn't good because it means that the objectclass requires
- // an attribute type that we don't know anything about. In this
- // case all we can do is log a message and construct a default
- // type.
- int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_REQUIRED_ATTR;
- String message = getMessage(msgID, oid, woidBuffer.toString());
- logError(ErrorLogCategory.SCHEMA, ErrorLogSeverity.SEVERE_WARNING,
- message, msgID);
-
- attr = DirectoryServer.getDefaultAttributeType(
- woidBuffer.toString());
+ if (allowUnknownElements)
+ {
+ attr = DirectoryServer.getDefaultAttributeType(
+ woidBuffer.toString());
+ }
+ else
+ {
+ // This isn't good because it means that the objectclass
+ // requires an attribute type that we don't know anything about.
+ int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_REQUIRED_ATTR;
+ String message = getMessage(msgID, oid, woidBuffer.toString());
+ throw new DirectoryException(ResultCode.CONSTRAINT_VIOLATION,
+ message, msgID);
+ }
}
attrs.add(attr);
@@ -693,16 +668,20 @@
AttributeType attr = schema.getAttributeType(woidBuffer.toString());
if (attr == null)
{
- // This isn't good because it means that the objectclass requires an
- // attribute type that we don't know anything about. In this case
- // all we can do is log a message and construct a default type.
- int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_REQUIRED_ATTR;
- String message = getMessage(msgID, oid, woidBuffer.toString());
- logError(ErrorLogCategory.SCHEMA, ErrorLogSeverity.SEVERE_WARNING,
- message, msgID);
-
- attr = DirectoryServer.getDefaultAttributeType(
- woidBuffer.toString());
+ if (allowUnknownElements)
+ {
+ attr = DirectoryServer.getDefaultAttributeType(
+ woidBuffer.toString());
+ }
+ else
+ {
+ // This isn't good because it means that the objectclass requires
+ // an attribute type that we don't know anything about.
+ int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_REQUIRED_ATTR;
+ String message = getMessage(msgID, oid, woidBuffer.toString());
+ throw new DirectoryException(ResultCode.CONSTRAINT_VIOLATION,
+ message, msgID);
+ }
}
attrs.add(attr);
@@ -729,17 +708,20 @@
AttributeType attr = schema.getAttributeType(woidBuffer.toString());
if (attr == null)
{
- // This isn't good because it means that the objectclass allows
- // an attribute type that we don't know anything about. In this
- // case all we can do is log a message and construct a default
- // type.
- int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_OPTIONAL_ATTR;
- String message = getMessage(msgID, oid, woidBuffer.toString());
- logError(ErrorLogCategory.SCHEMA, ErrorLogSeverity.SEVERE_WARNING,
- message, msgID);
-
- attr = DirectoryServer.getDefaultAttributeType(
- woidBuffer.toString());
+ if (allowUnknownElements)
+ {
+ attr = DirectoryServer.getDefaultAttributeType(
+ woidBuffer.toString());
+ }
+ else
+ {
+ // This isn't good because it means that the objectclass allows
+ // an attribute type that we don't know anything about.
+ int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_OPTIONAL_ATTR;
+ String message = getMessage(msgID, oid, woidBuffer.toString());
+ throw new DirectoryException(ResultCode.CONSTRAINT_VIOLATION,
+ message, msgID);
+ }
}
attrs.add(attr);
@@ -770,16 +752,20 @@
AttributeType attr = schema.getAttributeType(woidBuffer.toString());
if (attr == null)
{
- // This isn't good because it means that the objectclass allows an
- // attribute type that we don't know anything about. In this case
- // all we can do is log a message and construct a default type.
- int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_OPTIONAL_ATTR;
- String message = getMessage(msgID, oid, woidBuffer.toString());
- logError(ErrorLogCategory.SCHEMA, ErrorLogSeverity.SEVERE_WARNING,
- message, msgID);
-
- attr = DirectoryServer.getDefaultAttributeType(
- woidBuffer.toString());
+ if (allowUnknownElements)
+ {
+ attr = DirectoryServer.getDefaultAttributeType(
+ woidBuffer.toString());
+ }
+ else
+ {
+ // This isn't good because it means that the objectclass allows an
+ // attribute type that we don't know anything about.
+ int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_UNKNOWN_OPTIONAL_ATTR;
+ String message = getMessage(msgID, oid, woidBuffer.toString());
+ throw new DirectoryException(ResultCode.CONSTRAINT_VIOLATION,
+ message, msgID);
+ }
}
attrs.add(attr);
@@ -800,11 +786,73 @@
}
- // This should only happen for the "top" objectclass.
if (superiorClass.getOID().equals(oid))
{
+ // This should only happen for the "top" objectclass.
superiorClass = null;
}
+ else
+ {
+ // Make sure that the inheritance configuration is acceptable.
+ ObjectClassType superiorType = superiorClass.getObjectClassType();
+ switch (objectClassType)
+ {
+ case ABSTRACT:
+ // Abstract classes may only inherit from other abstract classes.
+ if (superiorType != ObjectClassType.ABSTRACT)
+ {
+ int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_INVALID_SUPERIOR_TYPE;
+ String message = getMessage(msgID, oid, objectClassType.toString(),
+ superiorType.toString(),
+ superiorClass.getNameOrOID());
+ throw new DirectoryException(ResultCode.CONSTRAINT_VIOLATION,
+ message, msgID);
+ }
+ break;
+
+ case AUXILIARY:
+ // Auxiliary classes may only inherit from abstract classes or other
+ // auxiliary classes.
+ if ((superiorType != ObjectClassType.ABSTRACT) &&
+ (superiorType != ObjectClassType.AUXILIARY))
+ {
+ int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_INVALID_SUPERIOR_TYPE;
+ String message = getMessage(msgID, oid, objectClassType.toString(),
+ superiorType.toString(),
+ superiorClass.getNameOrOID());
+ throw new DirectoryException(ResultCode.CONSTRAINT_VIOLATION,
+ message, msgID);
+ }
+ break;
+
+ case STRUCTURAL:
+ // Structural classes may only inherit from abstract classes or other
+ // structural classes.
+ if ((superiorType != ObjectClassType.ABSTRACT) &&
+ (superiorType != ObjectClassType.STRUCTURAL))
+ {
+ int msgID = MSGID_ATTR_SYNTAX_OBJECTCLASS_INVALID_SUPERIOR_TYPE;
+ String message = getMessage(msgID, oid, objectClassType.toString(),
+ superiorType.toString(),
+ superiorClass.getNameOrOID());
+ throw new DirectoryException(ResultCode.CONSTRAINT_VIOLATION,
+ message, msgID);
+ }
+
+ // Structural classes must have the "top" objectclass somewhere in the
+ // superior chain.
+ if (! superiorChainIncludesTop(superiorClass))
+ {
+ int msgID =
+ MSGID_ATTR_SYNTAX_OBJECTCLASS_STRUCTURAL_SUPERIOR_NOT_TOP;
+ String message = getMessage(msgID, oid);
+ throw new DirectoryException(ResultCode.CONSTRAINT_VIOLATION,
+ message, msgID);
+ }
+ break;
+ }
+ }
+
return new ObjectClass(value.stringValue(), primaryName, names, oid,
@@ -1341,5 +1389,35 @@
return startPos;
}
+
+
+
+ /**
+ * Indicates whether the provided objectclass or any of its superiors is equal
+ * to the "top" objectclass.
+ *
+ * @param superiorClass The objectclass for which to make the determination.
+ *
+ * @return {@code true} if the provided class or any of its superiors is
+ * equal to the "top" objectclass, or {@code false} if not.
+ */
+ private static boolean superiorChainIncludesTop(ObjectClass superiorClass)
+ {
+ assert debugEnter(CLASS_NAME, "superiorChainIncludesTop",
+ String.valueOf(superiorClass));
+
+ if (superiorClass == null)
+ {
+ return false;
+ }
+ else if (superiorClass.hasName(OC_TOP))
+ {
+ return true;
+ }
+ else
+ {
+ return superiorChainIncludesTop(superiorClass.getSuperiorClass());
+ }
+ }
}
--
Gitblit v1.10.0