11

I was reading the use-package documentation, which says, "Here is the simplest use-package declaration:"

;; This is only needed once, near the top of the file
(eval-when-compile
  ;; Following line is not needed if use-package.el is in ~/.emacs.d
  (add-to-list 'load-path "<path where use-package is installed>")
  (require 'use-package))

(use-package foo)

As an Emacs beginner, I have a few questions about this part if I may.

  1. Do I need (package-initialize) before these lines? It seems to me that without doing that, the use-package macro wouldn't be available.
  2. I do not need the 4th line in the above snippet, right? As I have installed use-package from MELPA Stable, and the package is installed to the default location ~/.emacs.d/elpa/use-package-2.4.
  3. In this example, is (use-package foo) equivalent to (require 'foo)?
Basil
  • 12,019
  • 43
  • 69
SparedWhisle
  • 569
  • 3
  • 13

1 Answers1

15
  1. Do I need (package-initialize) before these lines?

If your version of Emacs (M-xemacs-versionRET) is older than 27, and you are using the built-in package manager, then you indeed need to call (package-initialize) before you can call on any installed packages, such as use-package.

From Emacs 27 onwards, package-initialize will effectively be called before user-init-file is loaded. This can be disabled by setting package-enable-at-startup to nil in the new early-init-file.

It seems to me that without doing that, the use-package macro wouldn't be available.

It depends. The example is written from the perspective of someone who doesn't use the built-in package manager (e.g. the author of use-package), and who manually installs packages so that they can be found by Emacs on their load-path. This is what package-install and package-initialize effectively automate for the user.

  1. I do not need the 4th line in the above snippet, right? As I have installed use-package from MELPA Stable, and the package is installed to the default location ~/.emacs.d/elpa/use-package-2.4.

Correct. If you install packages using the package manager and call package-initialize, then you do not need to manually edit your load-path.

  1. In this example, is (use-package foo) equivalent to (require 'foo)?

Let's find out: with point after the closing parenthesis of (use-package foo), call M-xpp-macroexpand-last-sexpRET. This will print what use-package is actually doing under the bonnet to the buffer *Pp Macroexpand Output*:

(progn
  (defvar use-package--warning0
    (lambda (keyword err)
      (let ((msg (format "%s/%s: %s" 'foo keyword
                         (error-message-string err))))
        (display-warning 'use-package msg :error))))
  (condition-case-unless-debug err
      (unless (require 'foo nil t)
        (display-warning 'use-package
                         (format "Cannot load %s" 'foo)
                         :error))
    (error
     (funcall use-package--warning0 :catch err))))

Stripping away all of the error reporting, we're left with:

(require 'foo nil t)

Which is like (require 'foo), but doesn't signal an error if the named feature foo can't be found.

Basil
  • 12,019
  • 43
  • 69