Mixing local and remote variables and proper usage and quotation

The name of the pictureThe name of the pictureThe name of the pictureClash Royale CLAN TAG#URR8PPP











up vote
2
down vote

favorite












The recommended pattern for bash as far as I know is to always quote the shell variables.

E.g. "$VAR" instead of $VAR.

But how can I achieve the same safety the quotes provide for variables meant to be interpreted remotely?

E.g in the following:



ssh server.com<<CODE
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt

CODE


For the code to work I need to escape $COUNT and $TARGET.

But how do I achieve the same safety that the "$COUNT" or "$TARGET" provides for this specific case?



Update

I have pasted only the part that is problematic.

I have also other lines that the variables are defined outside of the heredoc so if I use <<'CODE' then the snippet breaks.

For a more complete example:



SOME_STRING="SOME VALUE" 
ssh server.com<<CODE
echo $SOME_VALUE > test_file.txt # <--- does not work if I use <<'CODE'
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt

CODE






share|improve this question






















  • It looks like you might have mixed up SOME_STRING with SOME_VALUE.
    – igal
    Oct 20 '17 at 13:15














up vote
2
down vote

favorite












The recommended pattern for bash as far as I know is to always quote the shell variables.

E.g. "$VAR" instead of $VAR.

But how can I achieve the same safety the quotes provide for variables meant to be interpreted remotely?

E.g in the following:



ssh server.com<<CODE
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt

CODE


For the code to work I need to escape $COUNT and $TARGET.

But how do I achieve the same safety that the "$COUNT" or "$TARGET" provides for this specific case?



Update

I have pasted only the part that is problematic.

I have also other lines that the variables are defined outside of the heredoc so if I use <<'CODE' then the snippet breaks.

For a more complete example:



SOME_STRING="SOME VALUE" 
ssh server.com<<CODE
echo $SOME_VALUE > test_file.txt # <--- does not work if I use <<'CODE'
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt

CODE






share|improve this question






















  • It looks like you might have mixed up SOME_STRING with SOME_VALUE.
    – igal
    Oct 20 '17 at 13:15












up vote
2
down vote

favorite









up vote
2
down vote

favorite











The recommended pattern for bash as far as I know is to always quote the shell variables.

E.g. "$VAR" instead of $VAR.

But how can I achieve the same safety the quotes provide for variables meant to be interpreted remotely?

E.g in the following:



ssh server.com<<CODE
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt

CODE


For the code to work I need to escape $COUNT and $TARGET.

But how do I achieve the same safety that the "$COUNT" or "$TARGET" provides for this specific case?



Update

I have pasted only the part that is problematic.

I have also other lines that the variables are defined outside of the heredoc so if I use <<'CODE' then the snippet breaks.

For a more complete example:



SOME_STRING="SOME VALUE" 
ssh server.com<<CODE
echo $SOME_VALUE > test_file.txt # <--- does not work if I use <<'CODE'
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt

CODE






share|improve this question














The recommended pattern for bash as far as I know is to always quote the shell variables.

E.g. "$VAR" instead of $VAR.

But how can I achieve the same safety the quotes provide for variables meant to be interpreted remotely?

E.g in the following:



ssh server.com<<CODE
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt

CODE


For the code to work I need to escape $COUNT and $TARGET.

But how do I achieve the same safety that the "$COUNT" or "$TARGET" provides for this specific case?



Update

I have pasted only the part that is problematic.

I have also other lines that the variables are defined outside of the heredoc so if I use <<'CODE' then the snippet breaks.

For a more complete example:



SOME_STRING="SOME VALUE" 
ssh server.com<<CODE
echo $SOME_VALUE > test_file.txt # <--- does not work if I use <<'CODE'
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt

CODE








share|improve this question













share|improve this question




share|improve this question








edited Oct 20 '17 at 17:24









Jeff Schaller

32.1k849109




32.1k849109










asked Oct 20 '17 at 12:25









Jim

2,771113256




