Emacs autocomplete and Dependency injection (DI)¶
В пассивных классах, которым зависимости внедряет программа, возникают трудности с автокомплитом в emacs с elpy-mode.
Вариантов решения здесь несколько.
- Устанавливать зависимости через конструктор класса, учитывая, что бэкенд jedi учитывает типы аргументов функций и возвращаемых значений, указанных в строках документирования.
- Устанавливать зависимость через метод установки (setter). Причем, не обязательно, чтобы этот метод использовался, достаточно просто объявить его в классе и прописать в строке документирования тип аргумента.
- Получать зависимость через метод доступа (getter). В отличии от первых двух вариантов, работать будет декларация типов возвращаемых значений, а не аргументов.
- Использовать Service Locator или паттерн Plugin, которые инициируют запрос и делегируют его исполнение резольверу зависимостей.
В случае с rope вместо декларации типов аргументов в строках документирования можно использовать Dynamic Object Analysis.
Но мы пойдем самым сложным путем, и заставим emacs решать эту проблему.
Итак.
1. Стартуем интерпретатор M-x run-python
(предварительно настраиваем elpy на использование ipython чтобы автокомплит работал и в шеле тоже):
(when (executable-find "ipython") (elpy-use-ipython))
2. посылаем в интерпретатор файл с которым работаем: M-x python-shell-send-file
.
3. определяем в интерпретаторе переменную, которая нужна. В моем случае нужна self.dao.engine
. Делаем в шелле что-то типа
self = StatsFactory().make_api()
у которого по счастливому стечению обстоятельств есть атрибут .dao.engine, который мне и нужен.
В итоге в интерпретаторе будет объявлена переменная self.dao.engine
.
4. Поскольку elpy заглушает вызов completion-at-point в выпадающем окне company-mode, вызываем вручную M-x completion-at-point
или M-x python-shell-completion-complete-or-indent
.
Чтобы не вызывать вручную, биндим их на любую удобную комбинацию клавиш, например “C-c TAB
”.
5. Таким образом можно автокомплитить любые недостающие переменные, - просто объявляем их в интерпретаторе, и они будут подсказываться в буфере редактирования файла.
P.S.: это старейшая возможность питон-мода, которая лего забывается из-за наличия jedi и rope)) IDLE работает по аналогичному принципу.
P.P.S.: ropemacs-mode должен быть выключен, если он установлен. Можно не выключать, а просто снять 'ropemacs-completion-at-point
с 'ropemacs-mode-hook
:
(add-hook 'ropemacs-mode-hook (lambda ()
(if ropemacs-mode
(remove-hook 'completion-at-point-functions 'ropemacs-completion-at-point t))
))
Updated on Jan 03, 2016
Добавил в forked rope поддержку подсказок типов в строках документирования для параметров функций, возвращаемого значения и атрибутов класса.
Updated on Jan 05, 2016
Добавил в forked rope поддержку подсказок типов на основании комментирования типов согласно PEP 0484 для присваиваний.
Updated on Feb 16, 2016
Форк принят в мастер (bd89775).
Updated on Nov 29, 2016
Реализация Type Hinting существенно переработана.