Отображение R2RML со значениями из другой таблицы
Я хочу использовать R2RML и Virtuoso для сопоставления некоторых таблиц из источника MySql. У меня есть таблица с "Вещи", и я хочу, чтобы они имели предикаты, которые не являются URI, но поступают из столбца имени из таблицы "Значения", связанной через thingID. Я могу сопоставить таблицу "Значения" через идентификатор "Thing" с thingId "Значений" - но с этим отображением я получаю только URI соответствующей записи "Значения". То, что я хочу иметь, это строка, хранящаяся в столбце "Значение".
Ожидаемая результирующая тройка должна быть, например:
<http://localhost:8890/ex/things/1> rdf:type <http://localhost:8890/ex/types/vmware> ;
ex:hasValue "Name from the table Values" .
Example of Things table:
ID typeId
1 3
Example of the Types table:
ID Name
3 vmware
Пример таблицы значений:
ID thingId Value
1 1 VMware Virtual Platform
Это мое отображение пока:
<#TriplesMapThings> a rr:TriplesMap; rr:logicalTable [ rr:tableSchema "exdb" ; rr:tableOwner "ex" ; rr:tableName "Things" ];
rr:subjectMap [ rr:termType rr:IRI ; rr:template "http://localhost:8890/ex/things/{id}"; rr:class ex:Things; rr:graph <http://localhost:8890/ex_test#> ];
rr:predicateObjectMap [ rr:predicateMap [ rr:constant ex:id ] ; rr:objectMap [ rr:column "id" ]; ] ;
rr:predicateObjectMap [ rr:predicateMap [ rr:constant ex:typeid ] ; rr:objectMap [ rr:column "typeId" ]; ] ;
rr:predicateObjectMap [ rr:predicateMap [ rr:constant rdf:type ] ; rr:objectMap [ rr:parentTriplesMap <#TriplesMapTypes>; rr:joinCondition [rr:child "typeId"; rr:parent "id";]; ];] ;
rr:predicateObjectMap [ rr:predicateMap [ rr:constant ex:hasValue ] ; rr:objectMap [ rr:parentTriplesMap <#TriplesMapValues>; rr:joinCondition [rr:child "id"; rr:parent "thingId";]; ];] .
<#TriplesMapTypes> a rr:TriplesMap; rr:logicalTable [ rr:tableSchema "exdb" ; rr:tableOwner "ex" ; rr:tableName "Types" ];
rr:subjectMap [ rr:termType rr:IRI ; rr:template "http://localhost:8890/ex/types/{nameUri}"; rr:class owl:Class; rr:graph <http://localhost:8890/ex_test#> ];
rr:predicateObjectMap [ rr:predicateMap [ rr:constant ex:id ] ; rr:objectMap [ rr:column "id" ]; ] ;
rr:predicateObjectMap [ rr:predicateMap [ rr:constant ex:name ] ; rr:objectMap [ rr:column "name" ]; ] .
<#TriplesMapValues> a rr:TriplesMap; rr:logicalTable [ rr:tableSchema "exdb" ; rr:tableOwner "ex" ; rr:tableName "Values" ];
rr:subjectMap [ rr:termType rr:IRI ; rr:template "http://localhost:8890/ex/values/{id}"; rr:class ex:Values; rr:graph <http://localhost:8890/ex_test#> ];
rr:predicateObjectMap [ rr:predicateMap [ rr:constant rdf:type ] ; rr:objectMap [ rr:parentTriplesMap <#TriplesMapAttributes>; rr:joinCondition [rr:child "attributeId"; rr:parent "id";]; ];] ;
rr:predicateObjectMap [ rr:predicateMap [ rr:constant ex:hasThing ] ; rr:objectMap [ rr:parentTriplesMap <#TriplesMapThings>; rr:joinCondition [rr:child "thingId"; rr:parent "id";]; ];] ;
rr:predicateObjectMap [ rr:predicateMap [ rr:constant ex:id ] ; rr:objectMap [ rr:column "id" ]; ] ;
rr:predicateObjectMap [ rr:predicateMap [ rr:constant ex:thingid ] ; rr:objectMap [ rr:column "thingId" ]; ] ;
rr:predicateObjectMap [ rr:predicateMap [ rr:constant ex:value ] ; rr:objectMap [ rr:column "value" ]; ] .
1 ответ
Самый простой способ - использовать SQL-запросы:
<#TriplesMapThings> a rr:TriplesMap;
rr:logicalTable [rr:sqlQuery “SELECT Things.ID, Types.Name FROM Things, Types WHERE Things.typeId = Types.ID” ];
rr:subjectMap [ rr:template “http://localhost:8890/ex/things/{ID}”];
rr:predicateObjectMap [
rr:predicate rdf:type;
rr:objectMap [ rr:template “http://localhost:8890/ex/types/{Name}”]
].
<#TriplesMapValues> a rr:TriplesMap;
rr:logicalTable [rr:tableName “Values” ];
rr:subjectMap [ rr:template “http://localhost:8890/ex/things/{thingId}”];
rr:predicateObjectMap [
rr:predicate ex:hasValue;
rr:objectMap [ rr:column “Value”]
].
Тем не менее, похоже, что это не будет работать с Virtuoso. Согласно их документации, rr:sqlQuery
не поддерживается
Если Types.Name
это уникальный ключ, я думаю, вы могли бы сделать следующее:
<#TriplesMapThings> a rr:TriplesMap;
rr:logicalTable [rr:tableName “Things” ];
rr:subjectMap [ rr:template “http://localhost:8890/ex/things/{ID}”];
rr:predicateObjectMap [
rr:predicate rdf:type;
rr:objectMap [
rr:parentTriplesMap <#TriplesMapTypes>;
rr:joinCondition [ rr:child “typeId”; rr:parent “ID”];
]
].
<#TriplesMapTypes> a rr:TriplesMap;
rr:logicalTable [rr:tableName “Types” ];
rr:subjectMap [ rr:template “http://localhost:8890/ex/types/{Name}”].
<#TriplesMapValues> a rr:TriplesMap;
rr:logicalTable [rr:tableName “Values” ];
rr:subjectMap [ rr:template “http://localhost:8890/ex/things/{thingId}”];
rr:predicateObjectMap [
rr:predicate ex:hasValue;
rr:objectMap [ rr:column “Value”]
].
Обратите внимание, что вы определяете URI субъекта для таблицы Types
с использованием Name
приписывать. Так что, даже если вы объединяетесь между Things.typeId
а также Types.ID
процессор R2RML должен использовать определение субъекта <#TriplesMapTypes>
TriplesMap
,
Если Types.Name
не является уникальным ключом, то вы должны сделать это с помощью запросов SQL.
Обратите внимание, что R2RML был разработан для использования запросов SQL в случае, если вам нужны сложные отображения (например, тот, который вы пытаетесь сделать).