2,771113256











  • It looks like you might have mixed up SOME_STRING with SOME_VALUE.
    – igal
    Oct 20 '17 at 13:15
















  • It looks like you might have mixed up SOME_STRING with SOME_VALUE.
    – igal
    Oct 20 '17 at 13:15















It looks like you might have mixed up SOME_STRING with SOME_VALUE.
– igal
Oct 20 '17 at 13:15




It looks like you might have mixed up SOME_STRING with SOME_VALUE.
– igal
Oct 20 '17 at 13:15










2 Answers
2






active

oldest

votes

















up vote
1
down vote













It looks like here-docs leave double quotes in place. For example, consider the following command:



cat <<HEREDOC
"this will still be quoted"
HEREDOC


This will produce the following quoted string as its output:



"this will still be quoted:


So you should just be able to quote your variables as usual:



SOME_STRING="SOME VALUE"
ssh server.com<<CODE
echo "$SOME_VALUE" > test_file.txt
TARGET="target dir"
COUNT="$( ls /foo/bar/$TARGET | wc -l )"
echo "$COUNT" > count.txt
CODE


Regarding quoting variables inside command substitutions, refer to the following post: Quoting within $(command substitution) in Bash



Note that I've copied your snippet verbatim, but it looks like you probably meant to use the variable SOME_STRING instead of SOME_VALUE. Here is a slightly modified version of your snippet that I can run locally with the expected results:



mkdir -p "/foo/bar/target dir"

SOME_STRING="SOME VALUE"
ssh localhost<<CODE
echo "$SOME_STRING" > test_file.txt
TARGET="target dir"
COUNT="$( ls "/foo/bar/$TARGET" | wc -l )"
echo "$COUNT" > count.txt
CODE





share|improve this answer






















  • The command substitution should be quoted? And what about the $TARGET in the command substitution? That is unquoted in your code
    – Jim
    Oct 20 '17 at 13:11










  • Tried that. Breaks the script
    – Jim
    Oct 20 '17 at 13:13










  • Yes, you would probably want to quote $TARGET as well. But my point is that the quoting isn't being affected by the here-doc, so there isn't a difference between the local and remote quoting in this situation. Whether or not you want to quote the command substitution or anything else is up to you. A general rule of thumb is to quote everything that you want treated as a single token.
    – igal
    Oct 20 '17 at 13:18










  • The snippet does not compile
    – Jim
    Oct 20 '17 at 13:19










  • Compile? You mean doesn't run as expected?
    – igal
    Oct 20 '17 at 13:22

















up vote
-1
down vote













We seem to get variations on this question a lot over the last few days.



In this case, quote the here-document:



ssh server.com <<'CODE'
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt
then
fi
CODE


The 'CODE' (as opposed to just CODE) will ensure that the here-document is passed to the utility as it is written, without expanding variables or performing command substitutions.



Note that you also have syntax errors in the here-document (spaces around = and no if ta match the then). You should also double-quote the expansions both $COUNT and $TARGET as usual.



ssh server.com <<'CODE'
TARGET="target dir"
COUNT=$( ls "/foo/bar/$TARGET" | wc -l )
printf '%sn' "$COUNT" >count.txt
CODE



If you are trying to count the number of files in a remote directory, use this instead:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ;' | wc -l


This will correctly count the number of files in /path/to/dir.



To write the result to a remote file:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ; | wc -l >file'



If the code that you need to execute remotely is very complex, then it may be better to create a script on the server to run it. The variable that you need to pass to the script can be passed on its command line:



ssh server ./script.sh "$SOME_VARIABLE"


The script:



#!/bin/sh

VAR="$1"

# do stuff





share|improve this answer






















  • The reason I am not using singe quotes around the CODE is because the rest of the commands are not interpreted correctly. Without quotes it works
    – Jim
    Oct 20 '17 at 12:44










  • E.g. if I have the line echo $SOME_VAR > ~/test_file.txt if I use <<'CODE then the file is empty i.e. nothing is printed. And SOME_VAR is defined outside of the here doc
    – Jim
    Oct 20 '17 at 12:57










  • I updated post too
    – Jim
    Oct 20 '17 at 12:59










  • I have more code and the logic is more complex than just counting files. I just pasted the part that shows the issue
    – Jim
    Oct 20 '17 at 13:00










  • @Jim See updated end of my answer.
    – Kusalananda
    Oct 20 '17 at 13:06











