dependency management system on top of use-package
Emacs Lisp
Latest commit e710817 Mar 16, 2017 @tarsius tarsius committed with Do not provide test-helper feature
"test-helper.el" isn't a library intended to be loaded with `require`.
Instead it is loaded with `load`.  Because of that, it is confusing to
provide a feature using `provide` anyway.  And because around 70 other
packages come with a file named "test-helper.el" and several dozen of
those still provide the feature `test-helper`, this also leads to a,
admittedly somewhat theoretical, feature conflict.

This is also discussed at rejeep/ert-runner.el#38.



req-package provides dependency management for use-package. This allows to write simple and modular configs. Migration from use-package is simple and syntax is almost same.


Load req-package:

(require 'req-package)

(req-package el-get ;; prepare el-get (optional)
  :force t ;; load package immediately, no dependency resolution
  (add-to-list 'el-get-recipe-path "~/.emacs.d/el-get/el-get/recipes")
  (el-get 'sync))

Define required packages with dependencies using :require. Optionally provide preferred installation source with :loader keyword. Use :force t if you want to avoid dependency management and load right now.

;; init-dired.el

(req-package dired) ;; this form is optional as it doesn't have any configuration

(req-package dired-single
  :require dired ;; depends on dired
  :config (...))

(req-package dired-isearch
  :require dired ;; depends on dired
  :config (...))

;; init-lua.el

(req-package lua-mode
  :loader :elpa ;; installed from elpa
  :config (...))

(req-package flymake-lua
  :require flymake lua-mode
  :config (...))

;; init-flymake.el

(req-package flymake
  :loader :built-in ;; use emacs built-in version
  :config (...))

(req-package flymake-cursor
  :loader :el-get ;; installed from el-get
  :require flymake
  :config (...))

(req-package flymake-custom
  :require flymake
  :loader :path ;; use package that is on load-path
  :load-path "/path/to/file/directory"
  :config (...))

Solve dependencies, install and load packages in right order:

;; order doesn't matter here
(require 'init-dired)
(require 'init-lua)
(require 'init-flymake)


req-package supports extensible package providers system. This is alternative to :ensure keyword in use-package. Use :loader keyword with :el-get, :elpa, :built-in or :path value. Extend req-package-providers-map if you want to introduce new provider. Tweak provider priorities using req-package-providers-priority map.


You can use req-package--log-open-log to see, what is happening with your configuration. You can choose log level in req-package group by req-package-log-level custom. These log levels are supported: fatal, error, warn, info, debug, trace.

Migrate from use-package

Just replace all (use-package ...) with (req-package [:require DEPS] ...) and add (req-package-finish) at the end of your configuration file. Do not use :ensure keyword, use providers system that is more powerful. There is a :force keyword which simulates plain old use-package behavior.


More complex req-package usage example can be found at

Use load-dir package to load all *.el files in a dir (e.g ~/.emacs.d/init.d)


Please, pull-request your changes to develop branch. Master is used for automatic release package builds by travis-ci.



  • once you called req-package-finish you are able reload package just by reload req-package form
  • proper errors handling. see req-package--log-open-log for messages
  • smart add-hook which invokes function if mode is loaded
  • refactor providers system
  • no need to use progn in :init and :config sections
  • no need to use list literal in :require section
  • :loader keyword now accepts loaders as keywords or as functions. e.g. :el-get, :elpa, :built-in, :path and my-loader-fn
  • req-package-force replaced with :force keyword


  • :loader keyword support


  • bugfixes


  • fixed some issues with packages installation. all packages will be installed at bootstrap time
  • custom package providers support by req-package-providers
  • priority feature for cross provider packages loading. you can choose, what to try first - elpa, el-get, or something else


  • el-get support


  • Major system refactoring.
  • Fixed bugs with defered loading.
  • Significant performance optimization.
  • max-specpdl-size, max-lisp-eval-depth issues completely solved.
  • Flexible :require keyword parsing.


  • Bug fixes.


  • Various tweaks and bug fixes.


  • All cycles of your dependencies will be printed now.
  • Also there are more handy log messages and some bug fixes.


  • There are nice error messages about cycled dependencies now.
  • Cycles printed in a way: pkg1 -> [pkg2 -> ...] pkg1.
  • It means there is a cycle around pkg1.


  • There is no need of explicit :ensure in your code now.
  • When you req-package it adds :ensure if package is available in your repos.
  • Also package deps :ensure‘d automatically too.
  • Just write (req-package pkg1 :require pkg2) and all you need will be installed.