3

I have a need to represent a hierarchy in my URL's like this:

http://www.me.org/
-----------------root1/
-----------------------level1/
------------------------------level2/etc

I want to define PREFIX's and used them in a SPARQL query like this:

PREFIX root1: <http://www.me.org/root1/>

select * where {
    ?s ?p root1:level1/level2/etc .
} limit 100

This will fail in ARQ with the following error:

Encountered " "/" "/ "" at line 10, column 43.
Was expecting one of:
    "values" ...
    "graph" ...
...

Should I be able to represent a hierarchy in my URL's like this or is SPARQL and PREFIX use limited to a single level ?

Interition
  • 381
  • 2
  • 15

3 Answers3

6

4.1.1.1 Prefixed Names

The PREFIX keyword associates a prefix label with an IRI. A prefixed name is a prefix label and a local part, separated by a colon ":". A prefixed name is mapped to an IRI by concatenating the IRI associated with the prefix and the local part. The prefix label or the local part may be empty. Note that SPARQL local names allow leading digits while XML local names do not. SPARQL local names also allow the non-alphanumeric characters allowed in IRIs via backslash character escapes (e.g. ns:id\=123). SPARQL local names have more syntactic restrictions than CURIEs.

Let's check the grammar to see whether \is one of the supposed non-alphanumeric characters:

19.8 Grammar

[169]     PN_LOCAL      ::=   (PN_CHARS_U | ':' | [0-9] | PLX ) ((PN_CHARS | '.' | ':' | PLX)* (PN_CHARS | ':' | PLX) )?
[170]     PLX           ::=   PERCENT | PN_LOCAL_ESC
[171]     PERCENT       ::=   '%' HEX HEX
[172]     HEX           ::=   [0-9] | [A-F] | [a-f]
[173]     PN_LOCAL_ESC  ::=   '\' ( '_' | '~' | '.' | '-' | '!' | '$' | '&' | "'" | '(' | ')' | '*' | '+' | ',' | ';' | '=' | '/' | '?'

| '#' | '@' | '%' )

Sure enough, we should be able to via:

PN_LOCAL &rightarrow; PLX &rightarrow; PN_LOCAL_ESC &rightarrow; '\' '/'

Thus you should be able to write:

?s ?p root1:level1\/level2\/element .
Joshua Taylor
  • 84,998
  • 9
  • 154
  • 353
  • 2
    +1 Was just typing the same thing but you beat me to it! – RobV Aug 28 '14 at 11:40
  • I appreciate the response is to spec. and means you cannot use "/" without prefixing an esc char of "\". The answer then is you cannot naturally represent the hierarchy of a URL namespace in SPARQL. @JoshuaTaylor . – Interition Aug 28 '14 at 12:04
  • 1
    @Interition Well, I guess it depends on whether or not you think it's natural to represent a hierarchy with a/b/c but not with a\/b\/c. It's not immediately clear that using two characters to separate "levels" is unnatural while using one is natural, but if that's your position, then no, there's no natural way to do it. – Joshua Taylor Aug 28 '14 at 12:08
  • @JoshuaTaylor I think the problem is that SPARQL/RDF value proposition is that it is an extension of the WWW and builds on the URI/URL principle which generally is seen as using / as a namespace separator so you would not expect to have to do something special to process a URL. This is too fundamental for us to get an answer here but I thank you for your quick response. – Interition Aug 28 '14 at 12:16
  • 1
    '/' is used for property paths. \/ for local names was added very late when the work on aligning SPARQL and Turtle happened and the SPARQL-WG was running out of time. The outcome wasn't subtle. – AndyS Aug 28 '14 at 12:34
  • 1
    @AndyS At the risk of complicating the specification for local names, property paths only appear in properties, so is it possible that future specifications could allow ex:a/b/c for subjects and objects, but require ex:a\/b\/c for properties? That seems kind of kludgy, too. – Joshua Taylor Aug 28 '14 at 12:55
6

You can use relative URIs in prefix declarations:

BASE <http://example/>
PREFIX root1:  <root1/>
PREFIX level1: <root1/level1/>
PREFIX level2: <root1/level1/level2/>

SELECT * {
  ?s ?p  level2:etc .
}

which avoids some of the overhead of repeating part-strings in URIs.

AndyS
  • 16,345
  • 17
  • 21
  • @RobV BASE and multiple PREFIX are options but our use case will tend to require quite a few which will look like duplication and won't be very elegant. – Interition Aug 28 '14 at 14:36
4

I think the problem is that SPARQL/RDF value proposition is that it is an extension of the WWW and builds on the URI/URL principle which generally is seen as using / as a namespace separator so you would not expect to have to do something special to process a URL

You seem to be conflating URIs with Prefixed Names, prefixed names are a convenience mechanism designed to allow you to write URIs down in more compact forms for human readability. As such they can't represent every possible URI without using escape characters for things that would otherwise be ambiguous in the grammar.

As Joshua Taylor's answer demonstrates the downside of this (in your opinion) is that you can't use relative URIs as-is with prefixed names which is merely a syntax limitation of SPARQL and other RDF serialisations that use similar syntactic constructs.

However we can naturally write down relative URIs without recourse to any special characters if we instead use a BASE directive e.g.

BASE <http://www.me.org/root1/>

SELECT *
WHERE
{
    ?s ?p <level1/level2/etc> .
}
LIMIT 100

Note in this case we have to enclose the relative URI in < > as we are using a URI rather than a prefixed name. Where the URI is relative a SPARQL processor will resolve it against the declared BASE giving you the desired full URI without needing to use any escape characters.

This perhaps gives you something you consider a more natural fit?

RobV
  • 28,022
  • 11
  • 77
  • 119