Skip to content

symfonic.diagnostics.inspection.legacy_imports

legacy_imports

Legacy import paths and the layer that now owns the behaviour.

Every row here is still supported: the refactor vacated no import path, and guide 22 says so as policy rather than intention. So a match is not a defect — it is the answer to "where did this move to?", which is the question an adopter opens a migration guide to ask and then has to answer 90 times by hand.

Rows are keyed on the imported name plus the modules it may legitimately be imported from, because the same name is reachable through a package re-export and through the module that defines it, and both spellings appear in adopter code. Only symbols verified to exist on both sides are listed; a row whose replacement did not exist would send an adopter to a broken import.

LegacyImport dataclass

LegacyImport(name: str, modules: frozenset[str], replacement: str, domain: str, reason: str, severity: Severity = Severity.INFO)

One legacy symbol, and where its behaviour now lives.

replacement_for

replacement_for(ref: ImportRef) -> LegacyImport | None

Return the registered replacement for ref, or None.

Source code in src/symfonic/diagnostics/inspection/legacy_imports.py
def replacement_for(ref: ImportRef) -> LegacyImport | None:
    """Return the registered replacement for *ref*, or ``None``."""
    if ref.name is None:
        return None
    for row in _BY_NAME.get(ref.name, ()):
        if ref.module in row.modules:
            return row
    return None