Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #!/usr/bin/env python
- import sys
- import re
- FILE = sys.argv[1]
- handle = open(FILE)
- fcontent = handle.read()
- handle.close()
- for myexpr in re.finditer(r'${([^}]+)}', fcontent, re.M|re.S):
- text = myexpr.group(1)
- try:
- exec text
- except SyntaxError:
- print "ERROR: unable to compile expression '%s'" % (text)
- This is some random text, with embedded python like
- ${print "foo"} and some bogus python like
- ${any:thing}.
- And a multiline statement, just for kicks:
- ${
- def multiline_stmt(foo):
- print foo
- multiline_stmt("ahem")
- }
- More text here.
- [user@host]$ ./exec_embedded_python.py test.txt
- foo
- ERROR: unable to compile expression 'any:thing'
- ahem
- def findExpr(s, i0=0, begin='${', end='}', compArgs=('<string>', 'eval')):
- assert 'n' not in s, 'line numbers not implemented'
- i0 = s.index(begin, i0) + len(begin)
- i1 = s.index(end, i0)
- code = errMsg = None
- while code is None and errMsg is None:
- expr = s[i0:i1]
- try: code = compile(expr, *compArgs)
- except SyntaxError, e:
- i1 = s.find(end, i1 + 1)
- if i1 < 0: errMsg, i1 = e.msg, i0 + e.offset
- return i0, i1, code, errMsg
- '''
- Search s for a (possibly invalid) Python expression bracketed by begin
- and end, which default to '${' and '}'. Return a 4-tuple.
- >>> s = 'foo ${a*b + c*d} bar'
- >>> i0, i1, code, errMsg = findExpr(s)
- >>> i0, i1, s[i0:i1], errMsg
- (6, 15, 'a*b + c*d', None)
- >>> ' '.join('%02x' % ord(byte) for byte in code.co_code)
- '65 00 00 65 01 00 14 65 02 00 65 03 00 14 17 53'
- >>> code.co_names
- ('a', 'b', 'c', 'd')
- >>> eval(code, {'a': 1, 'b': 2, 'c': 3, 'd': 4})
- 14
- >>> eval(code, {'a': 'a', 'b': 2, 'c': 'c', 'd': 4})
- 'aacccc'
- >>> eval(code, {'a': None})
- Traceback (most recent call last):
- ...
- NameError: name 'b' is not defined
- Expressions containing start and/or end are allowed.
- >>> s = '{foo ${{"}": "${"}["}"]} bar}'
- >>> i0, i1, code, errMsg = findExpr(s)
- >>> i0, i1, s[i0:i1], errMsg
- (7, 23, '{"}": "${"}["}"]', None)
- If the first match is syntactically invalid Python, i0 points to the
- start of the match, i1 points to the parse error, code is None and
- errMsg contains a message from the compiler.
- >>> s = '{foo ${qwerty asdf zxcvbnm!!!} ${7} bar}'
- >>> i0, i1, code, errMsg = findExpr(s)
- >>> i0, i1, s[i0:i1], errMsg
- (7, 18, 'qwerty asdf', 'invalid syntax')
- >>> print code
- None
- If a second argument is given, start searching there.
- >>> i0, i1, code, errMsg = findExpr(s, i1)
- >>> i0, i1, s[i0:i1], errMsg
- (33, 34, '7', None)
- Raise ValueError if there are no further matches.
- >>> i0, i1, code, errMsg = findExpr(s, i1)
- Traceback (most recent call last):
- ...
- ValueError: substring not found
- In ambiguous cases, match the shortest valid expression. This is not
- always ideal behavior.
- >>> s = '{foo ${x or {} # return {} instead of None} bar}'
- >>> i0, i1, code, errMsg = findExpr(s)
- >>> i0, i1, s[i0:i1], errMsg
- (7, 25, 'x or {} # return {', None)
- This implementation must not be used with multi-line strings. It does
- not adjust line number information in the returned code object, and it
- does not take the line number into account when computing the offset
- of a parse error.
- '''
Add Comment
Please, Sign In to add comment