예제 #1
0
 def test_general_to_from(self):
     old = parse_imports("import pathlib")
     new = parse_imports("from pathlib import Path")
     assert (
         str(pi.ImportedNames.compare(old, new))
         == "New imported ``Path'' from ``pathlib'' (previously, full ``pathlib'' was imported)"
     )
예제 #2
0
 def test_from_to_general(self):
     old = parse_imports("from pathlib import Path")
     new = parse_imports("import pathlib")
     assert (
         str(pi.ImportedNames.compare(old, new))
         == "New imported package ``pathlib'' (previously, only ``Path'' was imported from ``pathlib'')"
     )
예제 #3
0
 def test_message_removed_fromimport_module(self):  # pylint: disable=invalid-name
     old = parse_imports("from module import one")
     new = parse_imports("")
     assert (
         str(pi.ImportedNames.compare(old, new))
         == "Removed import of ``one'' from removed ``module''"
     )
예제 #4
0
 def test_message_new_import(self):
     old = parse_imports("")
     new_one = parse_imports("import one")
     new_more = parse_imports("import one, two")
     assert str(pi.ImportedNames.compare(old, new_one)) == "New imported package ``one''"
     assert (
         str(pi.ImportedNames.compare(old, new_more)) == "New imported packages ``one'', ``two''"
     )
예제 #5
0
    def test_external_name_usage(self):
        old = self._make_summary("def function(): return some_path")
        new = self._make_summary("def function(): return pathy.join(lst)")
        old_imports = parse_imports("from os import path")
        new_imports = parse_imports("from os import path as pathy")

        pyfference = pf.pyff_function(old, new, old_imports, new_imports)
        assert len(pyfference.implementation) == 2
예제 #6
0
    def test_new_importfrom_module(self):
        old = parse_imports("from os import path")
        new = parse_imports("from module import name")

        change = pi.ImportedNames.compare(old, new)
        assert len(change.fromimports.new) == 1
        assert len(change.fromimports.new_modules) == 1
        assert change.fromimports.new_modules == {"module"}
예제 #7
0
 def test_message_new_fromimport(self):
     old = parse_imports("from module import one")
     new_one = parse_imports("from module import one, two")
     new_more = parse_imports("from module import one, two, three")
     assert str(pi.ImportedNames.compare(old, new_one)) == "New imported ``two'' from ``module''"
     assert (
         str(pi.ImportedNames.compare(old, new_more))
         == "New imported ``three'', ``two'' from ``module''"
     )
예제 #8
0
    def test_example_04(self):
        old_import = parse_imports("from pathlib import Path")
        new_import = parse_imports("import pathlib")

        old = ast.parse("Path.home()")
        new = ast.parse("pathlib.Path.home()")

        change = ps.find_external_name_matches(old, new, old_import,
                                               new_import)
        assert change is not None
예제 #9
0
    def test_message_remove_import(self):
        old = parse_imports("import one, two")
        new_one = parse_imports("import one")
        new_more = parse_imports("")

        assert str(pi.ImportedNames.compare(old, new_one)) == "Removed import of package ``two''"
        assert (
            str(pi.ImportedNames.compare(old, new_more))
            == "Removed import of packages ``one'', ``two''"
        )  # pylint: disable=line-too-long
예제 #10
0
    def test_no_external(self):
        old_imports = parse_imports(
            "import os; from ast import Name; import sys as system")
        new_imports = parse_imports("from os import path; import unittest")

        old_function = ast.parse("def function(a, b, c): return a if b else c")
        new_function = ast.parse(
            "def function(a, b, c): temp = a / c; return temp if b else None")

        assert pf.compare_import_usage(old_function, new_function, old_imports,
                                       new_imports) is None
예제 #11
0
    def test_removed_import(self):
        old = parse_imports("import os; import sys")
        old_with_comma = parse_imports("import os, sys")
        new = parse_imports("import os")

        change = pi.ImportedNames.compare(old, new)
        assert len(change.removed_imports) == 1
        assert max(change.removed_imports).canonical_name == "sys"

        change = pi.ImportedNames.compare(old_with_comma, new)
        assert len(change.removed_imports) == 1
        assert max(change.removed_imports).canonical_name == "sys"
예제 #12
0
 def test_message_new_fromimport_module(self):  # pylint: disable=invalid-name
     old = parse_imports("")
     new_one = parse_imports("from module import one")
     new_more = parse_imports("from module import one, two")
     assert (
         str(pi.ImportedNames.compare(old, new_one))
         == "New imported ``one'' from new ``module''"
     )
     assert (
         str(pi.ImportedNames.compare(old, new_more))
         == "New imported ``one'', ``two'' from new ``module''"
     )