Your Answer







StackExchange.ready(function()
var channelOptions =
tags: "".split(" "),
id: "106"
;
initTagRenderer("".split(" "), "".split(" "), channelOptions);

StackExchange.using("externalEditor", function()
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled)
StackExchange.using("snippets", function()
createEditor();
);

else
createEditor();

);

function createEditor()
StackExchange.prepareEditor(
heartbeatType: 'answer',
convertImagesToLinks: false,
noModals: false,
showLowRepImageUploadWarning: true,
reputationToPostImages: null,
bindNavPrevention: true,
postfix: "",
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
);



);













 

draft saved


draft discarded


















StackExchange.ready(
function ()
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2funix.stackexchange.com%2fquestions%2f399335%2fmixing-local-and-remote-variables-and-proper-usage-and-quotation%23new-answer', 'question_page');

);

Post as a guest






























2 Answers
2






active

oldest

votes








2 Answers
2






active

oldest

votes









active

oldest

votes






active

oldest

votes








up vote
1
down vote













It looks like here-docs leave double quotes in place. For example, consider the following command:



cat <<HEREDOC
"this will still be quoted"
HEREDOC


This will produce the following quoted string as its output:



"this will still be quoted:


So you should just be able to quote your variables as usual:



SOME_STRING="SOME VALUE"
ssh server.com<<CODE
echo "$SOME_VALUE" > test_file.txt
TARGET="target dir"
COUNT="$( ls /foo/bar/$TARGET | wc -l )"
echo "$COUNT" > count.txt
CODE


Regarding quoting variables inside command substitutions, refer to the following post: Quoting within $(command substitution) in Bash



Note that I've copied your snippet verbatim, but it looks like you probably meant to use the variable SOME_STRING instead of SOME_VALUE. Here is a slightly modified version of your snippet that I can run locally with the expected results:



mkdir -p "/foo/bar/target dir"

SOME_STRING="SOME VALUE"
ssh localhost<<CODE
echo "$SOME_STRING" > test_file.txt
TARGET="target dir"
COUNT="$( ls "/foo/bar/$TARGET" | wc -l )"
echo "$COUNT" > count.txt
CODE





share|improve this answer






















  • The command substitution should be quoted? And what about the $TARGET in the command substitution? That is unquoted in your code
    – Jim
    Oct 20 '17 at 13:11










  • Tried that. Breaks the script
    – Jim
    Oct 20 '17 at 13:13










  • Yes, you would probably want to quote $TARGET as well. But my point is that the quoting isn't being affected by the here-doc, so there isn't a difference between the local and remote quoting in this situation. Whether or not you want to quote the command substitution or anything else is up to you. A general rule of thumb is to quote everything that you want treated as a single token.
    – igal
    Oct 20 '17 at 13:18










  • The snippet does not compile
    – Jim
    Oct 20 '17 at 13:19










  • Compile? You mean doesn't run as expected?
    – igal
    Oct 20 '17 at 13:22














up vote
1
down vote













It looks like here-docs leave double quotes in place. For example, consider the following command:



cat <<HEREDOC
"this will still be quoted"
HEREDOC


This will produce the following quoted string as its output:



"this will still be quoted:


So you should just be able to quote your variables as usual:



SOME_STRING="SOME VALUE"
ssh server.com<<CODE
echo "$SOME_VALUE" > test_file.txt
TARGET="target dir"
COUNT="$( ls /foo/bar/$TARGET | wc -l )"
echo "$COUNT" > count.txt
CODE


Regarding quoting variables inside command substitutions, refer to the following post: Quoting within $(command substitution) in Bash



Note that I've copied your snippet verbatim, but it looks like you probably meant to use the variable SOME_STRING instead of SOME_VALUE. Here is a slightly modified version of your snippet that I can run locally with the expected results:



mkdir -p "/foo/bar/target dir"

