Automate html file editing with python - Change the author Hello I would like to use python to change the author of an html file, in order to do so I have written a few lines.

First I have used the HTMLParser class from the standard library to make a class that indicates which line of the html page needs to be changed.

from html.parser import HTMLParser

class AuthorFinder(HTMLParser):
    def __init__(self):
        super().__init__()
        self._edition_line = None

    def handle_starttag(self, tag, attrs):
    '''
    If the tag handled is the meta tag containing the author's name, then
    the value of _edition_line will be set to the current line (starting from 0)
    '''
    if tag.lower() == 'meta':
        for a_tuple in attrs:
            name, value = (field.lower() for field in a_tuple)
            if name == 'name' and value == 'author':
                # getpos() returns (line, column) starting from (1, 1)
                # whereas I want the first index to be 0.
                self._edition_line = self.getpos()[0] - 1

    @property
    def edition_line(self):
        return self._edition_line


I then use that class to get the line of the meta tag that contains the author. The following function changes the whole line and return and the new html page as a string.

def change_author(html_code, author):
    html_parser = AuthorFinder()
    html_parser.feed(html_code)
    author_line = html_parser.edition_line
    html_lines = html_code.splitlines()
    new_tag = '&lt;meta name="author" content="{}"&gt;'.format(author)
    html_lines[author_line] = new_tag
    new_html = '\n'.join(html_lines)
    return new_html


From there you can easily change the author of several html files with something as simple as this:

# put the path to your html files in here
html_files = ['example1.html', 'example2.html']
new_author = 'Mario Luigi'
for filename in html_files:
    with open(filename, 'rt') as f:
        html_code = f.read()
    new_code = change_author(html_code, new_author)
    new_filename = '{}-NewAuthor.html'.format(filename.split('.')[0])
    with open(new_filename, 'w') as f:
        f.write(new_code)


Here is my first, quick attempt at automating file editing. I would like, in the future, to automate more changes but for now let's focus on this one. The script works fine but I'm pretty sure it can be improved in several ways as:


the class AuthorFinder will keep on parsing even though the desired meta tag has been found
if no meta tag with the author's name has been found, no author will be added
the previous indentation is ignored
...  


I will try to find ways to improve this, and hope to get suggestions from here as well. Thank you for reading, and good day.
I'm going to try writing a few different versions of your program. I think it would make for a nice, basic comparison of the various alternatives.
Of course, this all hinges on the number of changes, and their complexity, you wish to make. In that regard, it would be nice to get some more information on those changes, even if you haven't written the code for it yet.

Pure lxml, .find() with a simple XPath expression.
from lxml import etree

parser = etree.HTMLParser()
tree = etree.parse('../resources/author_parser_test_1.html', parser=parser)

author_tag = tree.find(&quot;./head/meta[@name='author']&quot;)

if author_tag is None:
    print(&quot;Couldn't find author tag&quot;)
else:
    author_tag.set('content', 'New Author')
    tree.write('../out/author_parser_test_1_res.html', method='html', pretty_print=False)


BeautifulSoup using lxml as the parser
from bs4 import BeautifulSoup

with open('../resources/author_parser_test_1.html', 'r') as file_1:
    soup = BeautifulSoup(file_1, features='lxml')

author_tag = soup.find('meta', attrs={'name': 'author'})

if author_tag is None:
    print(&quot;Couldn't find author tag&quot;)
else:
    author_tag['content'] = 'New author'
    with open('../out/author_parser_test_1_res.html', 'w') as file_1:
        file_1.write(soup.prettify())


I will keep updating this post as I work.