7

Largely following the approach described by Bozhidar Batsov on the page: http://batsov.com/articles/2012/02/19/package-management-in-emacs-the-good-the-bad-and-the-ugly/, I tried to build my emacs file to check if any package in a given list was not installed and install it using package.el if so. Things seem to have been working, but either I made a change to my emacs file that I do remember, or something else is going on. Now when I added 'outpair' to my list of packages I get an error.

(require 'cl)

(require 'package)
(add-to-list 'package-archives
         '("marmalade" . "http://marmalade-repo.org/packages/"))
(add-to-list 'package-archives
         '("melpa" . "http://melpa.milkbox.net/packages/"))
(package-initialize)

(defvar my-packages
  '(auctex auto-complete autopair magit yasnippet)
  "A list of packages to ensure are installed at launch.")

(defun my-packages-installed-p ()
   (loop for p in my-packages
          when (not (package-installed-p p)) do (return -1)
                  finally (return 1)))

(unless (my-packages-installed-p)
  ;; check for new packages (package versions)
  (package-refresh-contents)
  ;; install the missing packages
  (dolist (p my-packages)
    (when (not (package-installed-p p))
      (package-install p))))

(let ((default-directory "~/.emacs.d/elpa/"))
     (normal-top-level-add-to-load-path '("."))
     (normal-top-level-add-subdirs-to-load-path))

(require 'exec-path-from-shell)
(when (memq window-system '(mac ns))
      (exec-path-from-shell-initialize))


(setq inhibit-splash-screen 1           ;;turn off splash screen
      initial-scratch-message nil       ;;remove initial message
      initial-major-mode 'org-mode)     ;;turn on org-mode

(scroll-bar-mode -1)  ;;turn off scroll bar
(tool-bar-mode -1)    ;;turn off tool bar
(menu-bar-mode -1)    ;;turn off menu bar

(delete-selection-mode 1)
(transient-mark-mode 1)
(setq x-select-enable-clipboard 1)

;;this is only used when running cocoa app.
(when window-system
  (setq frame-title-format '(buffer-file-name "%f" ("%b")))
    (set-face-attribute 'default nil
                          :family "Inconsolata"
                          :height 140
                          :weight 'normal
                          :width 'normal)

  (when (functionp 'set-fontset-font)
      (set-fontset-font "fontset-default"
                        'unicode
                        (font-spec :family "DejaVu Sans Mono"
                        :width 'normal
                        :size 12.4
                        :weight 'normal))))

(setq-default indicate-empty-lines t)
(when (not indicate-empty-lines)
 (toggle-indicate-empty-lines))


;set custom window width and height
(defun custom-set-frame-size ()
  (add-to-list 'default-frame-alist '(height . 65))
  (add-to-list 'default-frame-alist '(width . 99)))
(custom-set-frame-size)
(add-hook 'before-make-frame-hook 'custom-set-frame-size)

(setq tab-width 2)
(setq indent-tabs-mode nil)

(setq make-backup-files -1) ;;turn off backup files

(global-set-key (kbd "RET") 'newline-and-indent)
;(global-set-key (kbd "C-;") 'comment-or-uncomment-region) ;already bound to "M-;"
(global-set-key (kbd "M-/") 'hippie-expand)
(global-set-key (kbd "C-+") 'text-scale-increase)
(global-set-key (kbd "C--") 'text-scale-decrease)
(global-set-key (kbd "C-c C-k") 'compile)
(global-set-key (kbd "C-x g") 'magit-status)

(defalias 'yes-or-no-p 'y-or-n-p)
(setq echo-keystrokes 0.1
      use-dialog-box -1
      visible-bell 1)
(show-paren-mode 1)
(require 'autopair)

(setq TeX-auto-save t)
(setq TeX-parse-self t)
(setq-default TeX-master nil)  ;Query for master file

(add-hook 'LaTex-mode-hook 'visual-line-mode)
(add-hook 'LaTex-mode-hook 'flyspell-mode)
(add-hook 'LaTex-mode-hook 'LaTex-math-mode)

(add-hook 'LaTex-mode-hook 'turn-on-reftex)
(setq reftex-plug-into-AUCTeX t)
(setq TeX-PDF-mode t)

(add-hook 'LaTeX-mode-hook (lambda()
(push
    '("latexmk" "latexmk -synctex=1 -pdf %s" TeX-run-TeX nil t
      :help "Run latexmk on file")
    TeX-command-list)))

(add-hook 'TeX-mode-hook '(lambda() (setq TeX-command-default "latexmk")))

(setq TeX-view-program-selection '((output-pdf "PDF Viewer")))
(setq TeX-view-program-list
  '(("PDF Viewer" "/Applications/Skim.app/Contents/SharedSupport/displayline -b -g %n %o %b")))



(ido-mode 1)
(setq ido-enable-flex-matching 1
      ido-use-virtual-buffers 1)

;;column number mode
(setq column-number-mode 1)

(require 'yasnippet)
(setq yas-snippet-dirs 'yas-installed-snippets-dir)
(yas-global-mode 1)

(require 'auto-complete-config)

(add-to-list 'ac-dictionary-directories "~/.emacs.d/ac-dict")
(ac-config-default)
(ac-set-trigger-key "TAB")
(ac-set-trigger-key "<tab>")


(require 'tex-site)
(require 'font-latex)

The error message I get is: "Warning (initialization): An error occurred while loading `/Users/jeimer/.emacs':

File error: Cannot open load file, no such file or directory, autopair

To ensure normal operation, you should investigate and remove the cause of the error in your initialization file. Start Emacs with the `--debug-init' option to view a complete error backtrace."

Does anyone know what is going on here and how to fix it?

Thanks!

1

2 Answers 2

3

Your my-packages-installed-p is returning -1 and 1. In the following unless block, you are using my-packages-installed-p as if it were a predicate function, which, the name notwithstanding, it isn't. Make these changes to my-packages-installed-p:

(defun my-packages-installed-p ()
   (loop for p in my-packages
          when (not (package-installed-p p)) do (return nil)
                  finally (return t)))
1
  • 1
    Totally makes sense. I had read an old blog post somewhere that when running emacs on a mac, they had to use -1 and 1 rather than nil and t respectively. This situation seem incorrect for my version of OS X and emacs. Thanks for the simple fix!
    – jeimer
    Commented Jan 9, 2015 at 15:59
2

unless evaluates the body if and only if the condition returns nil. From its docstring (emphasis mine):

If COND yields nil, do BODY, else return nil.

Obviously, neither 1 nor -1 are nil, obviously, so your my-packages-installed-p never returns nil regardless of whether your packages are installed or not. Consequently the body of your unless clause is always skipped, and autopair is never actually installed by your code!

The whole predicate is redundant anyway, since the dolist loop also checks whether a package is installed. All your predicate adds is another redundant iteration over the list of desired packages. You can remove it entirely, and instead call package-refresh-contents implicitly if you install the first package:

(dolist (package my-packages)
  (unless (package-installed-p package)
    (unless package-archive-contents
      (package-refresh-contents))
    (package-install package)))

You can also remove your load-path-related code. It's entirely redundant as well: package.el manages the load-path for you, automatically adding newly installed packages as needed.

You may also want to take a look at use-package, which—among other features for package initialisation and configuration—handles package installation for you.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.