Skip to content
This repository has been archived by the owner on Sep 7, 2023. It is now read-only.

Latest commit

 

History

History
273 lines (230 loc) · 8.33 KB

sparql.md

File metadata and controls

273 lines (230 loc) · 8.33 KB

SPARQL

Notes I made while watching Wouter Beek's series on SparQL

Terms

Syntax:

  • ?variable
  • <absolute-uri>
  • end of a tripple pattern.
  • repeat the subject;
  • repeat the subject and predicate,

?s ?p ?o --> subject/predicate/object


Notation Example
Absolute IRI <http://www.w3.org/1999/02/22-rdf-syntax-ns#type>
Relative IRI <type> (requires base)
Prefixed IRI rdf:type (requires prefix)
Type IRI a (only in predicate position)

(Table imported from this video)


Symbol Notation type
. Simple triple
; Predicate list
, Object list

(Table imported from this video)


Example Datatype IRI
false xsd:boolean
11 xsd:integer
1.1 xsd:decimal
1.1e0 xsd:double
"abc" xsd:string

prefix xsd: <http://www.w3.org/2001/XMLSchema#>

(Table imported from here)


  • Okay so one thing you have to understand is that you can't look at sparql like most code where it goes line-by-line. The entire thing gets parsed at once
  • Don't interpet it as an SQL database. Just because a Record has a property called Track, doesn't mean you can query for Tracks.
  • Also it's case sensitive! mo:Record & mo:track work. mo:record & mo:Track breaks. (Usually, a capital means it's a type, and a non-capital means it's a predicate)
  • There are somewhat-standardised prefixes. See the Linked Open Vocabularies vocabs page (for some/all of them?)

Structure

Note: you can test out the triplydb/pokemon examples here

Okay, the value you provide and where you put ?variables changes things

WHERE {
  ?thing rdf:type ?type .
}

Queries everything with rdf:type for example

Basic spo select

# Prologue

SELECT ?s ?p ?o {  # Projection: columns
    ?s ?p ?o. # Pattern: cells/content
}
limit x  # Modifier: affects rows

Filter select on object value

select ?pokemon {
    ?pokemon <https://triplydb.com/academy/pokemon/vocab/colour> "yellow"
}

Bind (assigning variables)

select ?pokemon ?color ? greeting {
    ?pokemon <https://triplydb.com/academy/pokemon/vocab/colour> ?color.
    bind("Hi!" as ?greeting)
}
limit 10

Literal string interpretation

