The standard pattern to create a sentinel in Python is
 
>>> Unset = object()
 
While this is often good enough, it has some shortcomings:
 
- repr(Unset) is unhelpful: <object at 0x1ded9911b60>
 
- copy/deepcopy create a copy of the sentinel object, which can lead to surprising results such as:
  >>> d = {'val': Unset}
  >>> d['val'] is Unset
  True
  >>> d2 = copy.deepcopy(d)
  >>> d2['val'] is Unset
  False
 
- The code "Unset = object()" is quite obscure for people not familiar with the sentinel pattern.
 
 
I propose to provide a sentinel() factory function so that
 
>>> Unset = sentinel("Unset")
>>> repr(unset)
<Unset>
>>> copy.copy(Unset) is Unset
True
>>> copy.deepcopy(Unset) is Unset
True
 
 
A simple implementation would be something like
 
def sentinel(name):
    return type(name, (), {
        '__repr__': lambda self: f"<{self.__class__.__name__}>",
        '__copy__': lambda self: self,
        '__deepcopy__': lambda self, memo: self,
    })
 
Likely, the implementation should be refined a bit more.
 
 
While it's not rocket science, getting sentinels correct is cumbersome for end users. Providing such a function in the standard library is only a minor maintainance burden, but a significant help for users working with sentinels.
 
Thanks for your consideration!
Tim