SOME_STRING="SOME VALUE"
ssh localhost<<CODE
echo "$SOME_STRING" > test_file.txt
TARGET="target dir"
COUNT="$( ls "/foo/bar/$TARGET" | wc -l )"
echo "$COUNT" > count.txt
CODE





share|improve this answer






















  • The command substitution should be quoted? And what about the $TARGET in the command substitution? That is unquoted in your code
    – Jim
    Oct 20 '17 at 13:11










  • Tried that. Breaks the script
    – Jim
    Oct 20 '17 at 13:13










  • Yes, you would probably want to quote $TARGET as well. But my point is that the quoting isn't being affected by the here-doc, so there isn't a difference between the local and remote quoting in this situation. Whether or not you want to quote the command substitution or anything else is up to you. A general rule of thumb is to quote everything that you want treated as a single token.
    – igal
    Oct 20 '17 at 13:18










  • The snippet does not compile
    – Jim
    Oct 20 '17 at 13:19










  • Compile? You mean doesn't run as expected?
    – igal
    Oct 20 '17 at 13:22












up vote
1
down vote










up vote
1
down vote









It looks like here-docs leave double quotes in place. For example, consider the following command:



cat <<HEREDOC
"this will still be quoted"
HEREDOC


This will produce the following quoted string as its output:



"this will still be quoted:


So you should just be able to quote your variables as usual:



SOME_STRING="SOME VALUE"
ssh server.com<<CODE
echo "$SOME_VALUE" > test_file.txt
TARGET="target dir"
COUNT="$( ls /foo/bar/$TARGET | wc -l )"
echo "$COUNT" > count.txt
CODE


Regarding quoting variables inside command substitutions, refer to the following post: Quoting within $(command substitution) in Bash



Note that I've copied your snippet verbatim, but it looks like you probably meant to use the variable SOME_STRING instead of SOME_VALUE. Here is a slightly modified version of your snippet that I can run locally with the expected results:



mkdir -p "/foo/bar/target dir"

SOME_STRING="SOME VALUE"
ssh localhost<<CODE
echo "$SOME_STRING" > test_file.txt
TARGET="target dir"
COUNT="$( ls "/foo/bar/$TARGET" | wc -l )"
echo "$COUNT" > count.txt
CODE





share|improve this answer














It looks like here-docs leave double quotes in place. For example, consider the following command:



cat <<HEREDOC
"this will still be quoted"
HEREDOC


This will produce the following quoted string as its output:



"this will still be quoted:


So you should just be able to quote your variables as usual:



SOME_STRING="SOME VALUE"
ssh server.com<<CODE
echo "$SOME_VALUE" > test_file.txt
TARGET="target dir"
COUNT="$( ls /foo/bar/$TARGET | wc -l )"
echo "$COUNT" > count.txt
CODE


Regarding quoting variables inside command substitutions, refer to the following post: Quoting within $(command substitution) in Bash



Note that I've copied your snippet verbatim, but it looks like you probably meant to use the variable SOME_STRING instead of SOME_VALUE. Here is a slightly modified version of your snippet that I can run locally with the expected results:



mkdir -p "/foo/bar/target dir"

SOME_STRING="SOME VALUE"
ssh localhost<<CODE
echo "$SOME_STRING" > test_file.txt
TARGET="target dir"
COUNT="$( ls "/foo/bar/$TARGET" | wc -l )"
echo "$COUNT" > count.txt
CODE






share|improve this answer














share|improve this answer



share|improve this answer








edited Oct 20 '17 at 13:35

























answered Oct 20 '17 at 13:06









igal

4,820930