select ?location {
    # "literal"^^<how-to-interpet>
    bind("Point(4.8649 52.33287)"^^<http://www.opengis.net/ont/geosparql#wktLiteral> as ?location)
}

Bind calculation

select ?pokemon ?weightKilograms ?weightPounds {
    ?pokemon <https://triplidb.com/academy/pokemon/vocab/weight> ?weightKilograms.
    bind(?weightKilograms * "2.20462"^^<http://www.w3.org/2001/XMLSchema#float> as ?weightPounds)
}

Query against multiple of the same, only returning when there are multiple but allowing switching around/duplicate

select ?color ?cry ?name ?type1 ?type2 {
  ?pokemon <https://triplydb.com/academy/pokemon/vocab/colour> ?color.
  ?pokemon <https://triplydb.com/academy/pokemon/vocab/cry> ?cry.
  ?pokemon <http://www.w3.org/2000/01/rdf-schema#label> ?name.
  ?pokemon <https://triplydb.com/academy/pokemon/vocab/type> ?type1.
  ?pokemon <https://triplydb.com/academy/pokemon/vocab/type> ?type2.
}

Get an object from an object of an object

select ?color ?cry ?name ?type1Name ?type2Name {
  ?pokemon <https://triplydb.com/academy/pokemon/vocab/colour> ?color.
  ?pokemon <https://triplydb.com/academy/pokemon/vocab/cry> ?cry.
  ?pokemon <http://www.w3.org/2000/01/rdf-schema#label> ?name.
  ?pokemon <https://triplydb.com/academy/pokemon/vocab/type> ?type1.
  ?pokemon <https://triplydb.com/academy/pokemon/vocab/type> ?type2.
  ?type1 <http://www.w3.org/2000/01/rdf-schema#label> ?type1Name.
  ?type2 <http://www.w3.org/2000/01/rdf-schema#label> ?type2Name.   
}

Abbrevations

Use prefixes to shorten the previous query

Most prefixes end with / or #

prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#>
prefix vocab: <https://triplydb.com/academy/pokemon/vocab/>
select ?color ?cry ?name ?type1Name ?type2Name {
  ?pokemon vocab:colour ?color.
  ?pokemon vocab:cry ?cry.
  ?pokemon rdfs:label ?name.
  ?pokemon vocab:type ?type1.
  ?pokemon vocab:type ?type2.
  ?type1 rdfs:label ?type1Name.
  ?type2 rdfs:label ?type2Name.   
}

Use base IRI

base <https://triplydb.com/academy/pokemon/vocab/>
prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#>
select ?color ?cry ?name ?type1Name ?type2Name {
  ?pokemon <colour> ?color.
  ?pokemon <cry> ?cry.
  ?pokemon rdfs:label ?name.
  ?pokemon <type> ?type1.
  ?pokemon <type> ?type2.
  ?type1 rdfs:label ?type1Name.
  ?type2 rdfs:label ?type2Name.   
}

Empty alias

base <https://triplydb.com/academy/pokemon/vocab/>
prefix : <http://www.w3.org/2000/01/rdf-schema#>
select ?color ?cry ?name ?type1Name ?type2Name {
  ?pokemon <colour> ?color.
  ?pokemon <cry> ?cry.
  ?pokemon :label ?name.
  ?pokemon <type> ?type1.
  ?pokemon <type> ?type2.
  ?type1 :label ?type1Name.
  ?type2 :label ?type2Name.   
}

Special IRI: rdf type

<http://www.3.org/1999/02/22-rdf-syntax-ns#type> -> a (This can only be used in the predicate position, not object or subject)

base <https://triplydb.com/academy/pokemon/vocab/>
prefix : <http://www.w3.org/2000/01/rdf-schema#>
select ?color ?cry ?name ?type1Name ?type2Name {
  ?pokemon a ?class.
  ?pokemon <colour> ?color.
  ?pokemon <cry> ?cry.
  ?pokemon :label ?name.
  ?pokemon <type> ?type1.
  ?pokemon <type> ?type2.
  ?type1 :label ?type1Name.
  ?type2 :label ?type2Name.   
}

In literals

prefix geo: <http://www.opengis.net/ont/geosparql#>
select ?location {
    bind("Point(4.8649 52.33287)"^^geo:wktLiteral as ?location)
}

End-of-lines

base <https://triplydb.com/academy/pokemon/vocab/>
prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#>
select ?color ?cry ?name ?type1Name ?type2Name {
  ?pokemon a ?class;
    <colour> ?color;
    <cry> ?cry;
    rdfs:label ?name;
    <type> ?type1, # You could also type <type> ?type1, ?type2 on one line
    ?type2.

  ?type1 rdfs:label ?type1Name, ?type2Name.   
}

Literal abbrevations (see table above)

prefix vocab: <https://triplydb.com/academy/pokemon/vocab/>
prefix xsd: <http://www.w3.org/2001/XMLSchema#>
select ?pokemon {
    # ?pokemon vocab:weight "80"^^xsd:integer.
    ?pokemon vocab:weight 80.
}

Bind + functions + html

PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX xsd: <http://www.w3.org/2001/XMLSchema#>
PREFIX foaf: <http://xmlns.com/foaf/0.1/>
prefix vocab: <https://triplydb.com/academy/pokemon/vocab/>
prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#>

select ?color ?name ?text ?widget {
  ?pokemon
    vocab:colour ?color;
    vocab:cry ?cry;
    rdfs:label ?name;
    foaf:depiction ?image.
  bind(concat("Hi!", " ", ?name) as ?text)

  # bind(concat("202", "0")^^xsd:gYear as ?widget)  # --> Error
  # bind(strdt(concat("202", "0"), xsd:gYear) as ?widget)  # --> No error

  bind(strdt(concat("<h2 style='color:", ?color, "'>", ?name, "</h2><img src='", str(?image), "'><audio controls><source src='", str(?cry), "'></audio>"), rdf:HTML) as ?widget)
}
limit 10

Discover all available predicates

prefix mo: <http://purl.org/ontology/mo/>
SELECT DISTINCT ?p {
  ?record a mo:Record; ?p ?o.
}

(Thanks Felix!)

Also check out Sparklis & its examples! (Thanks Claire!)

Thanks to Wouter Beeks video series as well as my colleagues for not banning me from the rocket chat for my questions