Take the 2-minute tour ×

I'm writing a deploy script, and I need to run a less compiler against all .less files in a directory. This is easy to do with the following find command:

find -name "*.less" -exec plessc {} {}.css \;

After running this command on a folder with a file named main.less, I'm left with a file named main.less.css, but I want it to be main.css.

I know I can easily strip the .less portion of the resulting files with this command: rename 's/\.less//' *.css but I'm hoping to learn something new about using -exec.

Is it possible to modify the name of the file that matches while using it in the -exec parameter?


share|improve this question
add comment

2 Answers

up vote 3 down vote accepted

Your find command is using a couple of non standard GNU extensions:

  • You do not state where to find, this is an error in POSIX but GNU find select the current directory in that case
  • You use a non isolated {}, POSIX find doesn't expand it in that case.

Here is a one liner that should work with most find implementations and fix your double extension issue:

find . -name "*.less" -exec sh -c "plessc \$0 \$(dirname \$0)/\$(basename \$0 less)css" {} \;

On Solaris 10 and older, sh -c should be replaced by ksh -c if the PATH isn't POSIX compliant.

share|improve this answer
add comment

No, it is not possible to do it directly. You can only use {} to directly insert the full filename. However, in exec, you COULD put in other things like awk. Or you can redirect output to another program via pipes.

From the find man page:

   -exec command ;
          Execute command; true if 0 status is  returned.   All  following
          arguments to find are taken to be arguments to the command until
          is  replaced by the current file name being processed everywhere
          protect  them  from  expansion  by  the shell.  See the EXAMPLES
          specified command is run once for each matched file. The command 
          is executed in the starting directory.   There  are  unavoidable
          security  problems  surrounding  use  of  the -exec action;  you
          should use the -execdir option instead.
share|improve this answer
add comment

Your Answer


