about summary refs log tree commit diff
path: root/.venv/lib/python3.12/site-packages/websockets/legacy/handshake.py
diff options
context:
space:
mode:
authorS. Solomon Darnell2025-03-28 21:52:21 -0500
committerS. Solomon Darnell2025-03-28 21:52:21 -0500
commit4a52a71956a8d46fcb7294ac71734504bb09bcc2 (patch)
treeee3dc5af3b6313e921cd920906356f5d4febc4ed /.venv/lib/python3.12/site-packages/websockets/legacy/handshake.py
parentcc961e04ba734dd72309fb548a2f97d67d578813 (diff)
downloadgn-ai-4a52a71956a8d46fcb7294ac71734504bb09bcc2.tar.gz
two version of R2R are here HEAD master
Diffstat (limited to '.venv/lib/python3.12/site-packages/websockets/legacy/handshake.py')
-rw-r--r--.venv/lib/python3.12/site-packages/websockets/legacy/handshake.py158
1 files changed, 158 insertions, 0 deletions
diff --git a/.venv/lib/python3.12/site-packages/websockets/legacy/handshake.py b/.venv/lib/python3.12/site-packages/websockets/legacy/handshake.py
new file mode 100644
index 00000000..6a7157c0
--- /dev/null
+++ b/.venv/lib/python3.12/site-packages/websockets/legacy/handshake.py
@@ -0,0 +1,158 @@
+from __future__ import annotations
+
+import base64
+import binascii
+
+from ..datastructures import Headers, MultipleValuesError
+from ..exceptions import InvalidHeader, InvalidHeaderValue, InvalidUpgrade
+from ..headers import parse_connection, parse_upgrade
+from ..typing import ConnectionOption, UpgradeProtocol
+from ..utils import accept_key as accept, generate_key
+
+
+__all__ = ["build_request", "check_request", "build_response", "check_response"]
+
+
+def build_request(headers: Headers) -> str:
+    """
+    Build a handshake request to send to the server.
+
+    Update request headers passed in argument.
+
+    Args:
+        headers: Handshake request headers.
+
+    Returns:
+        ``key`` that must be passed to :func:`check_response`.
+
+    """
+    key = generate_key()
+    headers["Upgrade"] = "websocket"
+    headers["Connection"] = "Upgrade"
+    headers["Sec-WebSocket-Key"] = key
+    headers["Sec-WebSocket-Version"] = "13"
+    return key
+
+
+def check_request(headers: Headers) -> str:
+    """
+    Check a handshake request received from the client.
+
+    This function doesn't verify that the request is an HTTP/1.1 or higher GET
+    request and doesn't perform ``Host`` and ``Origin`` checks. These controls
+    are usually performed earlier in the HTTP request handling code. They're
+    the responsibility of the caller.
+
+    Args:
+        headers: Handshake request headers.
+
+    Returns:
+        ``key`` that must be passed to :func:`build_response`.
+
+    Raises:
+        InvalidHandshake: If the handshake request is invalid.
+            Then, the server must return a 400 Bad Request error.
+
+    """
+    connection: list[ConnectionOption] = sum(
+        [parse_connection(value) for value in headers.get_all("Connection")], []
+    )
+
+    if not any(value.lower() == "upgrade" for value in connection):
+        raise InvalidUpgrade("Connection", ", ".join(connection))
+
+    upgrade: list[UpgradeProtocol] = sum(
+        [parse_upgrade(value) for value in headers.get_all("Upgrade")], []
+    )
+
+    # For compatibility with non-strict implementations, ignore case when
+    # checking the Upgrade header. The RFC always uses "websocket", except
+    # in section 11.2. (IANA registration) where it uses "WebSocket".
+    if not (len(upgrade) == 1 and upgrade[0].lower() == "websocket"):
+        raise InvalidUpgrade("Upgrade", ", ".join(upgrade))
+
+    try:
+        s_w_key = headers["Sec-WebSocket-Key"]
+    except KeyError as exc:
+        raise InvalidHeader("Sec-WebSocket-Key") from exc
+    except MultipleValuesError as exc:
+        raise InvalidHeader("Sec-WebSocket-Key", "multiple values") from exc
+
+    try:
+        raw_key = base64.b64decode(s_w_key.encode(), validate=True)
+    except binascii.Error as exc:
+        raise InvalidHeaderValue("Sec-WebSocket-Key", s_w_key) from exc
+    if len(raw_key) != 16:
+        raise InvalidHeaderValue("Sec-WebSocket-Key", s_w_key)
+
+    try:
+        s_w_version = headers["Sec-WebSocket-Version"]
+    except KeyError as exc:
+        raise InvalidHeader("Sec-WebSocket-Version") from exc
+    except MultipleValuesError as exc:
+        raise InvalidHeader("Sec-WebSocket-Version", "multiple values") from exc
+
+    if s_w_version != "13":
+        raise InvalidHeaderValue("Sec-WebSocket-Version", s_w_version)
+
+    return s_w_key
+
+
+def build_response(headers: Headers, key: str) -> None:
+    """
+    Build a handshake response to send to the client.
+
+    Update response headers passed in argument.
+
+    Args:
+        headers: Handshake response headers.
+        key: Returned by :func:`check_request`.
+
+    """
+    headers["Upgrade"] = "websocket"
+    headers["Connection"] = "Upgrade"
+    headers["Sec-WebSocket-Accept"] = accept(key)
+
+
+def check_response(headers: Headers, key: str) -> None:
+    """
+    Check a handshake response received from the server.
+
+    This function doesn't verify that the response is an HTTP/1.1 or higher
+    response with a 101 status code. These controls are the responsibility of
+    the caller.
+
+    Args:
+        headers: Handshake response headers.
+        key: Returned by :func:`build_request`.
+
+    Raises:
+        InvalidHandshake: If the handshake response is invalid.
+
+    """
+    connection: list[ConnectionOption] = sum(
+        [parse_connection(value) for value in headers.get_all("Connection")], []
+    )
+
+    if not any(value.lower() == "upgrade" for value in connection):
+        raise InvalidUpgrade("Connection", " ".join(connection))
+
+    upgrade: list[UpgradeProtocol] = sum(
+        [parse_upgrade(value) for value in headers.get_all("Upgrade")], []
+    )
+
+    # For compatibility with non-strict implementations, ignore case when
+    # checking the Upgrade header. The RFC always uses "websocket", except
+    # in section 11.2. (IANA registration) where it uses "WebSocket".
+    if not (len(upgrade) == 1 and upgrade[0].lower() == "websocket"):
+        raise InvalidUpgrade("Upgrade", ", ".join(upgrade))
+
+    try:
+        s_w_accept = headers["Sec-WebSocket-Accept"]
+    except KeyError as exc:
+        raise InvalidHeader("Sec-WebSocket-Accept") from exc
+    except MultipleValuesError as exc:
+        raise InvalidHeader("Sec-WebSocket-Accept", "multiple values") from exc
+
+    if s_w_accept != accept(key):
+        raise InvalidHeaderValue("Sec-WebSocket-Accept", s_w_accept)