Java tutorial
/* $This file is distributed under the terms of the license in /doc/license.txt$ */ package edu.cornell.mannlib.vitro.webapp.dao.jena; import java.util.ArrayList; import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.Comparator; import java.util.HashMap; import java.util.Iterator; import java.util.List; import java.util.Map; import org.apache.commons.lang.StringUtils; import org.apache.commons.logging.Log; import org.apache.commons.logging.LogFactory; import com.hp.hpl.jena.ontology.AllValuesFromRestriction; import com.hp.hpl.jena.ontology.DatatypeProperty; import com.hp.hpl.jena.ontology.OntModel; import com.hp.hpl.jena.ontology.OntProperty; import com.hp.hpl.jena.ontology.OntResource; import com.hp.hpl.jena.ontology.ProfileException; import com.hp.hpl.jena.ontology.Restriction; import com.hp.hpl.jena.query.Query; import com.hp.hpl.jena.query.QueryExecution; import com.hp.hpl.jena.query.QueryExecutionFactory; import com.hp.hpl.jena.query.QueryFactory; import com.hp.hpl.jena.query.QuerySolution; import com.hp.hpl.jena.query.ResultSet; import com.hp.hpl.jena.rdf.model.Property; import com.hp.hpl.jena.rdf.model.RDFNode; import com.hp.hpl.jena.rdf.model.Resource; import com.hp.hpl.jena.rdf.model.ResourceFactory; import com.hp.hpl.jena.rdf.model.Statement; import com.hp.hpl.jena.rdf.model.StmtIterator; import com.hp.hpl.jena.shared.Lock; import com.hp.hpl.jena.util.iterator.ClosableIterator; import com.hp.hpl.jena.vocabulary.OWL; import com.hp.hpl.jena.vocabulary.RDF; import com.hp.hpl.jena.vocabulary.RDFS; import edu.cornell.mannlib.vitro.webapp.application.ApplicationUtils; import edu.cornell.mannlib.vitro.webapp.beans.BaseResourceBean; import edu.cornell.mannlib.vitro.webapp.beans.DataProperty; import edu.cornell.mannlib.vitro.webapp.beans.DataPropertyStatement; import edu.cornell.mannlib.vitro.webapp.beans.Individual; import edu.cornell.mannlib.vitro.webapp.beans.PropertyInstance; import edu.cornell.mannlib.vitro.webapp.beans.VClass; import edu.cornell.mannlib.vitro.webapp.dao.DataPropertyDao; import edu.cornell.mannlib.vitro.webapp.dao.InsertException; import edu.cornell.mannlib.vitro.webapp.dao.VitroVocabulary; import edu.cornell.mannlib.vitro.webapp.dao.jena.event.EditEvent; import edu.cornell.mannlib.vitro.webapp.modules.tboxreasoner.TBoxReasonerStatus; import edu.cornell.mannlib.vitro.webapp.rdfservice.RDFService; public class DataPropertyDaoJena extends PropertyDaoJena implements DataPropertyDao { protected static final Log log = LogFactory.getLog(DataPropertyDaoJena.class.getName()); private class DataPropertyRanker implements Comparator<DataProperty> { @Override public int compare(DataProperty dp1, DataProperty dp2) { int diff = dp1.getDisplayTier() - dp2.getDisplayTier(); if (diff == 0) return dp1.getPublicName().compareTo(dp2.getPublicName()); else return diff; } } public DataPropertyDaoJena(RDFService rdfService, DatasetWrapperFactory dwf, WebappDaoFactoryJena wadf) { super(rdfService, dwf, wadf); } public void deleteDataProperty(DataProperty dtp) { deleteDataProperty(dtp.getURI()); } public void deleteDataProperty(String URI) { deleteDataProperty(URI, getOntModelSelector().getTBoxModel()); } public boolean annotateDataPropertyAsExternalIdentifier(String dataPropertyURI) { OntModel ontModel = getOntModelSelector().getTBoxModel(); ontModel.enterCriticalSection(Lock.WRITE); try { com.hp.hpl.jena.ontology.OntResource ind = ontModel.getOntResource(dataPropertyURI); if (ind != null) { ontModel.add(ind, DATAPROPERTY_ISEXTERNALID, "TRUE"); return true; } else { return false; } } finally { ontModel.leaveCriticalSection(); } } public void deleteDataProperty(String URI, OntModel ontModel) { // TODO check if used as onProperty of restriction ontModel.enterCriticalSection(Lock.WRITE); try { getOntModel().getBaseModel().notifyEvent(new EditEvent(getWebappDaoFactory().getUserURI(), true)); DatatypeProperty dp = ontModel.getDatatypeProperty(URI); if (dp != null) { Iterator<Resource> restIt = ontModel.listSubjectsWithProperty(OWL.onProperty, dp); while (restIt.hasNext()) { Resource restRes = restIt.next(); if (restRes.canAs(OntResource.class)) { OntResource restOntRes = restRes.as(OntResource.class); smartRemove(restOntRes, ontModel); } } removeRulesMentioningResource(dp, ontModel); dp.remove(); } getOntModel().getBaseModel().notifyEvent(new EditEvent(getWebappDaoFactory().getUserURI(), false)); } finally { ontModel.leaveCriticalSection(); } // remove ABox statements after removing property // so dependentResource deletion test will pass removeABoxStatementsWithPredicate(URI); } @Override public void fillDataPropertiesForIndividual(Individual entity) { if (entity == null) return; List<DataProperty> dataprops = new ArrayList<DataProperty>(); dataprops.addAll(getDataPropertyStatements(entity.getDataPropertyStatements())); entity.setDatatypePropertyList(dataprops); } private List<DataProperty> getDataPropertyStatements(List<DataPropertyStatement> dataPropertyStmts) { if (dataPropertyStmts == null || dataPropertyStmts.isEmpty()) { return new ArrayList<DataProperty>(); } HashMap<String, DataProperty> hash = new HashMap<String, DataProperty>(); for (DataPropertyStatement dataPropertyStmt : dataPropertyStmts) { if (hash.containsKey(dataPropertyStmt.getDatapropURI())) { DataProperty p = hash.get(dataPropertyStmt.getDatapropURI()); p.addDataPropertyStatement(dataPropertyStmt); } else { OntModel ontModel = getOntModelSelector().getTBoxModel(); ontModel.enterCriticalSection(Lock.READ); try { OntProperty op = ontModel.getOntProperty(dataPropertyStmt.getDatapropURI()); if (op != null) { DataProperty p = datapropFromOntProperty(op); hash.put(p.getURI(), p); p.addDataPropertyStatement(dataPropertyStmt); } } finally { ontModel.leaveCriticalSection(); } } } List<DataProperty> dataprops = new ArrayList<DataProperty>(hash.values()); Collections.sort(dataprops, new DataPropertyRanker()); return dataprops; } private DataProperty datapropFromOntProperty(OntProperty op) { if (op == null) { return null; } if (op.getURI() == null) { return null; } else { DataProperty dp = new DataProperty(); dp.setURI(op.getURI()); dp.setNamespace(op.getNameSpace()); dp.setLocalName(op.getLocalName()); dp.setLocalNameWithPrefix(getWebappDaoFactory().makeLocalNameWithPrefix(dp)); dp.setName(op.getLocalName()); dp.setPublicName(getLabelOrId(op)); dp.setPickListName(getWebappDaoFactory().makePickListName(dp)); Resource dRes = op.getDomain(); if (dRes != null) { dp.setDomainClassURI(dRes.isAnon() ? PSEUDO_BNODE_NS + dRes.getId().toString() : dRes.getURI()); } Resource rRes = op.getRange(); if (rRes != null) { dp.setRangeDatatypeURI(rRes.getURI()); } if (op.isFunctionalProperty()) { dp.setFunctional(true); } dp.setExample(getPropertyStringValue(op, EXAMPLE_ANNOT)); dp.setDescription(getPropertyStringValue(op, DESCRIPTION_ANNOT)); dp.setPublicDescription(getPropertyStringValue(op, PUBLIC_DESCRIPTION_ANNOT)); dp.setDisplayTier((getWebappDaoFactory()).getJenaBaseDao().getPropertyNonNegativeIntValue(op, DISPLAY_RANK_ANNOT)); dp.setDisplayLimit( (getWebappDaoFactory()).getJenaBaseDao().getPropertyNonNegativeIntValue(op, DISPLAY_LIMIT)); //There might be multiple HIDDEN_FROM_DISPLAY_BELOW_ROLE_LEVEL_ANNOT properties, only use the highest StmtIterator it = op.listProperties(HIDDEN_FROM_DISPLAY_BELOW_ROLE_LEVEL_ANNOT); BaseResourceBean.RoleLevel hiddenRoleLevel = null; while (it.hasNext()) { Statement stmt = it.nextStatement(); RDFNode obj; if (stmt != null && (obj = stmt.getObject()) != null && obj.isURIResource()) { Resource res = obj.as(Resource.class); if (res != null && res.getURI() != null) { BaseResourceBean.RoleLevel roleFromModel = BaseResourceBean.RoleLevel .getRoleByUri(res.getURI()); if (roleFromModel != null && (hiddenRoleLevel == null || roleFromModel.compareTo(hiddenRoleLevel) > 0)) { hiddenRoleLevel = roleFromModel; } } } } dp.setHiddenFromDisplayBelowRoleLevel(hiddenRoleLevel);//this might get set to null //There might be multiple PROHIBITED_FROM_UPDATE_BELOW_ROLE_LEVEL_ANNOT properties, only use the highest it = op.listProperties(PROHIBITED_FROM_UPDATE_BELOW_ROLE_LEVEL_ANNOT); BaseResourceBean.RoleLevel prohibitedRoleLevel = null; while (it.hasNext()) { Statement stmt = it.nextStatement(); RDFNode obj; if (stmt != null && (obj = stmt.getObject()) != null && obj.isURIResource()) { Resource res = obj.as(Resource.class); if (res != null && res.getURI() != null) { BaseResourceBean.RoleLevel roleFromModel = BaseResourceBean.RoleLevel .getRoleByUri(res.getURI()); if (roleFromModel != null && (prohibitedRoleLevel == null || roleFromModel.compareTo(prohibitedRoleLevel) > 0)) { prohibitedRoleLevel = roleFromModel; } } } } dp.setProhibitedFromUpdateBelowRoleLevel(prohibitedRoleLevel);//this might get set to null //There might be multiple HIDDEN_FROM_PUBLISH_BELOW_ROLE_LEVEL_ANNOT properties, only use the highest it = op.listProperties(HIDDEN_FROM_PUBLISH_BELOW_ROLE_LEVEL_ANNOT); BaseResourceBean.RoleLevel publishRoleLevel = null; while (it.hasNext()) { Statement stmt = it.nextStatement(); RDFNode obj; if (stmt != null && (obj = stmt.getObject()) != null && obj.isURIResource()) { Resource res = obj.as(Resource.class); if (res != null && res.getURI() != null) { BaseResourceBean.RoleLevel roleFromModel = BaseResourceBean.RoleLevel .getRoleByUri(res.getURI()); if (roleFromModel != null && (publishRoleLevel == null || roleFromModel.compareTo(publishRoleLevel) > 0)) { publishRoleLevel = roleFromModel; } } } } dp.setHiddenFromPublishBelowRoleLevel(publishRoleLevel);//this might get set to null dp.setCustomEntryForm(getPropertyStringValue(op, PROPERTY_CUSTOMENTRYFORMANNOT)); dp.setExternalId(getOntModelSelector().getTBoxModel().contains(op, DATAPROPERTY_ISEXTERNALID, "TRUE")); Resource groupRes = (Resource) op.getPropertyValue(PROPERTY_INPROPERTYGROUPANNOT); if (groupRes != null) { dp.setGroupURI(groupRes.getURI()); } return dp; } } public List getAllDataProperties() { List allDataprops = new ArrayList(); OntModel ontModel = getOntModelSelector().getTBoxModel(); try { ontModel.enterCriticalSection(Lock.READ); try { ClosableIterator dataprops = ontModel.listDatatypeProperties(); try { while (dataprops.hasNext()) { com.hp.hpl.jena.ontology.DatatypeProperty jDataprop = (com.hp.hpl.jena.ontology.DatatypeProperty) dataprops .next(); DataProperty dataprop = datapropFromOntProperty(jDataprop); if (dataprop != null && !(NONUSER_NAMESPACES.contains(dataprop.getNamespace()))) allDataprops.add(dataprop); } } finally { dataprops.close(); } } finally { ontModel.leaveCriticalSection(); } } catch (ProfileException pe) { // TODO language profile doesn't support data properties. // With RDFS, we might like to return properties with rdfs:range containing a datatype } return allDataprops; } public List getAllExternalIdDataProperties() { List allDataprops = new ArrayList(); OntModel ontModel = getOntModelSelector().getTBoxModel(); ontModel.enterCriticalSection(Lock.READ); try { ClosableIterator dataprops = ontModel.listDatatypeProperties(); try { while (dataprops.hasNext()) { com.hp.hpl.jena.ontology.DatatypeProperty jDataprop = (com.hp.hpl.jena.ontology.DatatypeProperty) dataprops .next(); DataProperty dataprop = datapropFromOntProperty(jDataprop); if (dataprop != null && ontModel.contains(jDataprop, DATAPROPERTY_ISEXTERNALID, ResourceFactory.createTypedLiteral(true))) allDataprops.add(dataprop); } } finally { dataprops.close(); } } finally { ontModel.leaveCriticalSection(); } if (allDataprops.size() < 0) return null; else return allDataprops; } public List<DataProperty> getDataPropertiesForVClass(String vclassURI) { return getDatapropsForClass(vclassURI); } public List<DataProperty> getDatapropsForClass(String vclassURI) { return filterAndConvertToDataProperties(getAllPropInstByVClass(vclassURI)); } public Collection<DataProperty> getAllPossibleDatapropsForIndividual(String individualURI) { return filterAndConvertToDataProperties(getAllPossiblePropInstForIndividual(individualURI)); } private List<DataProperty> filterAndConvertToDataProperties(List<PropertyInstance> propInsts) { List<DataProperty> dataprops = new ArrayList<DataProperty>(); for (PropertyInstance propInst : propInsts) { OntModel tboxModel = getOntModel(); tboxModel.enterCriticalSection(Lock.READ); boolean add = false; try { add = (propInst.getPropertyURI() != null && tboxModel.contains( tboxModel.getResource(propInst.getPropertyURI()), RDF.type, OWL.DatatypeProperty)); } finally { tboxModel.leaveCriticalSection(); } if (add) { DataProperty dataprop = getDataPropertyByURI(propInst.getPropertyURI()); dataprop.setRangeDatatypeURI(propInst.getRangeClassURI()); dataprops.add(dataprop); } } return dataprops; } protected boolean reasoningAvailable() { TBoxReasonerStatus status = ApplicationUtils.instance().getTBoxReasonerModule().getStatus(); return status.isConsistent() && !status.isInErrorState(); } private String getRequiredDatatypeURI(Individual individual, DataProperty dataprop, List<String> vclassURIs) { OntModel ontModel = getOntModelSelector().getTBoxModel(); String datatypeURI = dataprop.getRangeDatatypeURI(); ontModel.enterCriticalSection(Lock.READ); try { // get universal restrictions applicable to data property Iterator<Resource> restIt = ontModel.listSubjectsWithProperty(OWL.onProperty, ontModel.getResource(dataprop.getURI())); while (restIt.hasNext()) { Resource restRes = restIt.next(); if (restRes.canAs(Restriction.class)) { Restriction rest = restRes.as(Restriction.class); if (rest.isAllValuesFromRestriction()) { AllValuesFromRestriction avfrest = rest.asAllValuesFromRestriction(); if (avfrest.getAllValuesFrom() != null) { // check if the individual has the restriction as one of its types if (!individual.isAnonymous() && ontModel .contains(ontModel.getResource(individual.getURI()), RDF.type, rest)) { datatypeURI = convertRequiredDatatypeURI(avfrest.getAllValuesFrom().getURI()); break; } else { // check if the restriction applies to one of the individual's types List<Resource> equivOrSubResources = new ArrayList<Resource>(); equivOrSubResources .addAll(ontModel.listSubjectsWithProperty(RDFS.subClassOf, rest).toList()); equivOrSubResources.addAll( ontModel.listSubjectsWithProperty(OWL.equivalentClass, rest).toList()); for (Resource equivOrSubRes : equivOrSubResources) { if (!equivOrSubRes.isAnon() && vclassURIs.contains(equivOrSubRes.getURI())) { datatypeURI = convertRequiredDatatypeURI( avfrest.getAllValuesFrom().getURI()); break; } } } } } } } } finally { ontModel.leaveCriticalSection(); } return datatypeURI; } /** * Converts datatypes used in allValuesFromRestrictions to actual * requirements for editing. Initially, this means we filter out * rdfs:Literal because we don't want to populate literals with this * as a datatype. */ private String convertRequiredDatatypeURI(String datatypeURI) { return (RDFS.Literal.getURI().equals(datatypeURI)) ? null : datatypeURI; } public String getRequiredDatatypeURI(Individual individual, DataProperty dataprop) { return getRequiredDatatypeURI(individual, dataprop, getVClassURIs(individual)); } private List<String> getVClassURIs(Individual individual) { List<String> vclassURIs = null; if (reasoningAvailable()) { vclassURIs = new ArrayList<String>(); for (VClass vc : individual.getVClasses(INDIRECT)) { if (vc.getURI() != null) { vclassURIs.add(vc.getURI()); } } } else { vclassURIs = getSupertypeURIs(individual); } return vclassURIs; } private boolean DIRECT = true; private boolean INDIRECT = !DIRECT; /** * This method will iterate through each of an individual's direct types * and get the URIs of all supertypes. */ protected List<String> getSupertypeURIs(Individual ind) { List<String> supertypeURIs = new ArrayList<String>(); if (ind.getVClasses() != null) { for (VClass vc : ind.getVClasses(DIRECT)) { String vcURI = vc.getURI(); if (vcURI != null) { supertypeURIs.add(vcURI); supertypeURIs.addAll(getWebappDaoFactory().getVClassDao().getAllSuperClassURIs(vcURI)); } } } else if (ind.getVClassURI() != null) { supertypeURIs.add(ind.getVClassURI()); supertypeURIs.addAll(getWebappDaoFactory().getVClassDao().getAllSuperClassURIs(ind.getVClassURI())); } return supertypeURIs; } public DataProperty getDataPropertyByURI(String dataPropertyURI) { OntModel tboxModel = getOntModelSelector().getTBoxModel(); tboxModel.enterCriticalSection(Lock.READ); try { return datapropFromOntProperty(tboxModel.getDatatypeProperty(dataPropertyURI)); } finally { tboxModel.leaveCriticalSection(); } } public String insertDataProperty(DataProperty dtp) throws InsertException { return insertDataProperty(dtp, getOntModelSelector().getTBoxModel()); } public String insertDataProperty(DataProperty dtp, OntModel ontModel) throws InsertException { ontModel.enterCriticalSection(Lock.WRITE); try { getOntModel().getBaseModel().notifyEvent(new EditEvent(getWebappDaoFactory().getUserURI(), true)); String errMsgStr = getWebappDaoFactory().checkURIForEditableEntity(dtp.getURI()); if (errMsgStr != null) { throw new InsertException(errMsgStr); } com.hp.hpl.jena.ontology.DatatypeProperty jDataprop = ontModel.createDatatypeProperty(dtp.getURI()); if (dtp.getPublicName() != null && dtp.getPublicName().length() > 0) { jDataprop.setLabel(dtp.getPublicName(), getDefaultLanguage()); } else { jDataprop.removeAll(RDFS.label); } jDataprop.removeAll(RDFS.domain); if ((dtp.getDomainClassURI() != null) && (dtp.getDomainClassURI().length() > 0)) { jDataprop.setDomain(ontModel.getResource(dtp.getDomainClassURI())); } if (dtp.getRangeDatatypeURI() != null && !dtp.getRangeDatatypeURI().equals("")) { Resource rangeResource = ontModel.getResource(dtp.getRangeDatatypeURI()); if (rangeResource != null) jDataprop.setRange(rangeResource); } if (dtp.getFunctional()) { ontModel.add(jDataprop, RDF.type, OWL.FunctionalProperty); } addPropertyStringValue(jDataprop, EXAMPLE, dtp.getExample(), ontModel); addPropertyStringValue(jDataprop, DESCRIPTION_ANNOT, dtp.getDescription(), ontModel); addPropertyStringValue(jDataprop, PUBLIC_DESCRIPTION_ANNOT, dtp.getPublicDescription(), ontModel); addPropertyNonNegativeIntValue(jDataprop, DISPLAY_RANK_ANNOT, dtp.getDisplayTier(), ontModel); addPropertyNonNegativeIntValue(jDataprop, DISPLAY_LIMIT, dtp.getDisplayLimit(), ontModel); //addPropertyStringValue(jDataprop, HIDDEN_ANNOT, dtp.getHidden(), ontModel); jDataprop.removeAll(HIDDEN_FROM_DISPLAY_BELOW_ROLE_LEVEL_ANNOT); if (HIDDEN_FROM_DISPLAY_BELOW_ROLE_LEVEL_ANNOT != null && dtp.getHiddenFromDisplayBelowRoleLevel() != null) { // only need to add if present jDataprop.addProperty(HIDDEN_FROM_DISPLAY_BELOW_ROLE_LEVEL_ANNOT, ResourceFactory.createResource(dtp.getHiddenFromDisplayBelowRoleLevel().getURI())); } jDataprop.removeAll(PROHIBITED_FROM_UPDATE_BELOW_ROLE_LEVEL_ANNOT); if (PROHIBITED_FROM_UPDATE_BELOW_ROLE_LEVEL_ANNOT != null && dtp.getProhibitedFromUpdateBelowRoleLevel() != null) { // only need to add if present jDataprop.addProperty(PROHIBITED_FROM_UPDATE_BELOW_ROLE_LEVEL_ANNOT, ResourceFactory.createResource(dtp.getProhibitedFromUpdateBelowRoleLevel().getURI())); } jDataprop.removeAll(HIDDEN_FROM_PUBLISH_BELOW_ROLE_LEVEL_ANNOT); if (HIDDEN_FROM_PUBLISH_BELOW_ROLE_LEVEL_ANNOT != null && dtp.getHiddenFromPublishBelowRoleLevel() != null) { // only need to add if present jDataprop.addProperty(HIDDEN_FROM_PUBLISH_BELOW_ROLE_LEVEL_ANNOT, ResourceFactory.createResource(dtp.getHiddenFromPublishBelowRoleLevel().getURI())); } /* if (dtp.isSelfEditProhibited()) { // only add the property if it's true addPropertyBooleanValue(jDataprop, PROPERTY_SELFEDITPROHIBITEDANNOT, dtp.isSelfEditProhibited(), ontModel); } if (dtp.isCuratorEditProhibited()) { // only add the property if it's true addPropertyBooleanValue(jDataprop, PROPERTY_CURATOREDITPROHIBITEDANNOT, dtp.isCuratorEditProhibited(), ontModel); } */ try { if (dtp.getGroupURI() != null && dtp.getGroupURI().length() > 0) { String badURIErrorStr = checkURI(dtp.getGroupURI()); if (badURIErrorStr == null) { jDataprop.addProperty(PROPERTY_INPROPERTYGROUPANNOT, ontModel.getResource(dtp.getGroupURI())); } else { log.error(badURIErrorStr); } } } catch (Exception e) { log.error("error linking data property " + dtp.getURI() + " to property group"); } addPropertyStringValue(jDataprop, PROPERTY_CUSTOMENTRYFORMANNOT, dtp.getCustomEntryForm(), ontModel); getOntModel().getBaseModel().notifyEvent(new EditEvent(getWebappDaoFactory().getUserURI(), false)); } finally { ontModel.leaveCriticalSection(); } return dtp.getURI(); } public void updateDataProperty(DataProperty dtp) { updateDataProperty(dtp, getOntModelSelector().getTBoxModel()); } public void updateDataProperty(DataProperty dtp, OntModel ontModel) { ontModel.enterCriticalSection(Lock.WRITE); try { getOntModel().getBaseModel().notifyEvent(new EditEvent(getWebappDaoFactory().getUserURI(), true)); com.hp.hpl.jena.ontology.DatatypeProperty jDataprop = ontModel.getDatatypeProperty(dtp.getURI()); updateRDFSLabel(jDataprop, dtp.getPublicName()); updatePropertyResourceURIValue(jDataprop, RDFS.domain, dtp.getDomainClassURI(), ontModel); updatePropertyResourceURIValue(jDataprop, RDFS.range, dtp.getRangeDatatypeURI(), ontModel); if (dtp.getFunctional()) { if (!ontModel.contains(jDataprop, RDF.type, OWL.FunctionalProperty)) { ontModel.add(jDataprop, RDF.type, OWL.FunctionalProperty); } } else { if (ontModel.contains(jDataprop, RDF.type, OWL.FunctionalProperty)) { ontModel.remove(jDataprop, RDF.type, OWL.FunctionalProperty); } } updatePropertyStringValue(jDataprop, EXAMPLE, dtp.getExample(), ontModel); updatePropertyStringValue(jDataprop, DESCRIPTION_ANNOT, dtp.getDescription(), ontModel); updatePropertyStringValue(jDataprop, PUBLIC_DESCRIPTION_ANNOT, dtp.getPublicDescription(), ontModel); updatePropertyNonNegativeIntValue(jDataprop, DISPLAY_RANK_ANNOT, dtp.getDisplayTier(), ontModel); updatePropertyNonNegativeIntValue(jDataprop, DISPLAY_LIMIT, dtp.getDisplayLimit(), ontModel); if (dtp.getHiddenFromDisplayBelowRoleLevel() != null) { updatePropertyResourceURIValue(jDataprop, HIDDEN_FROM_DISPLAY_BELOW_ROLE_LEVEL_ANNOT, dtp.getHiddenFromDisplayBelowRoleLevel().getURI(), ontModel); } if (dtp.getProhibitedFromUpdateBelowRoleLevel() != null) { updatePropertyResourceURIValue(jDataprop, PROHIBITED_FROM_UPDATE_BELOW_ROLE_LEVEL_ANNOT, dtp.getProhibitedFromUpdateBelowRoleLevel().getURI(), ontModel); } if (dtp.getHiddenFromPublishBelowRoleLevel() != null) { updatePropertyResourceURIValue(jDataprop, HIDDEN_FROM_PUBLISH_BELOW_ROLE_LEVEL_ANNOT, dtp.getHiddenFromPublishBelowRoleLevel().getURI(), ontModel); } if (dtp.getGroupURI() != null) { updatePropertyResourceURIValue(jDataprop, PROPERTY_INPROPERTYGROUPANNOT, dtp.getGroupURI(), ontModel); } updatePropertyStringValue(jDataprop, PROPERTY_CUSTOMENTRYFORMANNOT, dtp.getCustomEntryForm(), ontModel); getOntModel().getBaseModel().notifyEvent(new EditEvent(getWebappDaoFactory().getUserURI(), false)); } finally { ontModel.leaveCriticalSection(); } } public List<DataProperty> getRootDataProperties() { List rootProperties = new ArrayList(); OntModel ontModel = getOntModelSelector().getTBoxModel(); ontModel.enterCriticalSection(Lock.READ); try { ClosableIterator propIt = ontModel.listDatatypeProperties(); try { while (propIt.hasNext()) { com.hp.hpl.jena.ontology.DatatypeProperty op = (com.hp.hpl.jena.ontology.DatatypeProperty) propIt .next(); boolean isRoot = false; Iterator parentIt = op.listSuperProperties(); if (parentIt != null) { List<Property> parentList = new ArrayList<Property>(); Iterator<RDFNode> parentNodeIt = op.listPropertyValues(RDFS.subPropertyOf); while (parentNodeIt.hasNext()) { RDFNode parentNode = parentNodeIt.next(); if (parentNode.canAs(Property.class)) { parentList.add(parentNode.as(Property.class)); } } if (parentList.size() == 0) { isRoot = true; } else { isRoot = true; Iterator<Property> pit = parentList.iterator(); while (pit.hasNext()) { Property pt = pit.next(); if ((!pt.equals(op)) && (!(ontModel.contains(op, OWL.equivalentProperty, pt)) || (ontModel.contains(pt, OWL.equivalentProperty, op)))) { isRoot = false; } } } } else { isRoot = true; } if (isRoot) { if (!NONUSER_NAMESPACES.contains(op.getNameSpace())) { rootProperties.add(datapropFromOntProperty(op)); } } } } finally { propIt.close(); } } finally { ontModel.leaveCriticalSection(); } if (rootProperties.size() == 0) return null; else return rootProperties; } /* * SPARQL-based methods for getting the individual's data properties. * Ideally this implementation should replace the existing way of getting * the data property list, but the consequences of this may be far-reaching, * so we are implementing a new method now and will merge the old approach * into the new one in a future release. */ /* This may be the intent behind JenaBaseDao.NONUSER_NAMESPACES, but that * value does not contain all of these namespaces. */ protected static final List<String> EXCLUDED_NAMESPACES = Arrays.asList( // Don't need to exclude these, because they are not owl:DatatypeProperty //"http://www.w3.org/1999/02/22-rdf-syntax-ns#", //"http://www.w3.org/2000/01/rdf-schema#", "http://www.w3.org/2002/07/owl#", //"http://vitro.mannlib.cornell.edu/ns/vitro/0.7#", "http://vitro.mannlib.cornell.edu/ns/vitro/public#"); /* * This is a hack to throw out properties in the vitro, rdf, rdfs, and owl namespaces. * It will be implemented in a better way in v1.3 (Editing and Display Configuration). */ protected static final String PROPERTY_FILTERS; static { List<String> namespaceFilters = new ArrayList<String>(); for (String namespace : EXCLUDED_NAMESPACES) { namespaceFilters.add("( !regex(str(?property), \"^" + namespace + "\" ))"); } PROPERTY_FILTERS = StringUtils.join(namespaceFilters, " && "); } protected static final String DATA_PROPERTY_QUERY_STRING = PREFIXES + "\n" + "SELECT DISTINCT ?property WHERE { \n" + " ?subject ?property ?object . \n" + //" ?property a owl:DatatypeProperty . \n" + " FILTER ( \n" + " isLiteral(?object) && \n" + " ( !regex(str(?property), \"^" + VitroVocabulary.PUBLIC + "\" )) && \n" + " ( !regex(str(?property), \"^" + VitroVocabulary.OWL + "\" )) && \n" + // NIHVIVO-2790 vitro:moniker has been deprecated, but display existing values for editorial management (deletion is encouraged). // This property will be hidden from public display by default. " ( ?property = <" + VitroVocabulary.MONIKER + "> || !regex(str(?property), \"^" + VitroVocabulary.vitroURI + "\" )) \n" + " ) \n" + "}"; @Override public List<DataProperty> getDataPropertyList(Individual subject) { return getDataPropertyList(subject.getURI()); } @Override public List<DataProperty> getDataPropertyList(String subjectUri) { // Due to a Jena bug, prebinding on ?subject combined with the isLiteral() // filter causes the query to fail. Insert the subjectUri manually instead. // QuerySolutionMap initialBindings = new QuerySolutionMap(); // initialBindings.add("subject", ResourceFactory.createResource(subjectUri)); String queryString = QueryUtils.subUriForQueryVar(DATA_PROPERTY_QUERY_STRING, "subject", subjectUri); log.debug(queryString); Query query = null; try { query = QueryFactory.create(queryString); } catch (Throwable th) { log.error("could not create SPARQL query for query string " + th.getMessage()); log.error(queryString); return null; } log.debug("Data property query string:\n" + query); ResultSet results = getPropertyQueryResults(queryString); List<DataProperty> properties = new ArrayList<DataProperty>(); while (results.hasNext()) { QuerySolution sol = results.next(); Resource resource = sol.getResource("property"); String uri = resource.getURI(); DataProperty property = getDataPropertyByURI(uri); if (property != null) { properties.add(property); } } return properties; } protected static final String LIST_VIEW_CONFIG_FILE_QUERY_STRING = "PREFIX display: <http://vitro.mannlib.cornell.edu/ontologies/display/1.1#>" + "SELECT ?property ?filename WHERE { \n" + " ?property display:listViewConfigFile ?filename . \n" + "}"; protected static Query listViewConfigFileQuery = null; static { try { listViewConfigFileQuery = QueryFactory.create(LIST_VIEW_CONFIG_FILE_QUERY_STRING); } catch (Throwable th) { log.error("could not create SPARQL query for LIST_VIEW_CONFIG_FILE_QUERY_STRING " + th.getMessage()); log.error(LIST_VIEW_CONFIG_FILE_QUERY_STRING); } } Map<DataProperty, String> customListViewConfigFileMap = null; @Override public String getCustomListViewConfigFileName(DataProperty dp) { if (customListViewConfigFileMap == null) { customListViewConfigFileMap = new HashMap<DataProperty, String>(); OntModel displayModel = getOntModelSelector().getDisplayModel(); //Get all property to list view config file mappings in the system QueryExecution qexec = QueryExecutionFactory.create(listViewConfigFileQuery, displayModel); ResultSet results = qexec.execSelect(); //Iterate through mappings looking for the current property and setting up a hashmap for subsequent retrieval while (results.hasNext()) { QuerySolution soln = results.next(); String propertyUri = soln.getResource("property").getURI(); DataProperty prop = getDataPropertyByURI(propertyUri); if (prop == null) { //This is a warning only if this property is the one for which we're searching if (dp.getURI().equals(propertyUri)) { log.warn("Can't find property for uri " + propertyUri); } else { log.debug("Can't find property for uri " + propertyUri); } } else { String filename = soln.getLiteral("filename").getLexicalForm(); customListViewConfigFileMap.put(prop, filename); } } qexec.close(); } return customListViewConfigFileMap.get(dp); } }