EDIT
Between the following answers, chepner's and Walter_A's solve the problem. Shortly, to print a single quote from within a find command, you
(1) use "\047" instead of the single quote or
(2) define a local variable, e.g. q="'" just before the find command and use $q instead of the single quote sign.
Therefore, the solution to this specific problem is not in using printf instead of echo or a for loop instead of find...exec, but both printf and for may help improve the code.
ORIGINAL QUESTION:
I am trying to automatize the following process:
find certain files in current directory;
append a line to a text file for each file name, where the filename is preceded by the string "file " and is enclosed between single quotes.
This is in fact a simplified version of the task: the files I search for are video files and ffmpeg does some work on them before trying to write their names to a text file. The purpose of the text file is to concatenate the output files later. The full line is this:
find . -maxdepth 1 -iname "name*" -exec sh -c 'ffmpeg -i "$0" -ss 3.3 -c:v libx264 -crf 20 -pix_fmt yuv420p -c:a copy "out/""$0"; echo "file ""\'""$(basename -- "$0")">>mylist.txt' {} \;
However, the video part works well and I would just focus on the printing of the single quote (on screen or to a file), which is giving me trouble. If I try this:
find . -iname "*" -exec sh -c 'echo "file ""$0"' {} \;
I get, as expected:
file a1.mp4
file a2.mp4
[...]
I now add a single quote before the file name $0; between double or single quotes, escaped or not (if escaped, I also tried it without quotes), between quotes after a dollar sign, but all I get is the symbol ">" followed by a blinking cursor, waiting for more input.
I have tried to insert the single quote as: "\'", '\'', \', $''', $'\'', $"\'"; I have put it within the string "file ", with and without single or double quotes; I have set a variable v="file ""\'""$0" within the exec and echoed it, between double quotes. All my attempts have failed, though. It would be good to understand why. Perhaps there is something to learn here... Thank you for the advice you might give.
______________ WORKAROUND _______________
I have found a workaround. I write a bash file instead of giving a single command from the Terminal. Before the find line I export a variable SQ="'". Then my find line becomes:
find . -maxdepth 1 -iname "*" -exec sh -c 'echo "file ""$SQ""$(basename -- "$0")""$SQ"' {} \;
And it works. Perhaps the single quotes occurring in an exported variable are not treated in the same way as single quotes occurring in strings within the shell or in local variables?
Assign a quote to a temp variable (I also remove the path).
q="'" find . -iname "*" -exec sh -c 'echo "file $q${0##*/}$q"' {} \;