/*******************************************************************************
 * Copyright (c) 1998, 2013 Oracle and/or its affiliates. All rights reserved.
 * This program and the accompanying materials are made available under the 
 * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 
 * which accompanies this distribution. 
 * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html
 * and the Eclipse Distribution License is available at 
 * http://www.eclipse.org/org/documents/edl-v10.php.
 *
 * Contributors:
 *     Oracle - initial API and implementation from Oracle TopLink
 *     08/23/2010-2.2 Michael O'Brien 
 *        - 323043: application.xml module ordering may cause weaving not to occur causing an NPE.
 *                       warn if expected "_persistence_*_vh" method not found
 *                       instead of throwing NPE during deploy validation.
 *     10/15/2010-2.2 Guy Pelletier 
 *       - 322008: Improve usability of additional criteria applied to queries at the session/EM
 ******************************************************************************/  
package org.eclipse.persistence.exceptions;

import org.eclipse.persistence.mappings.*;
import org.eclipse.persistence.mappings.foundation.AbstractTransformationMapping;
import org.eclipse.persistence.internal.helper.*;
import org.eclipse.persistence.internal.oxm.record.XMLRecord;
import org.eclipse.persistence.internal.sessions.AbstractRecord;

import java.lang.reflect.*;
import java.util.Collection;

import org.eclipse.persistence.descriptors.ClassDescriptor;
import org.eclipse.persistence.descriptors.DescriptorEvent;
import org.eclipse.persistence.exceptions.i18n.ExceptionMessageGenerator;

/**
 *    <B>Purpose</B>: This exception is used for any problem that is detected with a descriptor or mapping.
 */
public class DescriptorException extends ValidationException {
    protected transient ClassDescriptor descriptor;
    protected transient DatabaseMapping mapping;
    public final static int ATTRIBUTE_AND_MAPPING_WITH_INDIRECTION_MISMATCH = 1;
    public final static int ATTRIBUTE_AND_MAPPING_WITHOUT_INDIRECTION_MISMATCH = 2;
    public final static int ATTRIBUTE_NAME_NOT_SPECIFIED = 6;
    public final static int ATTRIBUTE_TYPE_NOT_VALID = 7;
    public final static int CLASS_INDICATOR_FIELD_NOT_FOUND = 8;
    public final static int DIRECT_FIELD_NAME_NOT_SET = 9;
    public final static int FIELD_NAME_NOT_SET_IN_MAPPING = 10;
    public final static int FOREIGN_KEYS_DEFINED_INCORRECTLY = 11;
    public final static int IDENTITY_MAP_NOT_SPECIFIED = 12;
    public final static int ILLEGAL_ACCESS_WHILE_GETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR = 13;
    public final static int ILLEGAL_ACCESS_WHILE_CLONING = 14;
    public final static int ILLEGAL_ACCESS_WHILE_CONSTRUCTOR_INSTANTIATION = 15;
    public final static int ILLEGAL_ACCESS_WHILE_EVENT_EXECUTION = 16;
    public final static int ILLEGAL_ACCESS_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR = 17;
    public final static int ILLEGAL_ACCESS_WHILE_INSTANTIATING_METHOD_BASED_PROXY = 18;
    public final static int ILLEGAL_ACCESS_WHILE_INVOKING_ATTRIBUTE_METHOD = 19;
    public final static int ILLEGAL_ACCESS_WHILE_INVOKING_FIELD_TO_METHOD = 20;
    public final static int ILLEGAL_ACCESS_WHILE_INVOKING_ROW_EXTRACTION_METHOD = 21;
    public final static int ILLEGAL_ACCESS_WHILE_METHOD_INSTANTIATION = 22;
    public final static int ILLEGAL_ACCESS_WHILE_OBSOLETE_EVENT_EXECUTION = 23;
    public final static int ILLEGAL_ACCESS_WHILE_SETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR = 24;
    public final static int ILLEGAL_ACCESS_WHILE_SETTING_VALUE_THRU_METHOD_ACCESSOR = 25;
    public final static int ILLEGAL_ARGUMENT_WHILE_GETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR = 26;
    public final static int ILLEGAL_ARGUMENT_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR = 27;
    public final static int ILLEGAL_ARGUMENT_WHILE_INSTANTIATING_METHOD_BASED_PROXY = 28;
    public final static int ILLEGAL_ARGUMENT_WHILE_INVOKING_ATTRIBUTE_METHOD = 29;
    public final static int ILLEGAL_ARGUMENT_WHILE_INVOKING_FIELD_TO_METHOD = 30;
    public final static int ILLEGAL_ARGUMENT_WHILE_OBSOLETE_EVENT_EXECUTION = 31;
    public final static int ILLEGAL_ARGUMENT_WHILE_SETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR = 32;
    public final static int ILLEGAL_ARGUMENT_WHILE_SETTING_VALUE_THRU_METHOD_ACCESSOR = 33;
    public final static int INSTANTIATION_WHILE_CONSTRUCTOR_INSTANTIATION = 34;
    public final static int INVALID_DATA_MODIFICATION_EVENT = 35;
    public final static int INVALID_DATA_MODIFICATION_EVENT_CODE = 36;
    public final static int INVALID_DESCRIPTOR_EVENT_CODE = 37;
    public final static int INVALID_IDENTITY_MAP = 38;
    public final static int JAVA_CLASS_NOT_SPECIFIED = 39;
    public final static int DESCRIPTOR_FOR_INTERFACE_IS_MISSING = 40;
    public final static int MAPPING_FOR_SEQUENCE_NUMBER_FIELD = 41;
    public final static int MISSING_CLASS_FOR_INDICATOR_FIELD_VALUE = 43;
    public final static int MISSING_CLASS_INDICATOR_FIELD = 44;
    public final static int MISSING_MAPPING_FOR_FIELD = 45;
    public final static int NO_MAPPING_FOR_PRIMARY_KEY = 46;
    public final static int MULTIPLE_TABLE_PRIMARY_KEY_NOT_SPECIFIED = 47;
    public final static int MULTIPLE_WRITE_MAPPINGS_FOR_FIELD = 48;
    public final static int NO_ATTRIBUTE_TRANSFORMATION_METHOD = 49;
    public final static int NO_FIELD_NAME_FOR_MAPPING = 50;
    public final static int NO_FOREIGN_KEYS_ARE_SPECIFIED = 51;
    public final static int NO_REFERENCE_KEY_IS_SPECIFIED = 52;
    public final static int NO_RELATION_TABLE = 53;
    public final static int NO_SOURCE_RELATION_KEYS_SPECIFIED = 54;
    public final static int NO_SUCH_METHOD_ON_FIND_OBSOLETE_METHOD = 55;
    public final static int NO_SUCH_METHOD_ON_INITIALIZING_ATTRIBUTE_METHOD = 56;
    public final static int NO_SUCH_METHOD_WHILE_CONSTRUCTOR_INSTANTIATION = 57;
    public final static int NO_SUCH_METHOD_WHILE_CONVERTING_TO_METHOD = 58;
    public final static int NO_SUCH_FIELD_WHILE_INITIALIZING_ATTRIBUTES_IN_INSTANCE_VARIABLE_ACCESSOR = 59;
    public final static int NO_SUCH_METHOD_WHILE_INITIALIZING_ATTRIBUTES_IN_METHOD_ACCESSOR = 60;
    public final static int NO_SUCH_METHOD_WHILE_INITIALIZING_CLASS_EXTRACTION_METHOD = 61;
    public final static int NO_SUCH_METHOD_WHILE_INITIALIZING_COPY_POLICY = 62;
    public final static int NO_SUCH_METHOD_WHILE_INITIALIZING_INSTANTIATION_POLICY = 63;
    public final static int NO_TARGET_FOREIGN_KEYS_SPECIFIED = 64;
    public final static int NO_TARGET_RELATION_KEYS_SPECIFIED = 65;
    public final static int NOT_DESERIALIZABLE = 66;
    public final static int NOT_SERIALIZABLE = 67;
    public final static int NULL_FOR_NON_NULL_AGGREGATE = 68;
    public final static int NULL_POINTER_WHILE_GETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR = 69;
    public final static int NULL_POINTER_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR = 70;
    public final static int NULL_POINTER_WHILE_SETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR = 71;
    public final static int NULL_POINTER_WHILE_SETTING_VALUE_THRU_METHOD_ACCESSOR = 72;
    public final static int PARENT_DESCRIPTOR_NOT_SPECIFIED = 73;
    public final static int PRIMARY_KEY_FIELDS_NOT_SPECIFIED = 74;
    public final static int REFERENCE_CLASS_NOT_SPECIFIED = 75;
    public final static int REFERENCE_DESCRIPTOR_IS_NOT_AGGREGATE = 77;
    public final static int REFERENCE_KEY_FIELD_NOT_PROPERLY_SPECIFIED = 78;
    public final static int REFERENCE_TABLE_NOT_SPECIFIED = 79;
    public final static int RELATION_KEY_FIELD_NOT_PROPERLY_SPECIFIED = 80;
    public final static int RETURN_TYPE_IN_GET_ATTRIBUTE_ACCESSOR = 81;
    public final static int SECURITY_ON_FIND_METHOD = 82;
    public final static int SECURITY_ON_FIND_OBSOLETE_METHOD = 83;
    public final static int SECURITY_ON_INITIALIZING_ATTRIBUTE_METHOD = 84;
    public final static int SECURITY_WHILE_CONVERTING_TO_METHOD = 85;
    public final static int SECURITY_WHILE_INITIALIZING_ATTRIBUTES_IN_INSTANCE_VARIABLE_ACCESSOR = 86;
    public final static int SECURITY_WHILE_INITIALIZING_ATTRIBUTES_IN_METHOD_ACCESSOR = 87;
    public final static int SECURITY_WHILE_INITIALIZING_CLASS_EXTRACTION_METHOD = 88;
    public final static int SECURITY_WHILE_INITIALIZING_COPY_POLICY = 89;
    public final static int SECURITY_WHILE_INITIALIZING_INSTANTIATION_POLICY = 90;
    public final static int SEQUENCE_NUMBER_PROPERTY_NOT_SPECIFIED = 91;
    public final static int SIZE_MISMATCH_OF_FOREIGN_KEYS = 92;
    public final static int TABLE_NOT_PRESENT = 93;
    public final static int TABLE_NOT_SPECIFIED = 94;
    public final static int TARGET_FOREIGN_KEYS_SIZE_MISMATCH = 96;
    public final static int TARGET_INVOCATION_WHILE_CLONING = 97;
    public final static int TARGET_INVOCATION_WHILE_EVENT_EXECUTION = 98;
    public final static int TARGET_INVOCATION_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR = 99;
    public final static int TARGET_INVOCATION_WHILE_INSTANTIATING_METHOD_BASED_PROXY = 100;
    public final static int TARGET_INVOCATION_WHILE_INVOKING_ATTRIBUTE_METHOD = 101;
    public final static int TARGET_INVOCATION_WHILE_INVOKING_FIELD_TO_METHOD = 102;
    public final static int TARGET_INVOCATION_WHILE_INVOKING_ROW_EXTRACTION_METHOD = 103;
    public final static int TARGET_INVOCATION_WHILE_METHOD_INSTANTIATION = 104;
    public final static int TARGET_INVOCATION_WHILE_OBSOLETE_EVENT_EXECUTION = 105;
    public final static int TARGET_INVOCATION_WHILE_SETTING_VALUE_THRU_METHOD_ACESSOR = 106;
    public final static int VALUE_NOT_FOUND_IN_CLASS_INDICATOR_MAPPING = 108;
    public final static int WRITE_LOCK_FIELD_IN_CHILD_DESCRIPTOR = 109;
    public final static int DESCRIPTOR_IS_MISSING = 110;
    public final static int MULTIPLE_TABLE_PRIMARY_KEY_MUST_BE_FULLY_QUALIFIED = 111;
    public final static int ONLY_ONE_TABLE_CAN_BE_ADDED_WITH_THIS_METHOD = 112;
    public final static int NULL_POINTER_WHILE_CONSTRUCTOR_INSTANTIATION = 113;
    public final static int NULL_POINTER_WHILE_METHOD_INSTANTIATION = 114;
    public final static int NO_ATTRBUTE_VALUE_CONVERSION_TO_FIELD_VALUE_PROVIDED = 115;
    public final static int NO_FIELD_VALUE_CONVERSION_TO_ATTRIBUTE_VALUE_PROVIDED = 116;
    public final static int LOCK_MAPPING_CANNOT_BE_READONLY = 118;
    public final static int LOCK_MAPPING_MUST_BE_READONLY = 119;
    public final static int CHILD_DOES_NOT_DEFINE_ABSTRACT_QUERY_KEY = 120;
    public final static int SET_EXISTENCE_CHECKING_NOT_UNDERSTOOD = 122;
    public final static int VALUE_HOLDER_INSTANTIATION_MISMATCH = 125;
    public final static int NO_SUB_CLASS_MATCH = 126;
    public final static int RETURN_AND_MAPPING_WITH_INDIRECTION_MISMATCH = 127;
    public final static int RETURN_AND_MAPPING_WITHOUT_INDIRECTION_MISMATCH = 128;
    public final static int PARAMETER_AND_MAPPING_WITH_INDIRECTION_MISMATCH = 129;
    public final static int PARAMETER_AND_MAPPING_WITHOUT_INDIRECTION_MISMATCH = 130;
    public final static int GET_METHOD_RETURN_TYPE_NOT_VALID = 131;
    public final static int SET_METHOD_PARAMETER_TYPE_NOT_VALID = 133;
    public final static int ILLEGAL_TABLE_NAME_IN_MULTIPLE_TABLE_FOREIGN_KEY = 135;
    public final static int ATTRIBUTE_AND_MAPPING_WITH_TRANSPARENT_INDIRECTION_MISMATCH = 138;
    public final static int RETURN_AND_MAPPING_WITH_TRANSPARENT_INDIRECTION_MISMATCH = 139;
    public final static int PARAMETER_AND_MAPPING_WITH_TRANSPARENT_INDIRECTION_MISMATCH = 140;
    public final static int FIELD_IS_NOT_PRESENT_IN_DATABASE = 141;
    public final static int TABLE_IS_NOT_PRESENT_IN_DATABASE = 142;
    public final static int MULTIPLE_TABLE_INSERT_ORDER_MISMATCH = 143;
    public final static int INVALID_USE_OF_TRANSPARENT_INDIRECTION = 144;
    public final static int MISSING_INDIRECT_CONTAINER_CONSTRUCTOR = 145;
    public final static int COULD_NOT_INSTANTIATE_INDIRECT_CONTAINER_CLASS = 146;
    public final static int INVALID_CONTAINER_POLICY = 147;
    public final static int INVALID_CONTAINER_POLICY_WITH_TRANSPARENT_INDIRECTION = 148;
    public final static int INVALID_USE_OF_NO_INDIRECTION = 149;
    public final static int INDIRECT_CONTAINER_INSTANTIATION_MISMATCH = 150;
    public final static int INVALID_MAPPING_OPERATION = 151;
    public final static int INVALID_INDIRECTION_POLICY_OPERATION = 152;
    public final static int REFERENCE_DESCRIPTOR_IS_NOT_AGGREGATECOLLECTION = 153;
    public final static int INVALID_INDIRECTION_CONTAINER_CLASS = 154;
    public final static int MISSING_FOREIGN_KEY_TRANSLATION = 155;
    public final static int STRUCTURE_NAME_NOT_SET_IN_MAPPING = 156;
    public final static int NORMAL_DESCRIPTORS_DO_NOT_SUPPORT_NON_RELATIONAL_EXTENSIONS = 157;
    public final static int PARENT_CLASS_IS_SELF = 158;
    public final static int PROXY_INDIRECTION_NOT_AVAILABLE = 159;
    public final static int INVALID_ATTRIBUTE_TYPE_FOR_PROXY_INDIRECTION = 160;
    public final static int INVALID_GET_RETURN_TYPE_FOR_PROXY_INDIRECTION = 161;
    public final static int INVALID_SET_PARAMETER_TYPE_FOR_PROXY_INDIRECTION = 162;
    public final static int INCORRECT_COLLECTION_POLICY = 163;
    public final static int INVALID_AMENDMENT_METHOD = 164;
    public final static int ERROR_OCCURED_IN_AMENDMENT_METHOD = 165;
    public final static int VARIABLE_ONE_TO_ONE_MAPPING_IS_NOT_DEFINED = 166;
    public final static int NO_CONSTRUCTOR_INDIRECT_COLLECTION_CLASS = 167;
    public final static int TARGET_INVOCATION_WHILE_CONSTRUCTOR_INSTANTIATION = 168;
    public final static int TARGET_INVOCATION_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY = 169;
    public final static int ILLEGAL_ACCESS_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY = 170;
    public final static int INSTANTIATION_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY = 171;
    public final static int NO_SUCH_METHOD_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY = 172;
    public final static int NULL_POINTER_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY = 173;
    public final static int ILLEGAL_ACCESS_WHILE_METHOD_INSTANTIATION_OF_FACTORY = 174;
    public final static int TARGET_INVOCATION_WHILE_METHOD_INSTANTIATION_OF_FACTORY = 175;
    public final static int NULL_POINTER_WHILE_METHOD_INSTANTIATION_OF_FACTORY = 176;
    public final static int NO_MAPPING_FOR_ATTRIBUTENAME = 177;
    public final static int NO_MAPPING_FOR_ATTRIBUTENAME_IN_ENTITY_BEAN = 178;
    public final static int UNSUPPORTED_TYPE_FOR_BIDIRECTIONAL_RELATIONSHIP_MAINTENANCE = 179;// Bug 2618982
    public final static int REFERENCE_DESCRIPTOR_CANNOT_BE_AGGREGATE = 180;
    public final static int ATTRIBUTE_TRANSFORMER_CLASS_NOT_FOUND = 181;
    public final static int FIELD_TRANSFORMER_CLASS_NOT_FOUND = 182;
    public final static int ATTRIBUTE_TRANSFORMER_CLASS_INVALID = 183;
    public final static int FIELD_TRANSFORMER_CLASS_INVALID = 184;
    public final static int RETURNING_POLICY_FIELD_TYPE_CONFLICT = 185;
    public final static int RETURNING_POLICY_FIELD_INSERT_CONFLICT = 186;
    public final static int RETURNING_POLICY_AND_DESCRIPTOR_FIELD_TYPE_CONFLICT = 187;
    public final static int RETURNING_POLICY_UNMAPPED_FIELD_TYPE_NOT_SET = 188;
    public final static int RETURNING_POLICY_MAPPED_FIELD_TYPE_NOT_SET = 189;
    public final static int RETURNING_POLICY_MAPPING_NOT_SUPPORTED = 190;
    public final static int RETURNING_POLICY_FIELD_NOT_SUPPORTED = 191;
    public final static int CUSTOM_QUERY_AND_RETURNING_POLICY_CONFLICT = 192;
    public final static int NO_CUSTOM_QUERY_FOR_RETURNING_POLICY = 193;
    public final static int CLASS_EXTRACTION_METHOD_MUST_BE_STATIC = 194;
    public final static int ISOLATED_DESCRIPTOR_REFERENCED_BY_SHARED_DESCRIPTOR = 195;
    public final static int UPDATE_ALL_FIELDS_NOT_SET = 196;
    public final static int INVALID_MAPPING_TYPE = 197;
    public final static int NEED_TO_IMPLEMENT_CHANGETRACKER = 198;
    public final static int NEED_TO_IMPLEMENT_FETCHGROUPTRACKER = 199;
    public final static int ATTEMPT_TO_REGISTER_DEAD_INDIRECTION = 200;
    public final static int UNIT_OF_WORK_ISOLATED_OBJECTS_ACCESSED_IN_SESSION = 201;
    public final static int INTERNAL_ERROR_ACCESSING_PKFIELD = 202;
    public final static int INTERNAL_ERROR_SET_METHOD = 203;
    public final static int INSERT_ORDER_CONFLICTS_WITH_MULTIPLE_TABLE_FOREIGN_KEYS = 204;
    public final static int INSERT_ORDER_CYCLICAL_DEPENDENCY_BETWEEN_TWO_TABLES = 205;
    public final static int INSERT_ORDER_CYCLICAL_DEPENDENCY_BETWEEN_THREE_OR_MORE_TABLES = 206;
    public final static int INSERT_ORDER_CHILD_BEFORE_PARENT = 207;
    public final static int CANNOT_SET_CONVERTER_FOR_NON_DIRECT_MAPPING = 208;
    public final static int DIRECT_KEY_NOT_SET = 209;
    public final static int LIST_ORDER_FIELD_REQUIRES_LIST = 210;
    public final static int LIST_ORDER_FIELD_REQUIRES_INDIRECT_LIST = 211;
    public final static int LIST_ORDER_FIELD_TABLE_IS_WRONG = 212;
    public final static int MULTIPLE_TARGET_FOREIGN_KEY_TABLES = 213;
    public final static int ONE_TO_ONE_MAPPING_CONFLICT = 214;
    public final static int NO_RELATION_TABLE_MECHANISM = 215;
    public final static int CANNOT_USE_ID_VALUE_FOR_COMPOSITE_ID = 216;
    public final static int INVALID_XPATH_FOR_DIRECT_MAPPING = 217;
    public final static int NULL_POINTER_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR_IN_MODULE_ORDER_BREAKS_WEAVING = 218;
    public final static int ADDITIONAL_CRITERIA_NOT_SUPPORTED_WITH_INHERITANCE_VIEWS = 219;
    public final static int MISSING_PARTITION_POLICY = 220;
    public final static int SERIALIZED_OBJECT_POLICY_FIELD_NOT_SET = 221;
    public final static int EXCEPTION_ACCESSING_PRIMARY_KEY_INSTANCE = 222;

