javasparqljenasemantic-webblank-nodes

Traversing anonymous/blank nodes in Jena


I am using Apache Jena's API, where a graph contains some anonymous/blank nodes as well, due to unionOf and intersectionOf. One of such example is:

<owl:Class>
   <owl:unionOf rdf:parseType="Collection">
        <rdf:Description rdf:about="http://www.summyUrl.com/something#Entity1"/>
        <rdf:Description rdf:about="http://www.summyUrl.com/something#Entity2"/>
   </owl:unionOf>
</owl:Class>

which is an anonymous node/resource. When I try to get its URI, it is something like:

"-50a5734d:15d839467d9:-1b8b"

I am neither able to do SPARQL query using such URIs (due to exception on parsing such URIs), nor able to find appropriate Jena method to handle it.

I am looking for a way to explode such nodes and get all the nested resources of it.

For example in below case, it should return <http:/.../Entity1>, <http:/.../Entity2> and <http:/.../Entity3>

<owl:Class>
   <owl:unionOf rdf:parseType="Collection">
        <rdf:Description rdf:about="http://www.summyUrl.com/something#Entity1"/>
        <owl:unionOf rdf:parseType="Collection">
            <rdf:Description rdf:about="http://www.summyUrl.com/something#Entity2"/>
            <rdf:Description rdf:about="http://www.summyUrl.com/something#Entity3"/>
        </owl:unionOf>
   </owl:unionOf>
</owl:Class>
  1. Is there any inbuilt method of Jena to handle it?

  2. If not, how can I do it efficiently?


Solution

  • I tried doing it in this way and it worked nicely:

    /**
     * Explodes <b>Anonymous resource</b> (Collection resource) in recursive way and provides
     * nested resources. Mainly considers <code>owl:unionOf</code>, <code>owl:intersactionOf</code>, <code>rdf:first</code> and <code>rdf:rest</code>
     * while traversing.
     * 
     * @param resource
     * @return LinkedList<Resource>
     */
    private List<Resource> explodeAnonymousResource(Resource resource)
    {
        private static List<Property> collectionProperties = new LinkedList<Property>(Arrays.asList(OWL.unionOf,OWL.intersectionOf,RDF.first,RDF.rest));
    
        List<Resource> resources=new LinkedList<Resource>();
        Boolean needToTraverseNext=false;
    
        if(resource.isAnon())
        {
            for(Property cp:collectionProperties)
            {
                if(resource.hasProperty(cp) && !resource.getPropertyResourceValue(cp).equals(RDF.nil))
                {
                    Resource nextResource=resource.getPropertyResourceValue(cp);
                    resources.addAll(explodeAnonymousResource(nextResource));
    
                    needToTraverseNext=true;
                }
            }
    
            if(!needToTraverseNext)
            {
                resources.add(resource);
            }
        }
        else
        {
            resources.add(resource);
        }
    
        return resources;
    }