From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.io!.POSTED.blaine.gmane.org!not-for-mail From: Philip Kaludercic Newsgroups: gmane.emacs.devel Subject: Re: [ELPA] Proposal to add consult-dir to ELPA Date: Fri, 15 Nov 2024 04:30:20 +0000 Message-ID: <87sertdspv.fsf@posteo.net> References: <87ldxmmmlo.fsf@gmail.com> Mime-Version: 1.0 Content-Type: multipart/mixed; boundary="=-=-=" Injection-Info: ciao.gmane.io; posting-host="blaine.gmane.org:116.202.254.214"; logging-data="26647"; mail-complaints-to="usenet@ciao.gmane.io" Cc: emacs-devel@gnu.org To: Karthik Chikmagalur Original-X-From: emacs-devel-bounces+ged-emacs-devel=m.gmane-mx.org@gnu.org Fri Nov 15 05:31:34 2024 Return-path: Envelope-to: ged-emacs-devel@m.gmane-mx.org Original-Received: from lists.gnu.org ([209.51.188.17]) by ciao.gmane.io with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1tBnza-0006nL-Ka for ged-emacs-devel@m.gmane-mx.org; Fri, 15 Nov 2024 05:31:34 +0100 Original-Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1tBnyx-0007bZ-Ay; Thu, 14 Nov 2024 23:30:55 -0500 Original-Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1tBnye-0007XB-QR for emacs-devel@gnu.org; Thu, 14 Nov 2024 23:30:36 -0500 Original-Received: from mout01.posteo.de ([185.67.36.65]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1tBnya-0007jn-EZ for emacs-devel@gnu.org; Thu, 14 Nov 2024 23:30:35 -0500 Original-Received: from submission (posteo.de [185.67.36.169]) by mout01.posteo.de (Postfix) with ESMTPS id AFE54240027 for ; Fri, 15 Nov 2024 05:30:23 +0100 (CET) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=posteo.net; s=2017; t=1731645023; bh=Jixy4mRPie596mTlRQDBbHecvlQm4S8GrV27oqb6MTk=; h=From:To:Cc:Subject:Autocrypt:OpenPGP:Date:Message-ID:MIME-Version: Content-Type:From; b=azHEFmJd0hjeXux102qjoss5qyvAheieK1+C/4B/vwxPfw9RXz0H0P2zXkAtPzdWs LDDMJywUJviPtED7UhP1Z6jddTn8ErvzG2UAs4/lAnTZ0yRMZQ7UguR9nndse4hKky rptK17PFOVk3rkVRJNa8XRtWTJaQ7rG25DXJWabn9hWZrLXtzr+yOXpu4cgDrMjeWa mICX3MzAQ1hxPMLrz3U1vcxFKkT5mzqID/9b/efZ/g24yHlLCnVEa/53vECYbbWoyZ p5Q8Ucxph0g0FnydY/GtpMP6C2B1rR/vL4Vprwlr9LRIcMQCU4YgaaKPi/58KYKdYA ivs8x6YzMPuqg== Original-Received: from customer (localhost [127.0.0.1]) by submission (posteo.de) with ESMTPSA id 4XqPFp54H8z9rxD; Fri, 15 Nov 2024 05:30:22 +0100 (CET) In-Reply-To: <87ldxmmmlo.fsf@gmail.com> (Karthik Chikmagalur's message of "Wed, 13 Nov 2024 21:05:23 -0800") Autocrypt: addr=philipk@posteo.net; keydata= mDMEZBBQQhYJKwYBBAHaRw8BAQdAHJuofBrfqFh12uQu0Yi7mrl525F28eTmwUDflFNmdui0QlBo aWxpcCBLYWx1ZGVyY2ljIChnZW5lcmF0ZWQgYnkgYXV0b2NyeXB0LmVsKSA8cGhpbGlwa0Bwb3N0 ZW8ubmV0PoiWBBMWCAA+FiEEDg7HY17ghYlni8XN8xYDWXahwukFAmQQUEICGwMFCQHhM4AFCwkI BwIGFQoJCAsCBBYCAwECHgECF4AACgkQ8xYDWXahwulikAEA77hloUiSrXgFkUVJhlKBpLCHUjA0 mWZ9j9w5d08+jVwBAK6c4iGP7j+/PhbkxaEKa4V3MzIl7zJkcNNjHCXmvFcEuDgEZBBQQhIKKwYB BAGXVQEFAQEHQI5NLiLRjZy3OfSt1dhCmFyn+fN/QKELUYQetiaoe+MMAwEIB4h+BBgWCAAmFiEE Dg7HY17ghYlni8XN8xYDWXahwukFAmQQUEICGwwFCQHhM4AACgkQ8xYDWXahwukm+wEA8cml4JpK NeAu65rg+auKrPOP6TP/4YWRCTIvuYDm0joBALw98AMz7/qMHvSCeU/hw9PL6u6R2EScxtpKnWof z4oM OpenPGP: id=philipk@posteo.net; url="https://keys.openpgp.org/vks/v1/by-email/philipk@posteo.net"; preference=signencrypt Received-SPF: pass client-ip=185.67.36.65; envelope-from=philipk@posteo.net; helo=mout01.posteo.de X-Spam_score_int: -43 X-Spam_score: -4.4 X-Spam_bar: ---- X-Spam_report: (-4.4 / 5.0 requ) BAYES_00=-1.9, DKIM_SIGNED=0.1, DKIM_VALID=-0.1, DKIM_VALID_AU=-0.1, DKIM_VALID_EF=-0.1, RCVD_IN_DNSWL_MED=-2.3, RCVD_IN_MSPIKE_H3=0.001, RCVD_IN_MSPIKE_WL=0.001, RCVD_IN_VALIDITY_RPBL_BLOCKED=0.001, RCVD_IN_VALIDITY_SAFE_BLOCKED=0.001, SPF_HELO_NONE=0.001, SPF_PASS=-0.001 autolearn=ham autolearn_force=no X-Spam_action: no action X-BeenThere: emacs-devel@gnu.org X-Mailman-Version: 2.1.29 Precedence: list List-Id: "Emacs development discussions." List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: emacs-devel-bounces+ged-emacs-devel=m.gmane-mx.org@gnu.org Original-Sender: emacs-devel-bounces+ged-emacs-devel=m.gmane-mx.org@gnu.org Xref: news.gmane.io gmane.emacs.devel:325458 Archived-At: --=-=-= Content-Type: text/plain Karthik Chikmagalur writes: > Hi, > > I'd like to add my package consult-dir to ELPA. The package is > developed at > > https://github.com/karthink/consult-dir Here are a few comments and suggestions from reading through the code: --=-=-= Content-Type: text/plain Content-Disposition: inline diff --git a/consult-dir.el b/consult-dir.el index 41fab53..cf25785 100644 --- a/consult-dir.el +++ b/consult-dir.el @@ -2,11 +2,11 @@ ;; Copyright (C) 2021-2024 Free Software Foundation, Inc. -;; Author: Karthik Chikmagalur +;; Author: Karthik Chikmagalur ;; Maintainer: Karthik Chikmagalur ;; Created: 2021 -;; Version: 0.1 -;; Package-Requires: ((emacs "27.1") (consult "1.0")) +;; Version: 0.1 ;please bump this! +;; Package-Requires: ((emacs "26.1") (project "0.3.0") (consult "1.0")) ;; Keywords: convenience ;; Homepage: https://github.com/karthink/consult-dir ;; @@ -28,24 +28,25 @@ ;;; Commentary: ;; ;; Consult-dir implements commands to easily switch between "active" -;; directories. The directory candidates are collected from user bookmarks, +;; directories. The directory candidates are collected from user bookmarks, ;; projectile project roots (if available), project.el project roots and recentf -;; file locations. The `default-directory' variable not changed in the process. +;; file locations. The `default-directory' variable not changed in the process. ;; -;; Call `consult-dir' from the minibuffer to choose a directory with completion -;; and insert it into the minibuffer prompt, shadowing or deleting any existing -;; directory. The file name input is retained. This lets the user switch to -;; distant directories very quickly when finding files, for instance. +;; Call `consult-dir' from the minibuffer to choose a directory with +;; completion and insert it into the minibuffer prompt, shadowing or +;; deleting any existing directory. The file name input is retained. +;; This lets the user switch to distant directories very quickly when +;; finding files, for instance. ;; ;; Call `consult-dir' from a regular buffer to choose a directory with -;; completion and then interactively find a file in that directory. The command +;; completion and then interactively find a file in that directory. The command ;; run with this directory is configurable via `consult-dir-default-command' and ;; defaults to `find-file'. ;; ;; Call `consult-dir-jump-file' from the minibuffer to asynchronously find a -;; file anywhere under the directory that is currently in the prompt. This can +;; file anywhere under the directory that is currently in the prompt. This can ;; be used with `consult-dir' to quickly switch directories and find files at an -;; arbitrary depth under them. `consult-dir-jump-file' uses `consult-find' under +;; arbitrary depth under them. `consult-dir-jump-file' uses `consult-find' under ;; the hood. ;; ;; To use this package, bind `consult-dir' and `consult-dir-jump-file' under the @@ -59,7 +60,7 @@ ;; - To make recent directories available, turn on `recentf-mode'. ;; ;; - To make projectile projects available, turn on projectile-mode and -;; configure `consult-dir-project-list-function'. Note that Projectile is NOT +;; configure `consult-dir-project-list-function'. Note that Projectile is NOT ;; required to install this package. ;; ;; - To make project.el projects available, configure @@ -75,7 +76,7 @@ (require 'cl-lib) (require 'bookmark) (require 'recentf) -(require 'seq) +(require 'seq) ;as you only use `seq-filter', could you stick to `cl-filter' to avoid a `require'? (require 'consult) (declare-function projectile-load-known-projects "projectile") @@ -89,41 +90,37 @@ (defvar tramp-default-method) (defgroup consult-dir nil - "Consulting `completing-read'." + "Consulting `completing-read'." ;This feels like it doesn't describe the package sufficiently :group 'convenience :group 'minibuffer - :group 'consult + :group 'consult ;I would stick to one group. :prefix "consult-dir-") (defcustom consult-dir-shadow-filenames t "Shadow file names instead of replacing them when using `consult-dir'." - :group 'consult-dir :type 'boolean) (defcustom consult-dir-default-command #'find-file "Command to run after selecting a directory using `consult-dir'. The default is to invoke `find-file' from the chosen -directory. Setting it to `consult-dir-dired' will instead open +directory. Setting it to `consult-dir-dired' will instead open the chosen directory in dired. Any arbitrary function (of no variables) can be specified -instead. It is run with `default-directory' set to the directory +instead. It is run with `default-directory' set to the directory chosen using `consult-dir'." - :group 'consult-dir :type '(choice (function-item :tag "Find file" find-file) (function-item :tag "Open directory" consult-dir-dired) (function :tag "Custom function"))) (defcustom consult-dir-tramp-default-remote-path "~" "Default path to use for remote directories when using `consult-dir'." - :group 'consult-dir - :type 'string) + :type 'directory) (defcustom consult-dir-tramp-local-hosts '("/sudo:root@localhost:/") "A list of local hosts to include." - :group 'consult-dir - :type '(repeat string)) + :type '(repeat repeat)) (defcustom consult-dir-project-list-function #'consult-dir-project-dirs "Function that returns the list of project directories. @@ -134,30 +131,30 @@ The options are 1. project.el project directories (the default) 2. projectile project directories -3. Any user-defined function. This function should take no +3. Any user-defined function. This function should take no arguments and return a list of directories." - :type '(radio + :type '(radio ;any reason for `radio' instead of `choice' as above (or vice versa) (function-item :tag "Project.el projects" consult-dir-project-dirs) (function-item :tag "Projectile projects" consult-dir-projectile-dirs) (function :tag "User-defined function"))) (defcustom consult-dir-sources - '(consult-dir--source-bookmark - consult-dir--source-default - consult-dir--source-project ;projectile if available, project.el otherwise - consult-dir--source-recentf - consult-dir--source-tramp-local) + (list #'consult-dir--source-bookmark + #'consult-dir--source-default + #'consult-dir--source-project ;projectile if available, project.el otherwise + #'consult-dir--source-recentf + #'consult-dir--source-tramp-local) "Directory sources for `consult-dir'. There are several built-in sources available, including bookmarked directories, recently visited file locations, project directories and more, see customization options. -You can add your own directory sources to the list. The entry +You can add your own directory sources to the list. The entry must be a variable in the plist format specified by Consult, see the documentation of `consult--multi' for details." :type - '(repeat (choice + '(repeat (choice ;I believe you could also use `set'? (const :tag "Bookmarked directories" consult-dir--source-bookmark) (const :tag "Current directory and project root" @@ -172,7 +169,7 @@ the documentation of `consult--multi' for details." consult-dir--source-tramp-ssh) (symbol :tag "Custom directory source")))) -(defcustom consult-dir-jump-file-command 'consult-find +(defcustom consult-dir-jump-file-command #'consult-find "Consult command used by `consult-dir-jump-file'. Available options are `consult-find' and `consult-fd' (both @@ -188,14 +185,14 @@ possess the same signature as `consult-find'." :type 'boolean) (defun consult-dir-dired () - (interactive) - (dired default-directory)) + (interactive) + (dired default-directory)) (defun consult-dir--tramp-parse-config (config) "Given a CONFIG, parse the hosts from it and return the results as a list." (let ((hosts)) (when (and (file-exists-p config) - (require 'tramp nil t)) + (require 'tramp nil t)) ;why are you assuming that TRAMP is not available post Emacs 27? (dolist (cand (tramp-parse-sconfig config)) (let ((user (if (car cand) (concat (car cand) "@"))) (host (cadr cand))) @@ -213,25 +210,25 @@ possess the same signature as `consult-find'." (defun consult-dir--default-dirs () "Return the default directory and project root if available." (let ((fulldir (expand-file-name default-directory)) - (dir (abbreviate-file-name default-directory)) - (root (consult--project-root))) - (cond ((and root (equal fulldir root)) (list dir)) - (root (list dir (abbreviate-file-name root))) - (t (list dir))))) + (dir (abbreviate-file-name default-directory)) + (root (consult--project-root))) + (cond ((and root (equal fulldir root)) (list dir)) + (root (list dir (abbreviate-file-name root))) + (t (list dir))))) (defun consult-dir--bookmark-dirs () "Return bookmarks that are directories." (bookmark-maybe-load-default-file) (let ((file-narrow ?f)) - (thread-last bookmark-alist - (cl-remove-if (lambda (cand) (bookmark-get-handler cand))) - (cl-remove-if-not (lambda (cand) - (let ((bm (bookmark-get-bookmark-record cand))) - (when-let ((file (alist-get 'filename bm))) - (if (file-remote-p file) - (string-suffix-p "/" file) - (file-directory-p file)))))) - (mapcar (lambda (cand) (propertize (car cand) 'consult--type file-narrow)))))) + ;; This should do the same, but I didn't test it: + (cl-loop for cand in bookmark-alist + unless (bookmark-get-handler cand) + when (let ((bm (bookmark-get-bookmark-record cand))) + (when-let ((file (alist-get 'filename bm))) + (if (file-remote-p file) + (string-suffix-p "/" file) + (file-directory-p file)))) + collect (propertize (car cand) 'consult--type file-narrow)))) (defun consult-dir-project-dirs () "Return a list of project directories managed by project.el." @@ -258,11 +255,11 @@ Used to avoid duplicating source entries in (defun consult-dir--project-list-make (&optional refresh) "Make hash table to store the list of projects. -The table is stored in `consult-dir--project-list-hash'. When +The table is stored in `consult-dir--project-list-hash. When REFRESH is non-nil force the hash to be rebuilt." (when consult-dir-project-list-function (let* ((proj-list (funcall consult-dir-project-list-function)) - (proj-sx (sxhash proj-list))) + (proj-sx (sxhash-equal proj-list))) (unless (or refresh (equal proj-sx (car consult-dir--project-list-hash))) (setq consult-dir--project-list-hash @@ -281,74 +278,74 @@ Entries that are also in the list of projects are removed." (let* ((current-dirs (consult-dir--default-dirs)) (proj-list-hash (consult-dir--project-list-make)) (in-other-source-p (lambda (dir) (not (or (and proj-list-hash (gethash dir proj-list-hash)) - (member dir current-dirs))))) + (member dir current-dirs))))) (file-directory-safe (lambda (f) (or (and (if (file-remote-p f) (string-suffix-p "/" f) (file-directory-p f)) (file-name-as-directory f)) (file-name-directory f))))) (thread-last recentf-list - (mapcar file-directory-safe) - (delete-dups) - (mapcar #'abbreviate-file-name) - (seq-filter in-other-source-p)))) + (mapcar file-directory-safe) + (delete-dups) + (mapcar #'abbreviate-file-name) + (seq-filter in-other-source-p)))) (defvar consult-dir--source-recentf - `(:name "Recentf dirs" - :narrow ?r - :category file - :face consult-file - :history file-name-history - :enabled ,(lambda () recentf-mode) - :items ,#'consult-dir--recentf-dirs) + `( :name "Recentf dirs" + :narrow ?r + :category file + :face consult-file + :history file-name-history + :enabled ,(lambda () recentf-mode) + :items ,#'consult-dir--recentf-dirs) "Recentf directory source for `consult-dir--pick'.") (defvar consult-dir--source-bookmark - `(:name "Bookmarks" - :narrow ?m - :category bookmark - :face consult-file - :history bookmark-history - :items ,#'consult-dir--bookmark-dirs) + `( :name "Bookmarks" + :narrow ?m + :category bookmark + :face consult-file + :history bookmark-history + :items ,#'consult-dir--bookmark-dirs) "Bookmark directory source for `consult-dir--pick'.") (defvar consult-dir--source-default - `(:name "This directory/project" - :narrow ?. - :category file - :face consult-file - :history file-name-history - :items ,#'consult-dir--default-dirs) + `( :name "This directory/project" + :narrow ?. + :category file + :face consult-file + :history file-name-history + :items ,#'consult-dir--default-dirs) "Current project directory for `consult-dir--pick'.") (defvar consult-dir--source-project - `(:name "Projects" - :narrow ?p - :category file - :face consult-file - :history file-name-history - :enabled ,(lambda () consult-dir-project-list-function) - :items ,(lambda () (let ((current-dirs (consult-dir--default-dirs))) - (seq-filter (lambda (proj) (not (member proj current-dirs))) - (consult-dir--project-dirs))))) + `( :name "Projects" + :narrow ?p + :category file + :face consult-file + :history file-name-history + :enabled ,(lambda () consult-dir-project-list-function) + :items ,(lambda () (let ((current-dirs (consult-dir--default-dirs))) + (seq-filter (lambda (proj) (not (member proj current-dirs))) + (consult-dir--project-dirs))))) "Project directory source for `consult-dir--pick'.") (defvar consult-dir--source-tramp-local - `(:name "Local" - :narrow ?l - :category file - :face consult-file - :history file-name-history - :items ,consult-dir-tramp-local-hosts) + `( :name "Local" + :narrow ?l + :category file + :face consult-file + :history file-name-history + :items ,consult-dir-tramp-local-hosts) "Local host candidate source for `consult-dir'.") (defvar consult-dir--source-tramp-ssh - `(:name "SSH Config" - :narrow ?s - :category file - :face consult-file - :history file-name-history - :items ,#'consult-dir--tramp-ssh-hosts) + `( :name "SSH Config" + :narrow ?s + :category file + :face consult-file + :history file-name-history + :items ,#'consult-dir--tramp-ssh-hosts) "SSH Config candiadate source for `consult-dir'.") (defun consult-dir--pick (&optional prompt) @@ -371,30 +368,30 @@ Optional argument PROMPT is the prompt." (search (file-name-nondirectory mc))) (run-at-time 0 nil (lambda () (funcall consult-dir-jump-file-command - dir - (concat search - (unless (string-empty-p search) - (plist-get (consult--async-split-style) - :initial)))))) + dir + (concat search + (unless (string-empty-p search) + (plist-get (consult--async-split-style) + :initial)))))) (abort-recursive-edit))) ;;;###autoload (defun consult-dir () - "Choose a directory and act on it. + "Choose a directory and act on it. The action taken on the directory is the value of -`consult-dir-default-command'. The default is to call +`consult-dir-default-command. The default is to call `find-file' starting at this directory. When called from the minibuffer, insert the directory into the -minibuffer prompt instead. Existing minibuffer contents will be +minibuffer prompt instead. Existing minibuffer contents will be shadowed or deleted depending on the value of `consult-dir-shadow-filenames'. The list of sources for directory paths is `consult-dir-sources', which can be customized." - (interactive) - (if (minibufferp) + (interactive) + (if (minibufferp) (let* ((enable-recursive-minibuffers t) (file-name (file-name-nondirectory (minibuffer-contents))) (new-dir (consult-dir--pick)) @@ -405,9 +402,8 @@ The list of sources for directory paths is (insert "/" new-full-name) (delete-minibuffer-contents) (insert new-full-name)))) - (let* ((new-dir (consult-dir--pick "In directory: ")) - (default-directory new-dir)) - (call-interactively consult-dir-default-command)))) + (let ((default-directory (consult-dir--pick "In directory: "))) + (call-interactively consult-dir-default-command)))) (provide 'consult-dir) ;;; consult-dir.el ends here --=-=-= Content-Type: text/plain > Here is what it does: > > Consult-dir allows you to easily insert directory paths into the > minibuffer prompt in Emacs. > > When using the minibuffer, you can switch to any directory you've > visited recently, or to any project root, a bookmarked directory, or a > remote host via tramp. > > This is useful > > - For specifying a "destination" to any command that reads a file or > directory name from the minibuffer. You can use it when finding files > or directories, copying files, attaching files to emails, and so on. > It works without assumptions on the command being invoked, so you can > use it even if you just want to copy some directory path into the > kill-ring. > > - When you want to quickly access a resource that is "far away" in the > filesystem tree from `default-directory'. > > I have found it to be a surprisingly versatile tool, and many users have > told me over the years that it solves a problem they didn't realize they > had. What is not clear to me is why this is not a part of Consult, if it is as useful as you say. Have you discussed this with Daniel? In any case, it would be useful to explain that somewhere. > I have signed the copyright papers, and there are no contributions to > the project from users over 3-4 lines in length. Consult-dir's only > external dependency (Consult) is in ELPA. 1+ (though I have suggested to depend on project so as to lower the dependency on Emacs). > Thank you, > Karthik > > -- Philip Kaludercic on siskin --=-=-=--