1515from ._exceptions import ChannelClosedError
1616from ._generic import ChannelMessageT
1717from ._receiver import Receiver , ReceiverStoppedError
18- from ._sender import Sender , SenderError
18+ from ._sender import Sender , SenderClosedError , SenderError
1919
2020_logger = logging .getLogger (__name__ )
2121
@@ -327,6 +327,9 @@ def __init__(self, channel: Anycast[_T], /) -> None:
327327 self ._channel : Anycast [_T ] = channel
328328 """The channel that this sender belongs to."""
329329
330+ self ._closed : bool = False
331+ """Whether the sender is closed."""
332+
330333 @override
331334 async def send (self , message : _T , / ) -> None :
332335 """Send a message across the channel.
@@ -343,7 +346,11 @@ async def send(self, message: _T, /) -> None:
343346 SenderError: If the underlying channel was closed.
344347 A [ChannelClosedError][frequenz.channels.ChannelClosedError] is
345348 set as the cause.
349+ SenderClosedError: If this sender was closed.
346350 """
351+ if self ._closed :
352+ raise SenderClosedError (self )
353+
347354 # pylint: disable=protected-access
348355 if self ._channel ._closed :
349356 raise SenderError ("The channel was closed" , self ) from ChannelClosedError (
@@ -367,6 +374,16 @@ async def send(self, message: _T, /) -> None:
367374 self ._channel ._recv_cv .notify (1 )
368375 # pylint: enable=protected-access
369376
377+ @override
378+ def close (self ) -> None :
379+ """Close this sender.
380+
381+ After closing, the sender will not be able to send any more messages. Any
382+ attempt to send a message through a closed sender will raise a
383+ [SenderError][frequenz.channels.SenderError].
384+ """
385+ self ._closed = True
386+
370387 def __str__ (self ) -> str :
371388 """Return a string representation of this sender."""
372389 return f"{ self ._channel } :{ type (self ).__name__ } "
0 commit comments