Skip to content

Nonsensical exception message when calling __new__ on non-instaniable objects #78465

Closed

Description

@pppery
mannequin
BPO 34284
Nosy @ncoghlan, @serhiy-storchaka, @pppery, @VadimPushtaev
PRs
  • bpo-34284: Nonsensical exception message when calling __new__ on non-instantiable objects #8576
  • Note: these values reflect the state of the issue at the time it was migrated and might not reflect the current state.

    Show more details

    GitHub fields:

    assignee = None
    closed_at = None
    created_at = <Date 2018-07-30.20:05:01.213>
    labels = ['interpreter-core', 'type-bug', 'library', '3.11']
    title = 'Nonsensical exception message when calling `__new__` on non-instaniable objects'
    updated_at = <Date 2022-01-28.19:35:48.358>
    user = 'https://github.com/pppery'

    bugs.python.org fields:

    activity = <Date 2022-01-28.19:35:48.358>
    actor = 'iritkatriel'
    assignee = 'none'
    closed = False
    closed_date = None
    closer = None
    components = ['Interpreter Core', 'Library (Lib)']
    creation = <Date 2018-07-30.20:05:01.213>
    creator = 'ppperry'
    dependencies = []
    files = []
    hgrepos = []
    issue_num = 34284
    keywords = ['patch']
    message_count = 18.0
    messages = ['322688', '322694', '322695', '322699', '322700', '322703', '322704', '322705', '322715', '322745', '323110', '323113', '323127', '323226', '323240', '323293', '324479', '324513']
    nosy_count = 4.0
    nosy_names = ['ncoghlan', 'serhiy.storchaka', 'ppperry', 'Vadim Pushtaev']
    pr_nums = ['8576']
    priority = 'low'
    resolution = None
    stage = 'patch review'
    status = 'open'
    superseder = None
    type = 'behavior'
    url = 'https://bugs.python.org/issue34284'
    versions = ['Python 3.11']

    Linked PRs

    Activity

    1. pppery commented on Jul 30, 2018

      ppperymannequin
      MannequinAuthor
      > type(sys.flags).__new__(type(sys.flags))
      Traceback (most recent call last):
        File "<pyshell#102>", line 1, in <module>
          type(sys.flags).__new__(type(sys.flags))
      TypeError: tuple.__new__(sys.flags) is not safe, use sys.flags.__new__()

      Ignoring the confusion caused by both the type and the instance being called "sys.flags", this error doesn't make sense. I am using "sys.flags" (the type).__new__, so why is it complaining?

      "type(sys.flags)()" produces the standard "non-instantiable type" error.

      The same behavior also happens for "sys.version_info", but strangely not for any of the other sys constants.

    2. added
      interpreter-core(Objects, Python, Grammar, and Parser dirs)
      stdlibStandard Library Python modules in the Lib/ directory
      type-bugAn unexpected behavior, bug, or error
      on Jul 30, 2018
    3. VadimPushtaev commented on Jul 30, 2018

      VadimPushtaevmannequin
      Mannequin

      I'm trying to do something about this. Let me know if you have some ideas.

    4. VadimPushtaev commented on Jul 30, 2018

      VadimPushtaevmannequin
      Mannequin

      Here is what I learned:

      1. Nothing is wrong with that "tuple.new(sys.flags) is not safe" part. __new__ is deleted from type(sys.flags), so parent's __new__ is called. tuple is indeed a base class for type(sys.flags).

      2. Another part where we recommend to use "sys.flags.new()" doesn't make much sense, so I choose to delete this advice if there is no __new__ in a class.

      3. This second part also may suggest a wrong class to call __new__ from:

      In [1]: from collections import namedtuple

      In [2]: class A(namedtuple('A', 'z')):
      ...: pass
      ...:

      In [3]: object.__new__(A)
      ---------------------------------------------------------------------------

      TypeError                                 Traceback (most recent call last)
      <ipython-input-3-24eacd9ea752> in <module>()
      ----> 1 object.__new__(A)

      TypeError: object.__new__(A) is not safe, use tuple.__new__()

      This should be A.__new__(), not tuple.__new__().

    5. pppery commented on Jul 30, 2018

      ppperymannequin
      MannequinAuthor

      Your PR is not an improvement:

      1. In this case, this will produce the error "tuple.new(sys.flags) is not safe". But I didn't call "tuple.new", I called sys.flags.new, and type(X).new(type(X)) should always be safe
      2. The change in error message for namedtuples (A) isn't related and (B) isn't correct. tuple.__new__(NamedTuple) works, and produces a namedtuple object, so tuple.new is what the error should point to.
    6. pppery commented on Jul 30, 2018

      ppperymannequin
      MannequinAuthor

      Same thing happens for other objects, like type(sys._getframe(0)).__new__(type(sys._getframe_)), and presumably any object that one cannot instantiate by calling

    7. changed the title [-]Nonsensical exception message when calling `__new__` on some sys objects[/-] [+]Nonsensical exception message when calling `__new__` on non-instaniable object[/+] on Jul 30, 2018
    8. VadimPushtaev commented on Jul 31, 2018

      VadimPushtaevmannequin
      Mannequin
      1. In this case, this will produce the error "tuple.__new__(sys.flags) is not safe". But I didn't call "tuple.__new__", I called sys.flags.__new__, and type(X).__new__(type(X)) should always be safe

      Should it? There is no sys.flags.__new__, tuple.__new__ is called and it has different __new__.

      1. The change in error message for namedtuples (A) isn't related and (B) isn't correct. tuple.__new__(NamedTuple) works, and produces a namedtuple object, so tuple.new is what the error should point to.

      I believe you are right about (A), it's not related and should be discussed separately.

    9. changed the title [-]Nonsensical exception message when calling `__new__` on non-instaniable object[/-] [+]Nonsensical exception message when calling `__new__` on some sys objects[/+] on Jul 31, 2018
    10. pppery commented on Jul 31, 2018

      ppperymannequin
      MannequinAuthor

      The error I'm expecting here is "cannot create sys.flags objects". Anything else violates the fact that type(*args) is sugar for:

      result = type.__new__(type, *args)
      if isinstance(result, type):
          result.__init__(*args)

      ("type" in the above snippet is a variable name, not the actual builtin "type")

    11. changed the title [-]Nonsensical exception message when calling `__new__` on some sys objects[/-] [+]Nonsensical exception message when calling `__new__` on non-instaniable objects[/+] on Jul 31, 2018
    12. 13 remaining items

    13. transferred this issue fromon Apr 10, 2022
    14. added a commit that references this issue on Jun 26, 2025
    15. serhiy-storchaka commented on Jun 26, 2025

      @serhiy-storchaka
      Member

      See also bpo-43916/gh-88082 which introduced the Py_TPFLAGS_DISALLOW_INSTANTIATION flag and added multiple tests.

      The error message was still nonsensical. #135981 fixes it.

    16. added a commit that references this issue on Jun 27, 2025
    17. added a commit that references this issue on Jun 27, 2025
    18. added a commit that references this issue on Jun 27, 2025
    19. added 3 commits that reference this issue on Jun 27, 2025
    20. added a commit that references this issue on Jul 11, 2025
    21. added a commit that references this issue on Jul 12, 2025
    22. added a commit that references this issue on Aug 4, 2025
    23. added a commit that references this issue on Aug 19, 2025
    Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

    Metadata

    Metadata

    Assignees

    No one assigned

      Labels

      3.11only security fixesinterpreter-core(Objects, Python, Grammar, and Parser dirs)stdlibStandard Library Python modules in the Lib/ directorytype-bugAn unexpected behavior, bug, or error

      Projects

      No projects

        Milestone

        No milestone

        Relationships

        None yet

        Development

        No branches or pull requests

        Issue actions