I have a plugin that generates and copies to the clipboard a ready-to-paste command which then creates a file that I want to move and rename via user input.

If I use this to get the latest modified file in the directory, then the file is correctly copied and renamed as specified in the script:

gnome-terminal --tab-with-profile=PROFILENAME --working-directory="/PATH/WAY" -x bash -c "$(xclip -se c -o); find /PATH/WAY -type f -printf '%TY-%Tm-%Td %TT %p\n' | sort -r | head -n1 | grep -o "/home.*" | xargs -I '{}' cp '{}' /PATH/TO/Desktop/test.txt; read -p 'Press Enter to close.'"

However, if I try to add the user input like this, then the variable does not seem to be set:

gnome-terminal --tab-with-profile=PROFILENAME --working-directory="/PATH/WAY" -x bash -c "$(xclip -se c -o); echo File name?; read newfile; echo File will be named $newfile.txt; find /PATH/WAY -type f -printf '%TY-%Tm-%Td %TT %p\n' | sort -r | head -n1 | grep -o "/PATH.*" | xargs -I '{}' cp '{}' /PATH/TO/Desktop/$newfile.flv; read -p 'Press Enter to close.'"

Because output says File will be named .txt while I'm expecting File will be named USERINPUT.txt, and the file is not copied.

Interestingly, if I use these commands in a bash script like this, then everything works ok:

echo File name?
read newfile
echo File will be named $newfile.txt
find /PATH/WAY -type f -printf '%TY-%Tm-%Td %TT %p\n' | sort -r | head -n1 | grep -o "/PATH.*" | xargs -I '{}' cp '{}' /PATH/TO/Desktop/$newfile.txt
read -p 'Press Enter to close.'

I don't understand what I'm doing wrong...

  • Ideally, this should be a script. It's a bit long for putting in one-line format. – wjandrea Nov 7 '17 at 21:51

The single big parameter after bash -c is within double quotes. That means, substitution of certain things (including $newfile) is performed here by the outmost shell, i.e. the shell that is about to launch gnome-terminal, before launching it. In that context this variable is undefined.

I recommend that you go for a separate script, as you've shown at the bottom of your post. The one-liners are terribly unreadable anyways.

Other possibilities include swapping ' and " quotes in the command line so that ' is the outer one (that is, $newline remains $newline and isn't substituted by the outmost shell, it's interpreted later by the one started by gnome-terminal); or escaping the $ sign in $newfile as \$newfile.

And while we're at it:

$(xsel ...) executes the clipboard's contents as a command (or series of commands) without any validation whatsoever. E.g. if your clipboard contains the string rm -rf ~, your home directory is whoops gone. I'm not sure what your intent is, but for your safety, you should ditch this approach and find another solution!

echo File name? performs shell pattern matching on files whose names consist of five characters: name and then one arbitrary character. Use a pair of single or double quotes.

You refer to the variable name $newfile without quote marks. This will result in faulty behavior if it contains whitespaces. Refer to it as "$newfile" instead.

  • Thanks @egmont and @wjandrea, I'm going for a separate script (although I tested the swapping of ' and " which also worked). I modified the echo command for this post, the actual one is not in English, but I'll use quotes anyway, probably a good habit to take up! – MonkeyBack Nov 7 '17 at 22:46

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.