ldp_rs.py 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141
  1. import logging
  2. from rdflib import Graph
  3. from lakesuperior.env import env
  4. from lakesuperior.globals import RES_UPDATED
  5. from lakesuperior.dictionaries.namespaces import ns_collection as nsc
  6. from lakesuperior.model.ldpr import Ldpr
  7. logger = logging.getLogger(__name__)
  8. class LdpRs(Ldpr):
  9. '''LDP-RS (LDP RDF source).
  10. Definition: https://www.w3.org/TR/ldp/#ldprs
  11. '''
  12. def __init__(self, uuid, repr_opts={}, handling='lenient', **kwargs):
  13. '''
  14. Extends Ldpr.__init__ by adding LDP-RS specific parameters.
  15. @param handling (string) One of `strict`, `lenient` (the default) or
  16. `none`. `strict` raises an error if a server-managed term is in the
  17. graph. `lenient` removes all sever-managed triples encountered. `none`
  18. skips all server-managed checks. It is used for internal modifications.
  19. '''
  20. super().__init__(uuid, **kwargs)
  21. self.base_types = super().base_types | {
  22. nsc['fcrepo'].Container,
  23. nsc['ldp'].Container,
  24. }
  25. # provided_imr can be empty. If None, it is an outbound resource.
  26. if self.provided_imr is not None:
  27. self.workflow = self.WRKF_INBOUND
  28. else:
  29. self.workflow = self.WRKF_OUTBOUND
  30. self._imr_options = repr_opts
  31. self.handling = handling
  32. ## LDP METHODS ##
  33. def patch(self, update_str):
  34. '''
  35. Update an existing resource by applying a SPARQL-UPDATE query.
  36. @param update_str (string) SPARQL-Update staements.
  37. '''
  38. self.handling = 'lenient' # FCREPO does that and Hyrax requires it.
  39. return self._sparql_update(update_str)
  40. #def _sparql_delta(self, q):
  41. # '''
  42. # Calculate the delta obtained by a SPARQL Update operation.
  43. # This is a critical component of the SPARQL update prcess and does a
  44. # couple of things:
  45. # 1. It ensures that no resources outside of the subject of the request
  46. # are modified (e.g. by variable subjects)
  47. # 2. It verifies that none of the terms being modified is server managed.
  48. # This method extracts an in-memory copy of the resource and performs the
  49. # query on that once it has checked if any of the server managed terms is
  50. # in the delta. If it is, it raises an exception.
  51. # NOTE: This only checks if a server-managed term is effectively being
  52. # modified. If a server-managed term is present in the query but does not
  53. # cause any change in the updated resource, no error is raised.
  54. # @return tuple(rdflib.Graph) Remove and add graphs. These can be used
  55. # with `BaseStoreLayout.update_resource` and/or recorded as separate
  56. # events in a provenance tracking system.
  57. # '''
  58. # logger.debug('Provided SPARQL query: {}'.format(q))
  59. # pre_gr = self.imr.graph
  60. # post_gr = pre_gr | Graph()
  61. # post_gr.update(q)
  62. # remove_gr, add_gr = self._dedup_deltas(pre_gr, post_gr)
  63. # #logger.debug('Removing: {}'.format(
  64. # # remove_gr.serialize(format='turtle').decode('utf8')))
  65. # #logger.debug('Adding: {}'.format(
  66. # # add_gr.serialize(format='turtle').decode('utf8')))
  67. # remove_gr = self._check_mgd_terms(remove_gr)
  68. # add_gr = self._check_mgd_terms(add_gr)
  69. # return set(remove_gr), set(add_gr)
  70. class Ldpc(LdpRs):
  71. '''LDPC (LDP Container).'''
  72. def __init__(self, uuid, *args, **kwargs):
  73. super().__init__(uuid, *args, **kwargs)
  74. self.base_types |= {
  75. nsc['fcrepo'].Container,
  76. nsc['ldp'].Container,
  77. }
  78. class LdpBc(Ldpc):
  79. '''LDP-BC (LDP Basic Container).'''
  80. def __init__(self, uuid, *args, **kwargs):
  81. super().__init__(uuid, *args, **kwargs)
  82. self.base_types |= {
  83. nsc['ldp'].BasicContainer,
  84. }
  85. class LdpDc(Ldpc):
  86. '''LDP-DC (LDP Direct Container).'''
  87. def __init__(self, uuid, *args, **kwargs):
  88. super().__init__(uuid, *args, **kwargs)
  89. self.base_types |= {
  90. nsc['ldp'].DirectContainer,
  91. }
  92. class LdpIc(Ldpc):
  93. '''LDP-IC (LDP Indirect Container).'''
  94. def __init__(self, uuid, *args, **kwargs):
  95. super().__init__(uuid, *args, **kwargs)
  96. self.base_types |= {
  97. nsc['ldp'].IndirectContainer,
  98. }