rdfresults.py 2.7 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970
  1. from __future__ import annotations
  2. from typing import IO, Any, MutableMapping, Optional, Union
  3. from rdflib.graph import Graph
  4. from rdflib.namespace import RDF, Namespace
  5. from rdflib.query import Result, ResultParser
  6. from rdflib.term import Node, Variable
  7. RS = Namespace("http://www.w3.org/2001/sw/DataAccess/tests/result-set#")
  8. class RDFResultParser(ResultParser):
  9. def parse(self, source: Union[IO, Graph], **kwargs: Any) -> Result:
  10. return RDFResult(source, **kwargs)
  11. class RDFResult(Result):
  12. def __init__(self, source: Union[IO, Graph], **kwargs: Any):
  13. if not isinstance(source, Graph):
  14. graph = Graph()
  15. graph.parse(source, **kwargs)
  16. else:
  17. graph = source
  18. rs = graph.value(predicate=RDF.type, object=RS.ResultSet)
  19. # there better be only one :)
  20. if rs is None:
  21. type_ = "CONSTRUCT"
  22. # use a new graph
  23. g = Graph()
  24. g += graph
  25. else:
  26. askAnswer = graph.value(rs, RS.boolean)
  27. if askAnswer is not None:
  28. type_ = "ASK"
  29. else:
  30. type_ = "SELECT"
  31. Result.__init__(self, type_)
  32. if type_ == "SELECT":
  33. # type error: Argument 1 to "Variable" has incompatible type "Node"; expected "str"
  34. self.vars = [Variable(v) for v in graph.objects(rs, RS.resultVariable)] # type: ignore[arg-type]
  35. self.bindings = []
  36. for s in graph.objects(rs, RS.solution):
  37. sol: MutableMapping[Variable, Optional[Node]] = {}
  38. for b in graph.objects(s, RS.binding):
  39. # type error: Argument 1 to "Variable" has incompatible type "Optional[Node]"; expected "str"
  40. sol[Variable(graph.value(b, RS.variable))] = graph.value( # type: ignore[arg-type]
  41. b, RS.value
  42. )
  43. # error: Argument 1 to "append" of "list" has incompatible type "MutableMapping[Variable, Optional[Node]]"; expected "Mapping[Variable, Identifier]"
  44. self.bindings.append(sol) # type: ignore[arg-type]
  45. elif type_ == "ASK":
  46. # type error: Item "Node" of "Optional[Node]" has no attribute "value"
  47. # type error: Item "None" of "Optional[Node]" has no attribute "value"
  48. self.askAnswer = askAnswer.value # type: ignore[union-attr]
  49. # type error: Item "Node" of "Optional[Node]" has no attribute "value"
  50. # type error: Item "None" of "Optional[Node]" has no attribute "value"
  51. if askAnswer.value is None: # type: ignore[union-attr]
  52. raise Exception("Malformed boolean in ask answer!")
  53. elif type_ == "CONSTRUCT":
  54. self.graph = g