Skip to content

Commit

Permalink
update rdflib to version 7
Browse files Browse the repository at this point in the history
  • Loading branch information
situx committed Feb 14, 2024
1 parent f738193 commit 5cf569a
Show file tree
Hide file tree
Showing 90 changed files with 7,223 additions and 2,651 deletions.
16 changes: 10 additions & 6 deletions dependencies/rdflib/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -42,11 +42,16 @@
True
"""
import logging
import sys
from importlib import metadata

_DISTRIBUTION_METADATA = metadata.metadata("rdflib")

__docformat__ = "restructuredtext en"

# The format of the __version__ line is matched by a regex in setup.py
__version__ = "6.2.0"
__date__ = "2022-12-20"
__version__: str = _DISTRIBUTION_METADATA["Version"]
__date__ = "2023-08-02"

__all__ = [
"URIRef",
Expand Down Expand Up @@ -82,15 +87,14 @@
"TIME",
"VANN",
"VOID",
"XMLNS",
"XSD",
"util",
"plugin",
"query",
"NORMALIZE_LITERALS",
]

import logging
import sys

logger = logging.getLogger(__name__)

try:
Expand Down
117 changes: 117 additions & 0 deletions dependencies/rdflib/_networking.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,117 @@
from __future__ import annotations

import string
import sys
from typing import Dict
from urllib.error import HTTPError
from urllib.parse import quote as urlquote
from urllib.parse import urljoin, urlsplit
from urllib.request import HTTPRedirectHandler, Request, urlopen
from urllib.response import addinfourl


def _make_redirect_request(request: Request, http_error: HTTPError) -> Request:
"""
Create a new request object for a redirected request.
The logic is based on `urllib.request.HTTPRedirectHandler` from `this commit <https://github.com/python/cpython/blob/b58bc8c2a9a316891a5ea1a0487aebfc86c2793a/Lib/urllib/request.py#L641-L751>_`.
:param request: The original request that resulted in the redirect.
:param http_error: The response to the original request that indicates a
redirect should occur and contains the new location.
:return: A new request object to the location indicated by the response.
:raises HTTPError: the supplied ``http_error`` if the redirect request
cannot be created.
:raises ValueError: If the response code is `None`.
:raises ValueError: If the response does not contain a ``Location`` header
or the ``Location`` header is not a string.
:raises HTTPError: If the scheme of the new location is not ``http``,
``https``, or ``ftp``.
:raises HTTPError: If there are too many redirects or a redirect loop.
"""
new_url = http_error.headers.get("Location")
if new_url is None:
raise http_error
if not isinstance(new_url, str):
raise ValueError(f"Location header {new_url!r} is not a string")

new_url_parts = urlsplit(new_url)

# For security reasons don't allow redirection to anything other than http,
# https or ftp.
if new_url_parts.scheme not in ("http", "https", "ftp", ""):
raise HTTPError(
new_url,
http_error.code,
f"{http_error.reason} - Redirection to url {new_url!r} is not allowed",
http_error.headers,
http_error.fp,
)

# http.client.parse_headers() decodes as ISO-8859-1. Recover the original
# bytes and percent-encode non-ASCII bytes, and any special characters such
# as the space.
new_url = urlquote(new_url, encoding="iso-8859-1", safe=string.punctuation)
new_url = urljoin(request.full_url, new_url)

# XXX Probably want to forget about the state of the current
# request, although that might interact poorly with other
# handlers that also use handler-specific request attributes
content_headers = ("content-length", "content-type")
newheaders = {
k: v for k, v in request.headers.items() if k.lower() not in content_headers
}
new_request = Request(
new_url,
headers=newheaders,
origin_req_host=request.origin_req_host,
unverifiable=True,
)

visited: Dict[str, int]
if hasattr(request, "redirect_dict"):
visited = request.redirect_dict
if (
visited.get(new_url, 0) >= HTTPRedirectHandler.max_repeats
or len(visited) >= HTTPRedirectHandler.max_redirections
):
raise HTTPError(
request.full_url,
http_error.code,
HTTPRedirectHandler.inf_msg + http_error.reason,
http_error.headers,
http_error.fp,
)
else:
visited = {}
setattr(request, "redirect_dict", visited)

setattr(new_request, "redirect_dict", visited)
visited[new_url] = visited.get(new_url, 0) + 1
return new_request


def _urlopen(request: Request) -> addinfourl:
"""
This is a shim for `urlopen` that handles HTTP redirects with status code
308 (Permanent Redirect).
This function should be removed once all supported versions of Python
handles the 308 HTTP status code.
:param request: The request to open.
:return: The response to the request.
"""
try:
return urlopen(request)
except HTTPError as error:
if error.code == 308 and sys.version_info < (3, 11):
# HTTP response code 308 (Permanent Redirect) is not supported by python
# versions older than 3.11. See <https://bugs.python.org/issue40321> and
# <https://github.com/python/cpython/issues/84501> for more details.
# This custom error handling should be removed once all supported
# versions of Python handles 308.
new_request = _make_redirect_request(request, error)
return _urlopen(new_request)
else:
raise
9 changes: 3 additions & 6 deletions dependencies/rdflib/_type_checking.py
Original file line number Diff line number Diff line change
Expand Up @@ -14,16 +14,13 @@
and this module is not part the the RDFLib public API.
"""

