Expansion of variables inside single quotes in a command in Bash
Inside single quotes everything is preserved literally, without exception.
That means you have to close the quotes, insert something, and then re-enter again.
'before'"$variable"'after'
'before'"'"'after'
'before'\''after'
Word concatenation is simply done by juxtaposition. As you can verify, each of the above lines is a single word to the shell. Quotes (single or double quotes, depending on the situation) don't isolate words. They are only used to disable interpretation of various special characters, like whitespace, $
, ;
... For a good tutorial on quoting see Mark Reed's answer. Also relevant: Which characters need to be escaped in bash?
Do not concatenate strings interpreted by a shell
You should absolutely avoid building shell commands by concatenating variables. This is a bad idea similar to concatenation of SQL fragments (SQL injection!).
Usually it is possible to have placeholders in the command, and to supply the command together with variables so that the callee can receive them from the invocation arguments list.
For example, the following is very unsafe. DON'T DO THIS
script="echo \"Argument 1 is: $myvar\""
/bin/sh -c "$script"
If the contents of $myvar
is untrusted, here is an exploit:
myvar='foo"; echo "you were hacked'
Instead of the above invocation, use positional arguments. The following invocation is better -- it's not exploitable:
script='echo "arg 1 is: $1"'
/bin/sh -c "$script" -- "$myvar"
Note the use of single ticks in the assignment to script
, which means that it's taken literally, without variable expansion or any other form of interpretation.
Difference between single and double quotes in Bash
Single quotes won't interpolate anything, but double quotes will. For example: variables, backticks, certain \
escapes, etc.
Example:
$ echo "$(echo "upg")"
upg
$ echo '$(echo "upg")'
$(echo "upg")
The Bash manual has this to say:
3.1.2.2 Single Quotes
Enclosing characters in single quotes (
'
) preserves the literal value of each character within the quotes. A single quote may not occur between single quotes, even when preceded by a backslash.3.1.2.3 Double Quotes
Enclosing characters in double quotes (
"
) preserves the literal value of all characters within the quotes, with the exception of$
,`
,\
, and, when history expansion is enabled,!
. The characters$
and`
retain their special meaning within double quotes (see Shell Expansions). The backslash retains its special meaning only when followed by one of the following characters:$
,`
,"
,\
, or newline. Within double quotes, backslashes that are followed by one of these characters are removed. Backslashes preceding characters without a special meaning are left unmodified. A double quote may be quoted within double quotes by preceding it with a backslash. If enabled, history expansion will be performed unless an!
appearing in double quotes is escaped using a backslash. The backslash preceding the!
is not removed.The special parameters
*
and@
have special meaning when in double quotes (see Shell Parameter Expansion).
How do I use variables in single quoted strings?
Variables are expanded in double quoted strings, but not in single quoted strings:
$ name=World
$ echo "Hello $name"
Hello World
$ echo 'Hello $name'
Hello $name
If you can simply switch quotes, do so.
If you prefer sticking with single quotes to avoid the additional escaping, you can instead mix and match quotes in the same argument:
$ echo 'single quoted. '"Double quoted. "'Single quoted again.'
single quoted. Double quoted. Single quoted again.
$ echo '"$name" has the value '"$name"
"$name" has the value World
Applied to your case:
echo 'test text "here_is_some_test_text_'"$counter"'" "output"' >> "$FILE"
how to use the bash variable in single quotes
Variables don't expand in single quotes, which means that you simply have to ensure that they are not single-quoted. You have several possibilities, for instance:
'payload={"text": "failure with '"${VAR}"' failed for"}'
or
"payload={\"text\": \"failure with ${VAR} failed for\"}"
Bash: Variable in single quote
I'll add yet another option to the list: define a variable as newline, then use that inside double-quotes.
nl=$'\n'
...
--summary "Today is ${date}. Poor whiskers takes a tumble.${nl}She's fine, though, don't worry."
How to escape single quotes within single quoted strings
If you really want to use single quotes in the outermost layer, remember that you can glue both kinds of quotation. Example:
alias rxvt='urxvt -fg '"'"'#111111'"'"' -bg '"'"'#111111'"'"
# ^^^^^ ^^^^^ ^^^^^ ^^^^
# 12345 12345 12345 1234
Explanation of how '"'"'
is interpreted as just '
:
'
End first quotation which uses single quotes."
Start second quotation, using double-quotes.'
Quoted character."
End second quotation, using double-quotes.'
Start third quotation, using single quotes.
If you do not place any whitespaces between (1) and (2), or between (4) and (5), the shell will interpret that string as a one long word.
Single quotes around variable value
Like every other command the assignment of a value to a variable will be parsed by the shell, too. To prevent the shell from parsing the special characters must be "quoted". Single characters can be quoted with the backslash (\), multiple characters can be quoted with single quotes (') or double quotes ("). Within single quotes every character will be taken literally. Double-quoted characters will mostly taken literally, with the main exeption (among some others): variables will be replaced with their contents.
To assign the Value "JSBDbshe66!#12$@a" in the command line it must be single-quoted because of the bang (!) sign (see bash bang for further information):
:~$ DEV_ARM_CLIENT_SECRET='JSBDbshe66!#12$@a'
The command
:~$ echo $DEV_ARM_CLIENT_SECRET
gives you the desired output:
JSBDbshe66!#12$@a
To copy this value to another variable just enter in the command line:
ARM_CLIENT_SECRET=$DEV_ARM_CLIENT_SECRET
Alternatively you can enter:
ARM_CLIENT_SECRET="$DEV_ARM_CLIENT_SECRET"
to receive the same result. The variable-name between the double quotes will be replaced with the value and finally the shell removes the Quotes. If you put the variable name between single quotes
ARM_CLIENT_SECRET='$DEV_ARM_CLIENT_SECRET'
every character between the quotes will be taken literally:
:~$ echo $ARM_CLIENT_SECRET
$DEV_ARM_CLIENT_SECRET
If you quote the single quotes via Backslash
:~$ ARM_CLIENT_SECRET=\'$DEV_ARM_CLIENT_SECRET\'
the value of "$ARM_CLIENT_SECRET" will be the same as $DEV_ARM_CLIENT_SECRET with an additional leading and a trailing single quote:
:~$ echo $ARM_CLIENT_SECRET
'JSBDbshe66!#12$@a'
How do I expand a variable inside single quotes?
You could just use double quotes, escaping the ones inside the JSON string:
curl https://www.googleapis.com/urlshortener/v1/url?key=MyKey -H \\
'Content-Type: application/json' -d "{\"longUrl\": \"$1\"}"
How to echo variable inside single quotes using Bash?
JSON string values should be quoted and so should parameter expansions. You can achieve this by using double quotes around the entire JSON string and escaping the inner double quotes, like this:
curl -i -H "Content-Type: application/json" -X POST -d "{\"mountpoint\":\"$final\"}" http://127.0.0.1:5000/connect
As mentioned in the comments, a more robust approach would be to use a tool such as jq
to generate the JSON:
json=$(jq -n --arg final "$final" '{ mountpoint: $final }')
curl -i -H "Content-Type: application/json" -X POST -d "$json" http://127.0.0.1:5000/connect
Related Topics
How to Recover the Return Value of a Function Passed to Multiprocessing.Process
Changes in Import Statement Python3
Pipe Raw Opencv Images to Ffmpeg
Python Multiprocessing Memory Usage
Getting Another Program's Output as Input on the Fly
How to Obtain Ports That a Process in Listening On
Cannot Get Environment Variables in Django Settings File
"Valueerror: _Type_ 'V' Not Supported" Error After Installing Pyreadline
Can't Install Gcloud on Amazon Linux:Invalid Syntax
How to Find the Target File's Full(Absolute Path) of the Symbolic Link or Soft Link in Python
Python Requests, How to Specify Port for Outgoing Traffic
How to Make Shell Output Redirect (>) Write While Script Is Still Running
How to Set File Permissions in Python3
Reading from Linux Command Line with Python