Ignore:
Timestamp:
2023-05-23T18:53:22Z (2 years ago)
Author:
GitHub <noreply@…>
Branches:
master
Children:
839140c, 96670de, f4a099c
Parents:
41131ca (diff), b03db14 (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the (diff) links above to see all the changes relative to each parent.
git-author:
Itamar Turner-Trauring <itamar@…> (2023-05-23 18:53:22)
git-committer:
GitHub <noreply@…> (2023-05-23 18:53:22)
Message:

Merge pull request #1301 from tahoe-lafs/4027-invalid-unicode

Invalid unicode in Authorization header should give better response

Fixes ticket:4027

File:
1 edited

Legend:

Unmodified
Added
Removed
  • TabularUnified src/allmydata/storage/http_server.py

    r41131ca rd510103  
    55from __future__ import annotations
    66
    7 from typing import Any, Callable, Union, cast
     7from typing import Any, Callable, Union, cast, Optional
    88from functools import wraps
    99from base64 import b64decode
     
    7676
    7777    If too few secrets were given, or too many, a ``ClientSecretsException`` is
    78     raised.
     78    raised; its text is sent in the HTTP response.
    7979    """
    8080    string_key_to_enum = {e.value: e for e in Secrets}
     
    8585            key = string_key_to_enum[string_key]
    8686            value = b64decode(string_value)
     87            if value == b"":
     88                raise ClientSecretsException(
     89                    "Failed to decode secret {}".format(string_key)
     90                )
    8791            if key in (Secrets.LEASE_CANCEL, Secrets.LEASE_RENEW) and len(value) != 32:
    8892                raise ClientSecretsException("Lease secrets must be 32 bytes long")
     
    9296    if result.keys() != required_secrets:
    9397        raise ClientSecretsException(
    94             "Expected {} secrets, got {}".format(required_secrets, result.keys())
     98            "Expected {} in X-Tahoe-Authorization headers, got {}".format(
     99                [r.value for r in required_secrets], list(result.keys())
     100            )
    95101        )
    96102    return result
     
    117123                try:
    118124                    # Check Authorization header:
     125                    try:
     126                        auth_header = request.requestHeaders.getRawHeaders(
     127                            "Authorization", [""]
     128                        )[0].encode("utf-8")
     129                    except UnicodeError:
     130                        raise _HTTPError(http.BAD_REQUEST, "Bad Authorization header")
    119131                    if not timing_safe_compare(
    120                         request.requestHeaders.getRawHeaders("Authorization", [""])[
    121                             0
    122                         ].encode("utf-8"),
     132                        auth_header,
    123133                        swissnum_auth_header(self._swissnum),
    124134                    ):
    125                         raise _HTTPError(http.UNAUTHORIZED)
     135                        raise _HTTPError(
     136                            http.UNAUTHORIZED, "Wrong Authorization header"
     137                        )
    126138
    127139                    # Check secrets:
     
    131143                    try:
    132144                        secrets = _extract_secrets(authorization, required_secrets)
    133                     except ClientSecretsException:
    134                         raise _HTTPError(http.BAD_REQUEST)
     145                    except ClientSecretsException as e:
     146                        raise _HTTPError(http.BAD_REQUEST, str(e))
    135147
    136148                    # Run the business logic:
     
    273285    """
    274286
    275     def __init__(self, code: int):
     287    def __init__(self, code: int, body: Optional[str] = None):
     288        Exception.__init__(self, (code, body))
    276289        self.code = code
     290        self.body = body
    277291
    278292
     
    500514        """Handle ``_HTTPError`` exceptions."""
    501515        request.setResponseCode(failure.value.code)
    502         return b""
     516        if failure.value.body is not None:
     517            return failure.value.body
     518        else:
     519            return b""
    503520
    504521    @app.handle_errors(CDDLValidationError)
Note: See TracChangeset for help on using the changeset viewer.