4,820930











  • The command substitution should be quoted? And what about the $TARGET in the command substitution? That is unquoted in your code
    – Jim
    Oct 20 '17 at 13:11










  • Tried that. Breaks the script
    – Jim
    Oct 20 '17 at 13:13










  • Yes, you would probably want to quote $TARGET as well. But my point is that the quoting isn't being affected by the here-doc, so there isn't a difference between the local and remote quoting in this situation. Whether or not you want to quote the command substitution or anything else is up to you. A general rule of thumb is to quote everything that you want treated as a single token.
    – igal
    Oct 20 '17 at 13:18










  • The snippet does not compile
    – Jim
    Oct 20 '17 at 13:19










  • Compile? You mean doesn't run as expected?
    – igal
    Oct 20 '17 at 13:22
















  • The command substitution should be quoted? And what about the $TARGET in the command substitution? That is unquoted in your code
    – Jim
    Oct 20 '17 at 13:11










  • Tried that. Breaks the script
    – Jim
    Oct 20 '17 at 13:13










  • Yes, you would probably want to quote $TARGET as well. But my point is that the quoting isn't being affected by the here-doc, so there isn't a difference between the local and remote quoting in this situation. Whether or not you want to quote the command substitution or anything else is up to you. A general rule of thumb is to quote everything that you want treated as a single token.
    – igal
    Oct 20 '17 at 13:18










  • The snippet does not compile
    – Jim
    Oct 20 '17 at 13:19










  • Compile? You mean doesn't run as expected?
    – igal
    Oct 20 '17 at 13:22















The command substitution should be quoted? And what about the $TARGET in the command substitution? That is unquoted in your code
– Jim
Oct 20 '17 at 13:11




The command substitution should be quoted? And what about the $TARGET in the command substitution? That is unquoted in your code
– Jim
Oct 20 '17 at 13:11












Tried that. Breaks the script
– Jim
Oct 20 '17 at 13:13




Tried that. Breaks the script
– Jim
Oct 20 '17 at 13:13












Yes, you would probably want to quote $TARGET as well. But my point is that the quoting isn't being affected by the here-doc, so there isn't a difference between the local and remote quoting in this situation. Whether or not you want to quote the command substitution or anything else is up to you. A general rule of thumb is to quote everything that you want treated as a single token.
– igal
Oct 20 '17 at 13:18




Yes, you would probably want to quote $TARGET as well. But my point is that the quoting isn't being affected by the here-doc, so there isn't a difference between the local and remote quoting in this situation. Whether or not you want to quote the command substitution or anything else is up to you. A general rule of thumb is to quote everything that you want treated as a single token.
– igal
Oct 20 '17 at 13:18












The snippet does not compile
– Jim
Oct 20 '17 at 13:19




The snippet does not compile
– Jim
Oct 20 '17 at 13:19












Compile? You mean doesn't run as expected?
– igal
Oct 20 '17 at 13:22




Compile? You mean doesn't run as expected?
– igal
Oct 20 '17 at 13:22












up vote
-1
down vote













We seem to get variations on this question a lot over the last few days.



In this case, quote the here-document:



ssh server.com <<'CODE'
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt
then
fi
CODE


The 'CODE' (as opposed to just CODE) will ensure that the here-document is passed to the utility as it is written, without expanding variables or performing command substitutions.



Note that you also have syntax errors in the here-document (spaces around = and no if ta match the then). You should also double-quote the expansions both $COUNT and $TARGET as usual.



ssh server.com <<'CODE'
TARGET="target dir"
COUNT=$( ls "/foo/bar/$TARGET" | wc -l )
printf '%sn' "$COUNT" >count.txt
CODE



If you are trying to count the number of files in a remote directory, use this instead:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ;' | wc -l


This will correctly count the number of files in /path/to/dir.



To write the result to a remote file:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ; | wc -l >file'



If the code that you need to execute remotely is very complex, then it may be better to create a script on the server to run it. The variable that you need to pass to the script can be passed on its command line:



ssh server ./script.sh "$SOME_VARIABLE"


The script:



#!/bin/sh

VAR="$1"

# do stuff





share|improve this answer






















  • The reason I am not using singe quotes around the CODE is because the rest of the commands are not interpreted correctly. Without quotes it works
    – Jim
    Oct 20 '17 at 12:44










  • E.g. if I have the line echo $SOME_VAR > ~/test_file.txt if I use <<'CODE then the file is empty i.e. nothing is printed. And SOME_VAR is defined outside of the here doc
    – Jim
    Oct 20 '17 at 12:57










  • I updated post too
    – Jim
    Oct 20 '17 at 12:59










  • I have more code and the logic is more complex than just counting files. I just pasted the part that shows the issue
    – Jim
    Oct 20 '17 at 13:00










  • @Jim See updated end of my answer.
    – Kusalananda
    Oct 20 '17 at 13:06















