"Extended" template-based INI file parsing in Python - python

I need to parse (and feed to a database) configuration files like this one (actually it is Asterisk's sip.conf):
[client-template](!,natted-template)
foo=foovalue
moo=moovalue
[client](client-template)
bar=barvalue
This syntax means that client-template is a template itself (because of ! in parentheses) based on natted-template (defined elsewhere). And client is an object definition, based on client-template.
I could use ConfigParser, but it looks like I need something more powerful or customized?

Well, now I've tried pyparsing:
import pyparsing as pp
filename = 'client.conf'
nametag = pp.Word(pp.alphanums + "-_")
variable = pp.Word(pp.alphanums)
value = pp.Word(pp.alphanums + "=")
vardef = pp.Group(variable('variable') + pp.Literal("=").suppress() + value('value'))
vardefs = pp.Group(pp.ZeroOrMore(vardef))('vardefs')
section = pp.Group(pp.Literal("[").suppress() \
+ nametag('objectname') \
+ pp.Literal("]").suppress() \
+ pp.Optional(
pp.Literal("(").suppress() \
+ pp.Optional("!")('istemplate')
+ pp.ZeroOrMore(pp.Optional(",").suppress() + nametag)('parenttemplates') \
+ pp.Literal(")").suppress()
) \
+ vardefs)
section = section + pp.Optional(pp.SkipTo(section)).suppress()
section_group = pp.Group(section + pp.ZeroOrMore(section))('sections')
config = (pp.SkipTo(section_group).suppress() \
+ section_group)
# res = config.parseString(open(filename).read())
This is a part of a solution (and this is comments unaware so far), but I can proceed with it.
Please, if there is more elegant solution, let me know.

Related

Openpyxl module: return weird value(not error) + hope to calculate

I wrote some codes trying to let the user be able to check the percentage of the money they spent(compared to the money they earned). Almost every step perform normally, until the final part.
a_c[('L'+row_t)].value return:
=<Cell 'Sheet1'.B5>/<Cell 'Sheet1'.J5>
yet I hope it should be some value.
Code:
st_column = st_column_r.capitalize()
row_s = str(a_c.max_row)
row_t = str(a_c.max_row + 1)
row = int(row_t)
a_c[('J'+row_t)] = ('=SUM(I2,J'+row_s+')') #總收入
errorprevention = a_c[('J'+row_t)].value
a_c[(st_column+row_t)] = ('=SUM('+(st_column+'2')+','+(st_column+row_s)+')')
a_c['L'+row_t].number_format = FORMAT_PERCENTAGE_00
if errorprevention != 0:
a_c[('L'+row_t)] = ('='+str(a_c[(st_column+row_t)])+'/'+str(a_c[('J'+row_t)]))
print('過往支出中,'+inputtype[st_column]+'類別佔總收入的比率為:'+a_c[('L'+row_t)].value)
Try changing the formula creation to;
a_c[('L' + row_t)].value = '=' + a_c[(st_column + row_t)].coordinate + '/' + a_c[('J' + row_t)].coordinate
or use an f string
a_c[('L' + row_t)].value = f"={a_c[(st_column + row_t)].coordinate}/{a_c[('J' + row_t)].coordinate}"

Python random hex generator

So I'm looking to generate a random hex value each time this is called
randhex = "\\x" + str(random.choice("123456789ABCDEF")) + str(random.choice("123456789ABCDEF"))
So far all I've come up with is to make different = calls (ex. randhex1 = ^^, randhex2) etc etc but that's tedious and inefficient and I don't want to do this
ErrorClass = "\\x" + str(random.choice("123456789ABCDEF")) + "\\x" + str(random.choice("123456789ABCDEF")) + "\\x" + str(random.choice("123456789ABCDEF")) + "\\x" + str(random.choice("123456789ABCDEF"))
because that doesn't look good and can be hard to tell how many there are.
I'm trying to assign it to this
ErrorClass = randhex1 + randhex2 + randhex3 + randhex4,
Flags = randhex5,
Flags2 = randhex6 + randhex7,
PIDHigh = randhex2 + randhex5,
and ideally, instead of having to assign different numbers, I want it all to be uniform or something like ErrorClass = randhex*4 which would be clean. If I do this, however, it simply copies the code to be something like this:
Input: ErrorClass = randhex + randhex + randhex + randhex
Output: \xFF\xFF\xFF\xFF
which obviously doesn't work because they are all the same then. Any help would be great.
Make a function that returns the randomly generated string. It will give you a new value every time you call it.
import random
def randhex():
return "\\x" + str(random.choice("0123456789ABCDEF")) + str(random.choice("0123456789ABCDEF"))
ErrorClass = randhex() + randhex() + randhex() + randhex()
Flags = randhex()
Flags2 = randhex() + randhex()
PIDHigh = randhex() + randhex()
print(ErrorClass)
print(Flags)
print(Flags2)
print(PIDHigh)
Sample result:
\xBF\x2D\xA2\xC2
\x74
\x55\x34
\xB6\xF5
For additional convenience, add a size parameter to randhex so you don't have to call it more than once per assignment:
import random
def randhex(size=1):
result = []
for i in range(size):
result.append("\\x" + str(random.choice("0123456789ABCDEF")) + str(random.choice("0123456789ABCDEF")))
return "".join(result)
ErrorClass = randhex(4)
Flags = randhex()
Flags2 = randhex(2)
PIDHigh = randhex(2)
print(ErrorClass)
print(Flags)
print(Flags2)
print(PIDHigh)

libclang python binding don't return any of fixits

I want to dump diagnostics and fixits from translation unit (tu). But below code don't works.
def dump_fixits():
"""Return diagnostics with fixits of translation unit."""
result = []
for diag in tu.diagnostics:
diag_fixits = [repr(it) for it in diag.fixits]
location = diag.location
file = "" if location.file is None else location.file.name
result.append((file + ":"
+ str(location.line) + ":"
+ str(location.column) + ": "
+ severity_map[diag.severity] + ": "
+ diag.spelling,
diag_fixits))
return result
(I'm using llvm 3.4)
I noticed conf.lib.clang_getDiagnosticNumFixIts() returns 0 everytime.
Is there any of solutions?
Sorry I misunderstood for fixit. I thought fixit can get spell miss but it isn't. Close this question. Thank you.

Query Spotlight for a range of dates via PyObjC

I'm using spotlight via pyobjc. Which is working well except for when I try to limit the time period using kMDItemContentCreationDate. I think the issue is with my time format. Any help would be greatly appreciated.
from Cocoa import *
import sys
emails = [sys.argv[1], ]
predicate = "(kMDItemContentType = 'com.apple.mail.emlx') && (" + \
'||'.join(["((kMDItemAuthorEmailAddresses = '%s'))" % m for m in emails]) + \
"&& (kMDItemContentCreationDate > '2011-03-23 00:00:00')" + \
"&& (kMDItemContentCreationDate < '2012-03-24 00:00:00')" + \
")"
query = NSMetadataQuery.alloc().init()
query.setPredicate_(NSPredicate.predicateWithFormat_(predicate))
query.setSortDescriptors_(NSArray.arrayWithObject_(NSSortDescriptor.alloc().initWithKey_ascending_('kMDItemContentCreationDate', False)))
query.startQuery()
NSRunLoop.currentRunLoop().runUntilDate_(NSDate.dateWithTimeIntervalSinceNow_(5))
query.stopQuery()
results = query.results()[:5]
for item in results:
print "subject: ", item.valueForAttribute_("kMDItemSubject")

Scripting Python for Linux commands

I have a question. I have been really trying to learn Python. For a project, I want to make an ncurses GUI for my backup server. My backup server runs rdiff-backup, and I want to have the ncurses take in variable names and plug them into my script. I have been trying to do a lot of reading so I don't ask dumb questions.
Here is my function for running the script:
def runScript():
# Cannot concatenate 'str' and 'list' objects
#script = rdiff + rdiffArgs
script = rdiff + ' ' + rdiffVerbosity + ' ' + rdiffStatistics \
+ ' ' + clientName + '#' + clientHost + '::' + clientDir \
+ ' ' + serverDir
os.system(script)
What I originally thought would be neat was to add all the variables into a list, so I could just run say
script = rdiff + rdiffArgs
Is there a better way to do this without all the space concatenation?
Thanks for your assistance
EDIT: Let me post the whole script so far. I wasn't very clear and I really appreciate your help and patience
#!/usr/bin/env python
import os
import smtplib
# Global variables
rdiff = '/usr/bin/rdiff-backup'
rdiffVerbosity = '-v5'
rdiffStatistics = '--print-statistics'
emailSmtp = 'smtp.gmail.com'
smtpPort = '465'
emailUsername = 'reports'
emailPassword = '3kc9dl'
emailTo = 'user#domain.com'
emailFrom = 'internal#domain.com'
serverName = 'root'
serverHost = 'SV-Datasafe'
serverDir = '/srv/backup/SV-Samba01'
clientName = 'root'
clientHost = 'SV-Samba01'
clientDir = '/srv'
rdiffArgs = rdiffArgs = [rdiffVerbosity, rdiffStatistics, \
clientName + '#' + clientHost + '::' \
+clientDir + ' ' + serverDir]
time = ''
dateStamp = datetime.now()
def sendEmail():
subject = dateStamp + clientName
body = clientDir + ' on ' + clientHost + ' backed up to ' + serverName + \
' in the directory ' + serverDir + ' on ' + dateStamp
message = """\
From: %s
To: %s
Subject: %s
%s
""" % (emailFrom, emailTo, subject, body)
deliverEmail = smtplib.SMTP(emailSmtp, port=smtpPort)
deliverEmail.login(emailUsername, emailPassword)
def runScript():
# Cannot concatenate 'str' and 'list' objects
#script = rdiff + rdiffArgs
script = rdiff + ' ' + rdiffVerbosity + ' ' + rdiffStatistics \
+ ' ' + clientName + '#' + clientHost + '::' + clientDir \
+ ' ' + serverDir
os.system(script)
# TODO:: Logging
you can use format specifiers
def runScript():
script = "%s %s %s#%s %s::%s %s" %(rdiff,rdiffVerbosity,rdiffStatistics,clientName,clientHost,clientDir,serverDir)
os.system(script)
or say your rdiffArgs is already in a list
rdiffArgs = [rdiffVerbosity,rdiffStatistics,clientName,clientHost,clientDir,serverDir]
you can join them with a space
rdiffArgs = ' '.join(rdiffArgs)
lastly, just so you might want to know, you can import rdiff in your script , since rdiff-backup is written in Python
from rdiff_backup.Main import Main as backup
task=['/etc', '/tmp/backup']
backup(task)
the above backs up /etc/ to /tmp/backup. That way, you don't have to make system call to rdiff-backup. Of course, this is up to you. making system call is sometimes easier
try to use subprocess module and pass arguments as list e.g.
client = clientName + '#' + clientHost + '::' + clientDir
cmd = [rdiff, rdiffVerbosity, rdiffStatistics, client , serverDir]
p = Popen(cmd ", shell=True)
print os.waitpid(p.pid, 0)[1]
or if have args already as list use something like this
cmd = [rdiff] + args
You join paths using os.path.join
You concatenate strings like so: "".join(['a', 'b']) or ", ".join(['c', 'd'])
Which part is difficult? I am not sure I understand the question 100%
Is this it?
script = rdiff + " ".join(rdiffArgs)

Categories

Resources