Skip to content

Commit

Permalink
Adds support for property dcat:temporalResolution
Browse files Browse the repository at this point in the history
  • Loading branch information
seitenbau-govdata committed Jun 22, 2022
1 parent 4d12fff commit 4b92221
Show file tree
Hide file tree
Showing 4 changed files with 97 additions and 1 deletion.
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -347,6 +347,7 @@ This mapping is compatible with the [DCAT-AP v1.1](https://joinup.ec.europa.eu/a
| dcat:Dataset | adms:sample | extra:sample | | list | See note about lists. It is assumed that these are one or more URIs referring to dcat:Distribution instances |
| dcat:Dataset | dct:spatial | extra:spatial_uri | | text | If the RDF provides them, profiles should store the textual and geometric representation of the location in extra:spatial_text, extra:spatial, extra:spatial_bbox and extra:spatial_centroid respectively |
| dcat:Dataset | dct:temporal | extra:temporal_start + extra:temporal_end | | text | None, one or both extras can be present |
| dcat:Dataset | dcat:temporalResolution| extra:temporal_resolution | | list | |
| dcat:Dataset | dct:publisher | extra:publisher_uri | | text | See note about URIs |
| foaf:Agent | foaf:name | extra:publisher_name | | text | |
| foaf:Agent | foaf:mbox | extra:publisher_email | organization:title | text | |
Expand Down
17 changes: 17 additions & 0 deletions ckanext/dcat/profiles.py
Original file line number Diff line number Diff line change
Expand Up @@ -1391,6 +1391,16 @@ def parse_dataset(self, dataset_dict, dataset_ref):
# call super method
super(EuropeanDCATAP2Profile, self).parse_dataset(dataset_dict, dataset_ref)

# Lists
for key, predicate, in (
('temporal_resolution', DCAT.temporalResolution),
):
values = self._object_value_list(dataset_ref, predicate)
if values:
dataset_dict['extras'].append({'key': key,
'value': json.dumps(values)})


# Spatial
spatial = self._spatial(dataset_ref, DCT.spatial)
for key in ('bbox', 'centroid'):
Expand All @@ -1416,6 +1426,13 @@ def graph_from_dataset(self, dataset_dict, dataset_ref):
if spatial_cent:
self._add_spatial_value_to_graph(spatial_ref, DCAT.centroid, spatial_cent)

# TemporalResolution
temporal_resolution = self._get_dataset_value(dataset_dict, 'temporal_resolution')
if temporal_resolution:
temporal_resolution_list = json.loads(temporal_resolution)
for value in temporal_resolution_list:
self.g.add((dataset_ref, DCAT.temporalResolution , Literal(value, datatype=XSD.duration)))

def graph_from_catalog(self, catalog_dict, catalog_ref):

# call super method
Expand Down
50 changes: 49 additions & 1 deletion ckanext/dcat/tests/test_euro_dcatap_2_profile_parse.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,14 +15,62 @@

from ckanext.dcat.processors import RDFParser, RDFSerializer
from ckanext.dcat.profiles import (DCAT, DCT, ADMS, LOCN, SKOS, GSP, RDFS,
GEOJSON_IMT, VCARD)
GEOJSON_IMT, VCARD, XSD)
from ckanext.dcat.utils import DCAT_EXPOSE_SUBCATALOGS, DCAT_CLEAN_TAGS
from ckanext.dcat.tests.utils import BaseParseTest

DCAT_AP_2_PROFILE = 'euro_dcat_ap_2'
DCAT_AP_PROFILES = [DCAT_AP_2_PROFILE]


class TestEuroDCATAP2ProfileParsing(BaseParseTest):

def test_temporal_resolution(self):
g = Graph()

dataset = URIRef('http://example.org/datasets/1')
g.add((dataset, RDF.type, DCAT.Dataset))

temporal_resolution = 'P1D'
g.add((dataset, DCAT.temporalResolution, Literal(temporal_resolution, datatype=XSD.duration)))

p = RDFParser(profiles=DCAT_AP_PROFILES)

p.g = g

datasets = [d for d in p.datasets()]

extras = self._extras(datasets[0])

temporal_resolution_list = json.loads(extras['temporal_resolution'])
assert len(temporal_resolution_list) == 1
assert temporal_resolution in temporal_resolution_list

def test_temporal_resolution_multiple(self):
g = Graph()

dataset = URIRef('http://example.org/datasets/1')
g.add((dataset, RDF.type, DCAT.Dataset))

temporal_resolution = 'P1D'
g.add((dataset, DCAT.temporalResolution, Literal(temporal_resolution, datatype=XSD.duration)))
temporal_resolution_2 = 'PT15M'
g.add((dataset, DCAT.temporalResolution, Literal(temporal_resolution_2, datatype=XSD.duration)))

p = RDFParser(profiles=DCAT_AP_PROFILES)

p.g = g

datasets = [d for d in p.datasets()]

extras = self._extras(datasets[0])

temporal_resolution_list = json.loads(extras['temporal_resolution'])
assert len(temporal_resolution_list) == 2
assert temporal_resolution in temporal_resolution_list
assert temporal_resolution_2 in temporal_resolution_list


class TestEuroDCATAP2ProfileParsingSpatial(BaseParseTest):

def test_spatial_multiple_dct_spatial_instances(self):
Expand Down
30 changes: 30 additions & 0 deletions ckanext/dcat/tests/test_euro_dcatap_2_profile_serialize.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,36 @@

class TestEuroDCATAP2ProfileSerializeDataset(BaseSerializeTest):

def test_graph_from_dataset(self):

dataset = {
'id': '4b6fe9ca-dc77-4cec-92a4-55c6624a5bd6',
'name': 'test-dataset',
'title': 'Test DCAT 2 dataset',
'notes': 'Lorem ipsum',
'url': 'http://example.com/ds1',
'version': '1.0b',
'metadata_created': '2021-06-21T15:21:09.034694',
'metadata_modified': '2021-06-21T15:21:09.075774',
'extras': [
{'key': 'temporal_resolution', 'value': '[\"PT15M\", \"P1D\"]'},
]
}

extras = self._extras(dataset)

s = RDFSerializer(profiles=DCAT_AP_PROFILES)
g = s.g

dataset_ref = s.graph_from_dataset(dataset)

# TemporalResolution
values = json.loads(extras['temporal_resolution'])
assert len([t for t in g.triples((dataset_ref, DCAT.temporalResolution, None))]) == len(values)
for value in values:
assert self._triple(g, dataset_ref, DCAT.temporalResolution, Literal(value,
datatype=XSD.duration))

def test_spatial(self):
dataset = {
'id': '4b6fe9ca-dc77-4cec-92a4-55c6624a5bd6',
Expand Down

0 comments on commit 4b92221

Please sign in to comment.