0001: package org.enhydra.shark.xpdl;
0002:
0003: import java.io.ByteArrayOutputStream;
0004: import java.io.StringReader;
0005: import java.lang.reflect.Method;
0006: import java.util.ArrayList;
0007: import java.util.Collection;
0008: import java.util.HashMap;
0009: import java.util.HashSet;
0010: import java.util.Iterator;
0011: import java.util.List;
0012: import java.util.Locale;
0013: import java.util.Map;
0014: import java.util.Properties;
0015: import java.util.Set;
0016:
0017: import javax.xml.parsers.DocumentBuilder;
0018: import javax.xml.parsers.DocumentBuilderFactory;
0019: import javax.xml.transform.Transformer;
0020: import javax.xml.transform.TransformerFactory;
0021: import javax.xml.transform.dom.DOMSource;
0022: import javax.xml.transform.stream.StreamResult;
0023:
0024: import org.apache.xerces.parsers.DOMParser;
0025: import org.enhydra.shark.xpdl.elements.*;
0026: import org.enhydra.shark.xpdl.elements.Package;
0027: import org.enhydra.shark.xpdl.elements.Version;
0028: import org.w3c.dom.Document;
0029: import org.xml.sax.InputSource;
0030:
0031: /**
0032: * Represents coresponding element from XPDL schema.
0033: *
0034: * @author Sasa Bojanic
0035: */
0036: public class StandardPackageValidator implements XMLValidator {
0037:
0038: public static final String VALIDATE_SUBFLOW_REFERENCES = "ValidateSubFlowReferences";
0039:
0040: public static final String VALIDATE_PERFORMER_EXPRESSIONS = "ValidatePerformerExpressions";
0041:
0042: public static final String VALIDATE_ACTUAL_PARAMETER_EXPRESSIONS = "ValidateActualParameterExpressions";
0043:
0044: public static final String VALIDATE_DEADLINE_EXPRESSIONS = "ValidateDeadlineExpressions";
0045:
0046: public static final String VALIDATE_CONDITION_EXPRESSIONS = "ValidateConditionExpressions";
0047:
0048: public static final String VALIDATE_UNUSED_VARIABLES = "ValidateUnusedVariables";
0049:
0050: public static final String VALIDATE_CONDITION_BY_TYPE = "ValidateConditionByType";
0051:
0052: public static final String GET_EXISTING_SCHEMA_VALIDATION_ERRORS = "GetExistingSchemaValidationErrors";
0053:
0054: public static final String CHECK_EXTERNAL_PACKAGES = "CheckExternalPackages";
0055:
0056: public static final String ALLOW_UNDEFINED_START = "AllowUndefinedStart";
0057:
0058: public static final String ALLOW_UNDEFINED_END = "AllowUndefinedEnd";
0059:
0060: public static final String ENCODING = "Encoding";
0061:
0062: public static final String LOCALE = "Locale";
0063:
0064: protected static final String CURRENT_XPDL_VERSION = "1.0";
0065:
0066: protected Properties properties;
0067:
0068: protected XMLInterface xmlInterface;
0069:
0070: protected Map epsValidationErrors = new HashMap();
0071:
0072: protected Map schemaValidationErrors = new HashMap();
0073:
0074: protected Properties settings;
0075:
0076: public StandardPackageValidator() {
0077: }
0078:
0079: public StandardPackageValidator(Properties settings) {
0080: this .settings = settings;
0081: }
0082:
0083: public void init(XMLInterface pXmlInterface, Package pPkg,
0084: boolean pGetExistingSchemaValidationErrors,
0085: String pEncoding, String pLocale) {
0086: Properties tempProperties = new Properties();
0087: tempProperties.putAll(settings);
0088: tempProperties
0089: .put(
0090: StandardPackageValidator.GET_EXISTING_SCHEMA_VALIDATION_ERRORS,
0091: String
0092: .valueOf(pGetExistingSchemaValidationErrors));
0093: tempProperties.put(
0094: StandardPackageValidator.CHECK_EXTERNAL_PACKAGES,
0095: "true");
0096: tempProperties
0097: .put(StandardPackageValidator.ENCODING, pEncoding);
0098: tempProperties.put(StandardPackageValidator.LOCALE, pLocale);
0099: init(tempProperties, pXmlInterface);
0100: }
0101:
0102: public void clearCache(Package pkg) {
0103: epsValidationErrors.remove(pkg);
0104: schemaValidationErrors.remove(pkg);
0105: }
0106:
0107: public void clearCache() {
0108: epsValidationErrors.clear();
0109: schemaValidationErrors.clear();
0110: xmlInterface = null;
0111: }
0112:
0113: public Map getExtPkgValidationErrors() {
0114: return epsValidationErrors;
0115: }
0116:
0117: public void init(Properties props) {
0118: this .properties = props;
0119: if (props == null) {
0120: clearCache();
0121: }
0122: }
0123:
0124: public void init(Properties pProps, XMLInterface pXmlInterface) {
0125: init(pProps);
0126: this .xmlInterface = pXmlInterface;
0127: }
0128:
0129: public void validateElement(XMLElement el, List existingErrors,
0130: boolean fullCheck) {
0131: if (!fullCheck && existingErrors.size() > 0) {
0132: return;
0133: }
0134: if (el.isEmpty() && !(el instanceof XMLCollection)
0135: && !el.isRequired()) {
0136: return;
0137: }
0138:
0139: try {
0140: Class cl = el.getClass();
0141: Method m = null;
0142: try {
0143: m = this .getClass().getMethod("validateElement",
0144: new Class[] { cl, List.class, boolean.class });
0145: } catch (Exception ex) {
0146: if (!(cl == XMLSimpleElement.class
0147: || cl == XMLAttribute.class
0148: || cl == XMLComplexChoice.class
0149: || cl == XMLComplexElement.class
0150: || cl == XMLCollectionElement.class || cl == XMLCollection.class)) {
0151: if (XMLComplexChoice.class.isAssignableFrom(cl)) {
0152: cl = XMLComplexChoice.class;
0153: } else if (XMLAttribute.class.isAssignableFrom(cl)) {
0154: cl = XMLAttribute.class;
0155: } else if (XMLSimpleElement.class
0156: .isAssignableFrom(cl)) {
0157: cl = XMLSimpleElement.class;
0158: } else if (XMLComplexElement.class
0159: .isAssignableFrom(cl)) {
0160: cl = XMLComplexElement.class;
0161: } else if (XMLCollection.class.isAssignableFrom(cl)) {
0162: cl = XMLCollection.class;
0163: }
0164: }
0165: }
0166:
0167: m = this .getClass().getMethod("validateElement",
0168: new Class[] { cl, List.class, boolean.class });
0169: // System.err.println("calling "+m.toString()+",
0170: // el=["+el.toName()+","+el.toValue()+"]");
0171: m.invoke(this , new Object[] { el, existingErrors,
0172: new Boolean(fullCheck) });
0173: return;
0174: } catch (Throwable e) {
0175: e.printStackTrace();
0176: }
0177:
0178: validateStandard(el, existingErrors, fullCheck);
0179: }
0180:
0181: public void validateElement(XMLAttribute el, List existingErrors,
0182: boolean fullCheck) {
0183: XMLElement parent = el.getParent();
0184:
0185: boolean isValid = true;
0186: if (el.toName().equals("Id")) {
0187: if (parent instanceof SubFlow) {
0188: checkSubFlowId(el, existingErrors, fullCheck);
0189: } else if (parent instanceof Tool) {
0190: checkToolId(el, existingErrors, fullCheck);
0191: } else if (parent instanceof TransitionRef) {
0192: checkTransitionRefId(el, existingErrors, fullCheck);
0193: } else if (parent instanceof DeclaredType) {
0194: checkDeclaredTypeId(el, existingErrors);
0195: } else {
0196: if (!isIdValid(el.toValue())) {
0197: isValid = false;
0198: XMLValidationError verr = new XMLValidationError(
0199: XMLValidationError.TYPE_ERROR,
0200: XMLValidationError.SUB_TYPE_LOGIC,
0201: XPDLValidationErrorIds.ERROR_INVALID_ID, el
0202: .toValue(), el);
0203: existingErrors.add(verr);
0204: }
0205: if ((parent instanceof XMLCollectionElement)
0206: && (fullCheck || isValid)) {
0207: if (!isIdUnique((XMLCollectionElement) parent)) {
0208: isValid = false;
0209: XMLValidationError verr = new XMLValidationError(
0210: XMLValidationError.TYPE_ERROR,
0211: XMLValidationError.SUB_TYPE_LOGIC,
0212: XPDLValidationErrorIds.ERROR_NON_UNIQUE_ID,
0213: el.toValue(), el);
0214: existingErrors.add(verr);
0215: }
0216: }
0217: }
0218: } else if (el.toName().equals("href")) {
0219: if (parent instanceof ExternalPackage) {
0220: String val = el.toValue();
0221: Package pkg = XMLUtil.getPackage(el);
0222: String epId = pkg.getExternalPackageId(val);
0223: if (epId == null || epId.equals("")) {
0224: XMLValidationError verr = new XMLValidationError(
0225: XMLValidationError.TYPE_ERROR,
0226: XMLValidationError.SUB_TYPE_LOGIC,
0227: XPDLValidationErrorIds.ERROR_NON_EXISTING_EXTERNAL_PACKAGE_REFERENCE,
0228: val, el);
0229: existingErrors.add(verr);
0230: }
0231: }
0232: } else if (parent instanceof Transition) {
0233: if (el.toName().equals("From")) {
0234: checkTransitionFrom(el, existingErrors);
0235: } else if (el.toName().equals("To")) {
0236: checkTransitionTo(el, existingErrors);
0237: }
0238: } else if (parent instanceof BlockActivity) {
0239: checkBlockId(el, existingErrors);
0240: }
0241:
0242: }
0243:
0244: public void validateElement(XMLComplexChoice el,
0245: List existingErrors, boolean fullCheck) {
0246: validateElement(el.getChoosen(), existingErrors, fullCheck);
0247: }
0248:
0249: public void validateElement(XMLEmptyChoiceElement el,
0250: List existingErrors, boolean fullCheck) {
0251: }
0252:
0253: public void validateElement(XMLCollection el, List existingErrors,
0254: boolean fullCheck) {
0255: for (Iterator it = el.toElements().iterator(); it.hasNext();) {
0256: XMLElement cel = (XMLElement) it.next();
0257: validateElement(cel, existingErrors, fullCheck);
0258: }
0259: }
0260:
0261: public void validateElement(XMLCollectionElement el,
0262: List existingErrors, boolean fullCheck) {
0263: validateElement((XMLComplexElement) el, existingErrors,
0264: fullCheck);
0265: }
0266:
0267: public void validateElement(XMLComplexElement el,
0268: List existingErrors, boolean fullCheck) {
0269: for (Iterator it = el.toElements().iterator(); it.hasNext();) {
0270: XMLElement cel = (XMLElement) it.next();
0271: validateElement(cel, existingErrors, fullCheck);
0272: }
0273: }
0274:
0275: public void validateElement(XMLSimpleElement el,
0276: List existingErrors, boolean fullCheck) {
0277: }
0278:
0279: protected void validateStandard(XMLElement el, List existingErrors,
0280: boolean fullCheck) {
0281: if (el instanceof XMLAttribute) {
0282: validateElement((XMLAttribute) el, existingErrors,
0283: fullCheck);
0284: } else if (el instanceof XMLSimpleElement) {
0285: validateElement((XMLSimpleElement) el, existingErrors,
0286: fullCheck);
0287: } else if (el instanceof XMLCollectionElement) {
0288: validateElement((XMLCollectionElement) el, existingErrors,
0289: fullCheck);
0290: } else if (el instanceof XMLComplexElement) {
0291: validateElement((XMLComplexElement) el, existingErrors,
0292: fullCheck);
0293: } else if (el instanceof XMLComplexChoice) {
0294: validateElement((XMLComplexChoice) el, existingErrors,
0295: fullCheck);
0296: } else if (el instanceof XMLCollection) {
0297: validateElement((XMLCollection) el, existingErrors,
0298: fullCheck);
0299: }
0300: }
0301:
0302: public void validateElement(Activities el, List existingErrors,
0303: boolean fullCheck) {
0304: validateStandard(el, existingErrors, fullCheck);
0305: }
0306:
0307: public void validateElement(Activity el, List existingErrors,
0308: boolean fullCheck) {
0309: validateStandard(el, existingErrors, fullCheck);
0310:
0311: boolean isValid = existingErrors.size() == 0;
0312:
0313: if (!(isValid || fullCheck)) {
0314: return;
0315: }
0316:
0317: Set ets = XMLUtil.getExceptionalOutgoingTransitions(el);
0318: if (el.getDeadlines().size() > 0) {
0319: if (ets.size() == 0) {
0320:
0321: XMLValidationError verr = new XMLValidationError(
0322: XMLValidationError.TYPE_ERROR,
0323: XMLValidationError.SUB_TYPE_LOGIC,
0324: XPDLValidationErrorIds.ERROR_DEADLINES_NOT_PROPERLY_HANDLED_NO_EXCEPTIONAL_TRANSITIONS,
0325: "", el);
0326: existingErrors.add(verr);
0327: isValid = false;
0328: }
0329: }
0330:
0331: if (!(isValid || fullCheck)) {
0332: return;
0333: }
0334:
0335: Set outTrans = XMLUtil.getOutgoingTransitions(el);
0336: Set inTrans = XMLUtil.getIncomingTransitions(el);
0337:
0338: // Split type and no. of outgoing transitions
0339: Split split = XMLUtil.getSplit(el);
0340: if ((split == null || split.getType().length() == 0)
0341: && outTrans.size() > 1) {
0342: isValid = false;
0343: XMLValidationError verr = new XMLValidationError(
0344: XMLValidationError.TYPE_ERROR,
0345: XMLValidationError.SUB_TYPE_LOGIC,
0346: XPDLValidationErrorIds.ERROR_MULTIPLE_OUTGOING_TRANSITIONS_WITHOUT_SPLIT_TYPE_DEFINED,
0347: "", el);
0348: existingErrors.add(verr);
0349: }
0350:
0351: if (!(isValid || fullCheck)) {
0352: return;
0353: }
0354:
0355: // Join type and no. of incoming transitions
0356: Join join = XMLUtil.getJoin(el);
0357: if ((join == null || join.getType().length() == 0)
0358: && inTrans.size() > 1) {
0359: isValid = false;
0360: XMLValidationError verr = new XMLValidationError(
0361: XMLValidationError.TYPE_ERROR,
0362: XMLValidationError.SUB_TYPE_LOGIC,
0363: XPDLValidationErrorIds.ERROR_MULTIPLE_INCOMING_TRANSITIONS_WITHOUT_JOIN_TYPE_DEFINED,
0364: "", el);
0365: existingErrors.add(verr);
0366: }
0367:
0368: if (!(fullCheck || isValid)) {
0369: return;
0370: }
0371:
0372: checkMultipleOtherwiseOrDefaultExceptionTransitions(el,
0373: outTrans, existingErrors, fullCheck);
0374:
0375: }
0376:
0377: public void validateElement(ActivitySet el, List existingErrors,
0378: boolean fullCheck) {
0379: validateStandard(el, existingErrors, fullCheck);
0380: boolean isValid = true;
0381: if (existingErrors.size() == 0 || fullCheck) {
0382: if (el.getActivities().toElements().size() == 0) {
0383: isValid = false;
0384: XMLValidationError verr = new XMLValidationError(
0385: XMLValidationError.TYPE_ERROR,
0386: XMLValidationError.SUB_TYPE_LOGIC,
0387: XPDLValidationErrorIds.ERROR_ACTIVITY_SET_NOT_DEFINED,
0388: "", el);
0389: existingErrors.add(verr);
0390: }
0391: }
0392: if (isValid || fullCheck) {
0393: isValid = checkGraphConnectionsForWpOrAs(el,
0394: existingErrors, fullCheck)
0395: || fullCheck;
0396: }
0397: if (isValid || fullCheck) {
0398: isValid = checkGraphConformanceForWpOrAs(el,
0399: existingErrors, fullCheck)
0400: || fullCheck;
0401: }
0402: }
0403:
0404: public void validateElement(ActivitySets el, List existingErrors,
0405: boolean fullCheck) {
0406: validateStandard(el, existingErrors, fullCheck);
0407: }
0408:
0409: public void validateElement(ActivityTypes el, List existingErrors,
0410: boolean fullCheck) {
0411: validateStandard(el, existingErrors, fullCheck);
0412: }
0413:
0414: public void validateElement(ActualParameter el,
0415: List existingErrors, boolean fullCheck) {
0416: // TODO: figure out how to check it
0417: validateStandard(el, existingErrors, fullCheck);
0418: }
0419:
0420: public void validateElement(ActualParameters el,
0421: List existingErrors, boolean fullCheck) {
0422: validateStandard(el, existingErrors, fullCheck);
0423: }
0424:
0425: public void validateElement(Application el, List existingErrors,
0426: boolean fullCheck) {
0427: validateStandard(el, existingErrors, fullCheck);
0428: }
0429:
0430: public void validateElement(Applications el, List existingErrors,
0431: boolean fullCheck) {
0432: validateStandard(el, existingErrors, fullCheck);
0433: }
0434:
0435: public void validateElement(ApplicationTypes el,
0436: List existingErrors, boolean fullCheck) {
0437: validateStandard(el, existingErrors, fullCheck);
0438: }
0439:
0440: public void validateElement(ArrayType el, List existingErrors,
0441: boolean fullCheck) {
0442: // TODO: see if need to be changed
0443: validateStandard(el, existingErrors, fullCheck);
0444: }
0445:
0446: public void validateElement(Author el, List existingErrors,
0447: boolean fullCheck) {
0448: validateStandard(el, existingErrors, fullCheck);
0449: }
0450:
0451: public void validateElement(Automatic el, List existingErrors,
0452: boolean fullCheck) {
0453: validateStandard(el, existingErrors, fullCheck);
0454: }
0455:
0456: public void validateElement(BasicType el, List existingErrors,
0457: boolean fullCheck) {
0458: validateStandard(el, existingErrors, fullCheck);
0459: }
0460:
0461: public void validateElement(BlockActivity el, List existingErrors,
0462: boolean fullCheck) {
0463: validateStandard(el, existingErrors, fullCheck);
0464: }
0465:
0466: public void validateElement(Codepage el, List existingErrors,
0467: boolean fullCheck) {
0468: validateStandard(el, existingErrors, fullCheck);
0469: }
0470:
0471: public void validateElement(Condition el, List existingErrors,
0472: boolean fullCheck) {
0473: validateStandard(el, existingErrors, fullCheck);
0474: String condType = el.getType();
0475: String condExpr = el.toValue();
0476: if (existingErrors.size() > 0 && !fullCheck) {
0477: return;
0478: }
0479:
0480: boolean validateCondByType = properties.getProperty(
0481: StandardPackageValidator.VALIDATE_CONDITION_BY_TYPE,
0482: "false").equals("true");
0483: if (condType
0484: .equals(XPDLConstants.CONDITION_TYPE_DEFAULTEXCEPTION)) {
0485: if (validateCondByType && condExpr.length() > 0) {
0486: XMLValidationError verr = new XMLValidationError(
0487: XMLValidationError.TYPE_WARNING,
0488: XMLValidationError.SUB_TYPE_LOGIC,
0489: XPDLValidationErrorIds.WARNING_DEFAULT_EXCEPTION_TRANSITION_WITH_EXPRESSION,
0490: condExpr, el);
0491: existingErrors.add(verr);
0492: }
0493: return;
0494:
0495: } else if (condType
0496: .equals(XPDLConstants.CONDITION_TYPE_OTHERWISE)) {
0497: if (validateCondByType && condExpr.length() > 0) {
0498: XMLValidationError verr = new XMLValidationError(
0499: XMLValidationError.TYPE_WARNING,
0500: XMLValidationError.SUB_TYPE_LOGIC,
0501: XPDLValidationErrorIds.WARNING_OTHERWISE_TRANSITION_WITH_EXPRESSION,
0502: condExpr, el);
0503: existingErrors.add(verr);
0504: }
0505: return;
0506: } else if (condType.equals(XPDLConstants.CONDITION_TYPE_NONE)) {
0507: if (validateCondByType && condExpr.length() > 0) {
0508: XMLValidationError verr = new XMLValidationError(
0509: XMLValidationError.TYPE_WARNING,
0510: XMLValidationError.SUB_TYPE_LOGIC,
0511: XPDLValidationErrorIds.WARNING_UNCONDITIONAL_TRANSITION_WITH_EXPRESSION,
0512: condExpr, el);
0513: existingErrors.add(verr);
0514: }
0515: } else if (condType
0516: .equals(XPDLConstants.CONDITION_TYPE_CONDITION)) {
0517: if (validateCondByType && condExpr.length() <= 0) {
0518: XMLValidationError verr = new XMLValidationError(
0519: XMLValidationError.TYPE_WARNING,
0520: XMLValidationError.SUB_TYPE_LOGIC,
0521: XPDLValidationErrorIds.WARNING_CONDITIONAL_TRANSITION_WITHOUT_EXPRESSION,
0522: "", el);
0523: existingErrors.add(verr);
0524: }
0525: } else if (condType
0526: .equals(XPDLConstants.CONDITION_TYPE_EXCEPTION)) {
0527: if (validateCondByType && condExpr.length() <= 0) {
0528: XMLValidationError verr = new XMLValidationError(
0529: XMLValidationError.TYPE_WARNING,
0530: XMLValidationError.SUB_TYPE_LOGIC,
0531: XPDLValidationErrorIds.WARNING_EXCEPTION_TRANSITION_WITHOUT_EXPRESSION,
0532: "", el);
0533: existingErrors.add(verr);
0534: }
0535: return;
0536: }
0537:
0538: if ((existingErrors.size() == 0 || fullCheck)
0539: && condExpr.length() > 0
0540: && properties
0541: .getProperty(
0542: StandardPackageValidator.VALIDATE_CONDITION_EXPRESSIONS,
0543: "false").equals("true")) {
0544: if (condExpr.toLowerCase().indexOf("true") >= 0
0545: || condExpr.toLowerCase().indexOf("false") >= 0
0546: || condExpr.toLowerCase().indexOf("boolean") >= 0
0547: || condExpr.toLowerCase().indexOf("equals") >= 0
0548: || condExpr.toLowerCase().indexOf(">") >= 0
0549: || condExpr.toLowerCase().indexOf(">=") >= 0
0550: || condExpr.toLowerCase().indexOf("<") >= 0
0551: || condExpr.toLowerCase().indexOf("<=") >= 0
0552: || condExpr.toLowerCase().indexOf("==") >= 0) {
0553: return;
0554: }
0555: if (!XMLUtil.canBeExpression(condExpr, XMLUtil
0556: .getWorkflowProcess(el).getAllVariables(), false)) {
0557: XMLValidationError verr = new XMLValidationError(
0558: XMLValidationError.TYPE_WARNING,
0559: XMLValidationError.SUB_TYPE_LOGIC,
0560: XPDLValidationErrorIds.WARNING_CONDITION_EXPRESSION_POSSIBLY_INVALID,
0561: condExpr, el);
0562: existingErrors.add(verr);
0563: }
0564: }
0565: }
0566:
0567: public void validateElement(ConformanceClass el,
0568: List existingErrors, boolean fullCheck) {
0569: validateStandard(el, existingErrors, fullCheck);
0570: }
0571:
0572: public void validateElement(Cost el, List existingErrors,
0573: boolean fullCheck) {
0574: validateStandard(el, existingErrors, fullCheck);
0575: }
0576:
0577: public void validateElement(CostUnit el, List existingErrors,
0578: boolean fullCheck) {
0579: validateStandard(el, existingErrors, fullCheck);
0580: }
0581:
0582: public void validateElement(Countrykey el, List existingErrors,
0583: boolean fullCheck) {
0584: validateStandard(el, existingErrors, fullCheck);
0585: }
0586:
0587: public void validateElement(Created el, List existingErrors,
0588: boolean fullCheck) {
0589: validateStandard(el, existingErrors, fullCheck);
0590: }
0591:
0592: public void validateElement(DataField el, List existingErrors,
0593: boolean fullCheck) {
0594: validateStandard(el, existingErrors, fullCheck);
0595: boolean validateVariableUsage = properties.getProperty(
0596: StandardPackageValidator.VALIDATE_UNUSED_VARIABLES,
0597: "false").equals("true");
0598: if (validateVariableUsage
0599: && (fullCheck || existingErrors.size() == 0)) {
0600: if (getNoOfReferences(
0601: el.getParent().getParent().getClass(),
0602: (XMLComplexElement) el.getParent().getParent(),
0603: DataField.class, el) == 0) {
0604: XMLValidationError verr = new XMLValidationError(
0605: XMLValidationError.TYPE_WARNING,
0606: XMLValidationError.SUB_TYPE_LOGIC,
0607: XPDLValidationErrorIds.WARNING_UNUSED_VARIABLE,
0608: el.getId(), el);
0609: existingErrors.add(verr);
0610: }
0611: }
0612: }
0613:
0614: public void validateElement(DataFields el, List existingErrors,
0615: boolean fullCheck) {
0616: validateStandard(el, existingErrors, fullCheck);
0617: }
0618:
0619: public void validateElement(DataType el, List existingErrors,
0620: boolean fullCheck) {
0621: validateStandard(el, existingErrors, fullCheck);
0622: }
0623:
0624: public void validateElement(DataTypes el, List existingErrors,
0625: boolean fullCheck) {
0626: validateStandard(el, existingErrors, fullCheck);
0627: }
0628:
0629: public void validateElement(Deadline el, List existingErrors,
0630: boolean fullCheck) {
0631: validateStandard(el, existingErrors, fullCheck);
0632: }
0633:
0634: public void validateElement(DeadlineCondition el,
0635: List existingErrors, boolean fullCheck) {
0636: validateStandard(el, existingErrors, fullCheck);
0637: String condExpr = el.toValue();
0638: if ((existingErrors.size() == 0 || fullCheck)
0639: && condExpr.length() > 0
0640: && properties
0641: .getProperty(
0642: StandardPackageValidator.VALIDATE_DEADLINE_EXPRESSIONS,
0643: "false").equals("true")) {
0644: if (condExpr.toLowerCase().indexOf("date") >= 0
0645: || condExpr.toLowerCase().indexOf("calendar") >= 0) {
0646: return;
0647: }
0648: if (!XMLUtil.canBeExpression(condExpr, XMLUtil
0649: .getWorkflowProcess(el).getAllVariables(), false)) {
0650: XMLValidationError verr = new XMLValidationError(
0651: XMLValidationError.TYPE_WARNING,
0652: XMLValidationError.SUB_TYPE_LOGIC,
0653: XPDLValidationErrorIds.WARNING_DEADLINE_EXPRESSION_POSSIBLY_INVALID,
0654: condExpr, el);
0655: existingErrors.add(verr);
0656: }
0657: }
0658:
0659: }
0660:
0661: public void validateElement(Deadlines el, List existingErrors,
0662: boolean fullCheck) {
0663: Iterator dls = el.toElements().iterator();
0664: int syncCount = 0;
0665: while (dls.hasNext()) {
0666: Deadline dl = (Deadline) dls.next();
0667: if (dl.getExecution()
0668: .equals(XPDLConstants.EXECUTION_SYNCHR)) {
0669: syncCount++;
0670: }
0671: }
0672:
0673: if (syncCount > 1) {
0674: XMLValidationError verr = new XMLValidationError(
0675: XMLValidationError.TYPE_ERROR,
0676: XMLValidationError.SUB_TYPE_LOGIC,
0677: XPDLValidationErrorIds.ERROR_MULTIPLE_SYNC_DEADLINES_DEFINED,
0678: "", el);
0679: existingErrors.add(verr);
0680: }
0681:
0682: if (fullCheck || syncCount > 1) {
0683: validateStandard(el, existingErrors, fullCheck);
0684: }
0685: }
0686:
0687: public void validateElement(DeclaredType el, List existingErrors,
0688: boolean fullCheck) {
0689: validateStandard(el, existingErrors, fullCheck);
0690: }
0691:
0692: public void validateElement(Description el, List existingErrors,
0693: boolean fullCheck) {
0694: validateStandard(el, existingErrors, fullCheck);
0695: }
0696:
0697: public void validateElement(Documentation el, List existingErrors,
0698: boolean fullCheck) {
0699: validateStandard(el, existingErrors, fullCheck);
0700: }
0701:
0702: public void validateElement(Duration el, List existingErrors,
0703: boolean fullCheck) {
0704: validateStandard(el, existingErrors, fullCheck);
0705: }
0706:
0707: public void validateElement(EnumerationType el,
0708: List existingErrors, boolean fullCheck) {
0709: validateStandard(el, existingErrors, fullCheck);
0710: }
0711:
0712: public void validateElement(EnumerationValue el,
0713: List existingErrors, boolean fullCheck) {
0714: validateStandard(el, existingErrors, fullCheck);
0715: }
0716:
0717: public void validateElement(ExceptionName el, List existingErrors,
0718: boolean fullCheck) {
0719: Activity act = XMLUtil.getActivity(el);
0720: Set ets = XMLUtil.getExceptionalOutgoingTransitions(act);
0721: boolean isValid = true;
0722: if (ets.size() == 0) {
0723: isValid = false;
0724: } else {
0725: String en = el.toValue();
0726: Iterator it = ets.iterator();
0727: while (it.hasNext()) {
0728: Transition t = (Transition) it.next();
0729: String cond = t.getCondition().toValue();
0730: String ctype = t.getCondition().getType();
0731: if (ctype
0732: .equals(XPDLConstants.CONDITION_TYPE_DEFAULTEXCEPTION)
0733: || cond.equals(en) || cond.length() == 0) {
0734: return;
0735: }
0736: }
0737: isValid = false;
0738: }
0739: if (!isValid) {
0740: XMLValidationError verr = new XMLValidationError(
0741: XMLValidationError.TYPE_ERROR,
0742: XMLValidationError.SUB_TYPE_LOGIC,
0743: XPDLValidationErrorIds.ERROR_DEADLINE_EXCEPTION_NOT_PROPERLY_HANDLED_MISSING_SPECIFIED_EXCEPTION_TRANSITION_OR_DEFAULT_EXCEPTION_TRANSITION,
0744: "", el);
0745: existingErrors.add(verr);
0746: }
0747: }
0748:
0749: public void validateElement(ExtendedAttribute el,
0750: List existingErrors, boolean fullCheck) {
0751: validateStandard(el, existingErrors, fullCheck);
0752: }
0753:
0754: public void validateElement(ExtendedAttributes el,
0755: List existingErrors, boolean fullCheck) {
0756: validateStandard(el, existingErrors, fullCheck);
0757: }
0758:
0759: public void validateElement(ExternalPackage el,
0760: List existingErrors, boolean fullCheck) {
0761: validateStandard(el, existingErrors, fullCheck);
0762: }
0763:
0764: public void validateElement(ExternalPackages el,
0765: List existingErrors, boolean fullCheck) {
0766: validateStandard(el, existingErrors, fullCheck);
0767: }
0768:
0769: public void validateElement(ExternalReference el,
0770: List existingErrors, boolean fullCheck) {
0771: validateStandard(el, existingErrors, fullCheck);
0772: }
0773:
0774: public void validateElement(FinishMode el, List existingErrors,
0775: boolean fullCheck) {
0776: validateStandard(el, existingErrors, fullCheck);
0777: }
0778:
0779: public void validateElement(FormalParameter el,
0780: List existingErrors, boolean fullCheck) {
0781: validateStandard(el, existingErrors, fullCheck);
0782: boolean validateVariableUsage = properties.getProperty(
0783: StandardPackageValidator.VALIDATE_UNUSED_VARIABLES,
0784: "false").equals("true");
0785: if (validateVariableUsage
0786: && el.getParent().getParent() instanceof WorkflowProcess
0787: && (fullCheck || existingErrors.size() == 0)) {
0788: if (getNoOfReferences(WorkflowProcess.class,
0789: (WorkflowProcess) el.getParent().getParent(),
0790: FormalParameter.class, el) == 0) {
0791: XMLValidationError verr = new XMLValidationError(
0792: XMLValidationError.TYPE_WARNING,
0793: XMLValidationError.SUB_TYPE_LOGIC,
0794: XPDLValidationErrorIds.WARNING_UNUSED_VARIABLE,
0795: el.getId(), el);
0796: existingErrors.add(verr);
0797: }
0798: }
0799: }
0800:
0801: // We use reflection here since this class will also be used by Shark engine
0802: protected int getNoOfReferences(Class parentCls,
0803: XMLComplexElement parent, Class elCls, XMLElement el) {
0804: int ret = -1;
0805: try {
0806: Class clsJM = Class.forName("org.enhydra.jawe.JaWEManager");
0807: Method mth = clsJM.getMethod("getInstance", null);
0808: Object jm = mth.invoke(null, null);
0809: mth = clsJM.getMethod("getXPDLUtils", null);
0810: Object xpdlu = mth.invoke(jm, null);
0811: mth = xpdlu.getClass().getMethod("getReferences",
0812: new Class[] { parentCls, elCls });
0813: List l = (List) mth.invoke(xpdlu,
0814: new Object[] { parent, el });
0815: ret = l.size();
0816: } catch (Exception ex) {
0817: }
0818: return ret;
0819: }
0820:
0821: public void validateElement(FormalParameters el,
0822: List existingErrors, boolean fullCheck) {
0823: validateStandard(el, existingErrors, fullCheck);
0824: }
0825:
0826: public void validateElement(Icon el, List existingErrors,
0827: boolean fullCheck) {
0828: validateStandard(el, existingErrors, fullCheck);
0829: }
0830:
0831: public void validateElement(Implementation el, List existingErrors,
0832: boolean fullCheck) {
0833: validateStandard(el, existingErrors, fullCheck);
0834: }
0835:
0836: public void validateElement(ImplementationTypes el,
0837: List existingErrors, boolean fullCheck) {
0838: validateStandard(el, existingErrors, fullCheck);
0839: }
0840:
0841: public void validateElement(InitialValue el, List existingErrors,
0842: boolean fullCheck) {
0843: validateStandard(el, existingErrors, fullCheck);
0844: }
0845:
0846: public void validateElement(Join el, List existingErrors,
0847: boolean fullCheck) {
0848: validateStandard(el, existingErrors, fullCheck);
0849: }
0850:
0851: public void validateElement(Length el, List existingErrors,
0852: boolean fullCheck) {
0853: validateStandard(el, existingErrors, fullCheck);
0854: }
0855:
0856: public void validateElement(Limit el, List existingErrors,
0857: boolean fullCheck) {
0858: validateStandard(el, existingErrors, fullCheck);
0859: }
0860:
0861: public void validateElement(ListType el, List existingErrors,
0862: boolean fullCheck) {
0863: validateStandard(el, existingErrors, fullCheck);
0864: }
0865:
0866: public void validateElement(Manual el, List existingErrors,
0867: boolean fullCheck) {
0868: validateStandard(el, existingErrors, fullCheck);
0869: }
0870:
0871: public void validateElement(Member el, List existingErrors,
0872: boolean fullCheck) {
0873: validateStandard(el, existingErrors, fullCheck);
0874: }
0875:
0876: public void validateElement(Namespace el, List existingErrors,
0877: boolean fullCheck) {
0878: validateStandard(el, existingErrors, fullCheck);
0879: }
0880:
0881: public void validateElement(Namespaces el, List existingErrors,
0882: boolean fullCheck) {
0883: validateStandard(el, existingErrors, fullCheck);
0884: }
0885:
0886: public void validateElement(No el, List existingErrors,
0887: boolean fullCheck) {
0888: validateStandard(el, existingErrors, fullCheck);
0889: }
0890:
0891: public void validateElement(
0892: org.enhydra.shark.xpdl.elements.Package el,
0893: List existingErrors, boolean fullCheck) {
0894: validateAgainstXPDLSchema(el, existingErrors, fullCheck);
0895: if (existingErrors.size() == 0 || fullCheck) {
0896: validateStandard(el, existingErrors, fullCheck);
0897: }
0898: if (existingErrors.size() == 0 || fullCheck) {
0899: checkExternalPackages(el, existingErrors, fullCheck);
0900: }
0901: }
0902:
0903: public void validateElement(PackageHeader el, List existingErrors,
0904: boolean fullCheck) {
0905: validateStandard(el, existingErrors, fullCheck);
0906: }
0907:
0908: public void validateElement(Participant el, List existingErrors,
0909: boolean fullCheck) {
0910: validateStandard(el, existingErrors, fullCheck);
0911: }
0912:
0913: public void validateElement(Participants el, List existingErrors,
0914: boolean fullCheck) {
0915: validateStandard(el, existingErrors, fullCheck);
0916: }
0917:
0918: public void validateElement(ParticipantType el,
0919: List existingErrors, boolean fullCheck) {
0920: validateStandard(el, existingErrors, fullCheck);
0921: }
0922:
0923: public void validateElement(Performer el, List existingErrors,
0924: boolean fullCheck) {
0925: // check performer
0926: String performer = el.toValue();
0927: Activity act = XMLUtil.getActivity(el);
0928: // if this is not an No or Tool activity, check peformer
0929: int actType = act.getActivityType();
0930: boolean toolOrNoAct = true;
0931: if (actType != XPDLConstants.ACTIVITY_TYPE_NO
0932: && actType != XPDLConstants.ACTIVITY_TYPE_TOOL) {
0933: toolOrNoAct = false;
0934: }
0935: if (!toolOrNoAct && performer.length() > 0) {
0936: XMLValidationError verr = new XMLValidationError(
0937: XMLValidationError.TYPE_WARNING,
0938: XMLValidationError.SUB_TYPE_LOGIC,
0939: XPDLValidationErrorIds.WARNING_ACTIVITY_CANNOT_HAVE_PERFORMER,
0940: "", el);
0941: existingErrors.add(verr);
0942: }
0943: if (toolOrNoAct
0944: && properties
0945: .getProperty(
0946: StandardPackageValidator.VALIDATE_PERFORMER_EXPRESSIONS,
0947: "false").equals("true")) {
0948: Participant p = XMLUtil.findParticipant(xmlInterface,
0949: XMLUtil.getWorkflowProcess(act), performer);
0950: if (p == null) {
0951: if (performer.length() > 0
0952: && !XMLUtil.canBeExpression(performer, XMLUtil
0953: .getWorkflowProcess(act)
0954: .getAllVariables(), true)) {
0955: XMLValidationError verr = new XMLValidationError(
0956: XMLValidationError.TYPE_WARNING,
0957: XMLValidationError.SUB_TYPE_LOGIC,
0958: XPDLValidationErrorIds.WARNING_PERFORMER_EXPRESSION_POSSIBLY_INVALID,
0959: performer, el);
0960: existingErrors.add(verr);
0961: }
0962: }
0963: }
0964:
0965: }
0966:
0967: public void validateElement(Priority el, List existingErrors,
0968: boolean fullCheck) {
0969: boolean notInt = false;
0970: try {
0971: if (el.toValue().trim().length() > 0) {
0972: Integer.parseInt(el.toValue());
0973: }
0974: } catch (Exception ex) {
0975: notInt = true;
0976: }
0977: if (notInt) {
0978: XMLValidationError verr = new XMLValidationError(
0979: XMLValidationError.TYPE_ERROR,
0980: XMLValidationError.SUB_TYPE_LOGIC,
0981: XPDLValidationErrorIds.ERROR_PRIORITY_INVALID_VALUE,
0982: el.toValue(), el);
0983: existingErrors.add(verr);
0984: }
0985: }
0986:
0987: public void validateElement(PriorityUnit el, List existingErrors,
0988: boolean fullCheck) {
0989: validateStandard(el, existingErrors, fullCheck);
0990: }
0991:
0992: public void validateElement(ProcessHeader el, List existingErrors,
0993: boolean fullCheck) {
0994: validateStandard(el, existingErrors, fullCheck);
0995: }
0996:
0997: public void validateElement(RecordType el, List existingErrors,
0998: boolean fullCheck) {
0999: validateStandard(el, existingErrors, fullCheck);
1000: }
1001:
1002: public void validateElement(RedefinableHeader el,
1003: List existingErrors, boolean fullCheck) {
1004: validateStandard(el, existingErrors, fullCheck);
1005: }
1006:
1007: public void validateElement(Responsible el, List existingErrors,
1008: boolean fullCheck) {
1009: XMLComplexElement pkgOrWp = XMLUtil.getWorkflowProcess(el);
1010: if (pkgOrWp == null) {
1011: pkgOrWp = XMLUtil.getPackage(el);
1012: }
1013: String rv = el.toValue();
1014: Participant p;
1015: if (pkgOrWp instanceof Package) {
1016: p = XMLUtil.findParticipant(xmlInterface,
1017: (Package) pkgOrWp, rv);
1018: } else {
1019: p = XMLUtil.findParticipant(xmlInterface,
1020: (WorkflowProcess) pkgOrWp, rv);
1021: }
1022: if (p == null) {
1023: XMLValidationError verr = new XMLValidationError(
1024: XMLValidationError.TYPE_ERROR,
1025: XMLValidationError.SUB_TYPE_LOGIC,
1026: XPDLValidationErrorIds.ERROR_NON_EXISTING_PARTICIPANT_REFERENCE,
1027: rv, el);
1028: existingErrors.add(verr);
1029: }
1030: }
1031:
1032: public void validateElement(Responsibles el, List existingErrors,
1033: boolean fullCheck) {
1034: validateStandard(el, existingErrors, fullCheck);
1035: }
1036:
1037: public void validateElement(Route el, List existingErrors,
1038: boolean fullCheck) {
1039: validateStandard(el, existingErrors, fullCheck);
1040: }
1041:
1042: public void validateElement(SchemaType el, List existingErrors,
1043: boolean fullCheck) {
1044: validateStandard(el, existingErrors, fullCheck);
1045: }
1046:
1047: public void validateElement(Script el, List existingErrors,
1048: boolean fullCheck) {
1049: validateStandard(el, existingErrors, fullCheck);
1050: }
1051:
1052: public void validateElement(SimulationInformation el,
1053: List existingErrors, boolean fullCheck) {
1054: validateStandard(el, existingErrors, fullCheck);
1055: }
1056:
1057: public void validateElement(Split el, List existingErrors,
1058: boolean fullCheck) {
1059: validateStandard(el, existingErrors, fullCheck);
1060: }
1061:
1062: public void validateElement(StartFinishModes el,
1063: List existingErrors, boolean fullCheck) {
1064: validateStandard(el, existingErrors, fullCheck);
1065: }
1066:
1067: public void validateElement(StartMode el, List existingErrors,
1068: boolean fullCheck) {
1069: validateStandard(el, existingErrors, fullCheck);
1070: }
1071:
1072: public void validateElement(SubFlow el, List existingErrors,
1073: boolean fullCheck) {
1074: validateStandard(el, existingErrors, fullCheck);
1075: if (existingErrors.size() == 0 || fullCheck) {
1076: WorkflowProcess wp = XMLUtil.findWorkflowProcess(
1077: xmlInterface, XMLUtil.getPackage(el), el.getId());
1078: if (wp != null) {
1079: ActualParameters aps = el.getActualParameters();
1080: checkParameterMatching(
1081: wp.getFormalParameters(),
1082: aps,
1083: existingErrors,
1084: properties
1085: .getProperty(
1086: StandardPackageValidator.VALIDATE_ACTUAL_PARAMETER_EXPRESSIONS,
1087: "false").equals("true"),
1088: fullCheck);
1089: }
1090: }
1091: }
1092:
1093: public void validateElement(TimeEstimation el, List existingErrors,
1094: boolean fullCheck) {
1095: validateStandard(el, existingErrors, fullCheck);
1096: }
1097:
1098: public void validateElement(Tool el, List existingErrors,
1099: boolean fullCheck) {
1100: validateStandard(el, existingErrors, fullCheck);
1101: if (existingErrors.size() == 0 || fullCheck) {
1102: String toolId = el.getId();
1103: WorkflowProcess wp = XMLUtil.getWorkflowProcess(el);
1104: Application app = XMLUtil.findApplication(xmlInterface, wp,
1105: toolId);
1106: if (app != null) {
1107: XMLElement ch = app.getApplicationTypes().getChoosen();
1108: if (ch instanceof FormalParameters) {
1109: ActualParameters aps = el.getActualParameters();
1110: checkParameterMatching(
1111: (FormalParameters) ch,
1112: aps,
1113: existingErrors,
1114: properties
1115: .getProperty(
1116: StandardPackageValidator.VALIDATE_ACTUAL_PARAMETER_EXPRESSIONS,
1117: "false").equals("true"),
1118: fullCheck);
1119: }
1120: }
1121: }
1122:
1123: }
1124:
1125: public void validateElement(Tools el, List existingErrors,
1126: boolean fullCheck) {
1127: boolean isValid = existingErrors.size() == 0;
1128: if (el.size() == 0) {
1129: XMLValidationError verr = new XMLValidationError(
1130: XMLValidationError.TYPE_ERROR,
1131: XMLValidationError.SUB_TYPE_LOGIC,
1132: XPDLValidationErrorIds.ERROR_NO_TOOLS_DEFINED, "",
1133: el);
1134: existingErrors.add(verr);
1135: isValid = false;
1136: }
1137:
1138: if (fullCheck || isValid) {
1139: validateStandard(el, existingErrors, fullCheck);
1140: }
1141: }
1142:
1143: public void validateElement(Transition el, List existingErrors,
1144: boolean fullCheck) {
1145: validateStandard(el, existingErrors, fullCheck);
1146: }
1147:
1148: public void validateElement(TransitionRef el, List existingErrors,
1149: boolean fullCheck) {
1150: validateStandard(el, existingErrors, fullCheck);
1151: }
1152:
1153: public void validateElement(TransitionRefs el, List existingErrors,
1154: boolean fullCheck) {
1155: Set outTrans = XMLUtil.getOutgoingTransitions(XMLUtil
1156: .getActivity(el));
1157: Split split = (Split) XMLUtil.getParentElement(Split.class, el);
1158: boolean isValid = true;
1159: if ((el.size() != outTrans.size())
1160: && outTrans.size() > 1
1161: && !split.getType().equals(
1162: XPDLConstants.JOIN_SPLIT_TYPE_AND)) {
1163: isValid = false;
1164: XMLValidationError verr = new XMLValidationError(
1165: XMLValidationError.TYPE_ERROR,
1166: XMLValidationError.SUB_TYPE_LOGIC,
1167: XPDLValidationErrorIds.ERROR_TRANSITION_REFS_AND_OUTGOING_TRANSITION_NUMBER_MISSMATCH,
1168: "", el);
1169: existingErrors.add(verr);
1170: }
1171: if (!(fullCheck || isValid)) {
1172: return;
1173: }
1174: validateStandard(el, existingErrors, fullCheck);
1175: }
1176:
1177: public void validateElement(TransitionRestriction el,
1178: List existingErrors, boolean fullCheck) {
1179: validateStandard(el, existingErrors, fullCheck);
1180: }
1181:
1182: public void validateElement(TransitionRestrictions el,
1183: List existingErrors, boolean fullCheck) {
1184: validateStandard(el, existingErrors, fullCheck);
1185: }
1186:
1187: public void validateElement(Transitions el, List existingErrors,
1188: boolean fullCheck) {
1189: validateStandard(el, existingErrors, fullCheck);
1190: if (fullCheck || existingErrors.size() == 0) {
1191: Map actConns = new HashMap();
1192: Set multipleConnections = new HashSet();
1193: for (int i = 0; i < el.size(); i++) {
1194: Transition t = (Transition) el.get(i);
1195: String actConn = "[" + t.getFrom() + "-" + t.getTo()
1196: + "]";
1197: if (actConns.containsKey(actConn)) {
1198: multipleConnections.add(actConns.get(actConn));
1199: multipleConnections.add(t);
1200:
1201: if (!fullCheck) {
1202: break;
1203: }
1204:
1205: }
1206: actConns.put(actConn, t);
1207: }
1208: if (multipleConnections.size() > 0) {
1209: Iterator it = multipleConnections.iterator();
1210: while (it.hasNext()) {
1211: Transition t = (Transition) it.next();
1212: String actConn = "[" + t.getFrom() + "-"
1213: + t.getTo() + "]";
1214: XMLValidationError verr = new XMLValidationError(
1215: XMLValidationError.TYPE_ERROR,
1216: XMLValidationError.SUB_TYPE_LOGIC,
1217: XPDLValidationErrorIds.ERROR_MULTIPLE_ACTIVITY_CONNECTIONS,
1218: actConn, t);
1219: existingErrors.add(verr);
1220: }
1221: }
1222:
1223: }
1224: }
1225:
1226: public void validateElement(TypeDeclaration el,
1227: List existingErrors, boolean fullCheck) {
1228: validateStandard(el, existingErrors, fullCheck);
1229: }
1230:
1231: public void validateElement(TypeDeclarations el,
1232: List existingErrors, boolean fullCheck) {
1233: validateStandard(el, existingErrors, fullCheck);
1234: }
1235:
1236: public void validateElement(UnionType el, List existingErrors,
1237: boolean fullCheck) {
1238: validateStandard(el, existingErrors, fullCheck);
1239: }
1240:
1241: public void validateElement(ValidFrom el, List existingErrors,
1242: boolean fullCheck) {
1243: validateStandard(el, existingErrors, fullCheck);
1244: }
1245:
1246: public void validateElement(ValidTo el, List existingErrors,
1247: boolean fullCheck) {
1248: validateStandard(el, existingErrors, fullCheck);
1249: }
1250:
1251: public void validateElement(Vendor el, List existingErrors,
1252: boolean fullCheck) {
1253: validateStandard(el, existingErrors, fullCheck);
1254: }
1255:
1256: public void validateElement(Version el, List existingErrors,
1257: boolean fullCheck) {
1258: validateStandard(el, existingErrors, fullCheck);
1259: }
1260:
1261: public void validateElement(WaitingTime el, List existingErrors,
1262: boolean fullCheck) {
1263: validateStandard(el, existingErrors, fullCheck);
1264: }
1265:
1266: public void validateElement(WorkflowProcess el,
1267: List existingErrors, boolean fullCheck) {
1268: boolean isValid = true;
1269: if (el.getActivities().toElements().size() == 0) {
1270: isValid = false;
1271: XMLValidationError verr = new XMLValidationError(
1272: XMLValidationError.TYPE_ERROR,
1273: XMLValidationError.SUB_TYPE_LOGIC,
1274: XPDLValidationErrorIds.ERROR_WORKFLOW_PROCESS_NOT_DEFINED,
1275: "", el);
1276: existingErrors.add(verr);
1277: }
1278: if (fullCheck || isValid) {
1279: validateStandard(el, existingErrors, fullCheck);
1280: }
1281: if (isValid || fullCheck) {
1282: checkGraphConnectionsForWpOrAs(el, existingErrors,
1283: fullCheck);
1284: }
1285: if (isValid || fullCheck) {
1286: checkGraphConformanceForWpOrAs(el, existingErrors,
1287: fullCheck);
1288: }
1289: }
1290:
1291: public void validateElement(WorkflowProcesses el,
1292: List existingErrors, boolean fullCheck) {
1293: validateStandard(el, existingErrors, fullCheck);
1294: }
1295:
1296: public void validateElement(WorkingTime el, List existingErrors,
1297: boolean fullCheck) {
1298: validateStandard(el, existingErrors, fullCheck);
1299: }
1300:
1301: public void validateElement(XPDLVersion el, List existingErrors,
1302: boolean fullCheck) {
1303: if (!el.toValue().equals(CURRENT_XPDL_VERSION)) {
1304: XMLValidationError verr = new XMLValidationError(
1305: XMLValidationError.TYPE_ERROR,
1306: XMLValidationError.SUB_TYPE_LOGIC,
1307: XPDLValidationErrorIds.ERROR_INVALID_XPDL_VERSION,
1308: el.toValue(), el);
1309: existingErrors.add(verr);
1310: }
1311: }
1312:
1313: // ********************* validation against XPDL schema *********************
1314: protected void validateAgainstXPDLSchema(Package pkg,
1315: List existingErrors, boolean fullCheck) {
1316: List schValidationErrors = (List) schemaValidationErrors
1317: .get(pkg);
1318: if (schValidationErrors != null
1319: && properties
1320: .getProperty(
1321: StandardPackageValidator.GET_EXISTING_SCHEMA_VALIDATION_ERRORS,
1322: "false").equals("true")) {
1323: existingErrors.addAll(schValidationErrors);
1324: return;
1325: }
1326: List errorMessages = new ArrayList();
1327: try {
1328: String encoding = properties.getProperty(
1329: StandardPackageValidator.ENCODING, "UTF-8");
1330:
1331: Document document = null;
1332:
1333: DocumentBuilderFactory dbf = DocumentBuilderFactory
1334: .newInstance();
1335: DocumentBuilder dbuilder = dbf.newDocumentBuilder();
1336: document = dbuilder.newDocument();
1337: ByteArrayOutputStream baos = new ByteArrayOutputStream();
1338:
1339: // Here we get all document elements
1340: XPDLRepositoryHandler repH = new XPDLRepositoryHandler();
1341: repH.toXML(document, pkg);
1342:
1343: // Use a Transformer for output
1344: TransformerFactory tFactory = TransformerFactory
1345: .newInstance();
1346: Transformer transformer = tFactory.newTransformer();
1347: transformer.setOutputProperty("indent", "yes");
1348: transformer.setOutputProperty(
1349: "{http://xml.apache.org/xslt}indent-amount", "4");
1350: transformer.setOutputProperty("encoding", encoding);
1351: DOMSource source = new DOMSource(document);
1352: StreamResult result = new StreamResult(baos);
1353: transformer.transform(source, result);
1354:
1355: // Create a Xerces DOM Parser
1356: DOMParser parser = new DOMParser();
1357: // Parse the Document and traverse the DOM
1358: try {
1359: String locale = properties
1360: .getProperty(StandardPackageValidator.LOCALE);
1361: Locale l = new Locale("");
1362: if (locale == null || locale.trim().length() == 0) {
1363: l = Locale.getDefault();
1364: } else if (!locale.equals("default")) {
1365: l = new Locale(locale);
1366: }
1367: parser.setLocale(l);
1368: parser
1369: .setFeature(
1370: "http://apache.org/xml/features/continue-after-fatal-error",
1371: true);
1372: ParsingErrors pErrors = new ParsingErrors();
1373: parser.setErrorHandler(pErrors);
1374: parser.setEntityResolver(new XPDLEntityResolver());
1375: parser.setFeature(
1376: "http://xml.org/sax/features/validation", true);
1377: parser
1378: .setFeature(
1379: "http://apache.org/xml/features/validation/schema",
1380: true);
1381: // parser.setFeature("http://apache.org/xml/features/validation/schema-full-checking",true);
1382: // System.out.println("Parsing from stream");
1383: parser.parse(new InputSource(new StringReader(baos
1384: .toString(encoding))));
1385: errorMessages = pErrors.getErrorMessages();
1386: } catch (Exception ex) {
1387: ex.printStackTrace();
1388: errorMessages.add("Fatal error while parsing document:"
1389: + ex.getMessage());
1390: }
1391: baos.close();
1392: } catch (Exception ex) {
1393: ex.printStackTrace();
1394: errorMessages
1395: .add("Fatal error while validating schema for package "
1396: + pkg.getId() + " :" + ex.getMessage());
1397: }
1398: schValidationErrors = new ArrayList();
1399: if (errorMessages.size() > 0) {
1400: Iterator it2 = errorMessages.iterator();
1401: while (it2.hasNext()) {
1402: String msg = (String) it2.next();
1403: XMLValidationError verr = new XMLValidationError(
1404: XMLValidationError.TYPE_ERROR,
1405: XMLValidationError.SUB_TYPE_SCHEMA, "", msg,
1406: pkg);
1407: schValidationErrors.add(verr);
1408: }
1409: }
1410: existingErrors.addAll(schValidationErrors);
1411: schemaValidationErrors.put(pkg, schValidationErrors);
1412: }
1413:
1414: // ********************* Logic checking
1415: // **************************************
1416:
1417: protected void checkExternalPackages(Package pkg,
1418: List existingErrors, boolean fullCheck) {
1419: if (properties.getProperty(
1420: StandardPackageValidator.CHECK_EXTERNAL_PACKAGES,
1421: "true").equals("false")) {
1422: return;
1423: }
1424: Iterator it = XMLUtil.getAllExternalPackageIds(xmlInterface,
1425: pkg, new HashSet()).iterator();
1426: while (it.hasNext()) {
1427: Package p = xmlInterface.getPackageById((String) it.next());
1428: List epErrors = (List) epsValidationErrors.get(p);
1429: if (epErrors == null) {
1430: epErrors = reCheckExternalPackage(p);
1431: }
1432: existingErrors.addAll(epErrors);
1433: }
1434: }
1435:
1436: public List reCheckExternalPackage(Package p) {
1437: List epErrors = (List) epsValidationErrors.get(p);
1438: if (epErrors != null) {
1439: epErrors.clear();
1440: } else {
1441: epErrors = new ArrayList();
1442: }
1443:
1444: Properties copy = new Properties();
1445: Iterator it = properties.entrySet().iterator();
1446: while (it.hasNext()) {
1447: Map.Entry me = (Map.Entry) it.next();
1448: String key = (String) me.getKey();
1449: String val = (String) me.getValue();
1450: if (key.equals(CHECK_EXTERNAL_PACKAGES)) {
1451: copy.setProperty(CHECK_EXTERNAL_PACKAGES, "false");
1452: } else if (key
1453: .equals(GET_EXISTING_SCHEMA_VALIDATION_ERRORS)) {
1454: copy.setProperty(GET_EXISTING_SCHEMA_VALIDATION_ERRORS,
1455: "false");
1456: } else {
1457: copy.setProperty(key, val);
1458: }
1459: }
1460: StandardPackageValidator pv = createValidatorInstance();
1461: pv.init(copy, xmlInterface);
1462: List l = new ArrayList();
1463: pv.validateElement(p, l, true);
1464: epsValidationErrors.put(p, l);
1465: schemaValidationErrors.remove(p);
1466: return l;
1467: }
1468:
1469: protected boolean checkToolId(XMLAttribute tlId,
1470: List existingErrors, boolean fullCheck) {
1471: XMLValidationError verr = null;
1472:
1473: String toolId = tlId.toValue();
1474: WorkflowProcess wp = XMLUtil.getWorkflowProcess(tlId);
1475: Application app = XMLUtil.findApplication(xmlInterface, wp,
1476: toolId);
1477: if (app == null) {
1478: verr = new XMLValidationError(
1479: XMLValidationError.TYPE_ERROR,
1480: XMLValidationError.SUB_TYPE_LOGIC,
1481: XPDLValidationErrorIds.ERROR_NON_EXISTING_APPLICATION_REFERENCE,
1482: toolId, tlId);
1483: existingErrors.add(verr);
1484: }
1485:
1486: return (verr != null);
1487: }
1488:
1489: protected boolean checkSubFlowId(XMLAttribute sbflwId,
1490: List existingErrors, boolean fullCheck) {
1491: XMLValidationError verr = null;
1492: String subflowId = sbflwId.toValue();
1493: if (subflowId.trim().equals("")) {
1494: verr = new XMLValidationError(
1495: XMLValidationError.TYPE_ERROR,
1496: XMLValidationError.SUB_TYPE_LOGIC,
1497: XPDLValidationErrorIds.ERROR_NON_EXISTING_WORKFLOW_PROCESS_REFERENCE,
1498: subflowId, sbflwId);
1499: }
1500:
1501: Package pkg = XMLUtil.getPackage(sbflwId);
1502: WorkflowProcess wp = null;
1503: if (verr == null) {
1504: wp = XMLUtil.findWorkflowProcess(xmlInterface, pkg,
1505: subflowId);
1506: if (wp == null
1507: && !isRemoteSubflowIdOK(subflowId)
1508: && properties
1509: .getProperty(
1510: StandardPackageValidator.VALIDATE_SUBFLOW_REFERENCES,
1511: "true").equals("true")) {
1512: verr = new XMLValidationError(
1513: XMLValidationError.TYPE_ERROR,
1514: XMLValidationError.SUB_TYPE_LOGIC,
1515: XPDLValidationErrorIds.ERROR_NON_EXISTING_WORKFLOW_PROCESS_REFERENCE,
1516: subflowId, sbflwId);
1517: }
1518: }
1519:
1520: if (verr != null) {
1521: existingErrors.add(verr);
1522: }
1523:
1524: return (verr == null);
1525: }
1526:
1527: protected void checkTransitionRefId(XMLAttribute trfId,
1528: List existingErrors, boolean fullCheck) {
1529: Set outTrans = XMLUtil.getOutgoingTransitions(XMLUtil
1530: .getActivity(trfId));
1531: String transitionId = trfId.toValue();
1532: if (!containsTransitionWithId(outTrans, transitionId)) {
1533: XMLValidationError verr = new XMLValidationError(
1534: XMLValidationError.TYPE_ERROR,
1535: XMLValidationError.SUB_TYPE_LOGIC,
1536: XPDLValidationErrorIds.ERROR_NON_EXISTING_TRANSITION_REFERENCE,
1537: transitionId, trfId);
1538: existingErrors.add(verr);
1539: }
1540: }
1541:
1542: protected boolean containsTransitionWithId(Set trans, String id) {
1543: Iterator it = trans.iterator();
1544: while (it.hasNext()) {
1545: Transition t = (Transition) it.next();
1546: if (t.getId().equals(id)) {
1547: return true;
1548: }
1549: }
1550: return false;
1551: }
1552:
1553: protected boolean isRemoteSubflowIdOK(String subflowId) {
1554: return false;
1555: }
1556:
1557: protected void checkMultipleOtherwiseOrDefaultExceptionTransitions(
1558: Activity act, Set outTrans, List existingErrors,
1559: boolean fullCheck) {
1560: boolean foundOtherwise = false;
1561: boolean foundMultipleOtherwise = false;
1562: boolean foundDefaultException = false;
1563: boolean foundMultipleDefaultException = false;
1564: Iterator ts = outTrans.iterator();
1565: while (ts.hasNext()) {
1566: Transition t = (Transition) ts.next();
1567: String ct = t.getCondition().getType();
1568: if (ct.equals(XPDLConstants.CONDITION_TYPE_OTHERWISE)) {
1569: if (foundOtherwise) {
1570: foundMultipleOtherwise = true;
1571: if (foundMultipleDefaultException || !fullCheck)
1572: break;
1573: } else {
1574: foundOtherwise = true;
1575: }
1576: } else if (ct
1577: .equals(XPDLConstants.CONDITION_TYPE_DEFAULTEXCEPTION)) {
1578: if (foundDefaultException) {
1579: foundMultipleDefaultException = true;
1580: if (foundMultipleOtherwise || !fullCheck)
1581: break;
1582: } else {
1583: foundDefaultException = true;
1584: }
1585: }
1586: }
1587:
1588: if (foundMultipleOtherwise) {
1589: XMLValidationError verr = new XMLValidationError(
1590: XMLValidationError.TYPE_ERROR,
1591: XMLValidationError.SUB_TYPE_LOGIC,
1592: XPDLValidationErrorIds.ERROR_MORE_THAN_ONE_OTHERWISE_TRANSITION,
1593: "", act);
1594: existingErrors.add(verr);
1595: }
1596: if (foundMultipleDefaultException) {
1597: XMLValidationError verr = new XMLValidationError(
1598: XMLValidationError.TYPE_ERROR,
1599: XMLValidationError.SUB_TYPE_LOGIC,
1600: XPDLValidationErrorIds.ERROR_MORE_THAN_ONE_DEFAULT_EXCEPTION_TRANSITION,
1601: "", act);
1602: existingErrors.add(verr);
1603: }
1604: }
1605:
1606: protected void checkTransitionFrom(XMLAttribute from,
1607: List existingErrors) {
1608: if (XMLUtil.getFromActivity(XMLUtil.getTransition(from)) == null) {
1609: XMLValidationError verr = new XMLValidationError(
1610: XMLValidationError.TYPE_ERROR,
1611: XMLValidationError.SUB_TYPE_LOGIC,
1612: XPDLValidationErrorIds.ERROR_NON_EXISTING_ACTIVITY_REFERENCE,
1613: from.toValue(), from);
1614: existingErrors.add(verr);
1615: }
1616: }
1617:
1618: protected void checkTransitionTo(XMLAttribute to,
1619: List existingErrors) {
1620: if (XMLUtil.getToActivity(XMLUtil.getTransition(to)) == null) {
1621: XMLValidationError verr = new XMLValidationError(
1622: XMLValidationError.TYPE_ERROR,
1623: XMLValidationError.SUB_TYPE_LOGIC,
1624: XPDLValidationErrorIds.ERROR_NON_EXISTING_ACTIVITY_REFERENCE,
1625: to.toValue(), to);
1626: existingErrors.add(verr);
1627: }
1628: }
1629:
1630: protected void checkDeclaredTypeId(XMLAttribute dtId,
1631: List existingErrors) {
1632: String tdId = dtId.toValue();
1633: TypeDeclaration td = XMLUtil.getPackage(dtId)
1634: .getTypeDeclaration(tdId);
1635: if (td == null) {
1636: XMLValidationError verr = new XMLValidationError(
1637: XMLValidationError.TYPE_ERROR,
1638: XMLValidationError.SUB_TYPE_LOGIC,
1639: XPDLValidationErrorIds.ERROR_NON_EXISTING_TYPE_DECLARATION_REFERENCE,
1640: tdId, dtId);
1641: existingErrors.add(verr);
1642: }
1643: }
1644:
1645: protected void checkBlockId(XMLAttribute bId, List existingErrors) {
1646: String blockId = bId.toValue();
1647: // check if the activity set exists
1648: ActivitySet as = XMLUtil.getWorkflowProcess(bId)
1649: .getActivitySet(blockId);
1650: if (as == null) {
1651: XMLValidationError verr = new XMLValidationError(
1652: XMLValidationError.TYPE_ERROR,
1653: XMLValidationError.SUB_TYPE_LOGIC,
1654: XPDLValidationErrorIds.ERROR_NON_EXISTING_ACTIVITY_SET_REFERENCE,
1655: blockId, bId);
1656: existingErrors.add(verr);
1657: }
1658: }
1659:
1660: public static boolean isEmpty(String str) {
1661: if (str == null || str.trim().length() == 0) {
1662: return true;
1663: }
1664:
1665: return false;
1666: }
1667:
1668: protected boolean isIdValid(String id) {
1669: return XMLUtil.isIdValid(id);
1670: }
1671:
1672: protected boolean isIdUnique(XMLCollectionElement newEl) {
1673:
1674: XMLElement parent = newEl.getParent();
1675: if (newEl instanceof Tool || newEl instanceof TransitionRef)
1676: return true;
1677: else if (newEl instanceof Activity)
1678: return checkActivityId((Activity) newEl);
1679: else if (newEl instanceof Transition)
1680: return checkTransitionId((Transition) newEl);
1681: else if (parent instanceof XMLCollection) {
1682: return XMLUtil
1683: .cntIds((XMLCollection) parent, newEl.getId()) <= 1;
1684: } else {
1685: return true;
1686: }
1687: }
1688:
1689: protected boolean checkActivityId(Activity newEl) {
1690: int idCnt = 0;
1691: WorkflowProcess proc = XMLUtil.getWorkflowProcess(newEl);
1692: String newId = newEl.getId();
1693: Activities acts = proc.getActivities();
1694: idCnt += XMLUtil.cntIds(acts, newId);
1695: ActivitySets actSets = proc.getActivitySets();
1696: for (int y = 0; y < actSets.size(); y++) {
1697: ActivitySet actSet = (ActivitySet) actSets.get(y);
1698: acts = actSet.getActivities();
1699: idCnt = idCnt + XMLUtil.cntIds(acts, newId);
1700: }
1701: return idCnt <= 1;
1702: }
1703:
1704: protected boolean checkTransitionId(Transition newEl) {
1705: int idCnt = 0;
1706: WorkflowProcess proc = XMLUtil.getWorkflowProcess(newEl);
1707:
1708: String newId = newEl.getId();
1709: Transitions trans = proc.getTransitions();
1710: idCnt += XMLUtil.cntIds(trans, newId);
1711: ActivitySets actSets = proc.getActivitySets();
1712: for (int y = 0; y < actSets.size(); y++) {
1713: ActivitySet actSet = (ActivitySet) actSets.get(y);
1714: trans = actSet.getTransitions();
1715: idCnt += XMLUtil.cntIds(trans, newId);
1716: }
1717: return idCnt <= 1;
1718: }
1719:
1720: /** Used for debug only */
1721: public static void printIM(boolean[][] im, java.util.List acts) {
1722: if (im != null) {
1723: for (int i = 0; i < im.length; i++) {
1724: for (int j = 0; j < im[i].length; j++) {
1725: System.out.print(acts.get(i) + "->" + acts.get(j)
1726: + "=" + im[i][j] + " ");
1727: }
1728: System.out.println();
1729: }
1730: } else {
1731: System.out.println("Passed array is null !!!");
1732: }
1733: }
1734:
1735: /** Used for debug only */
1736: public static void printIM2(boolean[][] im, java.util.List acts) {
1737: System.out.println("Activities are" + acts);
1738: if (im != null) {
1739: for (int i = 0; i < im.length; i++) {
1740: for (int j = 0; j < im[i].length; j++) {
1741: System.out.print(((im[i][j]) ? "1" : "0") + " ");
1742: }
1743: System.out.println();
1744: }
1745: } else {
1746: System.out.println("Passed array is null !!!");
1747: }
1748: }
1749:
1750: // ************************** GRAPH CONFORMANCE CHECKING
1751: // ****************************
1752:
1753: /**
1754: * Checks if graph conforms to the given conformance class.
1755: *
1756: * @return true if graph is conformant, false otherwise
1757: */
1758: protected boolean checkGraphConformanceForWpOrAs(
1759: XMLCollectionElement wpOrAs, List existingErrors,
1760: boolean fullCheck) {
1761:
1762: Package pkg = XMLUtil.getPackage(wpOrAs);
1763: String conformanceClass = pkg.getConformanceClass()
1764: .getGraphConformance();
1765: // ct=0->NON_BLOCKED, ct=1->LOOP_BLOCKED, ct=2->FULL_BLOCKED,
1766: // ct=-1->default NON_BLOCKED
1767: int ct = XMLUtil.getConformanceClassNo(conformanceClass);
1768: Activities acts = (Activities) wpOrAs.get("Activities");
1769: List activities = acts.toElements();
1770:
1771: if (activities.size() == 0) {
1772: return true;
1773: }
1774: boolean isGraphConformant = true;
1775:
1776: Set splitActs = XMLUtil.getSplitOrJoinActivities(activities, 0);
1777: Set joinActs = XMLUtil.getSplitOrJoinActivities(activities, 1);
1778:
1779: Set noSplitActs = new HashSet(activities);
1780: noSplitActs.removeAll(splitActs);
1781:
1782: GraphChecker gc = null;
1783: if (ct > 0 && (isGraphConformant || fullCheck)) {
1784: boolean[][] incidenceMatrix = createIncidenceMatrix(acts);
1785: if (incidenceMatrix == null) {
1786: XMLValidationError verr = new XMLValidationError(
1787: XMLValidationError.TYPE_ERROR,
1788: XMLValidationError.SUB_TYPE_CONFORMANCE,
1789: "Unexpected error while checking graph conformance!",
1790: "", wpOrAs);
1791: existingErrors.add(verr);
1792:
1793: return false;
1794: }
1795:
1796: gc = new GraphChecker(incidenceMatrix);
1797:
1798: // call method to check loop cycling
1799: boolean loopError = false;
1800: if (fullCheck) {
1801: int[] loopNodes = gc.getCyclicNodes();
1802: if (loopNodes != null) {
1803: isGraphConformant = false;
1804: loopError = true;
1805: for (int i = 0; i < loopNodes.length; i++) {
1806: Activity act = (Activity) activities
1807: .get(loopNodes[i]);
1808: XMLValidationError verr = new XMLValidationError(
1809: XMLValidationError.TYPE_ERROR,
1810: XMLValidationError.SUB_TYPE_CONFORMANCE,
1811: XPDLValidationErrorIds.ERROR_LOOP_CONTAINED_ACTIVITY_IN_LOOP_BLOCKED_MODE,
1812: "", act);
1813: existingErrors.add(verr);
1814: }
1815: }
1816: } else {
1817: loopError = gc.isGraphCyclic();
1818: if (loopError) {
1819: isGraphConformant = false;
1820: XMLValidationError verr = new XMLValidationError(
1821: XMLValidationError.TYPE_ERROR,
1822: XMLValidationError.SUB_TYPE_CONFORMANCE,
1823: XPDLValidationErrorIds.ERROR_CYCLIC_GRAPH_IN_LOOP_BLOCKED_MODE,
1824: "", wpOrAs);
1825: existingErrors.add(verr);
1826: }
1827: }
1828: }
1829: // Here we check FULL_BLOCK conformance
1830: if (ct == 2 && (isGraphConformant || fullCheck)) {
1831: // check if there is more then one starting activity
1832: if (XMLUtil.getStartingActivities(wpOrAs).size() != 1) {
1833: isGraphConformant = false;
1834: XMLValidationError verr = new XMLValidationError(
1835: XMLValidationError.TYPE_ERROR,
1836: XMLValidationError.SUB_TYPE_CONFORMANCE,
1837: XPDLValidationErrorIds.ERROR_MULTIPLE_STARTING_ACTIVITIES_IN_FULL_BLOCKED_MODE,
1838: "", wpOrAs);
1839: existingErrors.add(verr);
1840: }
1841: // check if there is more then one ending activity
1842: if ((isGraphConformant || fullCheck)
1843: && XMLUtil.getEndingActivities(wpOrAs).size() != 1) {
1844: isGraphConformant = false;
1845: XMLValidationError verr = new XMLValidationError(
1846: XMLValidationError.TYPE_ERROR,
1847: XMLValidationError.SUB_TYPE_CONFORMANCE,
1848: XPDLValidationErrorIds.ERROR_MULTIPLE_ENDING_ACTIVITIES_IN_FULL_BLOCKED_MODE,
1849: "", wpOrAs);
1850: existingErrors.add(verr);
1851: }
1852:
1853: // check if the number of splits and joins matches
1854: boolean smerr = false;
1855: if ((isGraphConformant || fullCheck)
1856: && splitActs.size() != joinActs.size()) {
1857: if (splitActs.size() > joinActs.size()) {
1858: XMLValidationError verr = new XMLValidationError(
1859: XMLValidationError.TYPE_ERROR,
1860: XMLValidationError.SUB_TYPE_CONFORMANCE,
1861: XPDLValidationErrorIds.ERROR_SPLIT_JOIN_MISSMATCH_IN_FULL_BLOCKED_MODE_MORE_SPLITS,
1862: "", wpOrAs);
1863: existingErrors.add(verr);
1864: } else {
1865: XMLValidationError verr = new XMLValidationError(
1866: XMLValidationError.TYPE_ERROR,
1867: XMLValidationError.SUB_TYPE_CONFORMANCE,
1868: XPDLValidationErrorIds.ERROR_SPLIT_JOIN_MISSMATCH_IN_FULL_BLOCKED_MODE_MORE_JOINS,
1869: "", wpOrAs);
1870: existingErrors.add(verr);
1871: }
1872: isGraphConformant = false;
1873: smerr = true;
1874: }
1875:
1876: // check for split/join type mismatch
1877: if ((isGraphConformant || fullCheck) && !smerr) {
1878: if (getNoOfANDSplitsOrJoins(splitActs, 0) != getNoOfANDSplitsOrJoins(
1879: joinActs, 1)) {
1880: XMLValidationError verr = new XMLValidationError(
1881: XMLValidationError.TYPE_ERROR,
1882: XMLValidationError.SUB_TYPE_CONFORMANCE,
1883: XPDLValidationErrorIds.ERROR_SPLIT_JOIN_MISSMATCH_IN_FULL_BLOCKED_MODE_DIFFERENT_TYPES,
1884: "", wpOrAs);
1885: existingErrors.add(verr);
1886: isGraphConformant = false;
1887: }
1888: }
1889: // first check for correct outgoing transitions
1890: if (isGraphConformant || fullCheck) {
1891: Iterator it = splitActs.iterator();
1892: // boolean andSplitError = false;
1893: // boolean xorSplitError = false;
1894: while (it.hasNext()) {
1895: Activity act = (Activity) it.next();
1896: if (XMLUtil.isANDTypeSplitOrJoin(act, 0)) {
1897: if (!checkANDSplit(act)) {
1898: isGraphConformant = false;
1899: // andSplitError = true;
1900:
1901: XMLValidationError verr = new XMLValidationError(
1902: XMLValidationError.TYPE_ERROR,
1903: XMLValidationError.SUB_TYPE_CONFORMANCE,
1904: XPDLValidationErrorIds.ERROR_CONDITIONAL_TRANSITION_FOR_AND_SPLIT_IN_FULL_BLOCKED_MODE,
1905: "", act);
1906: existingErrors.add(verr);
1907:
1908: if (!fullCheck) {
1909: break;
1910: }
1911: }
1912: } else {
1913: if (!checkXORSplit(act)) {
1914: isGraphConformant = false;
1915: // xorSplitError = true;
1916:
1917: XMLValidationError verr = new XMLValidationError(
1918: XMLValidationError.TYPE_ERROR,
1919: XMLValidationError.SUB_TYPE_CONFORMANCE,
1920: XPDLValidationErrorIds.ERROR_NO_OTHERWISE_TRANSITION_FOR_XOR_SPLIT_IN_FULL_BLOCKED_MODE,
1921: "", act);
1922: existingErrors.add(verr);
1923:
1924: if (!fullCheck) {
1925: break;
1926: }
1927: }
1928: }
1929: }
1930:
1931: // check activities that has only one outgoing transition, if
1932: // there is condition on it -> report XOR split with conditional
1933: // transition error
1934: it = noSplitActs.iterator();
1935: while (it.hasNext()) {
1936: Activity act = (Activity) it.next();
1937: if (!checkXORSplit(act)) {
1938: isGraphConformant = false;
1939: // xorSplitError = true;
1940:
1941: XMLValidationError verr = new XMLValidationError(
1942: XMLValidationError.TYPE_ERROR,
1943: XMLValidationError.SUB_TYPE_CONFORMANCE,
1944: XPDLValidationErrorIds.ERROR_NO_OTHERWISE_TRANSITION_FOR_XOR_SPLIT_IN_FULL_BLOCKED_MODE,
1945: "", act);
1946: existingErrors.add(verr);
1947:
1948: if (!fullCheck) {
1949: break;
1950: }
1951: }
1952: }
1953: }
1954:
1955: // now perform search on every split activity for corresponding join
1956: // activity
1957: if (isGraphConformant || fullCheck) {
1958: // boolean noCorrespondingJoinError = false;
1959: Iterator it = splitActs.iterator();
1960: while (it.hasNext()) {
1961: Activity act = (Activity) it.next();
1962: int splitIndex = activities.indexOf(act);
1963: if (splitIndex == -1) {
1964: XMLValidationError verr = new XMLValidationError(
1965: XMLValidationError.TYPE_ERROR,
1966: XMLValidationError.SUB_TYPE_CONFORMANCE,
1967: "Unexpected error while searching for split/join matching for graph conformance!",
1968: "", wpOrAs);
1969: existingErrors.add(verr);
1970:
1971: isGraphConformant = false;
1972: if (!fullCheck) {
1973: break;
1974: }
1975:
1976: continue;
1977: }
1978: int ji = gc.getJoinIndex(splitIndex);
1979: // The correspondin join can't be found
1980: if (ji < 0) {
1981: isGraphConformant = false;
1982: // noCorrespondingJoinError = true;
1983:
1984: XMLValidationError verr = new XMLValidationError(
1985: XMLValidationError.TYPE_ERROR,
1986: XMLValidationError.SUB_TYPE_CONFORMANCE,
1987: XPDLValidationErrorIds.ERROR_NO_CORRESPONDING_JOIN_ACTIVITY_IN_FULL_BLOCKED_MODE,
1988: "", act);
1989: existingErrors.add(verr);
1990:
1991: if (!fullCheck) {
1992: break;
1993: }
1994: // if the join is found and their types are different
1995: // the graph is not conformant
1996: } else {
1997: if (XMLUtil.isANDTypeSplitOrJoin(act, 0) != XMLUtil
1998: .isANDTypeSplitOrJoin(
1999: (Activity) activities.get(ji),
2000: 1)) {
2001: isGraphConformant = false;
2002: // noCorrespondingJoinError = true;
2003:
2004: if (XMLUtil.isANDTypeSplitOrJoin(act, ji)) {
2005: XMLValidationError verr = new XMLValidationError(
2006: XMLValidationError.TYPE_ERROR,
2007: XMLValidationError.SUB_TYPE_CONFORMANCE,
2008: XPDLValidationErrorIds.ERROR_NO_CORRESPONDING_JOIN_ACTIVITY_TYPE_IN_FULL_BLOCKED_MODE_AND_XOR,
2009: "", act);
2010: existingErrors.add(verr);
2011:
2012: } else {
2013: XMLValidationError verr = new XMLValidationError(
2014: XMLValidationError.TYPE_ERROR,
2015: XMLValidationError.SUB_TYPE_CONFORMANCE,
2016: XPDLValidationErrorIds.ERROR_NO_CORRESPONDING_JOIN_ACTIVITY_TYPE_IN_FULL_BLOCKED_MODE_XOR_AND,
2017: "", act);
2018: existingErrors.add(verr);
2019: }
2020: if (!fullCheck) {
2021: break;
2022: }
2023: }
2024: }
2025: }
2026: }
2027: }
2028:
2029: return isGraphConformant;
2030: }
2031:
2032: protected boolean[][] createIncidenceMatrix(Activities activities) {
2033: int size = activities.size();
2034: boolean[][] incidenceMatrix = new boolean[size][size];
2035: for (int indAct = 0; indAct < size; indAct++) {
2036: Activity a = (Activity) activities.get(indAct);
2037: Iterator trs = XMLUtil.getOutgoingTransitions(a).iterator();
2038: while (trs.hasNext()) {
2039: Transition t = (Transition) trs.next();
2040: String aOut = t.getTo();
2041: Activity toAct = activities.getActivity(aOut);
2042: if (toAct == null)
2043: return null;
2044: int indOut = activities.indexOf(toAct);
2045: incidenceMatrix[indAct][indOut] = true;
2046: }
2047: }
2048: return incidenceMatrix;
2049: }
2050:
2051: /**
2052: * Returns the number of activities in the given set that have split or join, depending
2053: * on second parameter.
2054: *
2055: * @param acts The set of activities that are searched for split or join
2056: * @param sOrJ 0 -> searching for split, otherwise, searching for join
2057: */
2058: protected int getNoOfANDSplitsOrJoins(Set acts, int sOrJ) {
2059: int no = 0;
2060: Iterator it = acts.iterator();
2061: while (it.hasNext()) {
2062: Activity act = (Activity) it.next();
2063: if (sOrJ == 0 && XMLUtil.isANDTypeSplitOrJoin(act, 0)) {
2064: no++;
2065: } else if (sOrJ == 1
2066: && XMLUtil.isANDTypeSplitOrJoin(act, 0)) {
2067: no++;
2068: }
2069: }
2070: return no;
2071: }
2072:
2073: protected boolean checkANDSplit(Activity act) {
2074: return !hasAnyPostcondition(act);
2075: }
2076:
2077: protected boolean checkXORSplit(Activity act) {
2078: // if activity has any postcondition, it must have an otherwise transition
2079: if (hasAnyPostcondition(act)) {
2080: Set ots = XMLUtil.getOutgoingTransitions(act);
2081: Iterator trs = ots.iterator();
2082: while (trs.hasNext()) {
2083: Transition t = (Transition) trs.next();
2084: if (t.getCondition().getType().equals(
2085: XPDLConstants.CONDITION_TYPE_OTHERWISE)) {
2086: return true;
2087: }
2088: }
2089: return false;
2090: }
2091:
2092: return true;
2093: }
2094:
2095: protected boolean hasAnyPostcondition(Activity act) {
2096: Set outL = XMLUtil.getOutgoingTransitions(act);
2097: Iterator it = outL.iterator();
2098: while (it.hasNext()) {
2099: if (!((Transition) it.next()).getCondition().toValue()
2100: .equals("")) {
2101: return true;
2102: }
2103: }
2104: return false;
2105: }
2106:
2107: // ************************** GRAPH CONNECTIONS CHECKING
2108: // ****************************
2109:
2110: protected boolean checkGraphConnectionsForWpOrAs(
2111: XMLCollectionElement wpOrAs, List existingErrors,
2112: boolean fullCheck) {
2113: if (wpOrAs == null)
2114: return false;
2115:
2116: boolean isWellConnected = true;
2117:
2118: Collection acts = ((Activities) wpOrAs.get("Activities"))
2119: .toElements();
2120: if (acts == null || acts.size() == 0) {
2121: return true;
2122: }
2123:
2124: Set startActs = null;
2125: Set endActs = null;
2126: if (fullCheck || isWellConnected) {
2127: startActs = XMLUtil.getStartingActivities(wpOrAs);
2128: boolean allowUndefinedStart = properties.getProperty(
2129: StandardPackageValidator.ALLOW_UNDEFINED_START,
2130: "true").equals("true");
2131: if (startActs.size() == 0
2132: && (!allowUndefinedStart || (wpOrAs instanceof ActivitySet))) {
2133: isWellConnected = false;
2134: XMLValidationError verr = new XMLValidationError(
2135: XMLValidationError.TYPE_ERROR,
2136: XMLValidationError.SUB_TYPE_LOGIC,
2137: XPDLValidationErrorIds.ERROR_NO_STARTING_ACTIVITY,
2138: "", wpOrAs);
2139: existingErrors.add(verr);
2140: }
2141: }
2142: if (fullCheck || isWellConnected) {
2143: endActs = XMLUtil.getEndingActivities(wpOrAs);
2144: boolean allowUndefinedEnd = properties.getProperty(
2145: StandardPackageValidator.ALLOW_UNDEFINED_END,
2146: "true").equals("true");
2147: if (endActs.size() == 0
2148: && (!allowUndefinedEnd || (wpOrAs instanceof ActivitySet))) {
2149: isWellConnected = false;
2150: XMLValidationError verr = new XMLValidationError(
2151: XMLValidationError.TYPE_ERROR,
2152: XMLValidationError.SUB_TYPE_LOGIC,
2153: XPDLValidationErrorIds.ERROR_NO_ENDING_ACTIVITY,
2154: "", wpOrAs);
2155: existingErrors.add(verr);
2156: }
2157: }
2158: if (fullCheck || isWellConnected) {
2159: Iterator it = acts.iterator();
2160: while (it.hasNext()) {
2161: Activity act = (Activity) it.next();
2162: boolean wc = checkActivityConnection(act,
2163: existingErrors, fullCheck);
2164: if (!wc) {
2165: isWellConnected = false;
2166: if (!fullCheck) {
2167: break;
2168: }
2169: }
2170: }
2171: }
2172:
2173: return isWellConnected;
2174: }
2175:
2176: /**
2177: * Checks if given activity is well connected.
2178: *
2179: * @return String describing the error, or empty string if there is no connection error
2180: * for giving activity.
2181: */
2182: protected boolean checkActivityConnection(Activity act,
2183: List existingErrors, boolean fullCheck) {
2184: return true;
2185: }
2186:
2187: protected static void checkParameterMatching(FormalParameters fps,
2188: ActualParameters aps, List existingErrors,
2189: boolean checkExpression, boolean fullCheck) {
2190:
2191: if (fps.size() != aps.size()) {
2192: XMLValidationError verr = new XMLValidationError(
2193: XMLValidationError.TYPE_ERROR,
2194: XMLValidationError.SUB_TYPE_LOGIC,
2195: XPDLValidationErrorIds.ERROR_FORMAL_AND_ACTUAL_PARAMETERS_NUMBER_MISSMATCH,
2196: "", aps);
2197: existingErrors.add(verr);
2198: }
2199:
2200: if (!(fullCheck || existingErrors.size() == 0)) {
2201: return;
2202: }
2203:
2204: for (int i = 0; i < fps.size(); i++) {
2205: FormalParameter fp = (FormalParameter) fps.get(i);
2206: if (aps.size() - 1 < i) {
2207: return;
2208: }
2209: ActualParameter ap = (ActualParameter) aps.get(i);
2210:
2211: String fpMode = fp.getMode();
2212: if (fpMode.equals(XPDLConstants.FORMAL_PARAMETER_MODE_IN)
2213: && !checkExpression) {
2214: continue;
2215: }
2216:
2217: // find the type of formal param.
2218: DataType fpdt = fp.getDataType();
2219: DataTypes fpdtt = fpdt.getDataTypes();
2220: XMLElement fpType = fpdtt.getChoosen();
2221:
2222: // find the type of actual param.
2223: Map idToDFOrFP = XMLUtil.getWorkflowProcess(aps)
2224: .getAllVariables();
2225: String apWRD = ap.toValue();
2226: XMLCollectionElement ce = (XMLCollectionElement) idToDFOrFP
2227: .get(apWRD);
2228:
2229: // if the actual parameter is an expression, and the mode is not
2230: // IN, return 2, which signals that parameter types don't match
2231: if (ce == null) {
2232: if (!fpMode
2233: .equals(XPDLConstants.FORMAL_PARAMETER_MODE_IN)) {
2234: XMLValidationError verr = new XMLValidationError(
2235: XMLValidationError.TYPE_ERROR,
2236: XMLValidationError.SUB_TYPE_LOGIC,
2237: XPDLValidationErrorIds.ERROR_NON_EXISTING_VARIABLE_REFERENCE,
2238: apWRD, ap);
2239: existingErrors.add(verr);
2240: continue;
2241: }
2242:
2243: boolean evaluateToString = false;
2244: if (fpType instanceof BasicType) {
2245: String fpAT = ((BasicType) fpType).getType();
2246: if (fpAT.equals(XPDLConstants.BASIC_TYPE_STRING)) {
2247: evaluateToString = true;
2248: }
2249: }
2250: // if the formal parameter mode is IN, do not check validity if not
2251: // neccessary, because
2252: // that could be expression written in any scripting language
2253: if (!XMLUtil.canBeExpression(apWRD, XMLUtil
2254: .getWorkflowProcess(ap).getAllVariables(),
2255: evaluateToString)) {
2256: if (apWRD.equals("null")) {
2257: continue;
2258: }
2259: if (fpType instanceof BasicType) {
2260: String fpAT = ((BasicType) fpType).getType();
2261: if (fpAT
2262: .equals(XPDLConstants.BASIC_TYPE_INTEGER)) {
2263: try {
2264: new Integer(apWRD);
2265: continue;
2266: } catch (Exception ex) {
2267: if (apWRD.toLowerCase()
2268: .indexOf("short") >= 0
2269: || apWRD.toLowerCase().indexOf(
2270: "integer") >= 0
2271: || apWRD.toLowerCase().indexOf(
2272: "long") >= 0) {
2273: continue;
2274: }
2275: }
2276: } else if (fpAT
2277: .equals(XPDLConstants.BASIC_TYPE_FLOAT)) {
2278: try {
2279: new Double(apWRD);
2280: continue;
2281: } catch (Exception ex) {
2282: if (apWRD.toLowerCase()
2283: .indexOf("short") >= 0
2284: || apWRD.toLowerCase().indexOf(
2285: "integer") >= 0
2286: || apWRD.toLowerCase().indexOf(
2287: "long") >= 0
2288: || apWRD.toLowerCase().indexOf(
2289: "float") >= 0
2290: || apWRD.toLowerCase().indexOf(
2291: "double") >= 0) {
2292: continue;
2293: }
2294: }
2295: } else if (fpAT
2296: .equals(XPDLConstants.BASIC_TYPE_BOOLEAN)) {
2297: if (apWRD.equals("false")
2298: || apWRD.equals("true")
2299: || apWRD.toLowerCase().indexOf(
2300: "boolean") >= 0) {
2301: continue;
2302: }
2303: }
2304: }
2305: XMLValidationError verr = new XMLValidationError(
2306: XMLValidationError.TYPE_WARNING,
2307: XMLValidationError.SUB_TYPE_LOGIC,
2308: XPDLValidationErrorIds.WARNING_ACTUAL_PARAMETER_EXPRESSION_POSSIBLY_INVALID,
2309: apWRD, ap);
2310: existingErrors.add(verr);
2311: }
2312:
2313: continue;
2314: }
2315:
2316: // if AP is a reference to a variable, check data types
2317: XMLElement apType = null;
2318: DataType apdt = (DataType) ce.get("DataType");
2319: DataTypes apdtt = apdt.getDataTypes();
2320: apType = apdtt.getChoosen();
2321:
2322: boolean invalidType = false;
2323: if (fpType.getClass().equals(apType.getClass())) {
2324: // if this is BasicType check for subtype matching
2325: if (fpType instanceof BasicType) {
2326: String fpAT = ((BasicType) fpType).getType();
2327: String apAT = ((BasicType) apType).getType();
2328: if (!fpAT.equals(apAT)) {
2329: invalidType = true;
2330: }
2331: }
2332: // if this is EnumerationType check for Enumeration values matching
2333: else if (fpType instanceof EnumerationType) {
2334: // first check the size of enums
2335: if (((EnumerationType) fpType).size() != ((EnumerationType) apType)
2336: .size()) {
2337: invalidType = true;
2338: } else {
2339: // check the enum elements values
2340: for (int j = 0; j < ((EnumerationType) fpType)
2341: .size(); j++) {
2342: EnumerationValue evFP = (EnumerationValue) ((EnumerationType) fpType)
2343: .get(j);
2344: EnumerationValue evAP = (EnumerationValue) ((EnumerationType) apType)
2345: .get(j);
2346: if (!evFP.getName().equals(evAP.getName())) {
2347: invalidType = true;
2348: }
2349: }
2350: }
2351: }
2352: // if this is DeclaredType check if their IDs are the same
2353: else if (fpType instanceof DeclaredType) {
2354: if (!((DeclaredType) fpType).getId().equals(
2355: ((DeclaredType) apType).getId())) {
2356: invalidType = true;
2357: }
2358: }
2359: } else {
2360: invalidType = true;
2361: }
2362: if (invalidType) {
2363: XMLValidationError verr = new XMLValidationError(
2364: XMLValidationError.TYPE_ERROR,
2365: XMLValidationError.SUB_TYPE_LOGIC,
2366: XPDLValidationErrorIds.ERROR_INVALID_ACTUAL_PARAMETER_VARIABLE_TYPE,
2367: "", ap);
2368: existingErrors.add(verr);
2369: }
2370: }
2371: }
2372:
2373: public String prepareMessageString(String msg) {
2374: if (msg != null) {
2375: msg = msg + "; ";
2376: } else {
2377: msg = "";
2378: }
2379: return msg;
2380: }
2381:
2382: public boolean hasErrors(List l) {
2383: for (int i = 0; i < l.size(); i++) {
2384: XMLValidationError verr = (XMLValidationError) l.get(i);
2385: if (verr.getType().equals(XMLValidationError.TYPE_ERROR)) {
2386: return true;
2387: }
2388: }
2389: return false;
2390: }
2391:
2392: protected StandardPackageValidator createValidatorInstance() {
2393: return new StandardPackageValidator();
2394: }
2395:
2396: public static void main(String[] args) {
2397: try {
2398: XMLInterfaceForJDK13 xmlI = new XMLInterfaceForJDK13();
2399: Package pkg = xmlI.parseDocument(args[0], true);
2400: StandardPackageValidator validator = new StandardPackageValidator();
2401: validator.init(new Properties(), xmlI);
2402:
2403: List verrors = new ArrayList();
2404: validator.validateElement(pkg, verrors, false);
2405: if (verrors.size() > 0) {
2406: System.out
2407: .println(args[0] + " is a valid XPDL package");
2408: } else {
2409: System.out.println(args[0]
2410: + " is not a valid XPDL package");
2411: }
2412: } catch (Exception ex) {
2413: ex.printStackTrace();
2414: System.exit(1);
2415: }
2416: }
2417:
2418: }
|