I am not quite sure what you are trying to do, but one issue which can come up is getting awk
to print out what ls
considers to be the last field, but which awk
does not consider to be so (via its default parsing). eg.
-rw-r--r-- | 433k | filename-with-no-spaces
-rw-r--r-- | 1k | link containing spaces -> /home/user/filename-with-no-spaces
Somehow you need to isolate the last ls
field. The approach taken below, is to find the length of all preceding fields and delilimiter. The rest is the filename field (plus other info, like a link's target).
The script below determines the maximum width of the variable-width size field (needed for output formatting). There are multiple ways to get this width; eg. (1) use awk
to process each line of ls
output ,in the main loop, adding each line to an array for subequent END{ }
processing. or (2) write the output of ls
to a temporary file, and then have awk
process that file. The method shown below uses (2).
Note that the output of ls
can send some perhaps unexpected, non-simple, outpt your way, as in the case of a link
, so it is generally safer to use find
and customize it's output to better suit your parsing needs.
f=7 # the number of (multi-space) delimiters before the start of the filename
myls="$(mktemp)" # a temp file to hold output from `ls`
w=$(ls --color=always -lFHk ~/ |tee "$myls" |awk '{print $5}' |wc -L) # max width of size field
h=k # size unit
awk --re-interval -v"f=$f" -v"w=$w" -v"h=$h" '
NF >= f {
regex = "^([^ ]+ +){"f"}"
match( $0, regex ) # find start of name field
printf( "%s | %"w"s%s | %s\n", $1, $5, h, substr( $0, RLENGTH ))
}' "$myls"
rm "$myls"
ls
output for your own good. That is almost never the right approach for most tasks. I would suggest telling us instead what you hope to accomplish, so others may suggest better approaches. – jw013 Jul 16 '12 at 01:31ls
in for loops etc. I don't see why I shouldn't useawk
to parse it. AFAIKls
gives a clean output, with fields separated by whitespaces. And I think thatless
was created to parse exactly that kind of data. – westeros91 Jul 16 '12 at 01:36ls
doesn't display filenames reliably when strange characters are present. There's also possible inconsistencies with the time format. There is no reliable way to parsels
output - it doesn't matter what you try to use. Awk does not have special magic that allows it to parsels
. Finally,less
is just a pager - it doesn't parse anything. – jw013 Jul 16 '12 at 01:47ls
wrapper. I have no intention of working with files based on the output ofls
. I merely want to show the output in a different form. I still don't see how special characters would cause a problem to that. And I don't know why I mentionedless
in my earlier comment (and I can't edit it now :P). I meantawk
alright. https://github.com/trapd00r/ls--/ parsesls
uses Perl. – westeros91 Jul 16 '12 at 01:56ls -lfH ${@} | awk 'NR>9{print ....}'
don't you? You don't need an intervening script. 99% of all unix tools allow piping of stdout from 1st program, into stdin of 2nd program, and chained on to a reasonable infinitystdout|stdin ...
Good luck. – shellter Jul 16 '12 at 02:34tree
. Most distributions have a package for it. – jw013 Jul 16 '12 at 12:48stat
and build the desired output yourself, instead of tweaking the output ofls
. – janmoesen Jul 16 '12 at 13:43