Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
92 changes: 87 additions & 5 deletions peps/pep-0748.rst
Original file line number Diff line number Diff line change
Expand Up @@ -252,6 +252,9 @@ backwards-compatibility purposes, new fields are only appended to these objects.
Existing fields will never be removed, renamed, or reordered. They are split
between client and server to minimize API confusion.

Client Configuration
^^^^^^^^^^^^^^^^^^^^

The ``TLSClientConfiguration`` class would be defined by the following code:

.. code-block:: python
Expand All @@ -273,7 +276,7 @@ The ``TLSClientConfiguration`` class would be defined by the following code:
inner_protocols: Sequence[NextProtocol | bytes] | None = None,
lowest_supported_version: TLSVersion | None = None,
highest_supported_version: TLSVersion | None = None,
trust_store: TrustStore | None = None,
trust_store: TrustStore = TrustStore.system(),
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I remember now why we had None here before: we wanted to avoid creating a shared default object in the API which should be immutable/comparable. So I think we need something else here:

  • A sentinel object (we deliberately chose not to do this IIRC)
  • Do not define the default, and specify that a missing TrustStore should default to the system trust store. This is my preference.

) -> None:
if inner_protocols is None:
inner_protocols = []
Expand Down Expand Up @@ -305,12 +308,87 @@ The ``TLSClientConfiguration`` class would be defined by the following code:
def highest_supported_version(self) -> TLSVersion | None:
return self._highest_supported_version

@property
def trust_store(self) -> TrustStore:
return self._trust_store

A ``trust_store`` is mandatory and is used to validate the server certificates.
It uses the system's trust store by default. Insecure connections are only
possible via the :ref:`insecure` module.
Comment on lines +316 to +317
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
It uses the system's trust store by default. Insecure connections are only
possible via the :ref:`insecure` module.
It uses the system's trust store by default. Insecure connections with
server authentication disabled are only possible via the :ref:`insecure` module.


When ``certificate_chain`` is set, it is a single signing chain comprising a
leaf client certificate including its corresponding private key and optionally a
list of intermediate certificates. These certificates will be offered to the
server during the handshake if required.

Server Configuration
^^^^^^^^^^^^^^^^^^^^

The ``TLSServerConfiguration`` class would be defined by the following code:

.. code-block:: python

class TLSServerConfiguration:
__slots__ = (
"_certificate_chain",
"_ciphers",
"_inner_protocols",
"_lowest_supported_version",
"_highest_supported_version",
"_trust_store",
)

def __init__(
self,
certificate_chain: Sequence[SigningChain],
ciphers: Sequence[CipherSuite] | None = None,
inner_protocols: Sequence[NextProtocol | bytes] | None = None,
lowest_supported_version: TLSVersion | None = None,
highest_supported_version: TLSVersion | None = None,
trust_store: TrustStore | None = None,
) -> None:
if inner_protocols is None:
inner_protocols = []

self._certificate_chain = certificate_chain
self._ciphers = ciphers
self._inner_protocols = inner_protocols
self._lowest_supported_version = lowest_supported_version
self._highest_supported_version = highest_supported_version
self._trust_store = trust_store

@property
def certificate_chain(self) -> Sequence[SigningChain]:
return self._certificate_chain

@property
def ciphers(self) -> Sequence[CipherSuite | int] | None:
return self._ciphers

@property
def inner_protocols(self) -> Sequence[NextProtocol | bytes]:
return self._inner_protocols

@property
def lowest_supported_version(self) -> TLSVersion | None:
return self._lowest_supported_version

@property
def highest_supported_version(self) -> TLSVersion | None:
return self._highest_supported_version

@property
def trust_store(self) -> TrustStore | None:
return self._trust_store

The ``TLSServerConfiguration`` object is similar to the client one, except that
it takes a ``Sequence[SigningChain]`` as the ``certificate_chain`` parameter.
Server authentication is mandatory, at least one signing chain comprising a leaf
server certificate including its corresponding private key and optionally a list
of intermediate certificates. It is possible to set more than a single signing
chain to support multiple virtual hosts.
Comment on lines +384 to +387
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Server authentication is mandatory, at least one signing chain comprising a leaf
server certificate including its corresponding private key and optionally a list
of intermediate certificates. It is possible to set more than a single signing
chain to support multiple virtual hosts.
Server authentication is mandatory, so the configuration must include
at least one signing chain comprising a leaf server certificate including
its corresponding private key and optionally a list of intermediate
certificates. It is possible to set more than a single signing chain to
support multiple virtual hosts. Insecure connections with server
authentication disabled are only possible via the :ref:`_insecure` module.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually, we should specify that implementations should raise a ValueError when providing an empty Sequence for the signing chain.


A ``trust_store`` is optional. Setting one enables client authentication and
uses the trust store to validate the client certificates. Leaving it ``None``
disables client authentication.

Context
~~~~~~~
Expand Down Expand Up @@ -1072,8 +1150,10 @@ The definitions of the errors are below:


class ConfigurationError(TLSError):
"""An special exception that implementations can use when the provided
configuration uses features not supported by that implementation."""
"""A special exception that implementations can use when the provided
configuration uses features not supported by that implementation. Do not
use this exception when the provided configuration is invalid, use
standard exceptions instead."""


Certificates
Expand Down Expand Up @@ -1440,6 +1520,8 @@ Note that this function only needs to verify that supported constructors were
used for the certificates, private keys, and trust store. It does not need to
parse or retrieve the objects to validate them further.

.. _insecure:

Insecure Usage
--------------

Expand Down
Loading