0001: // THIS SOFTWARE IS PROVIDED BY SOFTARIS PTY.LTD. AND OTHER METABOSS
0002: // CONTRIBUTORS ``AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES, INCLUDING,
0003: // BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
0004: // FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SOFTARIS PTY.LTD.
0005: // OR OTHER METABOSS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
0006: // INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
0007: // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
0008: // OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
0009: // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
0010: // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
0011: // EVEN IF SOFTARIS PTY.LTD. OR OTHER METABOSS CONTRIBUTORS ARE ADVISED OF THE
0012: // POSSIBILITY OF SUCH DAMAGE.
0013: //
0014: // Copyright 2000-2005 © Softaris Pty.Ltd. All Rights Reserved.
0015: package com.metaboss.sdlctools.models.modelassistant.metabossmodel.domainsupport;
0016:
0017: import java.util.ArrayList;
0018: import java.util.Collection;
0019: import java.util.HashSet;
0020: import java.util.Iterator;
0021: import java.util.List;
0022: import java.util.Set;
0023:
0024: import javax.jmi.reflect.ConstraintViolationException;
0025: import javax.jmi.reflect.RefObject;
0026:
0027: import com.metaboss.sdlctools.models.metabossmodel.ModelElementConstraint;
0028: import com.metaboss.sdlctools.models.metabossmodel.datadictionarymodel.Structure;
0029: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.Message;
0030: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.Operation;
0031: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.OperationInputField;
0032: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.OperationOutputField;
0033: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.OperationOutputMessage;
0034: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.Service;
0035: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.Servicemodule;
0036: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.TransactionPolicyEnum;
0037: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.systemimplementationmodel.AssociationRole;
0038: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.systemimplementationmodel.Attribute;
0039: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.systemimplementationmodel.AttributeStereotypeEnum;
0040: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.systemimplementationmodel.Domain;
0041: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.systemimplementationmodel.Entity;
0042: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.systemimplementationmodel.EntityStereotypeEnum;
0043: import com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.systemimplementationmodel.PrimaryKeyElement;
0044: import com.metaboss.util.StringUtils;
0045:
0046: /** This class containse helper methods dealing with the Domain Support Servicemodule model element */
0047: class TargetUpdateEntityOperationHelper {
0048: private ModelAssistantImpl mModelAssistantImpl;
0049:
0050: TargetUpdateEntityOperationHelper(
0051: ModelAssistantImpl pModelAssistantImpl) {
0052: mModelAssistantImpl = pModelAssistantImpl;
0053: // Add entity lifecycle listener
0054: mModelAssistantImpl.addLifecycleListener(Entity.class,
0055: new ModelAssistantImpl.ModelElementLifecycleListener() {
0056: public void onElementJustCreated(
0057: RefObject pModelElementJustCreated) {
0058: Entity lEntity = (Entity) pModelElementJustCreated;
0059: String lEntityName = lEntity.getName();
0060: if (lEntityName == null)
0061: return; // Domain does not have a name
0062: Domain lDomain = lEntity.getDomain();
0063: if (lDomain == null)
0064: return; // Entity is not associated with domain
0065: String lDomainName = lDomain.getName();
0066: if (lDomainName == null)
0067: return; // Domain does not have a name
0068: com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.System lSystem = lDomain
0069: .getSystem();
0070: if (lSystem == null)
0071: return; // Domain is not associated with system
0072: Servicemodule lServicemodule = lSystem
0073: .findServicemodule(StylesheetImpl
0074: .getDomainSupportServicemoduleName(lDomainName));
0075: if (lServicemodule == null)
0076: return; // There is no support servicemodule yet
0077: Service lDomainSupportService = lServicemodule
0078: .findService(StylesheetImpl
0079: .getDataManagementServiceName(lDomainName));
0080: if (lDomainSupportService == null)
0081: return; // There is no domain support service yet
0082: // Create or remove associated element
0083: if (lEntity.isModifiable())
0084: ensurePresent(lDomainSupportService,
0085: lEntity, lEntityName);
0086: else
0087: ensureAbsent(lDomainSupportService,
0088: lEntityName);
0089: }
0090:
0091: public void onElementBeingDeleted(
0092: RefObject pModelElementBeingDeleted) {
0093: Entity lEntity = (Entity) pModelElementBeingDeleted;
0094: String lEntityName = lEntity.getName();
0095: if (lEntityName == null)
0096: return; // Domain does not have a name
0097: Domain lDomain = lEntity.getDomain();
0098: if (lDomain == null)
0099: return; // Entity is not associated with domain
0100: String lDomainName = lDomain.getName();
0101: if (lDomainName == null)
0102: return; // Domain does not have a name
0103: com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.System lSystem = lDomain
0104: .getSystem();
0105: if (lSystem == null)
0106: return; // Domain is not associated with system
0107: Servicemodule lServicemodule = lSystem
0108: .findServicemodule(StylesheetImpl
0109: .getDomainSupportServicemoduleName(lDomainName));
0110: if (lServicemodule == null)
0111: return; // There is no support servicemodule yet
0112: Service lDomainSupportService = lServicemodule
0113: .findService(StylesheetImpl
0114: .getDataManagementServiceName(lDomainName));
0115: if (lDomainSupportService == null)
0116: return; // There is no domain support service yet
0117: // Remove associated element
0118: ensureAbsent(lDomainSupportService, lEntityName);
0119: }
0120: });
0121: // Add entity Name attribute change listener
0122: mModelAssistantImpl
0123: .addAttributeChangeListener(
0124: Entity.class,
0125: "Name",
0126: new ModelAssistantImpl.ModelElementAttributeChangeListener() {
0127: public void onAttributeBeingUpdated(
0128: RefObject pModelElementBeingUpdated,
0129: String pAttributeName,
0130: Object pOldValue, Object pNewValue) {
0131: Entity lEntity = (Entity) pModelElementBeingUpdated;
0132: Domain lDomain = lEntity.getDomain();
0133: if (lDomain == null)
0134: return; // Entity is not associated with domain
0135: String lDomainName = lDomain.getName();
0136: if (lDomainName == null)
0137: return; // Domain does not have a name
0138: com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.System lSystem = lDomain
0139: .getSystem();
0140: if (lSystem == null)
0141: return; // Domain is not associated with system
0142: Servicemodule lServicemodule = lSystem
0143: .findServicemodule(StylesheetImpl
0144: .getDomainSupportServicemoduleName(lDomainName));
0145: if (lServicemodule == null)
0146: return; // There is no support servicemodule yet
0147: Service lDomainSupportService = lServicemodule
0148: .findService(StylesheetImpl
0149: .getDataManagementServiceName(lDomainName));
0150: if (lDomainSupportService == null)
0151: return; // There is no domain support service yet
0152: if (pNewValue == null) {
0153: // Only old value is known - ensure that the element is deleted
0154: ensureAbsent(lDomainSupportService,
0155: (String) pOldValue);
0156: } else {
0157: // New value is known - analyse the criteria and deal with the element accordingly
0158: if (lEntity.isModifiable()) {
0159: // The element must be present - rename or create
0160: if (pOldValue != null)
0161: ensureRenamedPresent(
0162: lDomainSupportService,
0163: lEntity,
0164: (String) pOldValue,
0165: (String) pNewValue);
0166: else
0167: ensurePresent(
0168: lDomainSupportService,
0169: lEntity,
0170: (String) pNewValue);
0171: } else {
0172: // The element must be absent - delete
0173: ensureAbsent(
0174: lDomainSupportService,
0175: (String) pNewValue);
0176: if (pOldValue != null)
0177: ensureAbsent(
0178: lDomainSupportService,
0179: (String) pOldValue);
0180: }
0181: }
0182: }
0183: });
0184: // Add entity stereotype change listener
0185: mModelAssistantImpl
0186: .addAttributeChangeListener(
0187: Entity.class,
0188: "stereotype",
0189: new ModelAssistantImpl.ModelElementAttributeChangeListener() {
0190: public void onAttributeBeingUpdated(
0191: RefObject pModelElementBeingUpdated,
0192: String pAttributeName,
0193: Object pOldValue, Object pNewValue) {
0194: Entity lEntity = (Entity) pModelElementBeingUpdated;
0195: String lEntityName = lEntity.getName();
0196: if (lEntityName == null)
0197: return; // Entity does not have a name
0198: Domain lDomain = lEntity.getDomain();
0199: if (lDomain == null)
0200: return; // Entity is not associated with domain
0201: String lDomainName = lDomain.getName();
0202: if (lDomainName == null)
0203: return; // Domain does not have a name
0204: com.metaboss.sdlctools.models.metabossmodel.enterprisemodel.System lSystem = lDomain
0205: .getSystem();
0206: if (lSystem == null)
0207: return; // Domain is not associated with system
0208: Servicemodule lServicemodule = lSystem
0209: .findServicemodule(StylesheetImpl
0210: .getDomainSupportServicemoduleName(lDomainName));
0211: if (lServicemodule == null)
0212: return; // There is no support servicemodule yet
0213: Service lDomainSupportService = lServicemodule
0214: .findService(StylesheetImpl
0215: .getDataManagementServiceName(lDomainName));
0216: if (lDomainSupportService == null)
0217: return; // There is no domain support service yet
0218: // Analyse the criteria and deal with the element accordingly
0219: if (EntityStereotypeEnum.CARD_FILE
0220: .equals(pNewValue))
0221: ensurePresent(
0222: lDomainSupportService,
0223: lEntity, lEntityName);
0224: else
0225: ensureAbsent(lDomainSupportService,
0226: lEntityName);
0227: }
0228: });
0229: }
0230:
0231: private static String sOperationConstraintTextBase = "A Data Management Service must have Update Entity operation for every modifiable Entity in the corresponding Domain.";
0232: private static String sProposedInstanceDetailsInputFieldConstraintTextBase = "An Update Entity Data Management Operation must have well formed Proposed Instance Details input parameter carrying modified details of the Entity.";
0233: private static String sUpdatedInstanceDetailsOutputFieldConstraintTextBase = "An Update Entity Data Management Operation must have well formed Updated Instance Details output parameter carrying actual details of the modified Entity.";
0234: private static String sVersionIdMismatchOutputMessageConstraintTextBase = "An Update Entity Data Management Operation must have well formed Entity Version Id Mismatch output message indicating concurrent update problem.";
0235: private static String sMandatoryReferenceCanNotBeEmptyOutputMessageConstraintTextBase = "An Update Entity Data Management Operation must have well formed Mandatory Reference Can Not Be Empty output message, one for each mandatory reference.";
0236: private static String sEntityNotFoundErrorOutputMessageConstraintTextBase = "An Update Entity Data Management Operation must have well formed Entity Not Found output message, one for the Entity itself and one for each mandatory reference.";
0237: private static final String sOperationInputConstraintTextBase = "An Update Entity Data Management Operation must have well formed Input Constraints performing sanity check on the input data.";
0238:
0239: // This helper verifies constraints
0240: void verifyConstraints(Collection pViolations,
0241: Service pDataManagementService, Entity pEntity,
0242: Collection pUnclaimedOperations) {
0243: String lEntityName = pEntity.getName();
0244: if (lEntityName == null)
0245: return;
0246: // Work on the Key structure
0247: String lOperationName = suggestOperationName(lEntityName);
0248: Operation lOperation = pDataManagementService
0249: .findOperation(lOperationName);
0250: if (lOperation == null) {
0251: if (pEntity.isModifiable())
0252: pViolations.add(new ConstraintViolationException(
0253: pDataManagementService, pDataManagementService
0254: .refMetaObject(),
0255: sOperationConstraintTextBase + " The '"
0256: + lOperationName
0257: + "' Operation not found."));
0258: return;
0259: }
0260: pUnclaimedOperations.remove(lOperation); // Claim the operation
0261: if (!pEntity.isModifiable()) {
0262: pViolations.add(new ConstraintViolationException(
0263: pDataManagementService, pDataManagementService
0264: .refMetaObject(),
0265: sOperationConstraintTextBase + " The '"
0266: + lOperationName
0267: + "' Operation unexpected."));
0268: return;
0269: }
0270: // Validate operation details
0271: if (!TransactionPolicyEnum.REQUIRED.equals(lOperation
0272: .getTransactionPolicy()))
0273: pViolations.add(new ConstraintViolationException(
0274: lOperation, lOperation.refMetaObject(),
0275: "Update Entity Operation must have transaction policy '"
0276: + TransactionPolicyEnum.REQUIRED.toString()
0277: + "'. The '"
0278: + lOperation.getTransactionPolicy()
0279: + "' Transaction policy is unexpected."));
0280: if (lOperation.isQuery())
0281: pViolations
0282: .add(new ConstraintViolationException(lOperation,
0283: lOperation.refMetaObject(),
0284: "Update Entity Operation must have the isQuery attribute set to false."));
0285: Structure lEntityDetailsStructure = pDataManagementService
0286: .getServicemodule() != null ? pDataManagementService
0287: .getServicemodule()
0288: .findStructure(
0289: StylesheetImpl
0290: .getEntityDetailsStructureName(lEntityName))
0291: : null;
0292: // Input Fields - only verify that the ones that we need exist. The extra ones are allowed
0293: {
0294: String lOperationInputFieldName = suggestProposedDetailsInputParameterName(lEntityName);
0295: OperationInputField lInputField = lOperation
0296: .findInputField(lOperationInputFieldName);
0297: if (lInputField != null) {
0298: if (lEntityDetailsStructure != null
0299: && lEntityDetailsStructure.equals(lInputField
0300: .getStructureType()) == false)
0301: pViolations.add(new ConstraintViolationException(
0302: lInputField, lInputField.refMetaObject(),
0303: sProposedInstanceDetailsInputFieldConstraintTextBase
0304: + " The '"
0305: + lOperationInputFieldName
0306: + "' input field has wrong type."));
0307: if (lInputField.isArray())
0308: pViolations
0309: .add(new ConstraintViolationException(
0310: lInputField,
0311: lInputField.refMetaObject(),
0312: sProposedInstanceDetailsInputFieldConstraintTextBase
0313: + " The '"
0314: + lOperationInputFieldName
0315: + "' input field is an array, which is wrong."));
0316: } else
0317: pViolations.add(new ConstraintViolationException(
0318: lOperation, lOperation.refMetaObject(),
0319: sProposedInstanceDetailsInputFieldConstraintTextBase
0320: + " The '" + lOperationInputFieldName
0321: + "' input field is missing."));
0322: }
0323: // Input constraints
0324: {
0325: Collection lPrimaryKeyElements = pEntity
0326: .getPrimaryKeyElements();
0327: String lOperationInputFieldName = suggestProposedDetailsInputParameterName(lEntityName);
0328: // Work on the field presence constraint.
0329: {
0330: String lConstraintName = lOperationInputFieldName
0331: + "FieldPresenceConstraint";
0332: ModelElementConstraint lModelElementConstraint = lOperation
0333: .findInputConstraint(lConstraintName);
0334: if (lModelElementConstraint == null)
0335: pViolations
0336: .add(new ConstraintViolationException(
0337: lOperation,
0338: lOperation.refMetaObject(),
0339: sOperationInputConstraintTextBase
0340: + " The '"
0341: + lConstraintName
0342: + "' Input Constraint is missing."));
0343: }
0344: // Work on the entity key presence constraint.
0345: {
0346: String lConstraintName = lEntityName
0347: + (lPrimaryKeyElements.isEmpty() ? "KeyFieldPresenceConstraint"
0348: : "KeyFieldsPresenceConstraint");
0349: ModelElementConstraint lModelElementConstraint = lOperation
0350: .findInputConstraint(lConstraintName);
0351: if (lModelElementConstraint == null)
0352: pViolations
0353: .add(new ConstraintViolationException(
0354: lOperation,
0355: lOperation.refMetaObject(),
0356: sOperationInputConstraintTextBase
0357: + " The '"
0358: + lConstraintName
0359: + "' Input Constraint is missing."));
0360: }
0361: // Work on the mandatory fields presence constraints.
0362: for (Iterator lAttributesIterator = pEntity
0363: .getCombinedAttributes().iterator(); lAttributesIterator
0364: .hasNext();) {
0365: Attribute lAttribute = (Attribute) lAttributesIterator
0366: .next();
0367: String lAttributeFieldName = StylesheetImpl
0368: .getEntityAttributeStructureFieldName(lAttribute
0369: .getName());
0370: String lConstraintName = lOperationInputFieldName
0371: + lAttributeFieldName
0372: + "FieldPresenceConstraint";
0373: ModelElementConstraint lModelElementConstraint = lOperation
0374: .findInputConstraint(lConstraintName);
0375: if (lPrimaryKeyElements.contains(lAttribute) == false
0376: && AttributeStereotypeEnum.MANDATORY
0377: .equals(lAttribute.getStereotype())) {
0378: if (lModelElementConstraint == null)
0379: pViolations
0380: .add(new ConstraintViolationException(
0381: lOperation,
0382: lOperation.refMetaObject(),
0383: sOperationInputConstraintTextBase
0384: + " The '"
0385: + lConstraintName
0386: + "' Input Constraint is missing."));
0387: } else {
0388: if (lModelElementConstraint != null)
0389: pViolations
0390: .add(new ConstraintViolationException(
0391: lOperation,
0392: lOperation.refMetaObject(),
0393: sOperationInputConstraintTextBase
0394: + " The '"
0395: + lConstraintName
0396: + "' Input Constraint is not required."));
0397: }
0398: }
0399: // Work on mandatory references presence constraints
0400: for (Iterator lReferencesIterator = pEntity
0401: .getCombinedReferences().iterator(); lReferencesIterator
0402: .hasNext();) {
0403: AssociationRole lReference = (AssociationRole) lReferencesIterator
0404: .next();
0405: String lRefefrenceFieldName = StylesheetImpl
0406: .getEntityReferenceStructureFieldName(lReference
0407: .getName());
0408: String lConstraintName = lOperationInputFieldName
0409: + lRefefrenceFieldName
0410: + "FieldPresenceConstraint";
0411: ModelElementConstraint lModelElementConstraint = lOperation
0412: .findInputConstraint(lConstraintName);
0413: if (lPrimaryKeyElements.contains(lReference) == false
0414: && lReference.isSingular()
0415: && lReference.isMandatory()) {
0416: if (lModelElementConstraint == null)
0417: pViolations
0418: .add(new ConstraintViolationException(
0419: lOperation,
0420: lOperation.refMetaObject(),
0421: sOperationInputConstraintTextBase
0422: + " The '"
0423: + lConstraintName
0424: + "' Input Constraint is missing."));
0425: } else {
0426: if (lModelElementConstraint != null)
0427: pViolations
0428: .add(new ConstraintViolationException(
0429: lOperation,
0430: lOperation.refMetaObject(),
0431: sOperationInputConstraintTextBase
0432: + " The '"
0433: + lConstraintName
0434: + "' Input Constraint is not required."));
0435: }
0436: }
0437:
0438: }
0439: // Output Fields - only verify that the ones that we need exist. The extra ones are allowed
0440: {
0441: String lOperationOutputFieldName = suggestUpdatedDetailsReturnParameterName(lEntityName);
0442: OperationOutputField lOutputField = lOperation
0443: .findOutputField(lOperationOutputFieldName);
0444: if (lOutputField != null) {
0445: if (lEntityDetailsStructure != null
0446: && lEntityDetailsStructure.equals(lOutputField
0447: .getStructureType()) == false)
0448: pViolations
0449: .add(new ConstraintViolationException(
0450: lOutputField,
0451: lOutputField.refMetaObject(),
0452: sUpdatedInstanceDetailsOutputFieldConstraintTextBase
0453: + " The '"
0454: + lOperationOutputFieldName
0455: + "' output field has wrong type."));
0456: if (lOutputField.isArray())
0457: pViolations
0458: .add(new ConstraintViolationException(
0459: lOutputField,
0460: lOutputField.refMetaObject(),
0461: sUpdatedInstanceDetailsOutputFieldConstraintTextBase
0462: + " The '"
0463: + lOperationOutputFieldName
0464: + "' output field is an array, which is wrong."));
0465: } else
0466: pViolations.add(new ConstraintViolationException(
0467: lOperation, lOperation.refMetaObject(),
0468: sUpdatedInstanceDetailsOutputFieldConstraintTextBase
0469: + " The '" + lOperationOutputFieldName
0470: + "' output field is missing."));
0471: }
0472: // Output Messages - only verify that the ones that we need exist. The extra ones are allowed
0473: {
0474: // Version Id mismatch
0475: {
0476: String lOperationOutputMessageName = suggestVersionMismatchReturnMessageName(lEntityName);
0477: OperationOutputMessage lOutputMessage = lOperation
0478: .findOutputMessage(lOperationOutputMessageName);
0479: if (lOutputMessage != null) {
0480: Message lEntityVersionIdMismatchMessage = pDataManagementService
0481: .getServicemodule() != null ? pDataManagementService
0482: .getServicemodule()
0483: .findMessage(
0484: StylesheetImpl
0485: .getEntityVersionIdMismatchMessageName(lEntityName))
0486: : null;
0487: if (lEntityVersionIdMismatchMessage != null
0488: && lEntityVersionIdMismatchMessage
0489: .equals(lOutputMessage
0490: .getMessageType()) == false)
0491: pViolations
0492: .add(new ConstraintViolationException(
0493: lOutputMessage,
0494: lOutputMessage.refMetaObject(),
0495: sVersionIdMismatchOutputMessageConstraintTextBase
0496: + " The '"
0497: + lOperationOutputMessageName
0498: + "' output message has wrong type."));
0499: if (lOutputMessage.isArray())
0500: pViolations
0501: .add(new ConstraintViolationException(
0502: lOutputMessage,
0503: lOutputMessage.refMetaObject(),
0504: sVersionIdMismatchOutputMessageConstraintTextBase
0505: + " The '"
0506: + lOperationOutputMessageName
0507: + "' output message is an array, which is wrong."));
0508: } else
0509: pViolations.add(new ConstraintViolationException(
0510: lOperation, lOperation.refMetaObject(),
0511: sVersionIdMismatchOutputMessageConstraintTextBase
0512: + " The '"
0513: + lOperationOutputMessageName
0514: + "' output message is missing."));
0515: }
0516:
0517: // We may have entity instances not found for the entities which may be specified during update
0518: Set lEntitiesWhichMayBeNotFoundWhenUpdatingInstance = new HashSet();
0519: lEntitiesWhichMayBeNotFoundWhenUpdatingInstance
0520: .add(pEntity);
0521: Util
0522: .collectEntitiesWhichMayBeNotFoundWhenUpdatingOrCreatingInstance(
0523: pEntity,
0524: lEntitiesWhichMayBeNotFoundWhenUpdatingInstance);
0525: for (Iterator lEntitiesWhichMayBeNotFoundWhenUpdatingInstanceIterator = lEntitiesWhichMayBeNotFoundWhenUpdatingInstance
0526: .iterator(); lEntitiesWhichMayBeNotFoundWhenUpdatingInstanceIterator
0527: .hasNext();) {
0528: Entity lEntityElement = (Entity) lEntitiesWhichMayBeNotFoundWhenUpdatingInstanceIterator
0529: .next();
0530: String lEntityElementName = lEntityElement.getName();
0531: if (lEntityElementName == null)
0532: continue;
0533: String lOperationOutputMessageName = StylesheetImpl
0534: .getEntityNotFoundOperationOutputMessageName(lEntityElementName);
0535: OperationOutputMessage lOutputMessage = lOperation
0536: .findOutputMessage(lOperationOutputMessageName);
0537: if (lOutputMessage != null) {
0538: Message lEntityInstanceNotFoundMessage = pDataManagementService
0539: .getServicemodule() != null ? pDataManagementService
0540: .getServicemodule()
0541: .findMessage(
0542: StylesheetImpl
0543: .getEntityInstanceNotFoundMessageName(lEntityElementName))
0544: : null;
0545: if (lEntityInstanceNotFoundMessage != null
0546: && lEntityInstanceNotFoundMessage
0547: .equals(lOutputMessage
0548: .getMessageType()) == false)
0549: pViolations
0550: .add(new ConstraintViolationException(
0551: lOutputMessage,
0552: lOutputMessage.refMetaObject(),
0553: sEntityNotFoundErrorOutputMessageConstraintTextBase
0554: + " The '"
0555: + lOperationOutputMessageName
0556: + "' output message has wrong type."));
0557: if (lOutputMessage.isArray())
0558: pViolations
0559: .add(new ConstraintViolationException(
0560: lOutputMessage,
0561: lOutputMessage.refMetaObject(),
0562: sEntityNotFoundErrorOutputMessageConstraintTextBase
0563: + " The '"
0564: + lOperationOutputMessageName
0565: + "' output message is an array, which is wrong."));
0566: } else
0567: pViolations.add(new ConstraintViolationException(
0568: lOperation, lOperation.refMetaObject(),
0569: sEntityNotFoundErrorOutputMessageConstraintTextBase
0570: + " The '"
0571: + lOperationOutputMessageName
0572: + "' output message is missing."));
0573: }
0574: }
0575: }
0576:
0577: // This helper is doing everything necessary to rectify errors reported in verifyConstraints()
0578: void rectifyModel(Service pDataManagementService, Entity pEntity,
0579: Collection pUnclaimedOperations) {
0580: // Check if we have an operation and than just call ensurePresent
0581: String lEntityName = pEntity.getName();
0582: String lOperationName = suggestOperationName(lEntityName);
0583: Operation lOperation = pDataManagementService
0584: .findOperation(lOperationName);
0585: if (lOperation != null)
0586: pUnclaimedOperations.remove(lOperation); // Claim the operation
0587: if (pEntity.isModifiable())
0588: ensurePresent(pDataManagementService, pEntity, lEntityName);
0589: else
0590: ensureAbsent(pDataManagementService, lEntityName);
0591: }
0592:
0593: // This helper renames and ensures that the element is present
0594: void ensureRenamedPresent(Service pDataManagementService,
0595: Entity pEntity, String pOldEntityName, String pNewEntityName) {
0596: // Note that this method only deals with renaming and than calls the ensure present method
0597: String lOldOperationName = suggestOperationName(pOldEntityName);
0598: Operation lOldOperation = pDataManagementService
0599: .findOperation(lOldOperationName);
0600: String lNewOperationName = suggestOperationName(pNewEntityName);
0601: Operation lNewOperation = pDataManagementService
0602: .findOperation(lNewOperationName);
0603: // Be relaxed here - allow for all sorts of mishaps
0604: if (lOldOperation != null) {
0605: if (lNewOperation != null) {
0606: // New and old structures are present - just delete the old one
0607: lOldOperation.refDelete();
0608: } else {
0609: // Old structure is present - new one is not - rename
0610: lOldOperation.setName(lNewOperationName);
0611: }
0612: }
0613: // Call the ensure present bit
0614: ensurePresent(pDataManagementService, pEntity, pNewEntityName);
0615: }
0616:
0617: // This helper makes sure that the version id attribute is present in the details structure
0618: void ensurePresent(Service pDataManagementService, Entity pEntity,
0619: String pEntityName) {
0620: Structure lEntityDetailsStructure = pDataManagementService
0621: .getServicemodule() != null ? pDataManagementService
0622: .getServicemodule()
0623: .findStructure(
0624: StylesheetImpl
0625: .getEntityDetailsStructureName(pEntityName))
0626: : null;
0627: // Work on the servicemodule
0628: String lOperationName = suggestOperationName(pEntityName);
0629: Operation lOperation = pDataManagementService
0630: .findOperation(lOperationName);
0631: if (lOperation == null) {
0632: lOperation = mModelAssistantImpl.mOperationClass
0633: .createOperation();
0634: lOperation.setService(pDataManagementService);
0635: lOperation.setName(lOperationName);
0636: }
0637: lOperation
0638: .setDescription(suggestOperationDescription(pEntityName));
0639: lOperation.setTransactionPolicy(TransactionPolicyEnum.REQUIRED);
0640: lOperation.setQuery(false);
0641: // Input Fields
0642: {
0643: Collection lOperationInputFields = lOperation
0644: .getInputFields();
0645: List lUnprocessedInputFields = new ArrayList();
0646: lUnprocessedInputFields.addAll(lOperationInputFields);
0647: {
0648: String lOperationInputFieldName = suggestProposedDetailsInputParameterName(pEntityName);
0649: OperationInputField lInputField = lOperation
0650: .findInputField(lOperationInputFieldName);
0651: if (lInputField == null) {
0652: lInputField = mModelAssistantImpl.mOperationInputFieldClass
0653: .createOperationInputField();
0654: lInputField.setName(lOperationInputFieldName);
0655: lInputField.setOperation(lOperation);
0656: } else {
0657: lUnprocessedInputFields.remove(lInputField);
0658: }
0659: lInputField
0660: .setDescription(suggestProposedDetailsInputParameterDescription(pEntityName));
0661: lInputField.setArray(false);
0662: lInputField.setDataType(null);
0663: lInputField.setStructureType(lEntityDetailsStructure);
0664: }
0665: // Delete all input fields left
0666: for (Iterator lUnprocessedInputFieldsIterator = lUnprocessedInputFields
0667: .iterator(); lUnprocessedInputFieldsIterator
0668: .hasNext();) {
0669: OperationInputField lInputField = (OperationInputField) lUnprocessedInputFieldsIterator
0670: .next();
0671: if (!lInputField.isDerived())
0672: lInputField.refDelete();
0673: }
0674: }
0675: // Input constraints
0676: {
0677: // Copy aside the collection of the constraints, so we can delete the unused ones
0678: Collection lUnclaimedConstraints = new ArrayList();
0679: lUnclaimedConstraints.addAll(lOperation
0680: .getInputConstraints());
0681:
0682: String lOperationInputFieldName = suggestProposedDetailsInputParameterName(pEntityName);
0683: String lOperationInputFieldOCLFieldName = lOperationInputFieldName
0684: .substring(0, 1).toLowerCase()
0685: + lOperationInputFieldName.substring(1);
0686: Collection lPrimaryKeyElements = pEntity
0687: .getPrimaryKeyElements();
0688:
0689: // Work on the input presence validation constraint
0690: {
0691: String lConstraintName = lOperationInputFieldName
0692: + "FieldPresenceConstraint";
0693: ModelElementConstraint lModelElementConstraint = lOperation
0694: .findInputConstraint(lConstraintName);
0695: if (lModelElementConstraint == null) {
0696: lModelElementConstraint = mModelAssistantImpl.mModelElementConstraintClass
0697: .createModelElementConstraint();
0698: lModelElementConstraint.setName(lConstraintName);
0699: lOperation.getInputConstraints().add(
0700: lModelElementConstraint);
0701: } else {
0702: // Claim the field
0703: lUnclaimedConstraints
0704: .remove(lModelElementConstraint);
0705: }
0706: lModelElementConstraint
0707: .setDescription("Verifies that the "
0708: + lOperationInputFieldName
0709: + " input field is not empty in the operation input");
0710: lModelElementConstraint.setDefaultErrorText("The '"
0711: + lOperationInputFieldName
0712: + "' input field must not be empty.");
0713: lModelElementConstraint.setOclExpression("not "
0714: + lOperationInputFieldOCLFieldName
0715: + ".oclIsUndefined()");
0716: }
0717: // Work on the key information presence constraint
0718: {
0719: // Build OCL expression and the error message
0720: String lInstanceIdFieldName = StylesheetImpl
0721: .getEntityInstanceIdStructureFieldName(
0722: pEntityName,
0723: pEntity
0724: .getInstanceIdAttributeNameOverride());
0725: // Ensure that the first character is lower case
0726: String lInstanceIdOCLFieldName = lInstanceIdFieldName
0727: .substring(0, 1).toLowerCase()
0728: + lInstanceIdFieldName.substring(1);
0729: String lConstraintName = pEntityName
0730: + (lPrimaryKeyElements.isEmpty() ? "KeyFieldPresenceConstraint"
0731: : "KeyFieldsPresenceConstraint");
0732:
0733: ModelElementConstraint lModelElementConstraint = lOperation
0734: .findInputConstraint(lConstraintName);
0735: if (lModelElementConstraint == null) {
0736: lModelElementConstraint = mModelAssistantImpl.mModelElementConstraintClass
0737: .createModelElementConstraint();
0738: lModelElementConstraint.setName(lConstraintName);
0739: lOperation.getInputConstraints().add(
0740: lModelElementConstraint);
0741: } else {
0742: // Claim the field
0743: lUnclaimedConstraints
0744: .remove(lModelElementConstraint);
0745: }
0746: lModelElementConstraint
0747: .setDescription("Ensures the "
0748: + lOperationInputFieldName
0749: + " structure contains enough data to uniquely identify the instance of the "
0750: + pEntityName);
0751: if (lPrimaryKeyElements.isEmpty()) {
0752: // Set default error text
0753: lModelElementConstraint
0754: .setDefaultErrorText(lOperationInputFieldName
0755: + " structure does not contain enough information to identify the instance of the "
0756: + pEntityName
0757: + " entity. "
0758: + lInstanceIdFieldName
0759: + " field must contain entity instance identifier.");
0760:
0761: // Build and set the OCL expression
0762: StringBuffer lOCLExpression = new StringBuffer();
0763: lOCLExpression.append("not ");
0764: lOCLExpression
0765: .append(lOperationInputFieldOCLFieldName);
0766: lOCLExpression.append(".");
0767: lOCLExpression.append(lInstanceIdOCLFieldName);
0768: lOCLExpression.append(".oclIsUndefined()");
0769: lModelElementConstraint
0770: .setOclExpression(lOCLExpression.toString());
0771: } else {
0772: // Set default error text
0773: lModelElementConstraint
0774: .setDefaultErrorText(lOperationInputFieldName
0775: + " structure does not contain enough information to identify the instance of the "
0776: + pEntityName
0777: + " entity. Either "
0778: + lInstanceIdFieldName
0779: + " field must contain entity instance identifier or all fields which are part of the natural primary key must be populated.");
0780:
0781: // Build and set the OCL expression
0782: StringBuffer lOCLExpression = new StringBuffer();
0783: lOCLExpression.append("(not ");
0784: lOCLExpression
0785: .append(lOperationInputFieldOCLFieldName);
0786: lOCLExpression.append(".");
0787: lOCLExpression.append(lInstanceIdOCLFieldName);
0788: lOCLExpression.append(".oclIsUndefined()) or ");
0789: if (lPrimaryKeyElements.size() > 1)
0790: lOCLExpression.append("(");
0791: for (Iterator lPrimaryKeyElementsIterator = pEntity
0792: .getPrimaryKeyElements().iterator();;) {
0793: PrimaryKeyElement lPrimaryKeyElement = (PrimaryKeyElement) lPrimaryKeyElementsIterator
0794: .next();
0795: String lFieldName = null;
0796: if (lPrimaryKeyElement instanceof Attribute) {
0797: Attribute lAttribute = (Attribute) lPrimaryKeyElement;
0798: lFieldName = StylesheetImpl
0799: .getEntityAttributeStructureFieldName(lAttribute
0800: .getName());
0801: } else if (lPrimaryKeyElement instanceof AssociationRole) {
0802: AssociationRole lReference = (AssociationRole) lPrimaryKeyElement;
0803: lFieldName = StylesheetImpl
0804: .getEntityReferenceStructureFieldName(lReference
0805: .getName());
0806: }
0807: // Ensure that the first character is lower case
0808: String lOCLFieldName = lFieldName.substring(0,
0809: 1).toLowerCase()
0810: + lFieldName.substring(1);
0811: lOCLExpression.append("(not ");
0812: lOCLExpression
0813: .append(lOperationInputFieldOCLFieldName);
0814: lOCLExpression.append(".");
0815: lOCLExpression.append(lOCLFieldName);
0816: lOCLExpression.append(".oclIsUndefined())");
0817:
0818: if (lPrimaryKeyElementsIterator.hasNext())
0819: lOCLExpression.append(" and ");
0820: else
0821: break;
0822: }
0823: if (lPrimaryKeyElements.size() > 1)
0824: lOCLExpression.append(")");
0825: lModelElementConstraint
0826: .setOclExpression(lOCLExpression.toString());
0827: }
0828: }
0829:
0830: // Work on the mandatory fields presence constraints.
0831: // Skip the fields which are part of primary key because they have stricter constraint above.
0832: // Attributes
0833: for (Iterator lAttributesIterator = pEntity
0834: .getCombinedAttributes().iterator(); lAttributesIterator
0835: .hasNext();) {
0836: Attribute lAttribute = (Attribute) lAttributesIterator
0837: .next();
0838: if (lPrimaryKeyElements.contains(lAttribute) == false
0839: && AttributeStereotypeEnum.MANDATORY
0840: .equals(lAttribute.getStereotype()))
0841: mandatoryAttributePresenceConstraint_EnsurePresent(
0842: lOperation, lOperationInputFieldName,
0843: lOperationInputFieldOCLFieldName,
0844: lAttribute.getName(), lUnclaimedConstraints);
0845: else
0846: mandatoryAttributePresenceConstraint_EnsureAbsent(
0847: lOperation, lOperationInputFieldName,
0848: lAttribute.getName(), lUnclaimedConstraints);
0849: }
0850: // References
0851: for (Iterator lReferencesIterator = pEntity
0852: .getCombinedReferences().iterator(); lReferencesIterator
0853: .hasNext();) {
0854: AssociationRole lReference = (AssociationRole) lReferencesIterator
0855: .next();
0856: if (lPrimaryKeyElements.contains(lReference) == false
0857: && lReference.isSingular()
0858: && lReference.isMandatory())
0859: mandatoryReferencePresenceConstraint_EnsurePresent(
0860: lOperation, lOperationInputFieldName,
0861: lOperationInputFieldOCLFieldName,
0862: lReference.getName(), lUnclaimedConstraints);
0863: else
0864: mandatoryReferencePresenceConstraint_EnsureAbsent(
0865: lOperation, lOperationInputFieldName,
0866: lReference.getName(), lUnclaimedConstraints);
0867: }
0868:
0869: // Remove unclaimed constraints
0870: for (Iterator lUnclaimedConstraintsIterator = lUnclaimedConstraints
0871: .iterator(); lUnclaimedConstraintsIterator
0872: .hasNext();) {
0873: ModelElementConstraint lUnclaimedConstraint = (ModelElementConstraint) lUnclaimedConstraintsIterator
0874: .next();
0875: if (!lUnclaimedConstraint.isDerived())
0876: lUnclaimedConstraint.refDelete();
0877: }
0878: }
0879: // Output Fields
0880: {
0881: Collection lOperationOutputFields = lOperation
0882: .getOutputFields();
0883: List lUnprocessedOutputFields = new ArrayList();
0884: lUnprocessedOutputFields.addAll(lOperationOutputFields);
0885: {
0886: String lOperationOutputFieldName = suggestUpdatedDetailsReturnParameterName(pEntityName);
0887: OperationOutputField lOutputField = lOperation
0888: .findOutputField(lOperationOutputFieldName);
0889: if (lOutputField == null) {
0890: lOutputField = mModelAssistantImpl.mOperationOutputFieldClass
0891: .createOperationOutputField();
0892: lOutputField.setName(lOperationOutputFieldName);
0893: lOperationOutputFields.add(lOutputField);
0894: } else {
0895: lUnprocessedOutputFields.remove(lOutputField);
0896: }
0897: lOutputField
0898: .setDescription(suggestUpdatedDetailsReturnParameterDescription(pEntityName));
0899: lOutputField.setArray(false);
0900: lOutputField.setDataType(null);
0901: lOutputField.setStructureType(lEntityDetailsStructure);
0902: }
0903: // Delete all output fields left
0904: for (Iterator lUnprocessedOutputFieldsIterator = lUnprocessedOutputFields
0905: .iterator(); lUnprocessedOutputFieldsIterator
0906: .hasNext();) {
0907: OperationOutputField lOutputField = (OperationOutputField) lUnprocessedOutputFieldsIterator
0908: .next();
0909: if (!lOutputField.isDerived())
0910: lOutputField.refDelete();
0911: }
0912: }
0913: // Output Messages
0914: {
0915: Collection lOperationOutputMessages = lOperation
0916: .getOutputMessages();
0917: List lUnprocessedOutputMessages = new ArrayList();
0918: lUnprocessedOutputMessages.addAll(lOperationOutputMessages);
0919:
0920: // Version Id mismatch is always present and has to be declared
0921: {
0922: String lOperationOutputMessageName = suggestVersionMismatchReturnMessageName(pEntityName);
0923: OperationOutputMessage lOutputMessage = lOperation
0924: .findOutputMessage(lOperationOutputMessageName);
0925: if (lOutputMessage == null) {
0926: lOutputMessage = mModelAssistantImpl.mOperationOutputMessageClass
0927: .createOperationOutputMessage();
0928: lOutputMessage.setName(lOperationOutputMessageName);
0929: lOutputMessage.setOperation(lOperation);
0930: } else {
0931: lUnprocessedOutputMessages.remove(lOutputMessage);
0932: }
0933: lOutputMessage
0934: .setDescription(suggestVersionMismatchReturnMessageDescription(pEntityName));
0935: lOutputMessage.setArray(false);
0936: Message lEntityVersionIdMismatchMessage = pDataManagementService
0937: .getServicemodule() != null ? pDataManagementService
0938: .getServicemodule()
0939: .findMessage(
0940: StylesheetImpl
0941: .getEntityVersionIdMismatchMessageName(pEntityName))
0942: : null;
0943: lOutputMessage
0944: .setMessageType(lEntityVersionIdMismatchMessage);
0945: }
0946:
0947: // We may have entity instances not found for the entities which may be specified during update (will at least have this entity)
0948: Set lEntitiesWhichMayBeNotFoundWhenUpdatingInstance = new HashSet();
0949: lEntitiesWhichMayBeNotFoundWhenUpdatingInstance
0950: .add(pEntity);
0951: Util
0952: .collectEntitiesWhichMayBeNotFoundWhenUpdatingOrCreatingInstance(
0953: pEntity,
0954: lEntitiesWhichMayBeNotFoundWhenUpdatingInstance);
0955: for (Iterator lEntitiesWhichMayBeNotFoundWhenUpdatingInstanceIterator = lEntitiesWhichMayBeNotFoundWhenUpdatingInstance
0956: .iterator(); lEntitiesWhichMayBeNotFoundWhenUpdatingInstanceIterator
0957: .hasNext();) {
0958: Entity lEntityElement = (Entity) lEntitiesWhichMayBeNotFoundWhenUpdatingInstanceIterator
0959: .next();
0960: // We need to use entity name parameter for the entity which is passed as a parameter.
0961: String lEntityElementName = lEntityElement
0962: .equals(pEntity) ? pEntityName : lEntityElement
0963: .getName();
0964: if (lEntityElementName == null)
0965: continue;
0966: String lOperationOutputMessageName = StylesheetImpl
0967: .getEntityNotFoundOperationOutputMessageName(lEntityElementName);
0968: OperationOutputMessage lOutputMessage = lOperation
0969: .findOutputMessage(lOperationOutputMessageName);
0970: if (lOutputMessage == null) {
0971: lOutputMessage = mModelAssistantImpl.mOperationOutputMessageClass
0972: .createOperationOutputMessage();
0973: lOutputMessage.setName(lOperationOutputMessageName);
0974: lOutputMessage.setOperation(lOperation);
0975: } else {
0976: lUnprocessedOutputMessages.remove(lOutputMessage);
0977: }
0978: lOutputMessage
0979: .setDescription(StylesheetImpl
0980: .getEntityNotFoundOperationOutputMessageDescription(lEntityElementName));
0981: lOutputMessage.setArray(false);
0982: Message lEntityInstanceNotFoundMessage = pDataManagementService
0983: .getServicemodule() != null ? pDataManagementService
0984: .getServicemodule()
0985: .findMessage(
0986: StylesheetImpl
0987: .getEntityInstanceNotFoundMessageName(lEntityElementName))
0988: : null;
0989: lOutputMessage
0990: .setMessageType(lEntityInstanceNotFoundMessage);
0991: }
0992:
0993: // Delete all output messages left
0994: for (Iterator lUnprocessedOutputMessagesIterator = lUnprocessedOutputMessages
0995: .iterator(); lUnprocessedOutputMessagesIterator
0996: .hasNext();) {
0997: OperationOutputMessage lOutputMessage = (OperationOutputMessage) lUnprocessedOutputMessagesIterator
0998: .next();
0999: if (!lOutputMessage.isDerived())
1000: lOutputMessage.refDelete();
1001: }
1002: }
1003: }
1004:
1005: // This helper makes sure that the version id attribute is absent in the details structure
1006: void ensureAbsent(Service pDataManagementService, String pEntityName) {
1007: // Work on the details structure
1008: Operation lOperation = pDataManagementService
1009: .findOperation(suggestOperationName(pEntityName));
1010: if (lOperation != null)
1011: lOperation.refDelete();
1012: }
1013:
1014: private void mandatoryAttributePresenceConstraint_EnsurePresent(
1015: Operation pOperation, String pOperationInputFieldName,
1016: String pOperationInputFieldOCLFieldName,
1017: String pAttributeName, Collection pUnclaimedConstraints) {
1018: String lAttributeFieldName = StylesheetImpl
1019: .getEntityAttributeStructureFieldName(pAttributeName);
1020: String lAttributeFieldOCLFieldName = lAttributeFieldName
1021: .substring(0, 1).toLowerCase()
1022: + lAttributeFieldName.substring(1);
1023: String lConstraintName = pOperationInputFieldName
1024: + lAttributeFieldName + "FieldPresenceConstraint";
1025: ModelElementConstraint lModelElementConstraint = pOperation
1026: .findInputConstraint(lConstraintName);
1027: if (lModelElementConstraint == null) {
1028: lModelElementConstraint = mModelAssistantImpl.mModelElementConstraintClass
1029: .createModelElementConstraint();
1030: lModelElementConstraint.setName(lConstraintName);
1031: pOperation.getInputConstraints().add(
1032: lModelElementConstraint);
1033: } else {
1034: // Claim the field if necessary
1035: if (pUnclaimedConstraints != null)
1036: pUnclaimedConstraints.remove(lModelElementConstraint);
1037: }
1038: lModelElementConstraint
1039: .setDescription("Ensures that the "
1040: + lAttributeFieldName
1041: + " mandatory field is either omitted or populated with non-empty value in the "
1042: + pOperationInputFieldName + " structure.");
1043: lModelElementConstraint
1044: .setDefaultErrorText("The '"
1045: + lAttributeFieldName
1046: + "' field is mandatory and must be either omitted or populated with non-empty value in the '"
1047: + pOperationInputFieldName + "' structure.");
1048: // Build and set the OCL expression
1049: StringBuffer lOCLExpression = new StringBuffer();
1050: lOCLExpression.append("not ");
1051: lOCLExpression.append(pOperationInputFieldOCLFieldName);
1052: lOCLExpression.append(".");
1053: lOCLExpression.append(lAttributeFieldOCLFieldName);
1054: lOCLExpression.append(".isEmpty()");
1055: lModelElementConstraint.setOclExpression(lOCLExpression
1056: .toString());
1057: }
1058:
1059: private void mandatoryAttributePresenceConstraint_EnsureAbsent(
1060: Operation pOperation, String pOperationInputFieldName,
1061: String pAttributeName, Collection pUnclaimedConstraints) {
1062: String lAttributeFieldName = StylesheetImpl
1063: .getEntityAttributeStructureFieldName(pAttributeName);
1064: String lConstraintName = pOperationInputFieldName
1065: + lAttributeFieldName + "FieldPresenceConstraint";
1066: ModelElementConstraint lModelElementConstraint = pOperation
1067: .findInputConstraint(lConstraintName);
1068: if (lModelElementConstraint != null) {
1069: // Claim the field if necessary
1070: if (pUnclaimedConstraints != null)
1071: pUnclaimedConstraints.remove(lModelElementConstraint);
1072: lModelElementConstraint.refDelete();
1073: }
1074: }
1075:
1076: private void mandatoryReferencePresenceConstraint_EnsurePresent(
1077: Operation pOperation, String pOperationInputFieldName,
1078: String pOperationInputFieldOCLFieldName,
1079: String pReferenceName, Collection pUnclaimedConstraints) {
1080: String lReferenceFieldName = StylesheetImpl
1081: .getEntityReferenceStructureFieldName(pReferenceName);
1082: String lReferenceFieldOCLFieldName = lReferenceFieldName
1083: .substring(0, 1).toLowerCase()
1084: + lReferenceFieldName.substring(1);
1085: String lConstraintName = pOperationInputFieldName
1086: + lReferenceFieldName + "FieldPresenceConstraint";
1087: ModelElementConstraint lModelElementConstraint = pOperation
1088: .findInputConstraint(lConstraintName);
1089: if (lModelElementConstraint == null) {
1090: lModelElementConstraint = mModelAssistantImpl.mModelElementConstraintClass
1091: .createModelElementConstraint();
1092: lModelElementConstraint.setName(lConstraintName);
1093: pOperation.getInputConstraints().add(
1094: lModelElementConstraint);
1095: } else {
1096: // Claim the field if necessary
1097: if (pUnclaimedConstraints != null)
1098: pUnclaimedConstraints.remove(lModelElementConstraint);
1099: }
1100: lModelElementConstraint
1101: .setDescription("Ensures that the "
1102: + lReferenceFieldName
1103: + " mandatory field is either omitted or populated with non-empty value in the "
1104: + pOperationInputFieldName + " structure.");
1105: lModelElementConstraint
1106: .setDefaultErrorText("The '"
1107: + lReferenceFieldName
1108: + "' field is mandatory and must be either omitted or populated with non-empty value in the '"
1109: + pOperationInputFieldName + "' structure.");
1110: // Build and set the OCL expression
1111: StringBuffer lOCLExpression = new StringBuffer();
1112: lOCLExpression.append("not ");
1113: lOCLExpression.append(pOperationInputFieldOCLFieldName);
1114: lOCLExpression.append(".");
1115: lOCLExpression.append(lReferenceFieldOCLFieldName);
1116: lOCLExpression.append(".isEmpty()");
1117: lModelElementConstraint.setOclExpression(lOCLExpression
1118: .toString());
1119: }
1120:
1121: private void mandatoryReferencePresenceConstraint_EnsureAbsent(
1122: Operation pOperation, String pOperationInputFieldName,
1123: String pReferenceName, Collection pUnclaimedConstraints) {
1124: String lReferenceFieldName = StylesheetImpl
1125: .getEntityReferenceStructureFieldName(pReferenceName);
1126: String lConstraintName = pOperationInputFieldName
1127: + lReferenceFieldName + "FieldPresenceConstraint";
1128: ModelElementConstraint lModelElementConstraint = pOperation
1129: .findInputConstraint(lConstraintName);
1130: if (lModelElementConstraint != null) {
1131: // Claim the field if necessary
1132: if (pUnclaimedConstraints != null)
1133: pUnclaimedConstraints.remove(lModelElementConstraint);
1134: lModelElementConstraint.refDelete();
1135: }
1136: }
1137:
1138: // Helper. Returns the message name
1139: private static String suggestOperationName(String pEntityName) {
1140: // Use normalised name here
1141: return "update"
1142: + StringUtils.suggestName(pEntityName, true, false);
1143: }
1144:
1145: // Helper. Returns the message description
1146: private static String suggestOperationDescription(String pEntityName) {
1147: // Use name 'as is' here
1148: return "Updates existing instance of " + pEntityName
1149: + " in the domain.";
1150: }
1151:
1152: // Helper. Returns the name
1153: private static String suggestProposedDetailsInputParameterName(
1154: String pEntityName) {
1155: return "ProposedDetails";
1156: }
1157:
1158: // Helper. Returns the description
1159: private static String suggestProposedDetailsInputParameterDescription(
1160: String pEntityName) {
1161: // Use name 'as is' here
1162: return "Proposed new details of the existing instance of the "
1163: + pEntityName
1164: + ". Only identifier fields and fields with new values need to be populated.";
1165: }
1166:
1167: // Helper. Returns the message name
1168: private static String suggestUpdatedDetailsReturnParameterName(
1169: String pEntityName) {
1170: return "UpdatedDetails";
1171: }
1172:
1173: // Helper. Returns the message description
1174: private static String suggestUpdatedDetailsReturnParameterDescription(
1175: String pEntityName) {
1176: // Use name 'as is' here
1177: return "Details of an instance after successfull update. Mostly the same as the details passed in, but may have some autogenerated fields populated or updated.";
1178: }
1179:
1180: // Helper. Returns the message name
1181: private static String suggestVersionMismatchReturnMessageName(
1182: String pEntityName) {
1183: // Use normalised name here
1184: return "VersionMismatchError";
1185: }
1186:
1187: // Helper. Returns the message description
1188: private static String suggestVersionMismatchReturnMessageDescription(
1189: String pEntityName) {
1190: // Use name 'as is' here
1191: return "Error message in case of version mismatch or null if this error has not occurred.";
1192: }
1193:
1194: }
|