Skip to content

Commit 0fd5784

Browse files
committed
Fix a problem with query generation when using "type_filter" or "reverse" with a multi-part path.
1 parent a61fda2 commit 0fd5784

2 files changed

Lines changed: 76 additions & 4 deletions

File tree

fairgraph/queries.py

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -134,17 +134,27 @@ def serialize(self) -> Dict[str, Any]:
134134
if self.properties:
135135
data["structure"] = [prop.serialize() for prop in self.properties]
136136
if self.type_filter or self.reverse:
137-
data["path"] = {"@id": data["path"]}
137+
if isinstance(self.path, str):
138+
first_path_element = {"@id": self.path}
139+
else:
140+
# for now we only support specifying type filters/reverse
141+
# for the first element in a multi-element path
142+
assert isinstance(self.path, (list, tuple))
143+
first_path_element = {"@id": self.path[0]}
138144
if self.type_filter:
139145
if isinstance(self.type_filter, (list, tuple)):
140-
data["path"]["typeFilter"] = [
146+
first_path_element["typeFilter"] = [
141147
{"@id": type_iri} for type_iri in self.type_filter
142148
]
143149
else:
144150
assert isinstance(self.type_filter, str)
145-
data["path"]["typeFilter"] = {"@id": self.type_filter}
151+
first_path_element["typeFilter"] = {"@id": self.type_filter}
146152
if self.reverse:
147-
data["path"]["reverse"] = True
153+
first_path_element["reverse"] = True
154+
if isinstance(self.path, str):
155+
data["path"] = first_path_element
156+
else:
157+
data["path"] = [first_path_element, *self.path[1:]]
148158
if self.expect_single:
149159
data["singleValue"] = "FIRST"
150160
return data

test/test_queries.py

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -526,3 +526,65 @@ def test_migrate_query():
526526
expected = json.load(fp)
527527

528528
assert migrated_query == expected
529+
530+
531+
def test_generate_query_type_filter_flattened():
532+
query = Query(
533+
node_type="https://openminds.ebrains.eu/publications/LivePaperVersion",
534+
label="fg-testing-livepaperversion",
535+
space="livepapers",
536+
properties=[
537+
QueryProperty("https://openminds.ebrains.eu/vocab/shortName", name="short_name"),
538+
QueryProperty(
539+
[
540+
"https://openminds.ebrains.eu/vocab/relatedPublication",
541+
"https://openminds.ebrains.eu/vocab/identifier",
542+
],
543+
type_filter="https://openminds.ebrains.eu/core/DOI",
544+
name="related_publications",
545+
),
546+
],
547+
)
548+
expected = {
549+
"@context": {
550+
"@vocab": "https://core.kg.ebrains.eu/vocab/query/",
551+
"merge": {"@id": "merge", "@type": "@id"},
552+
"query": "https://schema.hbp.eu/myQuery/",
553+
"propertyName": {"@id": "propertyName", "@type": "@id"},
554+
"path": {"@id": "path", "@type": "@id"}
555+
},
556+
"meta": {
557+
"type": "https://openminds.ebrains.eu/publications/LivePaperVersion",
558+
"description": "Automatically generated by fairgraph",
559+
"name": "fg-testing-livepaperversion"
560+
},
561+
"structure": [
562+
{
563+
"path": "@id",
564+
"filter": {
565+
"op": "EQUALS",
566+
"parameter": "id"
567+
}
568+
},
569+
{
570+
"propertyName": "query:space",
571+
"path": "https://core.kg.ebrains.eu/vocab/meta/space",
572+
"filter": {
573+
"op": "EQUALS",
574+
"value": "livepapers"
575+
}
576+
},
577+
{"propertyName": "short_name", "path": "https://openminds.ebrains.eu/vocab/shortName"},
578+
{
579+
"propertyName": "related_publications",
580+
"path": [
581+
{
582+
"@id": "https://openminds.ebrains.eu/vocab/relatedPublication",
583+
"typeFilter": {"@id": "https://openminds.ebrains.eu/core/DOI"}
584+
},
585+
"https://openminds.ebrains.eu/vocab/identifier"
586+
]
587+
}
588+
]
589+
}
590+
assert query.serialize() == expected

0 commit comments

Comments
 (0)