Reputation: 95
This command works well in command prompt :
]$ ls -ltr ../cmxserver.log*|grep "`date | awk '{print $2" "$3}'`"|cut -d "/" -f2
cmxserver.log.2
cmxserver.log.1
cmxserver.log
However, using this in for loop gives error bash: syntax error near unexpected token `|'
]$for y in `ls -ltr ../cmxserver.log*|grep "`date | awk '{print $2" "$3}'`"|cut -d "/" -f2`
-bash: syntax error near unexpected token `|'
Any idea ?
Thanks
Upvotes: 3
Views: 15870
Reputation: 241791
You probably understood what you meant when you typed:
for y in `ls -ltr ../cmxserver.log*|grep "`date | awk '{print $2" "$3}'`"|cut -d "/" -f2`
But you have managed to completely confuse bash. Bash (and other shells) don't nest backticks (`) unless the inner ones are backslashed. As written, the second backtick is considered to close the first one, resulting in the command ls -ltr ../cmxserver.log*|grep "
. Since you did not put a space before date
, the word date
is parsed as part of the word including the command substitution. Similarly, the single-quoted '{print $2"$3}'
is parsed as being prepended to the backticked command "|cut -d "/" -f2
.
Of course, both of those backticked commands are syntax errors because they contain unclosed double quotes, but before bash reaches the point of parsing and executing the commands, it is left with something which roughly speaking looks like:
for y in word1 | awk word2
which is a syntax error because the pipe symbol can only appear between complete commands, and for y in word1
is not a complete command.
Backticks are deprecated. Stop using them.
If you had written:
for y in $(ls -ltr ../cmxserver.log* |
grep "$(date | awk '{print $2" "$3}')" |
cut -d "/" -f2)
both bash and human readers would have found the expression much easier to parse, and bash would have parsed it as you expected.
Having said that, it is never a good idea to try to parse ls
output, and it is never necessary to parse date
output because you can specify a format string; in this case, you could have used date +"%b %d"
to get the month and day. (First link courtesy of a comment by Charles Duffy.)
Upvotes: 2
Reputation: 614
The whole line can be solved by find
command:
find .. -maxdepth 1 -mtime -1 -daystart -name 'cmxserver.log*' -printf "%f\n"
..
- directory where to search-maxdepth 1
- don't go recursive to subdirectories-mtime -1
- only today's files-daystart
- count the day since midnight, not last 24 hrs-name 'cmxserver.log*'
- filenames-printf "%f\n"
- print only basenameUpvotes: 4