I need to produce JSON configuration files
with echo
and tee
called from my Python script.
By trial-and-error I've found out that I have to use single quotes.
Yet I don't understand all the behaviour that I came across
when using Python's run()
.
The following code prints my questions:
#!/usr/bin/env python3
from subprocess import run
conf_file="""{
"alt-speed-down": 50,
}"""
print("Question 1. It does not work with double quotes. Why?")
run(f"""echo "{conf_file}" """, shell=True)
print("It works with single quotes.")
run(f"""echo '{conf_file}'""", shell=True)
conf_file="""{
"alt-speed-down": 50,
}"""
print("""Question 2. It does not work with double quotes, even when I escape the quotes.
Whereas when I type in my shell:
echo ""This is a quoted string.""
it works. Why?
""")
run(f"""echo "{conf_file}" """, shell=True)
print("""Question 3. It works with single quotes, even with escaped quotes.
whearas when I type in my shell:
echo '"this is quoted"'
I get the backslashes printed. Why aren't
the backslashes printed when called with Python's run()?""")
run(f"""echo '{conf_file}'""", shell=True)
I use Bash as my shell. Why does escaping double quotes differ when done from my Bash shell compared to Python's run. Am I not accessing my Bash shell with specifying
shell=True
in run()
?
P.S. I know that generating JSON with json
module is a way to do this, but in my case it is mostly copying already existing JSON from
my backed up configuration files. I want to avoid reading such JSON files into a string in my script - the script is meant to be run on the newly reinstalled OS where such backups won't be initially available. That is why I need to have many string variables in my Python string that store such JSON configuration files
bash
. – Kusalananda Feb 22 '23 at 10:54json
module, which generates working JSON. Also, usingtee
from a language that can do whatever you want with strings sounds like you really want to spend a tiny bit more time learning Python if you choose to use it. – Marcus Müller Feb 22 '23 at 11:07"""
gives me when defining multiline strings. Thanks to this I do not have to escape many quotes in my multiline Bash commands or JSON files. Also, Python being statically scoped helps a bit when my configuration scripts get really lengthy. – John Smith Feb 22 '23 at 11:27run()
just to do anecho
? Python has aprint
function built-in! – jwodder Feb 22 '23 at 19:16run(f"""doas systemctl stop transmission-daemon && doas sed -i '/^/d' /var/lib/transmission-daemon/info/settings.json && echo '{conf_file}'|doas tee /var/lib/transmission-daemon/info/settings.json && doas sed -i '/^/d' /etc/transmission-daemon/settings.json && echo '{conf_file}'|doas tee /etc/transmission-daemon/settings.json""", shell=True)
but I didn't want to clutter the question with something that is not string manipulation and quoting. – John Smith Feb 22 '23 at 20:41JSON
module for parsing/modifying/generating json. Also much of what you learn in perl, awk, or sed (and grep to a lesser extent) helps with learning the others - not so much with python, it's too different. Or just use bash - nothing in your script above requires python. – cas Feb 23 '23 at 00:35