    /**
     * INTERNAL:
     * TopLink exceptions should only be thrown by TopLink.
     */
    protected DescriptorException(String theMessage) {
        super(theMessage);
    }

    /**
     * INTERNAL:
     * TopLink exceptions should only be thrown by TopLink.
     */
    protected DescriptorException(String theMessage, DatabaseMapping mapping) {
        this(theMessage);
        if (mapping != null) {
            this.mapping = mapping;
            this.descriptor = mapping.getDescriptor();
        }
    }

    /**
     * INTERNAL:
     * TopLink exceptions should only be thrown by TopLink.
     */
    protected DescriptorException(String theMessage, ClassDescriptor descriptor) {
        this(theMessage);
        this.descriptor = descriptor;
    }

    protected DescriptorException(String theMessage, ClassDescriptor descriptor, Throwable exception) {
        this(theMessage, descriptor);
        setInternalException(exception);
    }

    public static DescriptorException additionalCriteriaNotSupportedWithInheritanceViews(ClassDescriptor descriptor) {
        Object[] args = { };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ADDITIONAL_CRITERIA_NOT_SUPPORTED_WITH_INHERITANCE_VIEWS, args), descriptor);
        exception.setErrorCode(ADDITIONAL_CRITERIA_NOT_SUPPORTED_WITH_INHERITANCE_VIEWS);
        return exception;
    }
    
    public static DescriptorException attemptToRegisterDeadIndirection(Object object, DatabaseMapping mapping) {
        Object[] args = { object };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ATTEMPT_TO_REGISTER_DEAD_INDIRECTION, args), mapping);
        exception.setErrorCode(ATTEMPT_TO_REGISTER_DEAD_INDIRECTION);
        return exception;
    }

    public static DescriptorException attributeAndMappingWithIndirectionMismatch(DatabaseMapping mapping) {
        Object[] args = { mapping.getAttributeName() };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ATTRIBUTE_AND_MAPPING_WITH_INDIRECTION_MISMATCH, args), mapping);
        exception.setErrorCode(ATTRIBUTE_AND_MAPPING_WITH_INDIRECTION_MISMATCH);
        return exception;
    }

    public static DescriptorException attributeAndMappingWithoutIndirectionMismatch(DatabaseMapping mapping) {
        Object[] args = { mapping.getAttributeName() };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ATTRIBUTE_AND_MAPPING_WITHOUT_INDIRECTION_MISMATCH, args), mapping);
        exception.setErrorCode(ATTRIBUTE_AND_MAPPING_WITHOUT_INDIRECTION_MISMATCH);
        return exception;
    }

    public static DescriptorException attributeAndMappingWithTransparentIndirectionMismatch(DatabaseMapping mapping, Class parameterType, String validTypeName) {
        Object[] args = { mapping.getAttributeName(), parameterType, validTypeName };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ATTRIBUTE_AND_MAPPING_WITH_TRANSPARENT_INDIRECTION_MISMATCH, args), mapping);
        exception.setErrorCode(ATTRIBUTE_AND_MAPPING_WITH_TRANSPARENT_INDIRECTION_MISMATCH);
        return exception;
    }

    public static DescriptorException attributeNameNotSpecified() {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ATTRIBUTE_NAME_NOT_SPECIFIED, args));
        descriptorException.setErrorCode(ATTRIBUTE_NAME_NOT_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException attributeTransformerClassNotFound(String className, AbstractTransformationMapping mapping, Exception exception) {
        Object[] args = { className };
        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ATTRIBUTE_TRANSFORMER_CLASS_NOT_FOUND, args));
        descriptorException.setErrorCode(ATTRIBUTE_TRANSFORMER_CLASS_NOT_FOUND);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException attributeTransformerClassInvalid(String className, AbstractTransformationMapping mapping, Exception exception) {
        Object[] args = { className };
        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ATTRIBUTE_TRANSFORMER_CLASS_INVALID, args));
        descriptorException.setErrorCode(ATTRIBUTE_TRANSFORMER_CLASS_INVALID);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);
        return descriptorException;

    }

    public static DescriptorException attributeTypeNotValid(CollectionMapping mapping, Class interfaceType) {
        Object[] args = { mapping.getAttributeName(), interfaceType };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ATTRIBUTE_TYPE_NOT_VALID, args), mapping);
        exception.setErrorCode(ATTRIBUTE_TYPE_NOT_VALID);
        return exception;
    }

    public static DescriptorException childDoesNotDefineAbstractQueryKeyOfParent(ClassDescriptor child, ClassDescriptor parent, String queryKeyName) {
        Object[] args = { queryKeyName, parent, child };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, CHILD_DOES_NOT_DEFINE_ABSTRACT_QUERY_KEY, args));
        descriptorException.setErrorCode(CHILD_DOES_NOT_DEFINE_ABSTRACT_QUERY_KEY);
        return descriptorException;
    }

    public static DescriptorException classIndicatorFieldNotFound(ClassDescriptor parentDescriptor, ClassDescriptor descriptor) {
        Object[] args = { descriptor, parentDescriptor, CR };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, CLASS_INDICATOR_FIELD_NOT_FOUND, args), descriptor);
        descriptorException.setErrorCode(CLASS_INDICATOR_FIELD_NOT_FOUND);
        return descriptorException;
    }

    public static DescriptorException couldNotInstantiateIndirectContainerClass(Class containerClass, Exception exception) {
        Object[] args = { containerClass, Helper.getShortClassName(containerClass) };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, COULD_NOT_INSTANTIATE_INDIRECT_CONTAINER_CLASS, args));
        descriptorException.setErrorCode(COULD_NOT_INSTANTIATE_INDIRECT_CONTAINER_CLASS);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException descriptorForInterfaceIsMissing(String interfaceName) {
        Object[] args = { interfaceName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, DESCRIPTOR_FOR_INTERFACE_IS_MISSING, args));
        descriptorException.setErrorCode(DESCRIPTOR_FOR_INTERFACE_IS_MISSING);
        return descriptorException;
    }

    public static DescriptorException descriptorIsMissing(String className, DatabaseMapping mapping) {
        Object[] args = { className };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, DESCRIPTOR_IS_MISSING, args), mapping);
        descriptorException.setErrorCode(DESCRIPTOR_IS_MISSING);
        return descriptorException;
    }

    public static DescriptorException directFieldNameNotSet(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, DIRECT_FIELD_NAME_NOT_SET, args), mapping);
        descriptorException.setErrorCode(DIRECT_FIELD_NAME_NOT_SET);
        return descriptorException;
    }

    
    public static DescriptorException errorAccessingSetMethodOfEntity(Class aClass, String methodName, ClassDescriptor descriptor, Exception underlying) {
        Object[] args = { aClass, methodName };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INTERNAL_ERROR_SET_METHOD, args), descriptor, underlying);
        return exception;
    }
    
    
    public static DescriptorException errorOccuredInAmendmentMethod(Class amendmentClass, String method, Exception exception, ClassDescriptor descriptor) {
        Object[] args = { amendmentClass, method };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ERROR_OCCURED_IN_AMENDMENT_METHOD, args), descriptor, exception);
        descriptorException.setErrorCode(ERROR_OCCURED_IN_AMENDMENT_METHOD);
        return descriptorException;
    }

    public static DescriptorException fieldIsNotPresentInDatabase(ClassDescriptor descriptor, String tableName, String fieldName) {
        Object[] args = { fieldName, tableName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, FIELD_IS_NOT_PRESENT_IN_DATABASE, args), descriptor);
        descriptorException.setErrorCode(FIELD_IS_NOT_PRESENT_IN_DATABASE);
        return descriptorException;
    }

    public static DescriptorException fieldNameNotSetInMapping(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, FIELD_NAME_NOT_SET_IN_MAPPING, args), mapping);
        descriptorException.setErrorCode(FIELD_NAME_NOT_SET_IN_MAPPING);
        return descriptorException;
    }

    public static DescriptorException fieldTransformerClassNotFound(String className, AbstractTransformationMapping mapping, Exception exception) {
        Object[] args = { className };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, FIELD_TRANSFORMER_CLASS_NOT_FOUND, args));
        descriptorException.setErrorCode(FIELD_TRANSFORMER_CLASS_NOT_FOUND);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException fieldTransformerClassInvalid(String className, AbstractTransformationMapping mapping, Exception exception) {
        Object[] args = { className };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, FIELD_TRANSFORMER_CLASS_INVALID, args));
        descriptorException.setErrorCode(FIELD_TRANSFORMER_CLASS_NOT_FOUND);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException foreignKeysDefinedIncorrectly(ForeignReferenceMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, FOREIGN_KEYS_DEFINED_INCORRECTLY, args), mapping);
        descriptorException.setErrorCode(FOREIGN_KEYS_DEFINED_INCORRECTLY);
        return descriptorException;
    }

    /**
     * PUBLIC:
     * Return the descriptor that the problem was detected in.
     */
    public ClassDescriptor getDescriptor() {
        return descriptor;
    }

    /**
     * PUBLIC:
     * Return the mapping that the problem was detected in.
     */
    public DatabaseMapping getMapping() {
        return mapping;
    }

    /**
     * PUBLIC:
     * Return the exception error message.
     * TopLink error messages are multi-line so that detail descriptions of the exception are given.
     */
    public String getMessage() {
        if (getDescriptor() == null) {
            return super.getMessage();
        }

        if (getMapping() != null) {
            return super.getMessage() + cr() + getIndentationString() + ExceptionMessageGenerator.getHeader("MappingHeader") + getMapping().toString() + cr() + getIndentationString() + ExceptionMessageGenerator.getHeader("DescriptorHeader") + getDescriptor().toString();
        } else {
            return super.getMessage() + cr() + getIndentationString() + ExceptionMessageGenerator.getHeader("DescriptorHeader") + getDescriptor().toString();
        }
    }

    public static DescriptorException getMethodReturnTypeNotValid(CollectionMapping mapping) {
        Object[] args = { mapping.getAttributeName() };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, GET_METHOD_RETURN_TYPE_NOT_VALID, args), mapping);
        exception.setErrorCode(GET_METHOD_RETURN_TYPE_NOT_VALID);
        return exception;
    }

    public static DescriptorException identityMapNotSpecified(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, IDENTITY_MAP_NOT_SPECIFIED, args), descriptor);
        descriptorException.setErrorCode(IDENTITY_MAP_NOT_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException illegalAccesstWhileGettingValueThruInstanceVaraibleAccessor(String attributeName, String objectName, Throwable exception) {
        Object[] args = { attributeName, objectName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_GETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_GETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileCloning(Object domainObject, String methodName, ClassDescriptor descriptor, Throwable exception) {
        Object[] args = { domainObject, methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_CLONING, args), descriptor, exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_CLONING);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileConstructorInstantiation(ClassDescriptor descriptor, Exception exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_CONSTRUCTOR_INSTANTIATION, args), descriptor, exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_CONSTRUCTOR_INSTANTIATION);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileConstructorInstantiationOfFactory(ClassDescriptor descriptor, Exception exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY, args), descriptor, exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileEventExecution(String eventMethodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { eventMethodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_EVENT_EXECUTION, args), descriptor, exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_EVENT_EXECUTION);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileGettingValueThruMethodAccessor(String methodName, String objectName, Throwable exception) {
        Object[] args = { methodName, objectName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileInstantiatingMethodBasedProxy(Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_INSTANTIATING_METHOD_BASED_PROXY, args));
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_INSTANTIATING_METHOD_BASED_PROXY);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileInvokingAttributeMethod(DatabaseMapping mapping, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_INVOKING_ATTRIBUTE_METHOD, args));
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_INVOKING_ATTRIBUTE_METHOD);
        descriptorException.setInternalException(exception);
        descriptorException.setMapping(mapping);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileInvokingFieldToMethod(String methodName, DatabaseMapping mapping, Throwable exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_INVOKING_FIELD_TO_METHOD, args));
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_INVOKING_FIELD_TO_METHOD);
        descriptorException.setInternalException(exception);
        descriptorException.setMapping(mapping);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileInvokingRowExtractionMethod(AbstractRecord row, Method method, ClassDescriptor descriptor, Throwable exception) {
        Object[] args = { row, method };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_INVOKING_ROW_EXTRACTION_METHOD, args), descriptor, exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_INVOKING_ROW_EXTRACTION_METHOD);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileMethodInstantiation(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_METHOD_INSTANTIATION, args), descriptor, exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_METHOD_INSTANTIATION);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileMethodInstantiationOfFactory(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_METHOD_INSTANTIATION_OF_FACTORY, args), descriptor, exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_METHOD_INSTANTIATION_OF_FACTORY);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileObsoleteEventExecute(String eventMethodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { eventMethodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_OBSOLETE_EVENT_EXECUTION, args), descriptor, exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_OBSOLETE_EVENT_EXECUTION);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileSettingValueThruInstanceVariableAccessor(String attributeName, String objectName, Object objectValue, Throwable exception) {
        Object[] args = { attributeName, objectName, String.valueOf(objectValue), CR };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_SETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_SETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException illegalAccessWhileSettingValueThruMethodAccessor(String setMethodName, Object value, Throwable exception) {
        Object[] args = { setMethodName, String.valueOf(value) };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ACCESS_WHILE_SETTING_VALUE_THRU_METHOD_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(ILLEGAL_ACCESS_WHILE_SETTING_VALUE_THRU_METHOD_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException illegalArgumentWhileGettingValueThruInstanceVariableAccessor(String attributeName, String typeName, String objectName, Throwable exception) {
        Object[] args = { attributeName, typeName, objectName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ARGUMENT_WHILE_GETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(ILLEGAL_ARGUMENT_WHILE_GETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException illegalArgumentWhileGettingValueThruMethodAccessor(String methodName, String objectName, Throwable exception) {
        Object[] args = { methodName, objectName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ARGUMENT_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(ILLEGAL_ARGUMENT_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException illegalArgumentWhileInstantiatingMethodBasedProxy(Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ARGUMENT_WHILE_INSTANTIATING_METHOD_BASED_PROXY, args));
        descriptorException.setErrorCode(ILLEGAL_ARGUMENT_WHILE_INSTANTIATING_METHOD_BASED_PROXY);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException illegalArgumentWhileInvokingAttributeMethod(DatabaseMapping mapping, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ARGUMENT_WHILE_INVOKING_ATTRIBUTE_METHOD, args));
        descriptorException.setErrorCode(ILLEGAL_ARGUMENT_WHILE_INVOKING_ATTRIBUTE_METHOD);
        descriptorException.setInternalException(exception);
        descriptorException.setMapping(mapping);
        return descriptorException;
    }

    public static DescriptorException illegalArgumentWhileInvokingFieldToMethod(String methodName, DatabaseMapping mapping, Throwable exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ARGUMENT_WHILE_INVOKING_FIELD_TO_METHOD, args));
        descriptorException.setInternalException(exception);
        descriptorException.setMapping(mapping);
        descriptorException.setErrorCode(ILLEGAL_ARGUMENT_WHILE_INVOKING_FIELD_TO_METHOD);
        return descriptorException;
    }

    public static DescriptorException illegalArgumentWhileObsoleteEventExecute(String eventMethodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { eventMethodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ARGUMENT_WHILE_OBSOLETE_EVENT_EXECUTION, args), descriptor, exception);
        descriptorException.setErrorCode(ILLEGAL_ARGUMENT_WHILE_OBSOLETE_EVENT_EXECUTION);
        return descriptorException;
    }

    public static DescriptorException illegalArgumentWhileSettingValueThruInstanceVariableAccessor(String attributeName, String typeName, Object value, Throwable exception) {
        Object[] args = { String.valueOf(value), attributeName, typeName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ARGUMENT_WHILE_SETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(ILLEGAL_ARGUMENT_WHILE_SETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException illegalArgumentWhileSettingValueThruMethodAccessor(String setMethodName, Object value, Throwable exception) {
        Object[] args = { setMethodName, String.valueOf(value) };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_ARGUMENT_WHILE_SETTING_VALUE_THRU_METHOD_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(ILLEGAL_ARGUMENT_WHILE_SETTING_VALUE_THRU_METHOD_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException illegalTableNameInMultipleTableForeignKeyField(ClassDescriptor descriptor, DatabaseTable table) {
        Object[] args = { table };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ILLEGAL_TABLE_NAME_IN_MULTIPLE_TABLE_FOREIGN_KEY, args), descriptor);
        descriptorException.setErrorCode(ILLEGAL_TABLE_NAME_IN_MULTIPLE_TABLE_FOREIGN_KEY);
        return descriptorException;
    }

    public static DescriptorException incorrectCollectionPolicy(DatabaseMapping mapping, Class attributeClass, Class containerClass) {
        Object[] args = { attributeClass, containerClass };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INCORRECT_COLLECTION_POLICY, args), mapping);
        descriptorException.setErrorCode(INCORRECT_COLLECTION_POLICY);
        return descriptorException;
    }

    public static DescriptorException indirectContainerInstantiationMismatch(Object attributeValue, DatabaseMapping mapping) {
        Object[] args = { mapping.getAttributeName(), attributeValue, CR };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INDIRECT_CONTAINER_INSTANTIATION_MISMATCH, args), mapping);
        exception.setErrorCode(INDIRECT_CONTAINER_INSTANTIATION_MISMATCH);
        return exception;
    }

    public static DescriptorException instantiationWhileConstructorInstantiation(ClassDescriptor descriptor, Exception exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INSTANTIATION_WHILE_CONSTRUCTOR_INSTANTIATION, args), descriptor, exception);
        descriptorException.setErrorCode(INSTANTIATION_WHILE_CONSTRUCTOR_INSTANTIATION);
        return descriptorException;
    }

    public static DescriptorException instantiationWhileConstructorInstantiationOfFactory(ClassDescriptor descriptor, Exception exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INSTANTIATION_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY, args), descriptor, exception);
        descriptorException.setErrorCode(INSTANTIATION_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY);
        return descriptorException;
    }

    public static DescriptorException invalidAmendmentMethod(Class amendmentClass, String method, Exception exception, ClassDescriptor descriptor) {
        Object[] args = { amendmentClass, method, CR };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_AMENDMENT_METHOD, args), descriptor, exception);
        descriptorException.setErrorCode(INVALID_AMENDMENT_METHOD);
        return descriptorException;
    }

    public static DescriptorException invalidAttributeTypeForProxyIndirection(Class attributeType, Class[] targetInterfaces, DatabaseMapping mapping) {
        StringBuffer buffer = new StringBuffer();
        for (int i = 0; i < targetInterfaces.length; i++) {
            buffer.append(targetInterfaces[i].getName());
            if (i != (targetInterfaces.length - 1)) {
                buffer.append(", ");
            }
        }

        Object[] args = { mapping.getAttributeName(), mapping.getDescriptor().getJavaClass().getName(), attributeType.getName(), buffer.toString(), CR };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_ATTRIBUTE_TYPE_FOR_PROXY_INDIRECTION, args), mapping);
        descriptorException.setErrorCode(INVALID_ATTRIBUTE_TYPE_FOR_PROXY_INDIRECTION);
        return descriptorException;
    }

    public static DescriptorException invalidContainerPolicy(org.eclipse.persistence.internal.queries.ContainerPolicy containerPolicy, Class javaClass) {
        Object[] args = { containerPolicy, javaClass };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_CONTAINER_POLICY, args));
        exception.setErrorCode(INVALID_CONTAINER_POLICY);
        return exception;
    }

    public static DescriptorException invalidContainerPolicyWithTransparentIndirection(DatabaseMapping mapping, org.eclipse.persistence.internal.queries.ContainerPolicy containerPolicy) {
        Object[] args = { containerPolicy };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_CONTAINER_POLICY_WITH_TRANSPARENT_INDIRECTION, args), mapping);
        exception.setErrorCode(INVALID_CONTAINER_POLICY_WITH_TRANSPARENT_INDIRECTION);
        return exception;
    }

    public static DescriptorException invalidDataModificationEvent(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_DATA_MODIFICATION_EVENT, args), mapping);
        descriptorException.setErrorCode(INVALID_DATA_MODIFICATION_EVENT);
        return descriptorException;
    }

    public static DescriptorException invalidDataModificationEventCode(Object event, ForeignReferenceMapping mapping) {
        Object[] args = { event };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_DATA_MODIFICATION_EVENT_CODE, args), mapping);
        descriptorException.setErrorCode(INVALID_DATA_MODIFICATION_EVENT_CODE);
        return descriptorException;
    }

    public static DescriptorException invalidDescriptorEventCode(DescriptorEvent event, ClassDescriptor descriptor) {
        Object[] args = { Integer.valueOf(event.getEventCode()) };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_DESCRIPTOR_EVENT_CODE, args), descriptor);
        descriptorException.setErrorCode(INVALID_DESCRIPTOR_EVENT_CODE);
        return descriptorException;
    }

    public static DescriptorException invalidGetMethodReturnTypeForProxyIndirection(Class attributeType, Class[] targetInterfaces, DatabaseMapping mapping) {
        StringBuffer buffer = new StringBuffer();
        for (int i = 0; i < targetInterfaces.length; i++) {
            buffer.append(targetInterfaces[i].getName());
            if (i != (targetInterfaces.length - 1)) {
                buffer.append(", ");
            }
        }

        Object[] args = { mapping.getGetMethodName(), mapping.getDescriptor().getJavaClass().getName(), attributeType.getName(), buffer.toString(), CR };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_GET_RETURN_TYPE_FOR_PROXY_INDIRECTION, args), mapping);
        descriptorException.setErrorCode(INVALID_GET_RETURN_TYPE_FOR_PROXY_INDIRECTION);
        return descriptorException;
    }

    public static DescriptorException invalidIdentityMap(ClassDescriptor descriptor, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_IDENTITY_MAP, args), descriptor, exception);
        descriptorException.setErrorCode(INVALID_IDENTITY_MAP);
        return descriptorException;
    }

    public static DescriptorException invalidIndirectionContainerClass(org.eclipse.persistence.internal.indirection.ContainerIndirectionPolicy policy, Class containerClass) {
        Object[] args = { containerClass };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_INDIRECTION_CONTAINER_CLASS, args), policy.getMapping());
        descriptorException.setErrorCode(INVALID_INDIRECTION_CONTAINER_CLASS);
        return descriptorException;
    }

    public static DescriptorException invalidIndirectionPolicyOperation(org.eclipse.persistence.internal.indirection.IndirectionPolicy policy, String operation) {
        Object[] args = { policy, operation };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_INDIRECTION_POLICY_OPERATION, args), policy.getMapping());
        descriptorException.setErrorCode(INVALID_INDIRECTION_POLICY_OPERATION);
        return descriptorException;
    }

    public static DescriptorException invalidMappingOperation(DatabaseMapping mapping, String operation) {
        Object[] args = { operation };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_MAPPING_OPERATION, args), mapping);
        descriptorException.setErrorCode(INVALID_MAPPING_OPERATION);
        return descriptorException;
    }

    public static DescriptorException invalidSetMethodParameterTypeForProxyIndirection(Class attributeType, Class[] targetInterfaces, DatabaseMapping mapping) {
        StringBuffer buffer = new StringBuffer();
        for (int i = 0; i < targetInterfaces.length; i++) {
            buffer.append(targetInterfaces[i].getName());
            if (i != (targetInterfaces.length - 1)) {
                buffer.append(", ");
            }
        }

        Object[] args = { mapping.getSetMethodName(), mapping.getDescriptor().getJavaClass().getName(), attributeType.getName(), buffer.toString(), CR };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_SET_PARAMETER_TYPE_FOR_PROXY_INDIRECTION, args), mapping);
        descriptorException.setErrorCode(INVALID_SET_PARAMETER_TYPE_FOR_PROXY_INDIRECTION);
        return descriptorException;
    }

    public static DescriptorException invalidUseOfNoIndirection(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_USE_OF_NO_INDIRECTION, args), mapping);
        exception.setErrorCode(INVALID_USE_OF_NO_INDIRECTION);
        return exception;
    }

    public static DescriptorException invalidUseOfTransparentIndirection(DatabaseMapping mapping) {
        Object[] args = {  };

        String message = org.eclipse.persistence.exceptions.i18n.ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_USE_OF_TRANSPARENT_INDIRECTION, args);
        DescriptorException exception = new DescriptorException(message, mapping);
        exception.setErrorCode(INVALID_USE_OF_TRANSPARENT_INDIRECTION);
        return exception;
    }

    public static DescriptorException isolateDescriptorReferencedBySharedDescriptor(String referenceClass, String sourceClass, DatabaseMapping mapping) {
        Object[] args = { referenceClass, sourceClass };

        String message = org.eclipse.persistence.exceptions.i18n.ExceptionMessageGenerator.buildMessage(DescriptorException.class, ISOLATED_DESCRIPTOR_REFERENCED_BY_SHARED_DESCRIPTOR, args);
        DescriptorException exception = new DescriptorException(message, mapping);
        exception.setErrorCode(ISOLATED_DESCRIPTOR_REFERENCED_BY_SHARED_DESCRIPTOR);
        return exception;
    }

    public static DescriptorException javaClassNotSpecified(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, JAVA_CLASS_NOT_SPECIFIED, args), descriptor);
        descriptorException.setErrorCode(JAVA_CLASS_NOT_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException mappingCanNotBeReadOnly(DatabaseMapping mapping) {
        Object[] args = { mapping.getDescriptor().getJavaClass() };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, LOCK_MAPPING_CANNOT_BE_READONLY, args), mapping);
        descriptorException.setErrorCode(LOCK_MAPPING_CANNOT_BE_READONLY);
        return descriptorException;
    }

    public static DescriptorException mappingForSequenceNumberField(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MAPPING_FOR_SEQUENCE_NUMBER_FIELD, args));
        descriptorException.setErrorCode(MAPPING_FOR_SEQUENCE_NUMBER_FIELD);
        descriptorException.setDescriptor(descriptor);
        return descriptorException;
    }

    public static DescriptorException missingClassForIndicatorFieldValue(Object classFieldValue, ClassDescriptor descriptor) {
        Object[] args = { classFieldValue, classFieldValue.getClass() };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MISSING_CLASS_FOR_INDICATOR_FIELD_VALUE, args), descriptor);
        descriptorException.setErrorCode(MISSING_CLASS_FOR_INDICATOR_FIELD_VALUE);
        return descriptorException;
    }

    public static DescriptorException missingClassIndicatorField(AbstractRecord row, ClassDescriptor descriptor) {
        Object[] args = { row };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MISSING_CLASS_INDICATOR_FIELD, args), descriptor);
        descriptorException.setErrorCode(MISSING_CLASS_INDICATOR_FIELD);
        return descriptorException;
    }

    /**
     * @since EclipseLink 2.5.0
     */
    public static DescriptorException missingClassIndicatorField(XMLRecord row, ClassDescriptor descriptor) {
        Object[] args = { row };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MISSING_CLASS_INDICATOR_FIELD, args), descriptor);
        descriptorException.setErrorCode(MISSING_CLASS_INDICATOR_FIELD);
        return descriptorException;
    }

    public static DescriptorException missingForeignKeyTranslation(ForeignReferenceMapping mapping, DatabaseField primaryKeyField) {
        Object[] args = { primaryKeyField };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MISSING_FOREIGN_KEY_TRANSLATION, args), mapping);
        exception.setErrorCode(MISSING_FOREIGN_KEY_TRANSLATION);
        return exception;
    }

    public static DescriptorException missingIndirectContainerConstructor(Class containerClass) {
        Object[] args = { containerClass.getName(), containerClass.getName() + "()" };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MISSING_INDIRECT_CONTAINER_CONSTRUCTOR, args));
        exception.setErrorCode(MISSING_INDIRECT_CONTAINER_CONSTRUCTOR);
        return exception;
    }

    public static DescriptorException missingMappingForField(DatabaseField field, ClassDescriptor descriptor) {
        Object[] args = { field };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MISSING_MAPPING_FOR_FIELD, args));
        descriptorException.setErrorCode(MISSING_MAPPING_FOR_FIELD);
        descriptorException.setDescriptor(descriptor);
        return descriptorException;
    }

    public static DescriptorException multipleTableInsertOrderMismatch(ClassDescriptor aDescriptor) {
        Object[] args = { aDescriptor.getMultipleTableInsertOrder(), aDescriptor.getTables(), CR };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MULTIPLE_TABLE_INSERT_ORDER_MISMATCH, args));
        descriptorException.setErrorCode(MULTIPLE_TABLE_INSERT_ORDER_MISMATCH);
        descriptorException.setDescriptor(aDescriptor);
        return descriptorException;
    }

    public static DescriptorException multipleTablePrimaryKeyMustBeFullyQualified(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MULTIPLE_TABLE_PRIMARY_KEY_MUST_BE_FULLY_QUALIFIED, args), descriptor);
        descriptorException.setErrorCode(MULTIPLE_TABLE_PRIMARY_KEY_MUST_BE_FULLY_QUALIFIED);
        return descriptorException;
    }

    public static DescriptorException multipleTablePrimaryKeyNotSpecified(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MULTIPLE_TABLE_PRIMARY_KEY_NOT_SPECIFIED, args), descriptor);
        descriptorException.setErrorCode(MULTIPLE_TABLE_PRIMARY_KEY_NOT_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException multipleWriteMappingsForField(String fieldName, DatabaseMapping mapping) {
        Object[] args = { fieldName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MULTIPLE_WRITE_MAPPINGS_FOR_FIELD, args), mapping);
        descriptorException.setErrorCode(MULTIPLE_WRITE_MAPPINGS_FOR_FIELD);
        return descriptorException;
    }

    public static DescriptorException mustBeReadOnlyMappingWhenStoredInCache(DatabaseMapping mapping) {
        Object[] args = { mapping.getDescriptor().getJavaClass() };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, LOCK_MAPPING_MUST_BE_READONLY, args), mapping);
        descriptorException.setErrorCode(LOCK_MAPPING_MUST_BE_READONLY);
        return descriptorException;
    }

    public static DescriptorException noAttributeTransformationMethod(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_ATTRIBUTE_TRANSFORMATION_METHOD, args), mapping);
        descriptorException.setErrorCode(NO_ATTRIBUTE_TRANSFORMATION_METHOD);
        return descriptorException;
    }

    public static DescriptorException noAttributeValueConversionToFieldValueProvided(Object attributeValue, DatabaseMapping mapping) {
        Object[] args = { attributeValue };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_ATTRBUTE_VALUE_CONVERSION_TO_FIELD_VALUE_PROVIDED, args), mapping);
        descriptorException.setErrorCode(NO_ATTRBUTE_VALUE_CONVERSION_TO_FIELD_VALUE_PROVIDED);
        return descriptorException;
    }

    public static DescriptorException noConstructorIndirectionContainerClass(org.eclipse.persistence.internal.indirection.ContainerIndirectionPolicy policy, Class containerClass) {
        Object[] args = { containerClass };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_CONSTRUCTOR_INDIRECT_COLLECTION_CLASS, args), policy.getMapping());
        descriptorException.setErrorCode(NO_CONSTRUCTOR_INDIRECT_COLLECTION_CLASS);
        return descriptorException;
    }

    public static DescriptorException noFieldNameForMapping(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_FIELD_NAME_FOR_MAPPING, args), mapping);
        descriptorException.setErrorCode(NO_FIELD_NAME_FOR_MAPPING);
        return descriptorException;
    }

    // CR#3779 - Added field as an argument
    public static DescriptorException noFieldValueConversionToAttributeValueProvided(Object fieldValue, DatabaseField field, DatabaseMapping mapping) {
        Object[] args = { fieldValue, field };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_FIELD_VALUE_CONVERSION_TO_ATTRIBUTE_VALUE_PROVIDED, args), mapping);
        descriptorException.setErrorCode(NO_FIELD_VALUE_CONVERSION_TO_ATTRIBUTE_VALUE_PROVIDED);
        return descriptorException;
    }

    public static DescriptorException noForeignKeysAreSpecified(ForeignReferenceMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_FOREIGN_KEYS_ARE_SPECIFIED, args), mapping);
        descriptorException.setErrorCode(NO_FOREIGN_KEYS_ARE_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException noMappingForPrimaryKey(DatabaseField field, ClassDescriptor descriptor) {
        Object[] args = { field };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_MAPPING_FOR_PRIMARY_KEY, args), descriptor);
        descriptorException.setErrorCode(NO_MAPPING_FOR_PRIMARY_KEY);
        return descriptorException;
    }

    public static DescriptorException noReferenceKeyIsSpecified(ForeignReferenceMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_REFERENCE_KEY_IS_SPECIFIED, args), mapping);
        descriptorException.setErrorCode(NO_REFERENCE_KEY_IS_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException noRelationTable(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_RELATION_TABLE, args), mapping);
        descriptorException.setErrorCode(NO_RELATION_TABLE);
        return descriptorException;
    }

    public static DescriptorException normalDescriptorsDoNotSupportNonRelationalExtensions(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NORMAL_DESCRIPTORS_DO_NOT_SUPPORT_NON_RELATIONAL_EXTENSIONS, args), descriptor);
        descriptorException.setErrorCode(NORMAL_DESCRIPTORS_DO_NOT_SUPPORT_NON_RELATIONAL_EXTENSIONS);
        return descriptorException;
    }

    public static DescriptorException noSourceRelationKeysSpecified(ForeignReferenceMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SOURCE_RELATION_KEYS_SPECIFIED, args), mapping);
        descriptorException.setErrorCode(NO_SOURCE_RELATION_KEYS_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException noSubClassMatch(Class theClass, DatabaseMapping mapping) {
        Object[] args = { theClass };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUB_CLASS_MATCH, args), mapping);

        descriptorException.setErrorCode(NO_SUB_CLASS_MATCH);
        return descriptorException;
    }

    public static DescriptorException noSuchFieldWhileInitializingAttributesInInstanceVariableAccessor(String attributeName, String javaClassName, Throwable exception) {
        Object[] args = { attributeName, javaClassName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_FIELD_WHILE_INITIALIZING_ATTRIBUTES_IN_INSTANCE_VARIABLE_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(NO_SUCH_FIELD_WHILE_INITIALIZING_ATTRIBUTES_IN_INSTANCE_VARIABLE_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException noSuchMethodOnFindObsoleteMethod(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_METHOD_ON_FIND_OBSOLETE_METHOD, args), descriptor, exception);
        descriptorException.setErrorCode(NO_SUCH_METHOD_ON_FIND_OBSOLETE_METHOD);
        return descriptorException;
    }

    public static DescriptorException noSuchMethodOnInitializingAttributeMethod(String attributeMethodName, DatabaseMapping mapping, Throwable exception) {
        Object[] args = { attributeMethodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_METHOD_ON_INITIALIZING_ATTRIBUTE_METHOD, args));
        descriptorException.setErrorCode(NO_SUCH_METHOD_ON_INITIALIZING_ATTRIBUTE_METHOD);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException noSuchMethodWhileConstructorInstantiation(ClassDescriptor descriptor, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_METHOD_WHILE_CONSTRUCTOR_INSTANTIATION, args), descriptor, exception);
        descriptorException.setErrorCode(NO_SUCH_METHOD_WHILE_CONSTRUCTOR_INSTANTIATION);
        return descriptorException;
    }

    public static DescriptorException noSuchMethodWhileConstructorInstantiationOfFactory(ClassDescriptor descriptor, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_METHOD_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY, args), descriptor, exception);
        descriptorException.setErrorCode(NO_SUCH_METHOD_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY);
        return descriptorException;
    }

    public static DescriptorException noSuchMethodWhileConvertingToMethod(String methodName, DatabaseMapping mapping, Throwable exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_METHOD_WHILE_CONVERTING_TO_METHOD, args));
        descriptorException.setErrorCode(NO_SUCH_METHOD_WHILE_CONVERTING_TO_METHOD);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException noSuchMethodWhileInitializingAttributesInMethodAccessor(String setMethodName, String getMethodName, String javaClassName) {
        Object[] args = { setMethodName, getMethodName, javaClassName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_METHOD_WHILE_INITIALIZING_ATTRIBUTES_IN_METHOD_ACCESSOR, args));
        descriptorException.setErrorCode(NO_SUCH_METHOD_WHILE_INITIALIZING_ATTRIBUTES_IN_METHOD_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException noSuchMethodWhileInitializingClassExtractionMethod(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_METHOD_WHILE_INITIALIZING_CLASS_EXTRACTION_METHOD, args), descriptor, exception);
        descriptorException.setErrorCode(NO_SUCH_METHOD_WHILE_INITIALIZING_CLASS_EXTRACTION_METHOD);
        return descriptorException;
    }

    public static DescriptorException noSuchMethodWhileInitializingCopyPolicy(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_METHOD_WHILE_INITIALIZING_COPY_POLICY, args), descriptor, exception);
        descriptorException.setErrorCode(NO_SUCH_METHOD_WHILE_INITIALIZING_COPY_POLICY);
        return descriptorException;
    }

    public static DescriptorException noSuchMethodWhileInitializingInstantiationPolicy(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_SUCH_METHOD_WHILE_INITIALIZING_INSTANTIATION_POLICY, args), descriptor, exception);
        descriptorException.setErrorCode(NO_SUCH_METHOD_WHILE_INITIALIZING_INSTANTIATION_POLICY);
        return descriptorException;
    }

    public static DescriptorException noTargetForeignKeysSpecified(ForeignReferenceMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_TARGET_FOREIGN_KEYS_SPECIFIED, args), mapping);
        descriptorException.setErrorCode(NO_TARGET_FOREIGN_KEYS_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException noTargetRelationKeysSpecified(ForeignReferenceMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_TARGET_RELATION_KEYS_SPECIFIED, args), mapping);
        descriptorException.setErrorCode(NO_TARGET_RELATION_KEYS_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException notDeserializable(DatabaseMapping mapping, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NOT_DESERIALIZABLE, args));
        descriptorException.setErrorCode(NOT_DESERIALIZABLE);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException notSerializable(DatabaseMapping mapping, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NOT_SERIALIZABLE, args));
        descriptorException.setErrorCode(NOT_SERIALIZABLE);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);

        return descriptorException;
    }

    public static DescriptorException nullForNonNullAggregate(Object object, DatabaseMapping mapping) {
        Object[] args = { object };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_FOR_NON_NULL_AGGREGATE, args), mapping);
        exception.setErrorCode(NULL_FOR_NON_NULL_AGGREGATE);
        return exception;
    }

    public static DescriptorException nullPointerWhileConstructorInstantiation(ClassDescriptor descriptor, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_POINTER_WHILE_CONSTRUCTOR_INSTANTIATION, args), descriptor, exception);
        descriptorException.setErrorCode(NULL_POINTER_WHILE_CONSTRUCTOR_INSTANTIATION);
        return descriptorException;
    }

    public static DescriptorException nullPointerWhileConstructorInstantiationOfFactory(ClassDescriptor descriptor, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_POINTER_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY, args), descriptor, exception);
        descriptorException.setErrorCode(NULL_POINTER_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY);
        return descriptorException;
    }

    public static DescriptorException nullPointerWhileGettingValueThruInstanceVariableAccessor(String attributeName, String objectName, Throwable exception) {
        Object[] args = { attributeName, objectName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_POINTER_WHILE_GETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(NULL_POINTER_WHILE_GETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException nullPointerWhileGettingValueThruMethodAccessor(String methodName, String objectName, Throwable exception) {
        Object[] args = { methodName, objectName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_POINTER_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(NULL_POINTER_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR);
        return descriptorException;
    }

    // 323403: Handle NPE because of module order issue that stops weaving from occurring
    public static DescriptorException nullPointerWhileGettingValueThruMethodAccessorCausedByWeavingNotOccurringBecauseOfModuleOrder(String methodName, String objectName, Throwable exception) {
        Object[] args = { methodName, objectName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_POINTER_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR_IN_MODULE_ORDER_BREAKS_WEAVING, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(NULL_POINTER_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR_IN_MODULE_ORDER_BREAKS_WEAVING);
        return descriptorException;
    }
    
    public static DescriptorException nullPointerWhileMethodInstantiation(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_POINTER_WHILE_METHOD_INSTANTIATION, args), descriptor, exception);
        descriptorException.setErrorCode(NULL_POINTER_WHILE_METHOD_INSTANTIATION);
        return descriptorException;
    }

    public static DescriptorException nullPointerWhileMethodInstantiationOfFactory(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_POINTER_WHILE_METHOD_INSTANTIATION_OF_FACTORY, args), descriptor, exception);
        descriptorException.setErrorCode(NULL_POINTER_WHILE_METHOD_INSTANTIATION_OF_FACTORY);
        return descriptorException;
    }

    public static DescriptorException nullPointerWhileSettingValueThruInstanceVariableAccessor(String attributeName, Object objectValue, Throwable exception) {
        Object[] args = { attributeName, String.valueOf(objectValue) };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_POINTER_WHILE_SETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(NULL_POINTER_WHILE_SETTING_VALUE_THRU_INSTANCE_VARIABLE_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException nullPointerWhileSettingValueThruMethodAccessor(String setMethodName, Object value, Throwable exception) {
        Object[] args = { setMethodName, String.valueOf(value) };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NULL_POINTER_WHILE_SETTING_VALUE_THRU_METHOD_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(NULL_POINTER_WHILE_SETTING_VALUE_THRU_METHOD_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException onlyOneTableCanBeAddedWithThisMethod(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ONLY_ONE_TABLE_CAN_BE_ADDED_WITH_THIS_METHOD, args), descriptor);
        descriptorException.setErrorCode(ONLY_ONE_TABLE_CAN_BE_ADDED_WITH_THIS_METHOD);
        return descriptorException;
    }

    public static DescriptorException parameterAndMappingWithIndirectionMismatch(DatabaseMapping mapping) {
        Object[] args = { mapping.getAttributeName() };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, PARAMETER_AND_MAPPING_WITH_INDIRECTION_MISMATCH, args), mapping);
        exception.setErrorCode(PARAMETER_AND_MAPPING_WITH_INDIRECTION_MISMATCH);
        return exception;
    }

    public static DescriptorException parameterAndMappingWithoutIndirectionMismatch(DatabaseMapping mapping) {
        Object[] args = { mapping.getAttributeName() };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, PARAMETER_AND_MAPPING_WITHOUT_INDIRECTION_MISMATCH, args), mapping);
        exception.setErrorCode(PARAMETER_AND_MAPPING_WITHOUT_INDIRECTION_MISMATCH);
        return exception;
    }

    public static DescriptorException parameterAndMappingWithTransparentIndirectionMismatch(DatabaseMapping mapping, Class parameterType, String validTypeName) {
        Object[] args = { mapping.getAttributeName(), parameterType, validTypeName };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, PARAMETER_AND_MAPPING_WITH_TRANSPARENT_INDIRECTION_MISMATCH, args), mapping);
        exception.setErrorCode(PARAMETER_AND_MAPPING_WITH_TRANSPARENT_INDIRECTION_MISMATCH);
        return exception;
    }

    public static DescriptorException parentClassIsSelf(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, PARENT_CLASS_IS_SELF, args), descriptor);
        exception.setErrorCode(PARENT_CLASS_IS_SELF);
        return exception;
    }

    public static DescriptorException parentDescriptorNotSpecified(String parentClassName, ClassDescriptor descriptor) {
        Object[] args = { parentClassName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, PARENT_DESCRIPTOR_NOT_SPECIFIED, args), descriptor);
        descriptorException.setErrorCode(PARENT_DESCRIPTOR_NOT_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException primaryKeyFieldsNotSepcified(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, PRIMARY_KEY_FIELDS_NOT_SPECIFIED, args), descriptor);
        descriptorException.setErrorCode(PRIMARY_KEY_FIELDS_NOT_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException proxyIndirectionNotAvailable(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, PROXY_INDIRECTION_NOT_AVAILABLE, args), mapping);
        descriptorException.setErrorCode(PROXY_INDIRECTION_NOT_AVAILABLE);
        return descriptorException;
    }

    public static DescriptorException referenceClassNotSpecified(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, REFERENCE_CLASS_NOT_SPECIFIED, args), mapping);
        descriptorException.setErrorCode(REFERENCE_CLASS_NOT_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException referenceDescriptorIsNotAggregate(String className, DatabaseMapping mapping) {
        Object[] args = { className };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, REFERENCE_DESCRIPTOR_IS_NOT_AGGREGATE, args), mapping);
        descriptorException.setErrorCode(REFERENCE_DESCRIPTOR_IS_NOT_AGGREGATE);
        return descriptorException;
    }

    public static DescriptorException referenceDescriptorCannotBeAggregate(DatabaseMapping mapping) {
        DescriptorException descriptorException = new DescriptorException("Reference descriptor cannot be aggregate.", mapping);
        descriptorException.setErrorCode(REFERENCE_DESCRIPTOR_CANNOT_BE_AGGREGATE);
        return descriptorException;
    }

    public static DescriptorException referenceDescriptorIsNotAggregateCollection(String className, DatabaseMapping mapping) {
        Object[] args = { className };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, REFERENCE_DESCRIPTOR_IS_NOT_AGGREGATECOLLECTION, args), mapping);
        descriptorException.setErrorCode(REFERENCE_DESCRIPTOR_IS_NOT_AGGREGATECOLLECTION);
        return descriptorException;
    }

    public static DescriptorException referenceKeyFieldNotProperlySpecified(DatabaseField field, ForeignReferenceMapping mapping) {
        Object[] args = { field };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, REFERENCE_KEY_FIELD_NOT_PROPERLY_SPECIFIED, args), mapping);
        descriptorException.setErrorCode(REFERENCE_KEY_FIELD_NOT_PROPERLY_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException referenceTableNotSpecified(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, REFERENCE_TABLE_NOT_SPECIFIED, args), mapping);
        descriptorException.setErrorCode(REFERENCE_TABLE_NOT_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException relationKeyFieldNotProperlySpecified(DatabaseField field, ForeignReferenceMapping mapping) {
        Object[] args = { field };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RELATION_KEY_FIELD_NOT_PROPERLY_SPECIFIED, args), mapping);
        descriptorException.setErrorCode(RELATION_KEY_FIELD_NOT_PROPERLY_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException returnAndMappingWithIndirectionMismatch(DatabaseMapping mapping) {
        Object[] args = { mapping.getAttributeName() };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURN_AND_MAPPING_WITH_INDIRECTION_MISMATCH, args), mapping);
        exception.setErrorCode(RETURN_AND_MAPPING_WITH_INDIRECTION_MISMATCH);
        return exception;
    }

    public static DescriptorException returnAndMappingWithoutIndirectionMismatch(DatabaseMapping mapping) {
        Object[] args = { mapping.getAttributeName() };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURN_AND_MAPPING_WITHOUT_INDIRECTION_MISMATCH, args), mapping);
        exception.setErrorCode(RETURN_AND_MAPPING_WITHOUT_INDIRECTION_MISMATCH);
        return exception;
    }

    public static DescriptorException returnAndMappingWithTransparentIndirectionMismatch(DatabaseMapping mapping, Class parameterType, String validTypeName) {
        Object[] args = { mapping.getAttributeName(), parameterType, validTypeName };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURN_AND_MAPPING_WITH_TRANSPARENT_INDIRECTION_MISMATCH, args), mapping);
        exception.setErrorCode(RETURN_AND_MAPPING_WITH_TRANSPARENT_INDIRECTION_MISMATCH);
        return exception;
    }

    public static DescriptorException returnTypeInGetAttributeAccessor(String attributeMethodName, DatabaseMapping mapping) {
        Object[] args = { attributeMethodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURN_TYPE_IN_GET_ATTRIBUTE_ACCESSOR, args));
        descriptorException.setErrorCode(RETURN_TYPE_IN_GET_ATTRIBUTE_ACCESSOR);
        descriptorException.setMapping(mapping);
        return descriptorException;
    }

    public static DescriptorException securityOnFindMethod(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SECURITY_ON_FIND_METHOD, args), descriptor, exception);
        descriptorException.setErrorCode(SECURITY_ON_FIND_METHOD);
        return descriptorException;
    }

    public static DescriptorException securityOnFindObsoleteMethod(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SECURITY_ON_FIND_OBSOLETE_METHOD, args), descriptor, exception);
        descriptorException.setErrorCode(SECURITY_ON_FIND_OBSOLETE_METHOD);
        return descriptorException;
    }

    public static DescriptorException securityOnInitializingAttributeMethod(String attributeMethodName, DatabaseMapping mapping, Throwable exception) {
        Object[] args = { attributeMethodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SECURITY_ON_INITIALIZING_ATTRIBUTE_METHOD, args));
        descriptorException.setErrorCode(SECURITY_ON_INITIALIZING_ATTRIBUTE_METHOD);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException securityWhileConvertingToMethod(String methodName, DatabaseMapping mapping, Throwable exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SECURITY_WHILE_CONVERTING_TO_METHOD, args));
        descriptorException.setErrorCode(SECURITY_WHILE_CONVERTING_TO_METHOD);
        descriptorException.setMapping(mapping);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException securityWhileInitializingAttributesInInstanceVariableAccessor(String attributeName, String javaClassName, Throwable exception) {
        Object[] args = { attributeName, javaClassName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SECURITY_WHILE_INITIALIZING_ATTRIBUTES_IN_INSTANCE_VARIABLE_ACCESSOR, args));
        descriptorException.setErrorCode(SECURITY_WHILE_INITIALIZING_ATTRIBUTES_IN_INSTANCE_VARIABLE_ACCESSOR);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException securityWhileInitializingAttributesInMethodAccessor(String setMethodName, String getMethodName, String javaClassName) {
        Object[] args = { setMethodName, getMethodName, javaClassName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SECURITY_WHILE_INITIALIZING_ATTRIBUTES_IN_METHOD_ACCESSOR, args));
        descriptorException.setErrorCode(SECURITY_WHILE_INITIALIZING_ATTRIBUTES_IN_METHOD_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException securityWhileInitializingClassExtractionMethod(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SECURITY_WHILE_INITIALIZING_CLASS_EXTRACTION_METHOD, args), descriptor, exception);
        descriptorException.setErrorCode(SECURITY_WHILE_INITIALIZING_CLASS_EXTRACTION_METHOD);
        return descriptorException;
    }

    public static DescriptorException classExtractionMethodMustBeStatic(String methodName, ClassDescriptor descriptor) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, CLASS_EXTRACTION_METHOD_MUST_BE_STATIC, args), descriptor);
        descriptorException.setErrorCode(CLASS_EXTRACTION_METHOD_MUST_BE_STATIC);
        return descriptorException;
    }

    public static DescriptorException securityWhileInitializingCopyPolicy(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SECURITY_WHILE_INITIALIZING_COPY_POLICY, args), descriptor, exception);
        descriptorException.setErrorCode(SECURITY_WHILE_INITIALIZING_COPY_POLICY);
        return descriptorException;
    }

    public static DescriptorException securityWhileInitializingInstantiationPolicy(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SECURITY_WHILE_INITIALIZING_INSTANTIATION_POLICY, args), descriptor, exception);
        descriptorException.setErrorCode(SECURITY_WHILE_INITIALIZING_INSTANTIATION_POLICY);
        return descriptorException;
    }

    public static DescriptorException sequenceNumberPropertyNotSpecified(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SEQUENCE_NUMBER_PROPERTY_NOT_SPECIFIED, args), descriptor);
        descriptorException.setErrorCode(SEQUENCE_NUMBER_PROPERTY_NOT_SPECIFIED);
        return descriptorException;
    }

    /**
     * INTERNAL:
     * Set the mapping.
     */
    public void setDescriptor(ClassDescriptor descriptor) {
        this.descriptor = descriptor;
    }

    public static DescriptorException setExistenceCheckingNotUnderstood(String token, ClassDescriptor descriptor) {
        Object[] args = { token };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SET_EXISTENCE_CHECKING_NOT_UNDERSTOOD, args), descriptor);
        descriptorException.setErrorCode(SET_EXISTENCE_CHECKING_NOT_UNDERSTOOD);
        return descriptorException;
    }

    /**
     * INTERNAL:
     * Set the mapping.
     */
    public void setMapping(DatabaseMapping mapping) {
        if (mapping != null) {
            this.mapping = mapping;
            setDescriptor(mapping.getDescriptor());
        }
    }

    public static DescriptorException setMethodParameterTypeNotValid(CollectionMapping mapping) {
        Object[] args = { mapping.getAttributeName() };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SET_METHOD_PARAMETER_TYPE_NOT_VALID, args), mapping);
        exception.setErrorCode(SET_METHOD_PARAMETER_TYPE_NOT_VALID);
        return exception;
    }

    public static DescriptorException sizeMismatchOfForeignKeys(ForeignReferenceMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SIZE_MISMATCH_OF_FOREIGN_KEYS, args), mapping);
        descriptorException.setErrorCode(SIZE_MISMATCH_OF_FOREIGN_KEYS);
        return descriptorException;
    }

    public static DescriptorException structureNameNotSetInMapping(DatabaseMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, STRUCTURE_NAME_NOT_SET_IN_MAPPING, args), mapping);
        descriptorException.setErrorCode(STRUCTURE_NAME_NOT_SET_IN_MAPPING);
        return descriptorException;
    }

    public static DescriptorException tableIsNotPresentInDatabase(ClassDescriptor descriptor) {
        Object[] args = { descriptor.getTableName() };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TABLE_IS_NOT_PRESENT_IN_DATABASE, args), descriptor);
        descriptorException.setErrorCode(TABLE_IS_NOT_PRESENT_IN_DATABASE);
        return descriptorException;
    }

    public static DescriptorException tableNotPresent(String tableName, ClassDescriptor descriptor) {
        Object[] args = { tableName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TABLE_NOT_PRESENT, args), descriptor);
        descriptorException.setErrorCode(TABLE_NOT_PRESENT);
        return descriptorException;
    }

    public static DescriptorException tableNotSpecified(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TABLE_NOT_SPECIFIED, args), descriptor);
        descriptorException.setErrorCode(TABLE_NOT_SPECIFIED);
        return descriptorException;
    }

    public static DescriptorException targetForeignKeysSizeMismatch(ForeignReferenceMapping mapping) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_FOREIGN_KEYS_SIZE_MISMATCH, args), mapping);
        descriptorException.setErrorCode(TARGET_FOREIGN_KEYS_SIZE_MISMATCH);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileCloning(Object domainObject, String methodName, ClassDescriptor descriptor, Throwable exception) {
        Object[] args = { domainObject, methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_CLONING, args), descriptor, exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_CLONING);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileConstructorInstantiation(ClassDescriptor descriptor, Exception exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_CONSTRUCTOR_INSTANTIATION, args), descriptor, exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_CONSTRUCTOR_INSTANTIATION);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileConstructorInstantiationOfFactory(ClassDescriptor descriptor, Exception exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY, args), descriptor, exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_CONSTRUCTOR_INSTANTIATION_OF_FACTORY);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileEventExecution(String eventMethodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { eventMethodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_EVENT_EXECUTION, args), descriptor, exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_EVENT_EXECUTION);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileGettingValueThruMethodAccessor(String methodName, String objectName, Throwable exception) {
        Object[] args = { methodName, objectName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_GETTING_VALUE_THRU_METHOD_ACCESSOR);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileInstantiatingMethodBasedProxy(Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_INSTANTIATING_METHOD_BASED_PROXY, args));
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_INSTANTIATING_METHOD_BASED_PROXY);
        descriptorException.setInternalException(exception);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileInvokingAttributeMethod(DatabaseMapping mapping, Throwable exception) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_INVOKING_ATTRIBUTE_METHOD, args));
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_INVOKING_ATTRIBUTE_METHOD);
        descriptorException.setInternalException(exception);
        descriptorException.setMapping(mapping);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileInvokingFieldToMethod(String methodName, DatabaseMapping mapping, Throwable exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_INVOKING_FIELD_TO_METHOD, args));
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_INVOKING_FIELD_TO_METHOD);
        descriptorException.setInternalException(exception);
        descriptorException.setMapping(mapping);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileInvokingRowExtractionMethod(AbstractRecord row, Method method, ClassDescriptor descriptor, Throwable exception) {
        Object[] args = { row, method };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_INVOKING_ROW_EXTRACTION_METHOD, args), descriptor, exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_INVOKING_ROW_EXTRACTION_METHOD);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileMethodInstantiation(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_METHOD_INSTANTIATION, args), descriptor, exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_METHOD_INSTANTIATION);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileMethodInstantiationOfFactory(String methodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { methodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_METHOD_INSTANTIATION_OF_FACTORY, args), descriptor, exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_METHOD_INSTANTIATION_OF_FACTORY);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileObsoleteEventExecute(String eventMethodName, ClassDescriptor descriptor, Exception exception) {
        Object[] args = { eventMethodName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_OBSOLETE_EVENT_EXECUTION, args), descriptor, exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_OBSOLETE_EVENT_EXECUTION);
        return descriptorException;
    }

    public static DescriptorException targetInvocationWhileSettingValueThruMethodAccessor(String setMethodName, Object value, Throwable exception) {
        Object[] args = { setMethodName, String.valueOf(value), CR };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, TARGET_INVOCATION_WHILE_SETTING_VALUE_THRU_METHOD_ACESSOR, args));
        descriptorException.setInternalException(exception);
        descriptorException.setErrorCode(TARGET_INVOCATION_WHILE_SETTING_VALUE_THRU_METHOD_ACESSOR);
        return descriptorException;
    }

    // Bug 2618982
    public static DescriptorException unsupportedTypeForBidirectionalRelationshipMaintenance(DatabaseMapping mapping, org.eclipse.persistence.internal.queries.ContainerPolicy containerPolicy) {
        Object[] args = { mapping.getAttributeName(), containerPolicy };
        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, UNSUPPORTED_TYPE_FOR_BIDIRECTIONAL_RELATIONSHIP_MAINTENANCE, args), mapping);
        exception.setErrorCode(UNSUPPORTED_TYPE_FOR_BIDIRECTIONAL_RELATIONSHIP_MAINTENANCE);
        return exception;
    }

    public static DescriptorException valueHolderInstantiationMismatch(Object attributeValue, DatabaseMapping mapping) {
        Object[] args = { mapping.getAttributeName(), attributeValue };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, VALUE_HOLDER_INSTANTIATION_MISMATCH, args), mapping);
        exception.setErrorCode(VALUE_HOLDER_INSTANTIATION_MISMATCH);
        return exception;
    }

    public static DescriptorException valueNotFoundInClassIndicatorMapping(ClassDescriptor parentDescriptor, ClassDescriptor descriptor) {
        Object[] args = { parentDescriptor };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, VALUE_NOT_FOUND_IN_CLASS_INDICATOR_MAPPING, args), descriptor);
        descriptorException.setErrorCode(VALUE_NOT_FOUND_IN_CLASS_INDICATOR_MAPPING);
        return descriptorException;
    }

    public static DescriptorException variableOneToOneMappingIsNotDefinedProperly(DatabaseMapping mapping, ClassDescriptor descriptor, String targetKeyName) {
        Object[] args = { targetKeyName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, VARIABLE_ONE_TO_ONE_MAPPING_IS_NOT_DEFINED, args), mapping);
        descriptorException.setErrorCode(VARIABLE_ONE_TO_ONE_MAPPING_IS_NOT_DEFINED);
        return descriptorException;
    }

    public static DescriptorException writeLockFieldInChildDescriptor(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, WRITE_LOCK_FIELD_IN_CHILD_DESCRIPTOR, args), descriptor);
        descriptorException.setErrorCode(WRITE_LOCK_FIELD_IN_CHILD_DESCRIPTOR);
        return descriptorException;
    }

    public static DescriptorException mappingForAttributeIsMissing(String attributeName, ClassDescriptor descriptor) {
        Object[] args = { attributeName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_MAPPING_FOR_ATTRIBUTENAME, args), descriptor);
        descriptorException.setErrorCode(NO_MAPPING_FOR_ATTRIBUTENAME);
        return descriptorException;
    }

    public static DescriptorException attributeMappingIsMissingForEntityBean(String attributeName, String beanName) {
        Object[] args = { attributeName, beanName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_MAPPING_FOR_ATTRIBUTENAME_IN_ENTITY_BEAN, args));
        descriptorException.setErrorCode(NO_MAPPING_FOR_ATTRIBUTENAME_IN_ENTITY_BEAN);
        return descriptorException;
    }

    public static DescriptorException returningPolicyFieldTypeConflict(String fieldName, String type1Name, String type2Name, ClassDescriptor descriptor) {
        Object[] args = { fieldName, type1Name, type2Name };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURNING_POLICY_FIELD_TYPE_CONFLICT, args), descriptor);
        descriptorException.setErrorCode(RETURNING_POLICY_FIELD_TYPE_CONFLICT);
        return descriptorException;
    }

    public static DescriptorException returningPolicyFieldInsertConflict(String fieldName, ClassDescriptor descriptor) {
        Object[] args = { fieldName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURNING_POLICY_FIELD_INSERT_CONFLICT, args), descriptor);
        descriptorException.setErrorCode(RETURNING_POLICY_FIELD_INSERT_CONFLICT);
        return descriptorException;
    }

    public static DescriptorException returningPolicyAndDescriptorFieldTypeConflict(String fieldName, String returningPolicyFieldTypeName, String descriptorFieldTypeName, ClassDescriptor descriptor) {
        Object[] args = { fieldName, returningPolicyFieldTypeName, descriptorFieldTypeName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURNING_POLICY_AND_DESCRIPTOR_FIELD_TYPE_CONFLICT, args), descriptor);
        descriptorException.setErrorCode(RETURNING_POLICY_AND_DESCRIPTOR_FIELD_TYPE_CONFLICT);
        return descriptorException;
    }

    public static DescriptorException returningPolicyUnmappedFieldTypeNotSet(String fieldName, ClassDescriptor descriptor) {
        Object[] args = { fieldName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURNING_POLICY_UNMAPPED_FIELD_TYPE_NOT_SET, args), descriptor);
        descriptorException.setErrorCode(RETURNING_POLICY_UNMAPPED_FIELD_TYPE_NOT_SET);
        return descriptorException;
    }

    public static DescriptorException returningPolicyMappedFieldTypeNotSet(String fieldName, ClassDescriptor descriptor) {
        Object[] args = { fieldName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURNING_POLICY_MAPPED_FIELD_TYPE_NOT_SET, args), descriptor);
        descriptorException.setErrorCode(RETURNING_POLICY_MAPPED_FIELD_TYPE_NOT_SET);
        return descriptorException;
    }

    public static DescriptorException returningPolicyMappingNotSupported(String fieldName, String mappingClassName, DatabaseMapping mapping) {
        Object[] args = { fieldName, mappingClassName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURNING_POLICY_MAPPING_NOT_SUPPORTED, args), mapping);
        descriptorException.setErrorCode(RETURNING_POLICY_MAPPING_NOT_SUPPORTED);
        return descriptorException;
    }

    public static DescriptorException returningPolicyFieldNotSupported(String fieldName, ClassDescriptor descriptor) {
        Object[] args = { fieldName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, RETURNING_POLICY_FIELD_NOT_SUPPORTED, args), descriptor);
        descriptorException.setErrorCode(RETURNING_POLICY_FIELD_NOT_SUPPORTED);
        return descriptorException;
    }

    public static DescriptorException customQueryAndReturningPolicyFieldConflict(String queryTypeName, String fieldName, ClassDescriptor descriptor) {
        Object[] args = { queryTypeName, fieldName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, CUSTOM_QUERY_AND_RETURNING_POLICY_CONFLICT, args), descriptor);
        descriptorException.setErrorCode(CUSTOM_QUERY_AND_RETURNING_POLICY_CONFLICT);
        return descriptorException;
    }

    public static DescriptorException noCustomQueryForReturningPolicy(String queryTypeName, String platformTypeName, ClassDescriptor descriptor) {
        Object[] args = { queryTypeName, platformTypeName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_CUSTOM_QUERY_FOR_RETURNING_POLICY, args), descriptor);
        descriptorException.setErrorCode(NO_CUSTOM_QUERY_FOR_RETURNING_POLICY);
        return descriptorException;
    }

    public static DescriptorException updateAllFieldsNotSet(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, UPDATE_ALL_FIELDS_NOT_SET, args), descriptor);
        descriptorException.setErrorCode(UPDATE_ALL_FIELDS_NOT_SET);
        return descriptorException;
    }

    public static DescriptorException invalidMappingType(DatabaseMapping mapping) {
        Object[] args = { mapping.getAttributeName() };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_MAPPING_TYPE, args), mapping);
        descriptorException.setErrorCode(INVALID_MAPPING_TYPE);
        return descriptorException;
    }

    public static DescriptorException needToImplementChangeTracker(ClassDescriptor descriptor) {
        Object[] args = { descriptor.getJavaClass() };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NEED_TO_IMPLEMENT_CHANGETRACKER, args), descriptor);
        descriptorException.setErrorCode(NEED_TO_IMPLEMENT_CHANGETRACKER);
        return descriptorException;
    }

    public static DescriptorException needToImplementFetchGroupTracker(Class aClass, ClassDescriptor descriptor) {
        Object[] args = { aClass };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NEED_TO_IMPLEMENT_FETCHGROUPTRACKER, args), descriptor);
        descriptorException.setErrorCode(NEED_TO_IMPLEMENT_FETCHGROUPTRACKER);
        return descriptorException;
    }

    public static DescriptorException errorUsingPrimaryKey(Object primaryKey, ClassDescriptor descriptor, Exception underlying) {
        Object[] args = { primaryKey };

        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INTERNAL_ERROR_ACCESSING_PKFIELD, args), descriptor, underlying);
        exception.setErrorCode(INTERNAL_ERROR_ACCESSING_PKFIELD);
        return exception;
    }

    public static DescriptorException unitOfWorkIsolatedObjectsAccessedInSession(ClassDescriptor descriptor) {
        Object[] args = { };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, UNIT_OF_WORK_ISOLATED_OBJECTS_ACCESSED_IN_SESSION, args), descriptor);
        descriptorException.setErrorCode(UNIT_OF_WORK_ISOLATED_OBJECTS_ACCESSED_IN_SESSION);
        return descriptorException;
    }

    public static DescriptorException insertOrderConflictsWithMultipleTableForeignKeys(ClassDescriptor descriptor, DatabaseTable table1, DatabaseTable table2) {
        Object[] args = { table1, table2 };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INSERT_ORDER_CONFLICTS_WITH_MULTIPLE_TABLE_FOREIGN_KEYS, args), descriptor);
        descriptorException.setErrorCode(INSERT_ORDER_CONFLICTS_WITH_MULTIPLE_TABLE_FOREIGN_KEYS);
        return descriptorException;
    }

    public static DescriptorException insertOrderCyclicalDependencyBetweenTwoTables(ClassDescriptor descriptor, DatabaseTable table1, DatabaseTable table2) {
        Object[] args = { table1, table2 };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INSERT_ORDER_CYCLICAL_DEPENDENCY_BETWEEN_TWO_TABLES, args), descriptor);
        descriptorException.setErrorCode(INSERT_ORDER_CYCLICAL_DEPENDENCY_BETWEEN_TWO_TABLES);
        return descriptorException;
    }

    public static DescriptorException insertOrderCyclicalDependencyBetweenThreeOrMoreTables(ClassDescriptor descriptor) {
        Object[] args = { };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INSERT_ORDER_CYCLICAL_DEPENDENCY_BETWEEN_THREE_OR_MORE_TABLES, args), descriptor);
        descriptorException.setErrorCode(INSERT_ORDER_CYCLICAL_DEPENDENCY_BETWEEN_THREE_OR_MORE_TABLES);
        return descriptorException;
    }

    public static DescriptorException insertOrderChildBeforeParent(ClassDescriptor descriptor, DatabaseTable table1, DatabaseTable table2) {
        Object[] args = { table1, table2 };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INSERT_ORDER_CHILD_BEFORE_PARENT, args), descriptor);
        descriptorException.setErrorCode(INSERT_ORDER_CHILD_BEFORE_PARENT);
        return descriptorException;
    }
    
    public static DescriptorException cannotSetConverterForNonDirectMapping(ClassDescriptor descriptor, DatabaseMapping mapping, String keyConverterClassName) {
        Object[] args = { mapping, keyConverterClassName };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, CANNOT_SET_CONVERTER_FOR_NON_DIRECT_MAPPING, args), descriptor);
        descriptorException.setErrorCode(CANNOT_SET_CONVERTER_FOR_NON_DIRECT_MAPPING);
        return descriptorException;
    }

    public static DescriptorException directKeyNotSet(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, DIRECT_KEY_NOT_SET, args), descriptor);
        descriptorException.setErrorCode(DIRECT_KEY_NOT_SET);
        return descriptorException;
    }

    public static DescriptorException listOrderFieldRequiersList(ClassDescriptor descriptor, DatabaseMapping mapping) {
        Object[] args = { mapping };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, LIST_ORDER_FIELD_REQUIRES_LIST, args), descriptor);
        descriptorException.setErrorCode(LIST_ORDER_FIELD_REQUIRES_LIST);
        return descriptorException;
    }

    public static DescriptorException listOrderFieldRequiersIndirectList(ClassDescriptor descriptor, DatabaseMapping mapping) {
        Object[] args = { mapping };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, LIST_ORDER_FIELD_REQUIRES_INDIRECT_LIST, args), descriptor);
        descriptorException.setErrorCode(LIST_ORDER_FIELD_REQUIRES_INDIRECT_LIST);
        return descriptorException;
    }

    public static DescriptorException listOrderFieldTableIsWrong(ClassDescriptor descriptor, DatabaseMapping mapping, DatabaseTable wrongTable, DatabaseTable correctTable) {
        Object[] args = { mapping, wrongTable, correctTable };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, LIST_ORDER_FIELD_TABLE_IS_WRONG, args), descriptor);
        descriptorException.setErrorCode(LIST_ORDER_FIELD_TABLE_IS_WRONG);
        return descriptorException;
    }

    public static DescriptorException multipleTargetForeignKeyTables(ClassDescriptor descriptor, DatabaseMapping mapping, Collection tables) {
        Object[] args = { mapping, tables };
    
        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MULTIPLE_TARGET_FOREIGN_KEY_TABLES, args), descriptor);
        descriptorException.setErrorCode(MULTIPLE_TARGET_FOREIGN_KEY_TABLES);
        return descriptorException;
    }

    public static DescriptorException oneToOneMappingConflict(ClassDescriptor descriptor, DatabaseMapping mapping) {
        Object[] args = { mapping };
    
        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, ONE_TO_ONE_MAPPING_CONFLICT, args), descriptor);
        descriptorException.setErrorCode(ONE_TO_ONE_MAPPING_CONFLICT);
        return descriptorException;
    }

    public static DescriptorException noRelationTableMechanism(DatabaseMapping mapping) {
        Object[] args = { mapping };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, NO_RELATION_TABLE_MECHANISM, args), mapping);
        descriptorException.setErrorCode(NO_RELATION_TABLE_MECHANISM);
        return descriptorException;
    }


    public static DescriptorException cannotUseIdValueForCompositeId(ClassDescriptor descriptor) {
        Object[] args = {  };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, CANNOT_USE_ID_VALUE_FOR_COMPOSITE_ID, args), descriptor);
        descriptorException.setErrorCode(CANNOT_USE_ID_VALUE_FOR_COMPOSITE_ID);
        return descriptorException;
    }
    
    public static DescriptorException invalidXpathForXMLDirectMapping(DatabaseMapping mapping) {
        Object[] args = {};

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, INVALID_XPATH_FOR_DIRECT_MAPPING, args), mapping);
        descriptorException.setErrorCode(INVALID_XPATH_FOR_DIRECT_MAPPING);
        return descriptorException;
    }
    
    public static DescriptorException missingPartitioningPolicy(String name, ClassDescriptor descriptor, DatabaseMapping mapping) {
        Object[] args = { name };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, MISSING_PARTITION_POLICY, args), descriptor);
        if (mapping != null) {
            descriptorException.setMapping(mapping);
        }
        descriptorException.setErrorCode(MISSING_PARTITION_POLICY);
        return descriptorException;
    }

    public static DescriptorException serializedObjectPolicyFieldNotSet(ClassDescriptor descriptor) {
        Object[] args = { };

        DescriptorException descriptorException = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, SERIALIZED_OBJECT_POLICY_FIELD_NOT_SET, args), descriptor);
        descriptorException.setErrorCode(SERIALIZED_OBJECT_POLICY_FIELD_NOT_SET);
        return descriptorException;
    }
    
    public static DescriptorException exceptionAccessingPrimaryKeyInstance(ClassDescriptor descriptor, Exception underlying) {
        Object[] args = { };
        DescriptorException exception = new DescriptorException(ExceptionMessageGenerator.buildMessage(DescriptorException.class, EXCEPTION_ACCESSING_PRIMARY_KEY_INSTANCE, args), descriptor, underlying);
        exception.setErrorCode(EXCEPTION_ACCESSING_PRIMARY_KEY_INSTANCE);
        return exception;
    }
}
