aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorArtur Malabarba2015-02-03 17:51:39 -0200
committerArtur Malabarba2015-02-03 17:51:39 -0200
commit2a4a5069a6a0dba8888d72e60b66a3df5ed5a8cb (patch)
treeccb750252fbfd10fe7403c846d049bf846d527dd
parent504fada7e7502b9052076c20f16f55d7e9bd3c58 (diff)
downloademacs-2a4a5069a6a0dba8888d72e60b66a3df5ed5a8cb.tar.gz
emacs-2a4a5069a6a0dba8888d72e60b66a3df5ed5a8cb.zip
emacs-lisp/package.el (package-menu-execute): Offer to remove packages.
-rw-r--r--lisp/ChangeLog4
-rw-r--r--lisp/emacs-lisp/package.el53
2 files changed, 38 insertions, 19 deletions
diff --git a/lisp/ChangeLog b/lisp/ChangeLog
index c834d7cc168..38d41b27ef4 100644
--- a/lisp/ChangeLog
+++ b/lisp/ChangeLog
@@ -21,6 +21,10 @@
21 (package-menu-mark-delete, package-menu--find-upgrades) 21 (package-menu-mark-delete, package-menu--find-upgrades)
22 (package-menu--status-predicate, describe-package-1): Use it 22 (package-menu--status-predicate, describe-package-1): Use it
23 23
24 (package--removable-packages): New function.
25 (package-autoremove): Use it.
26 (package-menu-execute): Offer to remove unneeded packages.
27
242015-02-03 Thierry Volpiatto <thierry.volpiatto@gmail.com> 282015-02-03 Thierry Volpiatto <thierry.volpiatto@gmail.com>
25 29
26 * emacs-lisp/package.el (package-reinstall): Don't change package's selected status. 30 * emacs-lisp/package.el (package-reinstall): Don't change package's selected status.
diff --git a/lisp/emacs-lisp/package.el b/lisp/emacs-lisp/package.el
index 298604e9892..d013fd4a329 100644
--- a/lisp/emacs-lisp/package.el
+++ b/lisp/emacs-lisp/package.el
@@ -1536,6 +1536,18 @@ If NOSAVE is non-nil, the package is not removed from
1536 'package-selected-packages (remove name package-selected-packages))) 1536 'package-selected-packages (remove name package-selected-packages)))
1537 (message "Package `%s' deleted." (package-desc-full-name pkg-desc)))))) 1537 (message "Package `%s' deleted." (package-desc-full-name pkg-desc))))))
1538 1538
1539(defun package--removable-packages ()
1540 "Return a list of names of packages no longer needed.
1541These are packages which are neither contained in
1542`package-selected-packages' nor a dependency of one that is."
1543 (let ((needed (cl-loop for p in package-selected-packages
1544 if (assq p package-alist)
1545 ;; `p' and its dependencies are needed.
1546 append (cons p (package--get-deps p)))))
1547 (cl-loop for p in (mapcar #'car package-alist)
1548 unless (memq p needed)
1549 collect p)))
1550
1539;;;###autoload 1551;;;###autoload
1540(defun package-autoremove () 1552(defun package-autoremove ()
1541 "Remove packages that are no more needed. 1553 "Remove packages that are no more needed.
@@ -1550,22 +1562,16 @@ will be deleted."
1550 (when (or package-selected-packages 1562 (when (or package-selected-packages
1551 (yes-or-no-p 1563 (yes-or-no-p
1552 "`package-selected-packages' is empty! Really remove ALL packages? ")) 1564 "`package-selected-packages' is empty! Really remove ALL packages? "))
1553 (let ((needed (cl-loop for p in package-selected-packages 1565 (let ((removable (package--removable-packages)))
1554 if (assq p package-alist) 1566 (if removable
1555 ;; `p' and its dependencies are needed. 1567 (when (y-or-n-p
1556 append (cons p (package--get-deps p))))) 1568 (format "%s packages will be deleted:\n%s, proceed? "
1557 (cl-loop for p in (mapcar #'car package-alist) 1569 (length removable)
1558 unless (memq p needed) 1570 (mapconcat #'symbol-name removable ", ")))
1559 collect p into lst 1571 (mapc (lambda (p)
1560 finally (if lst 1572 (package-delete (cadr (assq p package-alist)) t))
1561 (when (y-or-n-p 1573 removable)
1562 (format "%s packages will be deleted:\n%s, proceed? " 1574 (message "Nothing to autoremove"))))))
1563 (length lst)
1564 (mapconcat #'symbol-name lst ", ")))
1565 (mapc (lambda (p)
1566 (package-delete (cadr (assq p package-alist)) t))
1567 lst))
1568 (message "Nothing to autoremove"))))))
1569 1575
1570(defun package-archive-base (desc) 1576(defun package-archive-base (desc)
1571 "Return the archive containing the package NAME." 1577 "Return the archive containing the package NAME."
@@ -2377,9 +2383,18 @@ Optional argument NOQUERY non-nil means do not ask the user to confirm."
2377 (package-delete elt) 2383 (package-delete elt)
2378 (error (message (cadr err))))) 2384 (error (message (cadr err)))))
2379 (error "Aborted"))) 2385 (error "Aborted")))
2380 (if (or delete-list install-list) 2386 (if (not (or delete-list install-list))
2381 (package-menu--generate t t) 2387 (message "No operations specified.")
2382 (message "No operations specified.")))) 2388 (when package-selected-packages
2389 (let ((removable (package--removable-packages)))
2390 (when (and removable
2391 (y-or-n-p
2392 (format "These %d packages are no longer needed, delete them (%s)? "
2393 (length removable)
2394 (mapconcat #'symbol-name removable ", "))))
2395 (mapc (lambda (p) (package-delete (cadr (assq p package-alist))))
2396 removable))))
2397 (package-menu--generate t t))))
2383 2398
2384(defun package-menu--version-predicate (A B) 2399(defun package-menu--version-predicate (A B)
2385 (let ((vA (or (aref (cadr A) 1) '(0))) 2400 (let ((vA (or (aref (cadr A) 1) '(0)))