import sys

__all__ = [
"_NamespaceSetString",
"_MulPathMod",
]


if sys.version_info >= (3, 8):
from typing import Literal as PyLiteral
else:
from typing_extensions import Literal as PyLiteral
from typing import Literal as PyLiteral

_NamespaceSetString = PyLiteral["core", "rdflib", "none"]
_MulPathMod = PyLiteral["*", "+", "?"] # noqa: F722
85 changes: 48 additions & 37 deletions dependencies/rdflib/collection.py
Original file line number Diff line number Diff line change
@@ -1,23 +1,31 @@
from __future__ import annotations

from typing import TYPE_CHECKING, Iterable, Iterator, List, Optional

from rdflib.namespace import RDF
from rdflib.term import BNode, Literal
from rdflib.term import BNode, Node

if TYPE_CHECKING:
from rdflib.graph import Graph

__all__ = ["Collection"]


class Collection(object):
class Collection:
__doc__ = """
See "Emulating container types":
https://docs.python.org/reference/datamodel.html#emulating-container-types
>>> from rdflib.term import Literal
>>> from rdflib.graph import Graph
>>> from pprint import pprint
>>> listName = BNode()
>>> listname = BNode()
>>> g = Graph('Memory')
>>> listItem1 = BNode()
>>> listItem2 = BNode()
>>> g.add((listName, RDF.first, Literal(1))) # doctest: +ELLIPSIS
>>> g.add((listname, RDF.first, Literal(1))) # doctest: +ELLIPSIS
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
>>> g.add((listName, RDF.rest, listItem1)) # doctest: +ELLIPSIS
>>> g.add((listname, RDF.rest, listItem1)) # doctest: +ELLIPSIS
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
>>> g.add((listItem1, RDF.first, Literal(2))) # doctest: +ELLIPSIS
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
Expand All @@ -27,7 +35,7 @@ class Collection(object):
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
>>> g.add((listItem2, RDF.first, Literal(3))) # doctest: +ELLIPSIS
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
>>> c = Collection(g,listName)
>>> c = Collection(g,listname)
>>> pprint([term.n3() for term in c])
[u'"1"^^<http://www.w3.org/2001/XMLSchema#integer>',
u'"2"^^<http://www.w3.org/2001/XMLSchema#integer>',
Expand All @@ -43,21 +51,22 @@ class Collection(object):
True
"""

def __init__(self, graph, uri, seq=[]):
def __init__(self, graph: Graph, uri: Node, seq: List[Node] = []):
self.graph = graph
self.uri = uri or BNode()
self += seq

def n3(self):
def n3(self) -> str:
"""
>>> from rdflib.term import Literal
>>> from rdflib.graph import Graph
>>> listName = BNode()
>>> listname = BNode()
>>> g = Graph('Memory')
>>> listItem1 = BNode()
>>> listItem2 = BNode()
>>> g.add((listName, RDF.first, Literal(1))) # doctest: +ELLIPSIS
>>> g.add((listname, RDF.first, Literal(1))) # doctest: +ELLIPSIS
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
>>> g.add((listName, RDF.rest, listItem1)) # doctest: +ELLIPSIS
>>> g.add((listname, RDF.rest, listItem1)) # doctest: +ELLIPSIS
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
>>> g.add((listItem1, RDF.first, Literal(2))) # doctest: +ELLIPSIS
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
Expand All @@ -67,19 +76,20 @@ def n3(self):
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
>>> g.add((listItem2, RDF.first, Literal(3))) # doctest: +ELLIPSIS
<Graph identifier=... (<class 'rdflib.graph.Graph'>)>
>>> c = Collection(g, listName)
>>> c = Collection(g, listname)
>>> print(c.n3()) #doctest: +NORMALIZE_WHITESPACE
( "1"^^<http://www.w3.org/2001/XMLSchema#integer>
"2"^^<http://www.w3.org/2001/XMLSchema#integer>
"3"^^<http://www.w3.org/2001/XMLSchema#integer> )
"""
return "( %s )" % (" ".join([i.n3() for i in self]))
# type error: "Node" has no attribute "n3"
return "( %s )" % (" ".join([i.n3() for i in self])) # type: ignore[attr-defined]

