Grep buffer sorted by: group | file | numerical position

Uses grep.kak command and sorts the *grep* buffer contents based on alphabetical grouping.

Community request for a solution to group by file name, ascending numerically, within their alphabetical groups.

Example:
alphabetical → file → numerical
file → numerical → alphabetical
numerical → file → alphabetical

map global user 'B' ': grep -E "FIXME|NOTE|TODO" %val{bufname} <ret>: grep-buffer-sort' -docstring "grep FIXME|NOTE|TODO in file"
map global user '<c-b>' ': grep -E "FIXME|NOTE|TODO" . <ret>: grep-buffer-sort' -docstring "grep FIXME|NOTE|TODO in project"

define-command -hidden grep-buffer-sort %{
    try %{ execute-keys -buffer *grep* 'gjd%s/[*/]<ret>&%s\s\s+<ret>c<space><esc>&<space>%|sort -k 3<ret>' }
}

Before

After

You can see the incorrect grouping patterns in the above picture.

Update 01

|sort -f -k3 -k1,3<ret>

yields slightly better results, but still not the correct pattern. Look at the TODO’s 4xHighlighters.kt ordering displaced, also NOTE 2xKakouneCommands.kt numerically descending.

Update 02

try %{ execute-keys -buffer *grep* 'gjd%s/[*/]<ret>&%s\s\s+<ret>c<space><esc>&<space>%sFIXME<ret>xd<space>gj<a-o>j<a-R><space>%sNOTE<ret>xd<space>gj<a-o>j<a-R><space>%sTODO<ret>xd<space>gj<a-o>j<a-R><space>' }

poor man’s solution. Same key pattern occurs three times so not very clever. If anyone got a better/clever solution please post it. Thanks.

Update 03

Cleaned it up a bit you can see the duplication in the key pattern. Not much of an issue, it works. Thanks @alexherbo2 for grep.kak. @robertmeta and @occivink you owe be a beer, it was a ruff road.

declare-user-mode gbuff
# FIXME: requires double <ret> to activate grep-buffer-sort
map global gbuff 'B' ': grep -E "FIXME|NOTE|TODO" %val{bufname} <ret>: grep-buffer-sort' -docstring "grep FIXME|NOTE|TODO in file"
map global gbuff '<c-b>' ': grep -E "FIXME|NOTE|TODO" <.> <ret>: grep-buffer-sort'       -docstring "grep FIXME|NOTE|TODO in dir"
map global gbuff '<up>' ': grep-next-match<ret>'                                         -docstring "Next grep match"
map global gbuff '<down>' ': grep-previous-match<ret>'                                   -docstring "Prev grep match"

# NOTE: locks into gbuff mode for <up> <down> jumpclient navigation
map global normal '0' ': enter-user-mode<space>-lock<space>gbuff<ret>'

define-command -hidden grep-buffer-sort %{
   try %{ execute-keys -buffer *grep* 'gjd%s/[*/]<ret>&%s\s\s+<ret>c<space><esc>&<space>' }
   try %{ execute-keys -buffer *grep* '%sFIXME<ret>xd<space>gj<a-o>ge<a-R><space>' }
   try %{ execute-keys -buffer *grep* '%sNOTE<ret>xd<space>gj<a-o>ge<a-R><space>' }
   try %{ execute-keys -buffer *grep* '%sTODO<ret>xd<space>gj<a-o>ge<a-R><space>' }
}
2 Likes

I don’t remember and don’t have ability to check, but doesn’t grep searches in the file the string after the colon, and changing amount of spaces (alignment) will make the jump fail?

Thanks for the reply Andrey,
the changes happen to the *grep* buffer not the grep search pattern except for the regex flag -E. I’m taking advantage of the hard work already done by @alexherbo2 in grep.kak.

Manipulation of the buffer still maintains an active jump list. The spaces are the distance from the gutter to the string of the original file.

The sort command uses each space to identify columns so sort -k 3 == column 3 == ‘F’,‘N’,‘T’.

grep.kak uses the flags -RHn == recursive, human (not byte), numerical.

So if you have any sed knowledge I think it might be the key to the buffer sort solution. I have no experience with sed and am reviewing sed1line.txt but honestly I’m lost when it comes to sed commands.

The sort command in the buffer is exhausted and provides no other functionality.

I cleaned this up a bit more now excludes the .git directory and *.md files on a recursive directory grep. Continues to work of the inbuilt functionality grep.kak and you can clone the snippet here. Pretty simple and very easy to extend for your language of choice. See kakoune explain the key-sequence for the regex sort.

hook global WinCreate .* %{
  add-highlighter window/ regex (?S)\b(FIXME[:(](.+?(?=\s\*/)|.+)) 1:black,blue+fg
  add-highlighter window/ regex (?S)\b(NOTE[:(](.+?(?=\s\*/)|.+)) 1:red,white+fg
  add-highlighter window/ regex (?S)\b(REMOVE[:(](.+?(?=\s\*/)|.+)) 1:black,magenta+fg
  add-highlighter window/ regex (?S)\b(TEST[:(](.+?(?=\s\*/)|.+)) 1:black,green+fg
  add-highlighter window/ regex (?S)\b(TODO[:(](.+?(?=\s\*/)|.+)) 1:black,yellow+fg
}
# NOTE: requires double <ret> to activate grep-buffer-sort
declare-user-mode gbuff
#----------------------------------------------------------------------------------------------------#
map global gbuff 'B' ': grep -E "FIXME|NOTE|REMOVE|TEST|TODO" %val{bufname} <ret>: grep-buffer-sort' \
  -docstring "grep FIXME|NOTE|REMOVE|TEST|TODO in current buffer file"
#----------------------------------------------------------------------------------------------------#
map global gbuff '<c-b>' ': grep --exclude-dir=.git --exclude=*.md -E "FIXME|NOTE|REMOVE|TEST|TODO" <.> <ret>: grep-buffer-sort' \
  -docstring "grep FIXME|NOTE|REMOVE|TEST|TODO from current directory"
#----------------------------------------------------------------------------------------------------#
map global gbuff '<up>' ': grep-next-match<ret>'       -docstring "Next grep match"
map global gbuff '<down>' ': grep-previous-match<ret>' -docstring "Prev grep match"
#----------------------------------------------------------------------------------------------------#
# NOTE: locks into gbuff mode for <up> <down> jumpclient navigation
map global user 'T' ': enter-user-mode<space>-lock<space>gbuff<ret>' \
  -docstring "enter grep FIXME|NOTE|REMOVE|TEST|TODO user mode"
#----------------------------------------------------------------------------------------------------#
define-command -hidden grep-buffer-sort %{
  try %{ execute-keys -buffer *grep* 'gjd%s:\d+?:\s+?[/*]<ret>s\s+<ret>d%s:\d+?:\s+<ret>s\s+<ret>d%s:\d+?:<ret>l&<space>' }
  try %{ execute-keys -buffer *grep* '%sFIXME<ret>xd<space>gj<a-o>ge<a-R><space>' }
  try %{ execute-keys -buffer *grep* '%sNOTE<ret>xd<space>gj<a-o>ge<a-R><space>' }
  try %{ execute-keys -buffer *grep* '%sREMOVE<ret>xd<space>gj<a-o>ge<a-R><space>' }
  try %{ execute-keys -buffer *grep* '%sTEST<ret>xd<space>gj<a-o>ge<a-R><space>' }
  try %{ execute-keys -buffer *grep* '%sTODO<ret>xd<space>gj<a-o>ge<a-R><space>' }
}

Bye :wave: