0

I have a string

start = """<?xml version="1.0" encoding="utf-8" ?><soap:Envelope \
         xmlns="http://tempuri.org/"> \
                    <UserName>username</UserName><Password>password</Password>\
                    xmlns="http://tempuri.org/"><oShipData>"""

I want to use environmental variables for username and password, instead of hardcoding them in the code, I tried this

import os
start = """<?xml version="1.0" encoding="utf-8" ?><soap:Envelope \
         xmlns="http://tempuri.org/"> \
                    <UserName>"""os.environ["username"]"""</UserName><Password>"""os.environ["password"]"""</Password>
                    xmlns="http://tempuri.org/"><oShipData>"""

But this gives me an error:

"errorMessage": "Syntax error in module 'test': invalid syntax (test.py, line 5)",
    "errorType": "Runtime.UserCodeSyntaxError"

How can I escape the strings and dynamically get values from os.environ within the strings?

martineau
  • 119,623
  • 25
  • 170
  • 301
ashakshan
  • 419
  • 1
  • 5
  • 17
  • Just add `+` on both sides to let it work. There're plenty of methods how you can achieve required result, take a look on [`str.format()`](https://docs.python.org/3/library/stdtypes.html#str.format). Your data is in XML format, so it'll be good to use [`xml.etree`](https://docs.python.org/3/library/xml.etree.elementtree.html) to build XML object. – Olvin Roght Dec 10 '20 at 22:01
  • Does this answer your question? [Multiline f-string in Python](https://stackoverflow.com/questions/45965007/multiline-f-string-in-python) – Random Davis Dec 10 '20 at 22:01
  • @RandomDavis , I tried using similar formatting like this f"house_bill_nbr = '{house_bill_nbr}'" in my code, but since this is XML, it was not accepting that kind of formatting – ashakshan Dec 10 '20 at 22:11

4 Answers4

1

You could use f-strings:

import os
start = f"""<?xml version="1.0" encoding="utf-8" ?><soap:Envelope \
         xmlns="http://tempuri.org/"> \
                    <UserName>{os.environ['username']}</UserName><Password>{os.environ['password']}</Password>
                    xmlns="http://tempuri.org/"><oShipData>"""
Andreas Forslöw
  • 2,220
  • 23
  • 32
0

You can add strings together in python. So "teststring" is a normal string, but "test"+variable+"string" will result in a string that has the value of variable in the middle, assuming that variable is of type string. If not, use "test"+str(variable)+"string".

import os
start = """<?xml version="1.0" encoding="utf-8" ?><soap:Envelope \
         xmlns="http://tempuri.org/"> \
                    <UserName>"""+str(os.environ["username"])+"""</UserName><Password>"""+str(os.environ["password"])+"""</Password>
                    xmlns="http://tempuri.org/"><oShipData>"""

should work.

HilbertB
  • 352
  • 1
  • 2
  • 12
0

If you're planning to work with XML object, it's always good to use some classes which generate XML document. In python there's built-in xml.etree.ElementTree.

Code:

import os
import xml.etree.ElementTree as ET

envelope = ET.Element("soap:Envelope", attrib={"xmlns": "http://tempuri.org/"})
username = ET.SubElement(envelope, "UserName")
username.text = os.environ["username"]
password = ET.SubElement(envelope, "Password")
password.text = os.environ["password"]

start = ET.tostring(envelope, encoding="utf-8", xml_declaration=True).decode()

Result:

<?xml version='1.0' encoding='utf-8'?>
<soap:Envelope xmlns="http://tempuri.org/"><UserName>user</UserName><Password>pass</Password></soap:Envelope>

P.S. On python 3.9+ you can use ET.indent(envelope) to get pretty printed result (insert this before ET.tostring() call).

Olvin Roght
  • 7,677
  • 2
  • 16
  • 35
-2

You can't just put the string and the code next to another, you muse concatenate them with a +

start = """
<?xml version="1.0" encoding="utf-8" ?>
    <soap:Envelope xmlns="http://tempuri.org/"> 
        <UserName>""" + os.environ["username"] + """</UserName>
        <Password>""" + os.environ["password"] + """</Password>
    <oShipData>"""
azro
  • 53,056
  • 7
  • 34
  • 70