PyXR

c:\python24\lib \ codeop.py



0001 r"""Utilities to compile possibly incomplete Python source code.
0002 
0003 This module provides two interfaces, broadly similar to the builtin
0004 function compile(), which take program text, a filename and a 'mode'
0005 and:
0006 
0007 - Return code object if the command is complete and valid
0008 - Return None if the command is incomplete
0009 - Raise SyntaxError, ValueError or OverflowError if the command is a
0010   syntax error (OverflowError and ValueError can be produced by
0011   malformed literals).
0012 
0013 Approach:
0014 
0015 First, check if the source consists entirely of blank lines and
0016 comments; if so, replace it with 'pass', because the built-in
0017 parser doesn't always do the right thing for these.
0018 
0019 Compile three times: as is, with \n, and with \n\n appended.  If it
0020 compiles as is, it's complete.  If it compiles with one \n appended,
0021 we expect more.  If it doesn't compile either way, we compare the
0022 error we get when compiling with \n or \n\n appended.  If the errors
0023 are the same, the code is broken.  But if the errors are different, we
0024 expect more.  Not intuitive; not even guaranteed to hold in future
0025 releases; but this matches the compiler's behavior from Python 1.4
0026 through 2.2, at least.
0027 
0028 Caveat:
0029 
0030 It is possible (but not likely) that the parser stops parsing with a
0031 successful outcome before reaching the end of the source; in this
0032 case, trailing symbols may be ignored instead of causing an error.
0033 For example, a backslash followed by two newlines may be followed by
0034 arbitrary garbage.  This will be fixed once the API for the parser is
0035 better.
0036 
0037 The two interfaces are:
0038 
0039 compile_command(source, filename, symbol):
0040 
0041     Compiles a single command in the manner described above.
0042 
0043 CommandCompiler():
0044 
0045     Instances of this class have __call__ methods identical in
0046     signature to compile_command; the difference is that if the
0047     instance compiles program text containing a __future__ statement,
0048     the instance 'remembers' and compiles all subsequent program texts
0049     with the statement in force.
0050 
0051 The module also provides another class:
0052 
0053 Compile():
0054 
0055     Instances of this class act like the built-in function compile,
0056     but with 'memory' in the sense described above.
0057 """
0058 
0059 import __future__
0060 
0061 _features = [getattr(__future__, fname)
0062              for fname in __future__.all_feature_names]
0063 
0064 __all__ = ["compile_command", "Compile", "CommandCompiler"]
0065 
0066 PyCF_DONT_IMPLY_DEDENT = 0x200          # Matches pythonrun.h
0067 
0068 def _maybe_compile(compiler, source, filename, symbol):
0069     # Check for source consisting of only blank lines and comments
0070     for line in source.split("\n"):
0071         line = line.strip()
0072         if line and line[0] != '#':
0073             break               # Leave it alone
0074     else:
0075         if symbol != "eval":
0076             source = "pass"     # Replace it with a 'pass' statement
0077 
0078     err = err1 = err2 = None
0079     code = code1 = code2 = None
0080 
0081     try:
0082         code = compiler(source, filename, symbol)
0083     except SyntaxError, err:
0084         pass
0085 
0086     try:
0087         code1 = compiler(source + "\n", filename, symbol)
0088     except SyntaxError, err1:
0089         pass
0090 
0091     try:
0092         code2 = compiler(source + "\n\n", filename, symbol)
0093     except SyntaxError, err2:
0094         pass
0095 
0096     if code:
0097         return code
0098     try:
0099         e1 = err1.__dict__
0100     except AttributeError:
0101         e1 = err1
0102     try:
0103         e2 = err2.__dict__
0104     except AttributeError:
0105         e2 = err2
0106     if not code1 and e1 == e2:
0107         raise SyntaxError, err1
0108 
0109 def _compile(source, filename, symbol):
0110     return compile(source, filename, symbol, PyCF_DONT_IMPLY_DEDENT)
0111 
0112 def compile_command(source, filename="<input>", symbol="single"):
0113     r"""Compile a command and determine whether it is incomplete.
0114 
0115     Arguments:
0116 
0117     source -- the source string; may contain \n characters
0118     filename -- optional filename from which source was read; default
0119                 "<input>"
0120     symbol -- optional grammar start symbol; "single" (default) or "eval"
0121 
0122     Return value / exceptions raised:
0123 
0124     - Return a code object if the command is complete and valid
0125     - Return None if the command is incomplete
0126     - Raise SyntaxError, ValueError or OverflowError if the command is a
0127       syntax error (OverflowError and ValueError can be produced by
0128       malformed literals).
0129     """
0130     return _maybe_compile(_compile, source, filename, symbol)
0131 
0132 class Compile:
0133     """Instances of this class behave much like the built-in compile
0134     function, but if one is used to compile text containing a future
0135     statement, it "remembers" and compiles all subsequent program texts
0136     with the statement in force."""
0137     def __init__(self):
0138         self.flags = PyCF_DONT_IMPLY_DEDENT
0139 
0140     def __call__(self, source, filename, symbol):
0141         codeob = compile(source, filename, symbol, self.flags, 1)
0142         for feature in _features:
0143             if codeob.co_flags & feature.compiler_flag:
0144                 self.flags |= feature.compiler_flag
0145         return codeob
0146 
0147 class CommandCompiler:
0148     """Instances of this class have __call__ methods identical in
0149     signature to compile_command; the difference is that if the
0150     instance compiles program text containing a __future__ statement,
0151     the instance 'remembers' and compiles all subsequent program texts
0152     with the statement in force."""
0153 
0154     def __init__(self,):
0155         self.compiler = Compile()
0156 
0157     def __call__(self, source, filename="<input>", symbol="single"):
0158         r"""Compile a command and determine whether it is incomplete.
0159 
0160         Arguments:
0161 
0162         source -- the source string; may contain \n characters
0163         filename -- optional filename from which source was read;
0164                     default "<input>"
0165         symbol -- optional grammar start symbol; "single" (default) or
0166                   "eval"
0167 
0168         Return value / exceptions raised:
0169 
0170         - Return a code object if the command is complete and valid
0171         - Return None if the command is incomplete
0172         - Raise SyntaxError, ValueError or OverflowError if the command is a
0173           syntax error (OverflowError and ValueError can be produced by
0174           malformed literals).
0175         """
0176         return _maybe_compile(self.compiler, source, filename, symbol)
0177 

Generated by PyXR 0.9.4
SourceForge.net Logo