Enhanced version of the builtin reload function. superreload remembers objects previously in the module, and - upgrades the class dictionary of every old class in the module - upgrades the code object of every old function and method - clears the module's namespace before reloading
(
module, reload=reload, old_objects=None, shell=None, import_from_tracker=None
)
| 545 | |
| 546 | |
| 547 | def superreload( |
| 548 | module, reload=reload, old_objects=None, shell=None, import_from_tracker=None |
| 549 | ): |
| 550 | """Enhanced version of the builtin reload function. |
| 551 | |
| 552 | superreload remembers objects previously in the module, and |
| 553 | |
| 554 | - upgrades the class dictionary of every old class in the module |
| 555 | - upgrades the code object of every old function and method |
| 556 | - clears the module's namespace before reloading |
| 557 | |
| 558 | """ |
| 559 | if old_objects is None: |
| 560 | old_objects = {} |
| 561 | |
| 562 | # collect old objects in the module |
| 563 | for name, obj in list(module.__dict__.items()): |
| 564 | if not append_obj(module, old_objects, name, obj): |
| 565 | continue |
| 566 | key = (module.__name__, name) |
| 567 | try: |
| 568 | old_objects.setdefault(key, []).append(weakref.ref(obj)) |
| 569 | except TypeError: |
| 570 | pass |
| 571 | |
| 572 | # reload module |
| 573 | try: |
| 574 | # clear namespace first from old cruft |
| 575 | old_dict = module.__dict__.copy() |
| 576 | old_name = module.__name__ |
| 577 | module.__dict__.clear() |
| 578 | module.__dict__["__name__"] = old_name |
| 579 | module.__dict__["__loader__"] = old_dict["__loader__"] |
| 580 | except (TypeError, AttributeError, KeyError): |
| 581 | pass |
| 582 | |
| 583 | try: |
| 584 | module = reload(module) |
| 585 | except: |
| 586 | # restore module dictionary on failed reload |
| 587 | module.__dict__.update(old_dict) |
| 588 | raise |
| 589 | |
| 590 | for name, new_obj in list(module.__dict__.items()): |
| 591 | key = (module.__name__, name) |
| 592 | if key not in old_objects: |
| 593 | # here 'shell' acts both as a flag and as an output var |
| 594 | imports_froms = ( |
| 595 | import_from_tracker.imports_froms if import_from_tracker else None |
| 596 | ) |
| 597 | symbol_map = import_from_tracker.symbol_map if import_from_tracker else None |
| 598 | if ( |
| 599 | shell is None |
| 600 | or name == "Enum" |
| 601 | or not append_obj(module, old_objects, name, new_obj, True) |
| 602 | or ( |
| 603 | imports_froms |
| 604 | and module.__name__ in imports_froms |
no test coverage detected
searching dependent graphs…