up vote
-1
down vote













We seem to get variations on this question a lot over the last few days.



In this case, quote the here-document:



ssh server.com <<'CODE'
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt
then
fi
CODE


The 'CODE' (as opposed to just CODE) will ensure that the here-document is passed to the utility as it is written, without expanding variables or performing command substitutions.



Note that you also have syntax errors in the here-document (spaces around = and no if ta match the then). You should also double-quote the expansions both $COUNT and $TARGET as usual.



ssh server.com <<'CODE'
TARGET="target dir"
COUNT=$( ls "/foo/bar/$TARGET" | wc -l )
printf '%sn' "$COUNT" >count.txt
CODE



If you are trying to count the number of files in a remote directory, use this instead:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ;' | wc -l


This will correctly count the number of files in /path/to/dir.



To write the result to a remote file:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ; | wc -l >file'



If the code that you need to execute remotely is very complex, then it may be better to create a script on the server to run it. The variable that you need to pass to the script can be passed on its command line:



ssh server ./script.sh "$SOME_VARIABLE"


The script:



#!/bin/sh

VAR="$1"

# do stuff





share|improve this answer






















  • The reason I am not using singe quotes around the CODE is because the rest of the commands are not interpreted correctly. Without quotes it works
    – Jim
    Oct 20 '17 at 12:44










  • E.g. if I have the line echo $SOME_VAR > ~/test_file.txt if I use <<'CODE then the file is empty i.e. nothing is printed. And SOME_VAR is defined outside of the here doc
    – Jim
    Oct 20 '17 at 12:57










  • I updated post too
    – Jim
    Oct 20 '17 at 12:59










  • I have more code and the logic is more complex than just counting files. I just pasted the part that shows the issue
    – Jim
    Oct 20 '17 at 13:00










  • @Jim See updated end of my answer.
    – Kusalananda
    Oct 20 '17 at 13:06













up vote
-1
down vote










up vote
-1
down vote









We seem to get variations on this question a lot over the last few days.



In this case, quote the here-document:



ssh server.com <<'CODE'
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt
then
fi
CODE


The 'CODE' (as opposed to just CODE) will ensure that the here-document is passed to the utility as it is written, without expanding variables or performing command substitutions.



Note that you also have syntax errors in the here-document (spaces around = and no if ta match the then). You should also double-quote the expansions both $COUNT and $TARGET as usual.



ssh server.com <<'CODE'
TARGET="target dir"
COUNT=$( ls "/foo/bar/$TARGET" | wc -l )
printf '%sn' "$COUNT" >count.txt
CODE



If you are trying to count the number of files in a remote directory, use this instead:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ;' | wc -l


This will correctly count the number of files in /path/to/dir.



To write the result to a remote file:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ; | wc -l >file'



If the code that you need to execute remotely is very complex, then it may be better to create a script on the server to run it. The variable that you need to pass to the script can be passed on its command line:



ssh server ./script.sh "$SOME_VARIABLE"


The script:



#!/bin/sh

VAR="$1"

# do stuff





share|improve this answer














We seem to get variations on this question a lot over the last few days.



In this case, quote the here-document:



ssh server.com <<'CODE'
TARGET="target dir"
COUNT= $( ls /foo/bar/$TARGET | wc -l )
echo $COUNT > count.txt
then
fi
CODE


The 'CODE' (as opposed to just CODE) will ensure that the here-document is passed to the utility as it is written, without expanding variables or performing command substitutions.



Note that you also have syntax errors in the here-document (spaces around = and no if ta match the then). You should also double-quote the expansions both $COUNT and $TARGET as usual.



ssh server.com <<'CODE'
TARGET="target dir"
COUNT=$( ls "/foo/bar/$TARGET" | wc -l )
printf '%sn' "$COUNT" >count.txt
CODE



