unofficial mirror of emacs-devel@gnu.org 
 help / color / mirror / code / Atom feed
From: Dmitry Gutov <dgutov@yandex.ru>
To: "andres.ramirez" <rrandresf@gmail.com>
Cc: emacs-devel <emacs-devel@gnu.org>
Subject: Re: project-find-regexp using ripgrep
Date: Mon, 22 Jun 2020 03:01:42 +0300	[thread overview]
Message-ID: <15b1e532-99e7-5f43-defc-3c32072af3d6@yandex.ru> (raw)
In-Reply-To: <86tuz69y51.fsf@gmail.com>

[-- Attachment #1: Type: text/plain, Size: 859 bytes --]

On 20.06.2020 07:09, andres.ramirez wrote:
>      Dmitry> Anybody?
> 
> Before the patch:
> --8<---------------cut here---------------start------------->8---
> Elapsed time: 6.010101s
> Elapsed time: 5.863914s
> --8<---------------cut here---------------end--------------->8---
> 
> After installing ripgrep and patch:
> --8<---------------cut here---------------start------------->8---
> Elapsed time: 3.261737s
> Elapsed time: 1.742008s
> --8<---------------cut here---------------end--------------->8---

Thanks, Andres. Looks promising.

Here's the latest version of the patch, if you'd like to test. I don't 
expect major changes in performance, but it does add a pipe to 'sort', 
which creates some overhead proportional to the number of search results.

To enable ripgrep with this, one needs to 'M-x customize-variable 
xref-search-command-template'.

[-- Attachment #2: xref-ripgrep.diff --]
[-- Type: text/x-patch, Size: 3019 bytes --]

diff --git a/lisp/progmodes/xref.el b/lisp/progmodes/xref.el
index 3e3a37f6da..a8283d0d4a 100644
--- a/lisp/progmodes/xref.el
+++ b/lisp/progmodes/xref.el
@@ -1246,12 +1246,45 @@ xref-matches-in-directory
 (declare-function tramp-tramp-file-p "tramp")
 (declare-function tramp-file-local-name "tramp")
 
+;; '-s' because 'git ls-files' can output broken symlinks.
+(defconst xref-grep-search-template
+  "xargs -0 grep <C> -snHE -e <R>"
+  "Use Grep to search a list of files piped from stdin.")
+
+;; See https://github.com/BurntSushi/ripgrep/issues/152 on
+;; the subject of non-deterministic output.
+(defconst xref-ripgrep-search-template
+  "xargs -0 rg <C> -nH --no-messages -g '!*/' -e <R> | sort -t: -k1 -k2n"
+  "Use ripgrep to search a list of files piped from stdin.
+
+The arguments are chosen carefully so that the output format is
+compatible with Grep.  As well as its '-s' argument.
+
+Note: by default, ripgrep's output order is non-deterministic
+because it does the search in parallel.  You can use the template
+without the '| sort ...' part if GNU sort is not available on
+your system and/or stable ordering is not important to you.")
+
+(defcustom xref-search-command-template xref-grep-search-template
+  "Command template to search a list of files piped from stdin.
+
+Allowed fields:
+
+  <C> for extra arguments such as -i and --color
+  <R> for the regexp itself (in Extended format)"
+  :type `(choice
+          (const :tag "Use Grep" ,xref-grep-search-template)
+          (const :tag "Use ripgrep" ,xref-ripgrep-search-template)
+          (string :tag "User defined")))
+
 ;;;###autoload
 (defun xref-matches-in-files (regexp files)
   "Find all matches for REGEXP in FILES.
 Return a list of xref values.
 FILES must be a list of absolute file names."
   (cl-assert (consp files))
+  (require 'grep)
+  (defvar grep-highlight-matches)
   (pcase-let*
       ((output (get-buffer-create " *project grep output*"))
        (`(,grep-re ,file-group ,line-group . ,_) (car grep-regexp-alist))
@@ -1261,13 +1294,12 @@ xref-matches-in-files
        ;; first file is remote, they all are, and on the same host.
        (dir (file-name-directory (car files)))
        (remote-id (file-remote-p dir))
-       ;; 'git ls-files' can output broken symlinks.
-       (command (format "xargs -0 grep %s -snHE -e %s"
-                        (if (and case-fold-search
-                                 (isearch-no-upper-case-p regexp t))
-                            "-i"
-                          "")
-                        (shell-quote-argument (xref--regexp-to-extended regexp)))))
+       ;; The 'auto' default would be fine too, but ripgrep can't handle
+       ;; the options we pass in that case.
+       (grep-highlight-matches)
+       (command (grep-expand-template xref-search-command-template
+                                      (xref--regexp-to-extended regexp)
+                                      regexp)))
     (when remote-id
       (require 'tramp)
       (setq files (mapcar

  reply	other threads:[~2020-06-22  0:01 UTC|newest]

Thread overview: 14+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-06-14 21:30 project-find-regexp using ripgrep Dmitry Gutov
2020-06-18  9:49 ` Ergus
2020-06-18  9:55   ` Dmitry Gutov
2020-06-18 10:20     ` Ergus
2020-06-20  1:06 ` Dmitry Gutov
2020-06-20  4:09   ` andres.ramirez
2020-06-22  0:01     ` Dmitry Gutov [this message]
2020-06-22  2:30       ` Eli Zaretskii
2020-06-22 13:10         ` Dmitry Gutov
2020-06-22 14:53           ` Eli Zaretskii
2020-06-22  3:12       ` andrés ramírez
2020-12-04  1:56         ` Dmitry Gutov
2020-12-09  4:14           ` andrés ramírez
2020-12-09 21:46             ` Dmitry Gutov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

  List information: https://www.gnu.org/software/emacs/

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=15b1e532-99e7-5f43-defc-3c32072af3d6@yandex.ru \
    --to=dgutov@yandex.ru \
    --cc=emacs-devel@gnu.org \
    --cc=rrandresf@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).