예제 #13
0
    def test_appeared(self):
        old_imports = parse_imports(
            "import os; from ast import Name; import sys as system")
        new_imports = parse_imports("import os; import unit")

        old_function = ast.parse(
            "def function(a, b, c): return os.path.join([a, b, c])")
        new_function = ast.parse(
            "def function(a, b, c): unit.method(); return os.path.join([a,b,c])"
        )

        change = pf.compare_import_usage(old_function, new_function,
                                         old_imports, new_imports)
        assert change.appeared == {"unit"}
예제 #14
0
    def test_removed_importfrom(self):
        old = parse_imports("from os import path; from os import environ")
        old_with_comma = parse_imports("from os import path, environ")
        new = parse_imports("from os import path")

        change = pi.ImportedNames.compare(old, new)
        assert len(change.fromimports.removed) == 1
        assert not change.fromimports.removed_modules
        assert change.fromimports.removed["os"].pop().canonical_name == "os.environ"

        change_with_comma = pi.ImportedNames.compare(old_with_comma, new)
        assert len(change_with_comma.fromimports.removed) == 1
        assert not change.fromimports.removed_modules
        assert change_with_comma.fromimports.removed["os"].pop().canonical_name == "os.environ"
예제 #15
0
    def test_gone(self):
        old_imports = parse_imports(
            "import os; from ast import Name; import sys as system")
        new_imports = parse_imports(
            "from os.path import join; import unittest")

        old_function = ast.parse(
            "def function(a, b, c): return os.path.join([a, b, c])")
        new_function = ast.parse(
            "def function(a, b, c): return join([a, b, c])")

        change = pf.compare_import_usage(old_function, new_function,
                                         old_imports, new_imports)
        assert change.appeared == {"join"}
        assert change.gone == {"os"}
예제 #16
0
 def _check_fqn(imports, code, expected_subs, expected_qualified_code):
     imports = parse_imports(imports)
     qualifier = ps.FullyQualifyNames(imports)
     original_ast = ast.parse(code)
     qualified_ast = qualifier.visit(original_ast)
     assert qualifier.substitutions == expected_subs
     assert ast.dump(
         ast.parse(expected_qualified_code)) == ast.dump(qualified_ast)
예제 #17
0
    def test_different_statement_count(self):
        old = self._make_summary("def function(): do_some_useless_stuff();")
        new = self._make_summary(
            "def function(): do_some_useless_stuff(); return None")
        no_imports = parse_imports("")

        pyfference = pf.pyff_function(old, new, no_imports, no_imports)
        assert len(pyfference.implementation) == 1
예제 #18
0
    def test_external_names(self):
        change = ps.pyff_statement(
            ast.parse("p = path.join(lst)"),
            ast.parse("p = pathy.join(lst)"),
            pi.ImportedNames(),
            pi.ImportedNames(),
        )
        # alone, the statements are different
        assert change.semantically_different()

        another_change = ps.pyff_statement(
            ast.parse("p = path.join(lst)"),
            ast.parse("p = pathy.join(lst)"),
            parse_imports("from os import path"),
            parse_imports("from os import path as pathy"),
        )
        # with information about imports, we can deduce the statements are semantically equivalent
        assert not another_change.semantically_different()
예제 #19
0
 def test_sanity(self):
     old = parse_imports("import four; from five import six, seven")
     new = parse_imports("import one, two, three; "
                         "from module import fst, snd; "
                         "from five import seven; "
                         "from eight import nine")
     imports = pi.ImportedNames.compare(old, new)
     functions = pf.FunctionsPyfference(
         new={
             "function":
             pf.FunctionSummary("function",
                                node=Mock(spec=ast.FunctionDef)),
             "funktion":
             pf.FunctionSummary("funktion",
                                node=Mock(spec=ast.FunctionDef)),
         },
         changed={
             "name":
             pf.FunctionPyfference("name",
                                   old_name="old_name",
                                   implementation=set())
         },
         removed={},
     )
     classes = pc.ClassesPyfference(new={"NewClass2", "NewClass"},
                                    changed=set())
     change = pm.ModulePyfference(imports, classes, functions)
     assert change.classes is not None
     assert change.functions is not None
     assert change.imports is not None
     assert str(change) == (
         "Removed import of package ``four''\n"
         "New imported packages ``one'', ``three'', ``two''\n"
         "Removed import of ``six'' from ``five''\n"
         "New imported ``fst'', ``snd'' from new ``module''\n"
         "New imported ``nine'' from new ``eight''\n"
         "New NewClass\n"
         "New NewClass2\n"
         "Function ``old_name'' renamed to ``name''\n"
         "New function ``function''\n"
         "New function ``funktion''")
     assert change.simplify() is change
