在 Python 中映射模块导入以方便重构

发布于 2024-09-16 05:50:47 字数 664 浏览 8 评论 0原文

我有一堆Python模块想要清理、重组和重构(有一些重复的代码,一些未使用的代码......),我想知道是否有一个工具可以制作哪个模块使用哪个其他模块的映射。

理想情况下,我想要一个像这样的地图:

main.py
 -> task_runner.py
  -> task_utils.py
  -> deserialization.py
   -> file_utils.py
 -> server.py
  -> (deserialization.py)
  -> db_access.py

checkup_script.py
re_test.py
main_bkp0.py
unit_tests.py

...这样我就可以知道我可以首先开始移动哪些文件(file_utils.py,db_access.py),哪些文件不被我的 main.py 使用,所以可以被删除等(我实际上正在使用大约 60 个模块)

编写一个执行此操作的脚本可能不会非常复杂(尽管有不同的导入语法来处理),但我我还希望我不是第一个想要这样做的人(如果有人为此制作了一个工具,它可能包括其他简洁的功能,例如告诉我哪些类和函数可能不被使用)。

您知道有哪些工具(甚至简单的脚本)可以帮助代码重组吗?

你知道我想要做的事情有更准确的术语吗?代码重组?

I have a bunch of Python modules I want to clean up, reorganize and refactor (there's some duplicate code, some unused code ...), and I'm wondering if there's a tool to make a map of which module uses which other module.

Ideally, I'd like a map like this:

main.py
 -> task_runner.py
  -> task_utils.py
  -> deserialization.py
   -> file_utils.py
 -> server.py
  -> (deserialization.py)
  -> db_access.py

checkup_script.py
re_test.py
main_bkp0.py
unit_tests.py

... so that I could tell which files I can start moving around first (file_utils.py, db_access.py), which files are not used by my main.py and so could be deleted, etc. (I'm actually working with around 60 modules)

Writing a script that does this probably wouldn't be very complicated (though there are different syntaxes for import to handle), but I'd also expect that I'm not the first one to want to do this (and if someone made a tool for this, it might include other neat features such as telling me which classes and functions are probably not used).

Do you know of any tools (even simple scripts) that assist code reorganization?

Do you know of a more exact term for what I'm trying to do? Code reorganization?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

-柠檬树下少年和吉他 2024-09-23 05:50:47

Python 的 modulefinder 就是这样做的。编写一个脚本将这些信息转换为导入图非常容易(您可以使用例如 graphviz):这里有一个清晰的解释。还有 snakefood 可以为您完成所有工作(并且还使用 AST! )

您可能需要查看 pylintpychecker 用于更一般的维护任务。

Python's modulefinder does this. It is quite easy to write a script that will turn this information into an import graph (which you can render with e.g. graphviz): here's a clear explanation. There's also snakefood which does all the work for you (and using ASTs, too!)

You might want to look into pylint or pychecker for more general maintenance tasks.

内心荒芜 2024-09-23 05:50:47

编写执行此操作的脚本可能不会很复杂(尽管导入处理有不同的语法),

这很简单。有导入从模块导入。需要处理两种语法。

你知道我想要做的事情有更准确的术语吗?代码重组?

设计。这就是所谓的“设计”。是的,您正在重构现有的设计,但是...

规则一

不要用现有的东西开始设计工作。如果你这样做,你只会“啃咬边缘”,做出一些小的、有时是无关紧要的改变。

规则二

从你应该拥有的东西开始设计工作,如果你更聪明的话。广泛而清晰地思考您真正应该做什么。忽略你所做的事。

规则三

使用正确的包和模块架构从头开始(或者像某些人所说的从头)进行设计。

为此创建一个单独的项目。

规则四

首先测试。为您的新架构编写单元测试。如果您有现有的单元测试,请将它们复制到新项目中。修改导入以反映新架构并重写测试以表达您光荣的新简化。

所有测试都失败,因为您没有移动任何代码。这是一件好事。

规则五

最后将代码移至新结构中。测试通过后停止移动代码。

顺便说一句,您不需要分析导入来执行此操作。您只需使用 grep 来查找模块和类。旧的导入以及旧的导入之间的纠结关系并不重要,不需要分析。你把它扔掉了。您不需要比 grep 更智能的工具。

如果你有移动代码的冲动,你必须非常自律。 (1) 您必须有失败的测试,然后 (2) 您可以移动一些代码来通过失败的测试。

Writing a script that does this probably wouldn't be very complicated (though there are different syntaxes for import to handle),

It's trivial. There's import and from module import. Two syntax to handle.

Do you know of a more exact term for what I'm trying to do? Code reorganization?

Design. It's called design. Yes, you're refactoring an existing design, but...

Rule One

Don't start a design effort with what you have. If you do, you'll only "nibble around the edges" making small and sometimes inconsequential changes.

Rule Two

Start a design effort with what you should have had if you'd only been smarter. Think broadly and clearly about what you're really supposed to be doing. Ignore what you did.

Rule Three

Design from the ground up (or de novo as some folks say) with the correct package and module architecture.

Create a separate project for this.

Rule Four

Test First. Write unit tests for your new architecture. If you have existing unit tests, copy them into the new project. Modify the imports to reflect the new architecture and rewrite the tests to express your glorious new simplification.

All the tests fail, because you haven't moved any code. That's a good thing.

Rule Five

Move code into the new structure last. Stop moving code when the tests pass.

You don't need to analyze imports to do this, BTW. You're just using grep to find modules and classes. The old imports and the tangled relationships among the old imports doesn't matter, and doesn't need to be analyzed. You're throwing it away. You don't need tools smarter than grep.

If feel an urge to move code, you must be very disciplined. (1) you must have test(s) which fail and then (2) you can move some code to pass the failing test(s).

岛歌少女 2024-09-23 05:50:47

chuckmove 是一个工具,可让您递归地重写整个源代码树中的导入以引用文件的新位置模块。

chuckmove --old sound.utils --new media.sound.utils src

...这会下降到 src,并将 import sound.utils 的语句重写为 import media.sound.utils。它支持所有 Python 导入格式。即from x import yimport xyz as w等。

chuckmove is a tool that lets you recursively rewrite imports in your entire source tree to refer to a new location of a module.

chuckmove --old sound.utils --new media.sound.utils src

...this descends into src, and rewrites statements that import sound.utils to import media.sound.utils instead. It supports the whole range of Python import formats. I.e. from x import y, import x.y.z as w etc.

烙印 2024-09-23 05:50:47

Modulefinder 可能不适用于 Python 3.5*,但 pydeps 工作得很好:

安装:

sudo apt install python-pygraphviz
pip install pydeps

然后,在目录中您想要从哪里进行映射,

pydeps --max-bacon=0 .

...以创建最大深度的地图。

*Python 3.5(而非 3.6)中的问题导致 modulefinder 出现问题,类似于 这个

Modulefinder may not work with Python 3.5*, but pydeps worked very well:

Installation:

sudo apt install python-pygraphviz
pip install pydeps

Then, in the directory where you want to map from,

pydeps --max-bacon=0 .

..to create a map of maximum depth.

*An issue in Python 3.5 but not 3.6 caused the problems with modulefinder, similar to this

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文