def _get_container(self, index):
def _get_container(self, index: int) -> Optional[Node]:
"""Gets the first, rest holding node at index."""
assert isinstance(index, int)
graph = self.graph
container = self.uri
container: Optional[Node] = self.uri
i = 0
while i < index:
i += 1
Expand All @@ -88,31 +98,31 @@ def _get_container(self, index):
break
return container

def __len__(self):
def __len__(self) -> int:
"""length of items in collection."""
return len(list(self.graph.items(self.uri)))

def index(self, item):
def index(self, item: Node) -> int:
"""
Returns the 0-based numerical index of the item in the list
"""
listName = self.uri
listname = self.uri
index = 0
while True:
if (listName, RDF.first, item) in self.graph:
if (listname, RDF.first, item) in self.graph:
return index
else:
newLink = list(self.graph.objects(listName, RDF.rest))
newlink = list(self.graph.objects(listname, RDF.rest))
index += 1
if newLink == [RDF.nil]:
if newlink == [RDF.nil]:
raise ValueError("%s is not in %s" % (item, self.uri))
elif not newLink:
elif not newlink:
raise Exception("Malformed RDF Collection: %s" % self.uri)
else:
assert len(newLink) == 1, "Malformed RDF Collection: %s" % self.uri
listName = newLink[0]
assert len(newlink) == 1, "Malformed RDF Collection: %s" % self.uri
listname = newlink[0]

def __getitem__(self, key):
def __getitem__(self, key: int) -> Node:
"""TODO"""
c = self._get_container(key)
if c:
Expand All @@ -124,15 +134,15 @@ def __getitem__(self, key):
else:
raise IndexError(key)

def __setitem__(self, key, value):
def __setitem__(self, key: int, value: Node) -> None:
"""TODO"""
c = self._get_container(key)
if c:
self.graph.set((c, RDF.first, value))
else:
raise IndexError(key)

def __delitem__(self, key):
def __delitem__(self, key: int) -> None:
"""
>>> from rdflib.namespace import RDF, RDFS
>>> from rdflib import Graph
Expand Down Expand Up @@ -183,8 +193,9 @@ def __delitem__(self, key):
pass
elif key == len(self) - 1:
# the tail
priorLink = self._get_container(key - 1)
self.graph.set((priorLink, RDF.rest, RDF.nil))
priorlink = self._get_container(key - 1)
# type error: Argument 1 to "set" of "Graph" has incompatible type "Tuple[Optional[Node], URIRef, URIRef]"; expected "Tuple[Node, Node, Any]"
self.graph.set((priorlink, RDF.rest, RDF.nil)) # type: ignore[arg-type]
graph.remove((current, None, None))
else:
next = self._get_container(key + 1)
Expand All @@ -193,11 +204,11 @@ def __delitem__(self, key):
graph.remove((current, None, None))
graph.set((prior, RDF.rest, next))

def __iter__(self):
def __iter__(self) -> Iterator[Node]:
"""Iterator over items in Collections"""
return self.graph.items(self.uri)

def _end(self):
def _end(self) -> Node:
# find end of list
container = self.uri
while True:
Expand All @@ -207,12 +218,13 @@ def _end(self):
else:
container = rest

def append(self, item):
def append(self, item: Node) -> Collection:
"""
>>> from rdflib.term import Literal
>>> from rdflib.graph import Graph
>>> listName = BNode()
>>> listname = BNode()
>>> g = Graph()
>>> c = Collection(g,listName,[Literal(1),Literal(2)])
>>> c = Collection(g,listname,[Literal(1),Literal(2)])
>>> links = [
... list(g.subjects(object=i, predicate=RDF.first))[0] for i in c]
>>> len([i for i in links if (i, RDF.rest, RDF.nil) in g])
Expand All @@ -231,8 +243,7 @@ def append(self, item):
self.graph.add((end, RDF.rest, RDF.nil))
return self

def __iadd__(self, other):

def __iadd__(self, other: Iterable[Node]):
end = self._end()
self.graph.remove((end, RDF.rest, None))

Expand All @@ -248,7 +259,7 @@ def __iadd__(self, other):
return self

def clear(self):
container = self.uri
container: Optional[Node] = self.uri
graph = self.graph
while container:
rest = graph.value(container, RDF.rest)
Expand Down
Loading

0 comments on commit 5cf569a

Please sign in to comment.