예제 #20
0
    def test_import(self):
        package_imports = parse_imports("import os")
        alias_imports = parse_imports("import os as operatingsystem")

        parse_pkg = lambda: ast.parse(
            "def function(): return os.path.join([1, 2, 3])")
        parse_alias = lambda: ast.parse(
            "def function(): return operatingsystem.path.join([1, 2, 3])")

        assert (ps.find_external_name_matches(
            parse_pkg(), parse_pkg(), package_imports, package_imports) is
                None)

        changes = ps.find_external_name_matches(parse_pkg(), parse_alias(),
                                                package_imports, alias_imports)
        assert changes is not None
        assert len(changes.changes) == 1
        change = changes.changes.pop()
        assert change.old == "os"
        assert change.new == "operatingsystem"
예제 #21
0
 def test_extract_external_baseclass(self):
     code = "from module import BaseKlass\n" "class Klass(BaseKlass):\n" "    pass"
     names = parse_imports(code)
     extractor = pc.ClassesExtractor(names)
     extractor.visit(ast.parse(code))
     assert len(extractor.classes) == 1
     summary = extractor.classes["Klass"]
     assert (
         str(summary) ==
         "class ``Klass'' derived from imported ``BaseKlass'' with 0 public methods"
     )
예제 #22
0
    def test_import(self):
        imported_names = parse_imports(
            "import package, pkg.module, something as alias")
        package_names = extract_names_from_function(
            "def function(): a = package.function()", imported_names)
        assert package_names == {"package"}

        module_names = extract_names_from_function(
            "def function(): a = pkg.module.attribute + 3", imported_names)
        assert module_names == {"pkg.module"}

        alias_names = extract_names_from_function(
            "def f(): a = alias.C().package + pkg.module.p", imported_names)
        assert alias_names == {"alias", "pkg.module"}
예제 #23
0
    def test_importfrom(self):
        imported_names = parse_imports("from pk import name, other as alias; "
                                       "from pk.mod import other")
        package_names = extract_names_from_function(
            "def function(): a = name()", imported_names)
        assert package_names == {"name"}

        alias_names = extract_names_from_function(
            "def function(): a = alias + 3", imported_names)
        assert alias_names == {"alias"}

        module_names = extract_names_from_function(
            "def function(): a = other(3) + pkg + mod", imported_names)
        assert module_names == {"other"}
예제 #24
0
 def test_extract_local_baseclass(self):
     code = ("import os\n"
             "class BaseKlass:\n"
             "    pass\n"
             "class Klass(BaseKlass):\n"
             "    pass\n")
     names = parse_imports(code)
     extractor = pc.ClassesExtractor(names)
     extractor.visit(ast.parse(code))
     assert len(extractor.classes) == 2
     summary = extractor.classes["Klass"]
     assert (
         str(summary) ==
         "class ``Klass'' derived from local ``BaseKlass'' with 0 public methods"
     )
예제 #25
0
    def test_importfrom(self):
        # package_import = parse_imports("import os.path")
        from_import = parse_imports("from os import path")
        alias_import = parse_imports("from os import path as pathy")

        # parse_pkg = lambda: ast.parse("def f(): return os.path.join([1,2,3])")
        parse_from = lambda: ast.parse("def f(): return path.join([1,2,3])")
        parse_alias = lambda: ast.parse("def f(): return pathy.join([1,2,3])")

        # BUG: We do not detect this
        # package_to_from = ps.find_external_name_matches(parse_pkg(), parse_from(),
        #                                                package_import, from_import)
        # _check_matches(package_to_from, 1, "os.path", "path")

        # BUG: We do not detect this
        # package_to_alias = ps.find_external_name_matches(parse_pkg(), parse_alias(),
        #                                                 package_import, alias_import)
        # _check_matches(package_to_alias, 1, "os.path", "pathy")

        from_to_alias = ps.find_external_name_matches(parse_from(),
                                                      parse_alias(),
                                                      from_import,
                                                      alias_import)
        self._check_matches(from_to_alias, 1, "path", "pathy")
예제 #26
0
 def _check_references(imports, code, references):
     imports = parse_imports(imports)
     qualifier = ps.FullyQualifyNames(imports)
     qualifier.visit(ast.parse(code))
     assert qualifier.references == references
예제 #27
0
 def test_importfrom_alias(self):
     names = parse_imports("from os import path, environ as environment")
     assert len(names) == 2
     assert "path" in names
     assert "environment" in names
예제 #28
0
 def test_importfrom_multiple(self):
     names = parse_imports("from os import path, environ")
     assert len(names) == 2
     assert "path" in names
     assert "environ" in names
예제 #29
0
 def test_importfrom_simple(self):
     names = parse_imports("from os import path")
     assert len(names) == 1
     assert "path" in names
예제 #30
0
 def test_import_alias(self):
     names = parse_imports("import os as operating_system, sys")
     assert len(names) == 2
     assert "operating_system" in names
     assert "sys" in names