Reputation: 2200
I am trying to modify a configuration file using Python. How can I do the equivalent of multiple sed commands in this format:
sed -ci 's/ServerTokens OS/ServerTokens Prod/' /etc/httpd/conf/httpd.conf
most efficiently in Python? This is what I am doing right now:
with open("httpd.conf", "r+") as file:
tmp = []
for i in file:
if '#ServerName' in i:
tmp.append(i.replace('#ServerName www.example.com', 'ServerName %s' % server_name , 1))
elif 'ServerAdmin' in i:
tmp.append(i.replace('root@localhost', webmaster_email, 1))
elif 'ServerTokens' in i:
tmp.append(i.replace('OS', 'Prod', 1))
elif 'ServerSignature' in i:
tmp.append(i.replace('On', 'Off', 1))
elif 'KeepAlive' in i:
tmp.append(i.replace('Off', 'On', 1))
elif 'Options' in i:
tmp.append(i.replace('Indexes FollowSymLinks', 'FollowSymLinks', 1))
elif 'DirectoryIndex' in i:
tmp.append(i.replace('index.html index.html.var', 'index.php index.html', 1))
else:
tmp.append(i)
file.seek(0)
for i in tmp:
file.write(i)
It's needlessly complex since I could just use subprocess and sed instead. Any suggestions?
Upvotes: 3
Views: 1006
Reputation: 2079
You can use regular expressions inside of Python in very similar way you do this in sed. Just use Python regular expressions library. You may be interested in re.sub() method, which does equivalent of sed's s
command used in your example.
If you want to do this efficiently, you probably have to run only one substitute command per line, skipping it if it was changed, similar way you do this in your example code. In order to achieve that, you may use re.subn
instead of re.sub
or re.match combined with groups that were matched.
Here's an example:
import re
server_name = 'blah'
webmaster_email = '[email protected]'
SUBS = ( (r'^#ServerName www.example.com', 'ServerName %s' % server_name),
(r'^ServerAdmin root@localhost', 'ServerAdmin %s' % webmaster_email),
(r'KeepAlive On', 'KeepAlive Off')
)
with open("httpd.conf", "r+") as file:
tmp=[]
for i in file:
for s in SUBS:
ret=re.subn(s[0], s[1], i)
if ret[1]>0:
tmp.append(ret[0])
break
else:
tmp.append(i)
for i in tmp:
print i,
Upvotes: 1