If you are trying to count the number of files in a remote directory, use this instead:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ;' | wc -l


This will correctly count the number of files in /path/to/dir.



To write the result to a remote file:



ssh server 'find "/path/to/dir" -maxdepth 1 -type f -exec echo . ; | wc -l >file'



If the code that you need to execute remotely is very complex, then it may be better to create a script on the server to run it. The variable that you need to pass to the script can be passed on its command line:



ssh server ./script.sh "$SOME_VARIABLE"


The script:



#!/bin/sh

VAR="$1"

# do stuff






share|improve this answer














share|improve this answer



share|improve this answer








edited Oct 20 '17 at 13:05

























answered Oct 20 '17 at 12:39









Kusalananda

105k14209326




105k14209326











  • The reason I am not using singe quotes around the CODE is because the rest of the commands are not interpreted correctly. Without quotes it works
    – Jim
    Oct 20 '17 at 12:44










  • E.g. if I have the line echo $SOME_VAR > ~/test_file.txt if I use <<'CODE then the file is empty i.e. nothing is printed. And SOME_VAR is defined outside of the here doc
    – Jim
    Oct 20 '17 at 12:57










  • I updated post too
    – Jim
    Oct 20 '17 at 12:59










  • I have more code and the logic is more complex than just counting files. I just pasted the part that shows the issue
    – Jim
    Oct 20 '17 at 13:00










  • @Jim See updated end of my answer.
    – Kusalananda
    Oct 20 '17 at 13:06

















  • The reason I am not using singe quotes around the CODE is because the rest of the commands are not interpreted correctly. Without quotes it works
    – Jim
    Oct 20 '17 at 12:44










  • E.g. if I have the line echo $SOME_VAR > ~/test_file.txt if I use <<'CODE then the file is empty i.e. nothing is printed. And SOME_VAR is defined outside of the here doc
    – Jim
    Oct 20 '17 at 12:57










  • I updated post too
    – Jim
    Oct 20 '17 at 12:59










  • I have more code and the logic is more complex than just counting files. I just pasted the part that shows the issue
    – Jim
    Oct 20 '17 at 13:00










  • @Jim See updated end of my answer.
    – Kusalananda
    Oct 20 '17 at 13:06
















The reason I am not using singe quotes around the CODE is because the rest of the commands are not interpreted correctly. Without quotes it works
– Jim
Oct 20 '17 at 12:44




The reason I am not using singe quotes around the CODE is because the rest of the commands are not interpreted correctly. Without quotes it works
– Jim
Oct 20 '17 at 12:44












E.g. if I have the line echo $SOME_VAR > ~/test_file.txt if I use <<'CODE then the file is empty i.e. nothing is printed. And SOME_VAR is defined outside of the here doc
– Jim
Oct 20 '17 at 12:57




E.g. if I have the line echo $SOME_VAR > ~/test_file.txt if I use <<'CODE then the file is empty i.e. nothing is printed. And SOME_VAR is defined outside of the here doc
– Jim
Oct 20 '17 at 12:57












I updated post too
– Jim
Oct 20 '17 at 12:59




I updated post too
– Jim
Oct 20 '17 at 12:59












I have more code and the logic is more complex than just counting files. I just pasted the part that shows the issue
– Jim
Oct 20 '17 at 13:00




I have more code and the logic is more complex than just counting files. I just pasted the part that shows the issue
– Jim
Oct 20 '17 at 13:00












@Jim See updated end of my answer.
– Kusalananda
Oct 20 '17 at 13:06





@Jim See updated end of my answer.
– Kusalananda
Oct 20 '17 at 13:06


















 

draft saved


draft discarded















































 


draft saved


draft discarded














StackExchange.ready(
function ()
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2funix.stackexchange.com%2fquestions%2f399335%2fmixing-local-and-remote-variables-and-proper-usage-and-quotation%23new-answer', 'question_page');

);

Post as a guest













































































Popular posts from this blog

How to check contact read email or not when send email to Individual?

Bahrain

Postfix configuration issue with fips on centos 7; mailgun relay