0

i'm having trouble creating the xml file in python. My script at start loads a text file, read each line and check if the content contains a specific string, depending on it i want to create a tag or in the xml file. For that i'm using the ElementTree module.

This the code

for line in myfile.read().splitlines():
    if 'EXTINF' in line:
        root = etree.Element("item")
        etree.SubElement(root, "title").text = line
    elif 'http' in line:
        etree.SubElement(root, "link").text = 'http:\\mysite.com\'
tree = etree.ElementTree(root)
tree.write('my\\path\\'+xml_file.xml)

The xml file contains only the last element iterated by for loop.

The output i would like is:

<item>
    <title> "my title" </title>
    <link> "http:\\mysite.com" </link>
</item>

<item>
    <title> "my title" </title>
    <link> "http:\\mysite.com" </link>
</item>

<item>
    <title> "my title" </title>
    <link> "http:\\mysite.com" </link>
</item>

What's wrong? Thanks

1 Answer 1

1

You're replacing the Element that you're assigning as the root variable each time you find 'EXTINF'.

for line in myfile.read().splitlines():
    if 'EXTINF' in line:
        root = etree.Element("item") ## Creates a New Element called "item" with a variable name of "root"
        etree.SubElement(root, "title").text = line ## Creates a subelement called "title" to the current root variable
    elif 'http' in line:
        etree.SubElement(root, "link").text = 'http:\\mysite.com\' ## Creates a subelement called "title" to the current root variable

tree = etree.ElementTree(root) ## Create an ElementTree Object using the current root variable
tree.write('my\\path\\'+xml_file.xml)

So, obviously, you need to determine what the root variable should be (the lowest node in the XML tree) and then use a different variable for creating SubElements of root. Also, based on your original code and your desired output, I'm assuming that only items with titles should be outputted, so your code would need to reflect that (specifically, in your code you only create the item element if 'EXTINF' is in the line, and none of your example outputs were lacking a title).

root = etree.Element("root")
for line in myfile.read().splitlines():
    if 'EXTINF' in line:  ## If it has a title, then create an item.
        subelement = etree.SubElement(root,"item")
        etree.SubElement(subelement, "title").text = line
        if 'http' in line: ## Check if it has a link
            etree.SubElement(subelement, "link").text = 'http:\\mysite.com\'
tree = etree.ElementTree(root)

If you're ok with items without titles:

for line in myfile.read().splitlines():
    subelement = etree.SubElement(root,"item") ## Always Create an item for each line
    if 'EXTINF' in line:
        etree.SubElement(subelement, "title").text = line
    if 'http' in line:
        etree.SubElement(subelement, "link").text = 'http:\\mysite.com\'

EDIT: Also, have you considered using myfile.readlines() instead of myfile.read().splitlines()?

Sign up to request clarification or add additional context in comments.

2 Comments

Thanks it works. With your code the xml output contains also a "root" tag element, what if i would like to print only "title" and "link" tag without "root"? Is it possible?
Technically you can, but it's generally frowned upon, goes against standards defined by W3C, and is not supported out-of-the box with etree afaik. If it really is necessary to do so, then you would probably do so by iterating over the tree and calling .tostring() on all the subelements of root, then joining all those strings together and writing them to the file like any other string.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.