ipython / ipython

Official repository for IPython itself. Other repos in the IPython organization contain things like the website, documentation builds, etc.
https://ipython.readthedocs.org
BSD 3-Clause "New" or "Revised" License
16.28k stars 4.44k forks source link

RuntimeError on first call to vars(posix) #14541

Open schuelermine opened 1 day ago

schuelermine commented 1 day ago

Reproduction

  1. Launch ipython in a terminal on Linux
  2. Type import posix
  3. Type vars(posix)

Observation

Python 3.12.5 (main, Aug  6 2024, 19:08:49) [GCC 13.3.0]
Type 'copyright', 'credits' or 'license' for more information
IPython 8.26.0 -- An enhanced Interactive Python. Type '?' for help.

In [1]: import posix

In [2]: vars(posix)
Out[2]: ---------------------------------------------------------------------------
RuntimeError                              Traceback (most recent call last)
File /nix/store/r39j2wlg58cb3b4iz9x8cbh18icrlcrv-python3.12-ipython-8.26.0/lib/python3.12/site-packages/IPython/core/formatters.py:711, in PlainTextFormatter.__call__(self, obj)
    704 stream = StringIO()
    705 printer = pretty.RepresentationPrinter(stream, self.verbose,
    706     self.max_width, self.newline,
    707     max_seq_length=self.max_seq_length,
    708     singleton_pprinters=self.singleton_printers,
    709     type_pprinters=self.type_printers,
    710     deferred_pprinters=self.deferred_printers)
--> 711 printer.pretty(obj)
    712 printer.flush()
    713 return stream.getvalue()

File /nix/store/r39j2wlg58cb3b4iz9x8cbh18icrlcrv-python3.12-ipython-8.26.0/lib/python3.12/site-packages/IPython/lib/pretty.py:394, in RepresentationPrinter.pretty(self, obj)
    391 for cls in _get_mro(obj_class):
    392     if cls in self.type_pprinters:
    393         # printer registered in self.type_pprinters
--> 394         return self.type_pprinters[cls](obj, self, cycle)
    395     else:
    396         # deferred printer
    397         printer = self._in_deferred_types(cls)

File /nix/store/r39j2wlg58cb3b4iz9x8cbh18icrlcrv-python3.12-ipython-8.26.0/lib/python3.12/site-packages/IPython/lib/pretty.py:695, in _dict_pprinter_factory.<locals>.inner(obj, p, cycle)
    693 p.begin_group(step, start)
    694 keys = obj.keys()
--> 695 for idx, key in p._enumerate(keys):
    696     if idx:
    697         p.text(',')

File /nix/store/r39j2wlg58cb3b4iz9x8cbh18icrlcrv-python3.12-ipython-8.26.0/lib/python3.12/site-packages/IPython/lib/pretty.py:297, in PrettyPrinter._enumerate(self, seq)
    295 def _enumerate(self, seq):
    296     """like enumerate, but with an upper limit on the number of items"""
--> 297     for idx, x in enumerate(seq):
    298         if self.max_seq_length and idx >= self.max_seq_length:
    299             self.text(',')

RuntimeError: dictionary changed size during iteration

Notes

Works correctly on subsequent vars(posix) calls, and if autocomplete has been used to suggest posix attributes before.

Environment

IPython: 8.26.0, obtained from nixpkgs 5633bcff0c6162b9e4b5f1264264611e950c8ec7 under python3Packages.ipython Underlying Python: 3.12.5 (main, Aug 6 2024, 19:08:49) [GCC 13.3.0] OS: NixOS 24.11.20241009.5633bcf (Vicuna), built from nixpkgs 5633bcff0c6162b9e4b5f1264264611e950c8ec7 Hardware: Lenovo Legion Y530-15ICH, Intel(R) Core(TM) i5-8300H (8) @ 4.00 GHz, 25072803840 bytes of memory

ivanov commented 1 day ago

confirming the bug. The issue is that __builtins__ ends up not being there in the keys on the first call and get added in the middle of it.

schuelermine commented 1 day ago

Why does [*vars(posix).items()] not result in the same error?