beyondgrep/ack1

Output line numbers of matches when acking a single file

ks1322 opened this issue · 5 comments

Ack automatically outputs line numbers when searching inside directories or in multiple files, but not when searching in a single file.

Here is related discussion on this bug: https://groups.google.com/forum/?fromgroups=#!topic/ack-users/DYLSP3bemLw

Workaround is to search in some second file as well, for example in /dev/null:

ack somepattern somefile /dev/null

Your "bug" is actually "intentional behavior that you don't like."

We can talk about the pros and cons of that design choice, but it's not a bug. It matches the behavior of grep.

With ack 2.00b02

plankton:~/ack2 :( $ ack foo t/resource-iterator.t  t/illegal-regex.t 
t/resource-iterator.t
49:            t/swamp/file.foo

t/illegal-regex.t
15:    [ 'illegal pattern',  '?foo', 't/' ],
16:    [ 'illegal -g regex', '-g', '?foo', 't/' ],
plankton:~/ack2 $ ack foo t/illegal-regex.t 
    [ 'illegal pattern',  '?foo', 't/' ],
    [ 'illegal -g regex', '-g', '?foo', 't/' ],

With grep:

plankton:~/ack2 $ grep foo t/resource-iterator.t  t/illegal-regex.t 
t/resource-iterator.t:            t/swamp/file.foo
t/illegal-regex.t:    [ 'illegal pattern',  '?foo', 't/' ],
t/illegal-regex.t:    [ 'illegal -g regex', '-g', '?foo', 't/' ],
plankton:~/ack2 $ grep foo t/illegal-regex.t 
    [ 'illegal pattern',  '?foo', 't/' ],
    [ 'illegal -g regex', '-g', '?foo', 't/' ],

Probably my description was not clear enough...

In the following example I expect ack will output line numbers of matches when searching a single file. But this is not the case and I don't know any way to make ack do it:

:~$ ack-grep unity .xsession-errors
Profile     : unity
Initializing unitymtgrabhandles options...done
Initializing unityshell options...done
:~$ 

I can do it easily with grep applying -n option, so I expect that ack will do the same thing, though ack prints line numbers by default and no additional options needed:

:~$ grep -n unity .xsession-errors
3:Profile     : unity
24:Initializing unitymtgrabhandles options...done
32:Initializing unityshell options...done
:~$ 

After looking at source code I found the reason of this behavior.

The problem is that printing line numbers depends on printing file name which is off for single file.
As a result no file name is printed and no line numbers are printed also.
This patch could fix the problem:

diff --git a/ack b/ack
index 6a9c66f..bcc37ba 100755
--- a/ack
+++ b/ack
@@ -2243,13 +2243,14 @@ sub print_match_or_context {

         if ( $show_filename ) {
             App::Ack::print_filename($display_filename, $sep) if not $heading;
-            my $display_line_no =
-                $color
-                    ? Term::ANSIColor::colored( $line_no, $ENV{ACK_COLOR_LINENO} )
-                    : $line_no;
-            App::Ack::print_line_no($display_line_no, $sep);
         }

+        my $display_line_no =
+            $color
+                ? Term::ANSIColor::colored( $line_no, $ENV{ACK_COLOR_LINENO} )
+                : $line_no;
+        App::Ack::print_line_no($display_line_no, $sep);
+
         if ( $output_func ) {
             while ( /$regex/go ) {
                 App::Ack::print( $output_func->() . "\n" );

Nevertheless using --with-filename option will always print file name and therefore line numbers.

Hi, the default choice is not really a problem. Grep has a flag to force line numbers on, which is what I'm looking for.

All future development on ack is happening on https://github.com/petdance/ack2. This issue has been moved here: beyondgrep/ack2#196