/* * Performs a set of semantic consistency checks on the document. Query * the results by calling getNumErrors() and getError(). * * @return the number of failed checks (errors) encountered. */ unsigned int SBMLInternalValidator::checkConsistency (bool writeDocument) { unsigned int nerrors = 0; unsigned int total_errors = 0; //if (getLevel() == 3) //{ // logError(L3NotSupported); // return 1; //} /* determine which validators to run */ bool id = ((mApplicableValidators & 0x01) == 0x01); bool sbml = ((mApplicableValidators & 0x02) == 0x02); bool sbo = ((mApplicableValidators & 0x04) == 0x04); bool math = ((mApplicableValidators & 0x08) == 0x08); bool units = ((mApplicableValidators & 0x10) == 0x10); bool over = ((mApplicableValidators & 0x20) == 0x20); bool practice = ((mApplicableValidators & 0x40) == 0x40); /* taken the state machine concept out for now if (LibSBMLStateMachine::isActive()) { units = LibSBMLStateMachine::getUnitState(); } */ IdentifierConsistencyValidator id_validator; ConsistencyValidator validator; SBOConsistencyValidator sbo_validator; MathMLConsistencyValidator math_validator; UnitConsistencyValidator unit_validator; OverdeterminedValidator over_validator; ModelingPracticeValidator practice_validator; SBMLDocument *doc; SBMLErrorLog *log = getErrorLog(); if (writeDocument) { char* sbmlString = writeSBMLToString(getDocument()); log->clearLog(); doc = readSBMLFromString(sbmlString); free (sbmlString); } else { doc = getDocument(); } /* calls each specified validator in turn * - stopping when errors are encountered */ if (id) { id_validator.init(); nerrors = id_validator.validate(*doc); if (nerrors > 0) { unsigned int origNum = log->getNumErrors(); log->add( id_validator.getFailures() ); if (origNum > 0 && log->contains(InvalidUnitIdSyntax) == true) { /* do not log dangling ref */ while (log->contains(DanglingUnitSIdRef) == true) { log->remove(DanglingUnitSIdRef); nerrors--; } total_errors += nerrors; if (nerrors > 0) { if (writeDocument) SBMLDocument_free(doc); return total_errors; } } else if (log->contains(DanglingUnitSIdRef) == false) { total_errors += nerrors; if (writeDocument) SBMLDocument_free(doc); return total_errors; } else { bool onlyDangRef = true; for (unsigned int a = 0; a < log->getNumErrors(); a++) { if (log->getError(a)->getErrorId() != DanglingUnitSIdRef) { onlyDangRef = false; break; } } total_errors += nerrors; if (onlyDangRef == false) { if (writeDocument) SBMLDocument_free(doc); return total_errors; } } } } if (sbml) { validator.init(); nerrors = validator.validate(*doc); total_errors += nerrors; if (nerrors > 0) { log->add( validator.getFailures() ); /* only want to bail if errors not warnings */ if (log->getNumFailsWithSeverity(LIBSBML_SEV_ERROR) > 0) { if (writeDocument) SBMLDocument_free(doc); return total_errors; } } } if (sbo) { sbo_validator.init(); nerrors = sbo_validator.validate(*doc); total_errors += nerrors; if (nerrors > 0) { log->add( sbo_validator.getFailures() ); /* only want to bail if errors not warnings */ if (log->getNumFailsWithSeverity(LIBSBML_SEV_ERROR) > 0) { if (writeDocument) SBMLDocument_free(doc); return total_errors; } } } if (math) { math_validator.init(); nerrors = math_validator.validate(*doc); total_errors += nerrors; if (nerrors > 0) { log->add( math_validator.getFailures() ); /* at this point bail if any problems * unit checks may crash if there have been math errors/warnings */ if (writeDocument) SBMLDocument_free(doc); return total_errors; } } if (units) { unit_validator.init(); nerrors = unit_validator.validate(*doc); total_errors += nerrors; if (nerrors > 0) { log->add( unit_validator.getFailures() ); /* only want to bail if errors not warnings */ if (log->getNumFailsWithSeverity(LIBSBML_SEV_ERROR) > 0) { if (writeDocument) SBMLDocument_free(doc); return total_errors; } } } /* do not even try if there have been unit warnings * changed this as would have bailed */ if (over) { over_validator.init(); nerrors = over_validator.validate(*doc); total_errors += nerrors; if (nerrors > 0) { log->add( over_validator.getFailures() ); /* only want to bail if errors not warnings */ if (log->getNumFailsWithSeverity(LIBSBML_SEV_ERROR) > 0) { if (writeDocument) SBMLDocument_free(doc); return total_errors; } } } if (practice) { practice_validator.init(); nerrors = practice_validator.validate(*doc); if (nerrors > 0) { unsigned int errorsAdded = 0; const std::list<SBMLError> practiceErrors = practice_validator.getFailures(); list<SBMLError>::const_iterator end = practiceErrors.end(); list<SBMLError>::const_iterator iter; for (iter = practiceErrors.begin(); iter != end; ++iter) { if (SBMLError(*iter).getErrorId() != 80701) { log->add( SBMLError(*iter) ); errorsAdded++; } else { if (units) { log->add( SBMLError(*iter) ); errorsAdded++; } } } total_errors += errorsAdded; } } if (writeDocument) SBMLDocument_free(doc); return total_errors; }
/** @cond doxygenLibsbmlInternal */ int CompFlatteningConverter::validateFlatDocument(Model * flatmodel, unsigned int pkgVersion, unsigned int level, unsigned int version) { int result; // create a dummyDocument that will mirror what the user options are // we need the dummyDoc to know things about unknown packages // but dont want the original model/error log SBMLDocument dummy = SBMLDocument(*(mDocument)); dummy.setModel(NULL); dummy.getErrorLog()->clearLog(); // Otherwise, transfer only errors 1090107->1090110 SBMLErrorLog* log = mDocument->getErrorLog(); for (unsigned int en=0; en<log->getNumErrors(); en++) { unsigned int errid = mDocument->getError(en)->getErrorId(); if (errid == CompFlatteningNotRecognisedNotReqd || errid == CompFlatteningNotRecognisedReqd || errid == CompFlatteningNotImplementedNotReqd || errid == CompFlatteningNotImplementedReqd) { dummy.getErrorLog()->add(*(mDocument->getError(en))); } } log->clearLog(); result = reconstructDocument(flatmodel, dummy, true ); if (result != LIBSBML_OPERATION_SUCCESS) { //delete flatmodel; restoreNamespaces(); return result; } //Now check to see if the flat model is valid // run regular validation on the flattened document if requested. // override comp flattening if necessary CompSBMLDocumentPlugin * dummyPlugin = static_cast<CompSBMLDocumentPlugin*> (dummy.getPlugin("comp")); if (dummyPlugin != NULL) { dummyPlugin->setOverrideCompFlattening(true); } std::string sbml = writeSBMLToStdString(&dummy); SBMLDocument *tempdoc = readSBMLFromString(sbml.c_str()); unsigned int errors = tempdoc->getErrorLog()->getNumFailsWithSeverity(LIBSBML_SEV_ERROR); // take out the error about a requiredpackage // if the user has specified to not abort for any packages // NOTE: we cannot actually remove it since the flattening code // uses it to check whether references might come from // other packages if (getAbortForNone() == true) { if (tempdoc->getErrorLog()->contains(RequiredPackagePresent)) { errors--; } } if (errors > 0) { // we have serious errors so we are going to bail on the // flattening - log ONLY the errors //Transfer the errors to mDocument and don't reset the model. if (log->contains(CompLineNumbersUnreliable) == false) { log->logPackageError("comp", CompLineNumbersUnreliable, pkgVersion, level, version); } std::string message = "Errors that follow relate to the flattened "; message += "document produced using the CompFlatteningConverter."; log->logPackageError("comp", CompFlatModelNotValid, pkgVersion, level, version); unsigned int nerrors = tempdoc->getErrorLog()->getNumErrors(); for (unsigned int n = 0; n < nerrors; n++) { const SBMLError* error = tempdoc->getError(n); if (error->getSeverity() >= LIBSBML_SEV_ERROR) { log->add( *(error) ); } if (error->getErrorId() >= CompFlatteningNotRecognisedNotReqd && error->getErrorId() <= CompFlatteningNotImplementedReqd) { log->add( *(error) ); } else if (error->getErrorId() == UnrequiredPackagePresent || error->getErrorId() == RequiredPackagePresent) { log->add( *(error) ); } } //delete flatmodel; restoreNamespaces(); delete tempdoc; return LIBSBML_CONV_INVALID_SRC_DOCUMENT; } else { delete tempdoc; } dummy.checkConsistency(); if (dummyPlugin != NULL) { dummyPlugin->setOverrideCompFlattening(false); } errors = dummy.getErrorLog()->getNumFailsWithSeverity(LIBSBML_SEV_ERROR); if (errors > 0) { // we have serious errors so we are going to bail on the // flattening - log ONLY the errors //Transfer the errors to mDocument and don't reset the model. if (log->contains(CompLineNumbersUnreliable) == false) { log->logPackageError("comp", CompLineNumbersUnreliable, pkgVersion, level, version); } std::string message = "Errors that follow relate to the flattened "; message += "document produced using the CompFlatteningConverter."; log->logPackageError("comp", CompFlatModelNotValid, pkgVersion, level, version); unsigned int nerrors = dummy.getErrorLog()->getNumErrors(); for (unsigned int n = 0; n < nerrors; n++) { const SBMLError* error = dummy.getError(n); if (error->getSeverity() >= LIBSBML_SEV_ERROR) { log->add( *(error) ); } if (error->getErrorId() >= CompFlatteningNotRecognisedNotReqd && error->getErrorId() <= CompFlatteningNotImplementedReqd) { log->add( *(error) ); } else if (error->getErrorId() == UnrequiredPackagePresent || error->getErrorId() == RequiredPackagePresent) { log->add( *(error) ); } } //delete flatmodel; restoreNamespaces(); return LIBSBML_CONV_INVALID_SRC_DOCUMENT; } else { // put any warnings into the document that will be have the // flat model unsigned int nerrors = dummy.getErrorLog()->getNumErrors(); for (unsigned int n = 0; n < nerrors; n++) { const SBMLError* error = dummy.getError(n); log->add( *(error) ); } return LIBSBML_OPERATION_SUCCESS; } }