Additional Refactoring Operations
Relevant source files
The following files were used as context for generating this wiki page:
The rope library provides a suite of advanced refactoring operations designed to automate complex code transformations safely. Beyond basic renaming, these operations include moving elements across scopes, extracting logic into functions or variables, inlining existing definitions, and structural restructurings based on pattern matching.
These operations leverage the library's core strengths in AST analysis and occurrence tracking to ensure that changes are applied consistently across a project. They often involve complex logic for handling imports, scope resolution, and maintaining code semantics during transformations.
Sources: rope/refactor/move.py, rope/refactor/extract.py, rope/refactor/inline.py, rope/refactor/restructure.py
Move Refactoring
The Move refactoring system allows for relocating modules, global classes/functions, and methods. It uses a factory pattern to instantiate the appropriate mover based on the selection at a specific offset.
Components and Architecture
create_move(): A factory function that determines whether the user is attempting to move a module, a global object, or a class method.MoveMethod: Relocates a method to a destination class. It creates the new method in the destination and modifies the original method to act as a delegate.MoveGlobal: Moves functions or classes to a different module, updating all references and managing necessary imports.MoveModule: Moves a Python module or package to a new location in the file system and updates all import statements across the project.
The diagram shows the decision logic used by the Move factory to select the specific refactoring class.
Sources: rope/refactor/move.py:34-60
Move Method Logic
When moving a method, the system calculates changes for both the source (old class) and the destination (new class). The old method is typically replaced by a call to the new location.
Sources: rope/refactor/move.py:63-100
Extract Refactoring
Extracting logic is split into two primary operations: ExtractMethod and ExtractVariable. These share a common base that handles range selection and AST validation.
Extraction Types
| Operation | Purpose | Key Constraints |
|---|---|---|
| Extract Method | Moves a block of statements into a new function/method. | Only one return statement allowed; no yield statements. |
| Extract Variable | Replaces an expression with a variable assignment. | Must be a single line; replaces occurrences of the expression. |
Sources: rope/refactor/extract.py:80-109, rope/refactor/extract.py:377-400
Extraction Flow
The sequence shows the process of identifying code blocks, finding similar instances if requested, and applying the replacement logic.
Sources: rope/refactor/extract.py:236-258
Inline Refactoring
Inlining is the inverse of extraction. It replaces a call or variable reference with its underlying definition.
InlineMethod: Replaces function calls with the function body, handling parameter mapping and potential name conflicts using unique prefixes.InlineVariable: Replaces variable usages with the expression assigned to that variable.InlineParameter: Inlines a parameter's default value into the function body.
Sources: rope/refactor/inline.py:65-95, rope/refactor/inline.py:270-285
Conflict Resolution in Inlining
If a variable name in the guest (inlined) code conflicts with a name in the host code, rope generates a unique prefix (e.g., __0__) to rename the guest variables before insertion.
Sources: rope/refactor/inline.py:465-485
Restructure and Use Function
These operations provide higher-level structural changes.
Restructure
Restructure uses pattern matching to transform code. It allows developers to define a pattern and a goal using wildcards (e.g., ${pyobject}).
Sources: rope/refactor/restructure.py:7-70
Use Function
UseFunction specifically searches for code blocks that match the body of a global function and replaces them with a call to that function.
UseFunction relies on the Restructure engine to identify and replace code blocks that could be served by an existing function.
Sources: rope/refactor/usefunction.py:73-95
Import Management
Most refactoring operations rely on ImportTools and ImportOrganizer to maintain the validity of the code after transformations.
organize_imports: Removes unused imports, removes duplicates, and sorts statements.relatives_to_absolutes: Converts relative import paths to absolute ones.add_import: Intelligently adds a new import statement while adhering to preferred styles (e.g.,import modulevsfrom module import name).
Sources: rope/refactor/importutils/init.py:23-65, rope/refactor/importutils/init.py:228-265
Summary
The additional refactoring operations in rope provide the mechanism for evolving codebase architecture. By combining precise AST analysis with occurrence tracking and automated import management, the library allows for complex changes—such as moving methods between classes or restructuring code via patterns—while maintaining functional integrity and minimizing manual cleanup.
Sources: rope/refactor/init.py:7-40