python-rope / rope

a python refactoring library
GNU Lesser General Public License v3.0
1.96k stars 164 forks source link

Inline method refactoring passes the wrong parameter to the inlined function body #760

Open researcher175 opened 8 months ago

researcher175 commented 8 months ago

Inline method refactoring passes the wrong parameter to the inlined function body

Steps to reproduce the behavior:

  1. Code before refactoring:

structure

-- en ---- __init.py__ ---- parsers.py -- test ---- __init.py__ ---- test.py

en.__init.py__:

class Parser(object):
    def __init__(self, lexicon={}, default=("NN", "NNP", "CD"), language=None):
        self.lexicon = lexicon
        self.default = default
        self.language = language

    def parse(self, s, tokenize=True, tags=True, chunks=True, relations=False, lemmata=False, encoding="utf-8", **kwargs):
        pass

parser = Parser(
    default=("NN", "NNP", "CD"),
    language="en"
)

def parse(s, *args, **kwargs):
    return parser.parse(s, *args, **kwargs)

en.parsers.py:

from abc import abstractmethod
from en import parse as pattern_parse

class BaseParser(object):
    @abstractmethod
    def parse(self, text):
        return

class PatternParser(BaseParser):

    def parse(self, text):
        return pattern_parse(text)

test.test.py:

import unittest

from en import parse as pattern_parse
import en.parsers as parsers

class TestPatternParser(unittest.TestCase):

    def setUp(self):
        self.parser = PatternParser()
        self.text = "And now for something completely different."

    def test_parse(self):
        self.assertEqual(self.parser.parse(self.text), pattern_parse(self.text))
  1. Apply the Inline Method refactoring to 'PatternParser.parse'

  2. Expected code after refactoring:

en.__init.py__:

class Parser(object):
    def __init__(self, lexicon={}, default=("NN", "NNP", "CD"), language=None):
        self.lexicon = lexicon
        self.default = default
        self.language = language

    def parse(self, s, tokenize=True, tags=True, chunks=True, relations=False, lemmata=False, encoding="utf-8", **kwargs):
        pass

parser = Parser(
    default=("NN", "NNP", "CD"),
    language="en"
)

def parse(s, *args, **kwargs):
    return parser.parse(s, *args, **kwargs)

en.parsers.py:

from abc import abstractmethod
from en import parse as pattern_parse

class BaseParser(object):
    @abstractmethod
    def parse(self, text):
        return

class PatternParser(BaseParser):

    pass

test.test.py:

import unittest

from en import parse as pattern_parse
import en.parsers as parsers

class TestPatternParser(unittest.TestCase):

    def setUp(self):
        self.parser = PatternParser()
        self.text = "And now for something completely different."

    def test_parse(self):
        self.assertEqual(pattern_parse(self.text), pattern_parse(self.text))

The transformation changes the attribute that is passed to the original function. The result is: self.assertEqual(pattern_parse(0self.parser.text), pattern_parse(self.text)) Causing test fail