5

In the following minimal test case:

from rdflib import Graph, Namespace, Literal, RDF

base = "http://test.com/ns"
foobar = Namespace("http://test.com/ns#")
g = Graph(base=base)
g.bind('foobar', foobar)

g.add((foobar.something, RDF.type, Literal('Blah')))
g.add((foobar.something, foobar.contains, Literal('a property')))

g.add((foobar.anotherthing, RDF.type, Literal('Blubb')))
g.add((foobar.anotherthing, foobar.contains, Literal('another property')))

print(g.serialize(format='turtle').decode("utf-8"))

I get

@base <http://test.com/ns> .
@prefix foobar: <http://test.com/ns#> .

<#anotherthing> a "Blubb" ;
    ns1:contains "another property" .

ns1:something a "Blah" ;
    ns1:contains "a property" .

what I'd expecte is more like

@base <http://test.com/ns> .
@prefix foobar: <http://test.com/ns#> .

<#anotherthing> a "Blubb" ;
    foobar:contains "another property" .

<#something> a "Blah" ;
    foobar:contains "a property" .

So either there is something I fundamentally don't understand about RDFLib and how to use namespaces, or there's something funky going on.
Any thoughts, anyone?

Balduin
  • 415
  • 4
  • 11
  • Strange indeed. It would not be a surprise if the result simply ignored the custom name, but this kind of output is not valid. – IS4 Jan 23 '21 at 14:21
  • I've been experimenting a bit, and it turns out that the problem seems to persist **only** if base and prefix point to the same URI. To me, this seems still a weird behaviour, but a workaround would then be to leave out the base alltogether, or not to bind the prefix. (I'll post an answer as soon as I know more, for future people with the same issue) – Balduin Jan 23 '21 at 15:12
  • Seems like a good idea to post the issue to the creators of RDFLib, if there is a bug in the implementation. – IS4 Jan 23 '21 at 15:20
  • 1
    You're totally right, I did open an issue on GitHub :) – Balduin Jan 23 '21 at 15:21

1 Answers1

2

Your base declaration also needs the final has or slash in it.

So try g = Graph(base="http://test.com/ns#") and everything will work fine

OR

Try without any base in this case.

Either will give you valid results. Yes there is something odd going on deep inside RDFlib with the base, but only when it's not ended with # or /.

By the way, your triples are a bit invalid: you can't use rdf:type with a range value of a literal, it has to be an rdf:Class instance.

Nicholas Car
  • 1,164
  • 4
  • 7