1

I'm trying to build a federated query that can have multiple optional fields. If any optional field has no corresponding statements, the result should have empty value on that field. Just the normal optional behaviour :) But if you run the code below with Wikidata Query Service the result set will be empty even though there exist corresponding statements for the other (optional) fields.

If you remove the optional ?Pmemberof field (that has no statements for the subject) everything works fine and the other statements are returned, which is by the way also the result I would expect for the original query.

PREFIX  rdf:  <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX  owl:  <http://www.w3.org/2002/07/owl#>
PREFIX  wdt:  <http://www.wikidata.org/prop/direct/>
PREFIX  xsd:  <http://www.w3.org/2001/XMLSchema#>
PREFIX  rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX  foaf: <http://xmlns.com/foaf/0.1/>
PREFIX  bif:  <bif:>

SELECT DISTINCT  ?wd ?label ?description ?birthname ?placeofbirth ?placeofdeath (GROUP_CONCAT(DISTINCT ?occupation ; separator=', ') AS ?occupations) (GROUP_CONCAT(DISTINCT ?employer ; separator=', ') AS ?employers) (GROUP_CONCAT(DISTINCT ?memberof ; separator=', ') AS ?memberofs)
WHERE
  { SERVICE <http://dbpedia.org/sparql>
      { ?dbp  rdf:type      foaf:Person ;
              rdfs:label    ?l ;
              owl:sameAs    ?wd .
        ?l    bif:contains  "Niki AND Lauda"
        FILTER strstarts(xsd:string(?wd), "http://www.wikidata.org/entity/")
      }
    OPTIONAL
      { ?wd  <http://schema.org/description>  ?description ;
             wdt:P1477             ?Pbirthname ;
             wdt:P19               ?Pplaceofbirth ;
             wdt:P20               ?Pplaceofdeath ;
             wdt:P106              ?Poccupation ;
             wdt:P108              ?Pemployer ;
             wdt:P463              ?Pmemberof # remove this line -> everything works fine
      }
    FILTER ( lang(?description) = "en" )
    SERVICE wikibase:label
      { bd:serviceParam
                  wikibase:language  "[AUTO_LANGUAGE],en" .
        ?Pdescription
                  rdfs:label         ?description .
        ?Pbirthname  rdfs:label      ?birthname .
        ?Pplaceofbirth
                  rdfs:label         ?placeofbirth .
        ?Pplaceofdeath
                  rdfs:label         ?placeofdeath .
        ?Poccupation  rdfs:label     ?occupation .
        ?Pemployer  rdfs:label       ?employer .
        ?Pmemberof  rdfs:label       ?memberof .
        ?wd       rdfs:label         ?label
      }
  }
GROUP BY ?wd ?label ?description ?birthname ?placeofbirth ?placeofdeath
LIMIT   1000

What am I doing wrong? I want to return all other statements even though ?Pmemberof may have no corresponding statements.

logi-kal
  • 7,107
  • 6
  • 31
  • 43
pnine
  • 83
  • 1
  • 8
  • 2
    everything in an OPTIONAL is still the intersection, i.e. either everything is there or nothing will be returned. So if something has no member, then all the other data is also not returned because it's technically a join with some empty set. You have to put each triple pattern into a separate OPTIONAL clause – UninformedUser Jun 24 '19 at 19:57
  • 1
    Oh silly me! Thanks! – pnine Jun 24 '19 at 20:31

0 Answers0