UPDATE: package is published on Melpa/GitHub now!

For daily work I’m using pyenv with the pyenv-virtualenv plugin (instead of virtualenv). I recommend using it as it has some nice features!

There is also pyenv-mode available for Emacs integration.

When I first began migrating from virtualenv to pyenv I used the follosing snippet to activate pyenv version (virtualenv) automatically via “directory variables” (.dir-locals.el).

However I’m too lazy to create a .dir-locals.el file for each new project, so I’ve written little hook. This hook will automatically activate pyenv (via pyenv-mode-set) if there’s a .python-version file present in project root.

Excluding pyenv-mode 2 small libraries are used for Emacs: f.el for files and s.el for strings. These are widely used libraries so there’s a good chance you already have them on your system.

Code:

(defun ssbb-pyenv-hook ()
  "Automatically activates pyenv version if .python-version file exists."
  (f-traverse-upwards
   (lambda (path)
     (let ((pyenv-version-path (f-expand ".python-version" path)))
       (if (f-exists? pyenv-version-path)
           (pyenv-mode-set (s-trim (f-read-text pyenv-version-path 'utf-8))))))))

(add-hook 'find-file-hook 'ssbb-pyenv-hook)

This hook is called when a file is opened within Emacs. Parent directories are then traversed up and if a .python-version file been found the pyenv-mode-set function is called with this file contents.

PS. I am learning English and this is my first blog post in this language. I would be grateful for the correction :)

Thanks baxx for the correction.