pyxlate Code
Translates a subset of the Python grammar to other languages
Brought to you by:
jamesm17
File | Date | Author | Commit |
---|---|---|---|
lib | 2014-09-15 |
![]() |
[6038bb] Commenting out import for "cpp" module (which d... |
test | 2014-01-29 |
![]() |
[bb36e6] Adding initial support for "import" statement. ... |
.gitignore | 2013-10-12 |
![]() |
[eaec38] Adding ignore file |
LICENSE.txt | 2013-01-19 |
![]() |
[541d9e] Initial commit |
Makefile | 2013-10-12 |
![]() |
[b5a627] Adding top-level Makefile |
README.txt | 2013-11-09 |
![]() |
[1491bb] Adding first step of type information |
convert.py | 2014-01-30 |
![]() |
[87d72b] Adding GCL target. |
make.include.template | 2013-10-12 |
![]() |
[42a991] Updating README and make.include.template to re... |
============================================================================== OVERVIEW ============================================================================== Pyxlate is a utility that converts from a subset of the Python grammar into other languages. The current plans are to translate into Perl, Ruby, and Tcl. This is not a magical conversion - you cannot put any arbitrary Python code through the converter and expect it to work. Rather, this is for a tolerant programmer who is willing to stay within a subset of the Python language and write code with some special handling that may be required in the target language(s). The motivation for writing this utility was to create a converged set of unit tests for software that has an API in Perl, Python, Ruby, and Tcl. The converter will allow a "write-once, use-many" approach. The conversion is done by using the Python Abstract Syntax Tree (AST) module ("ast"). By leveraging ast, the hard work of parsing and building an AST is done automatically and each node on the tree can be visited to convert to the target language(s) through the use of string templates. source.py -> (convert.py) -> target.{pl,rb,tcl,...} The Python AST module documentation can be found here: http://docs.python.org/2/library/ast.html ============================================================================== LICENSE ============================================================================== Pyxlate is released under a MIT-style license (see LICENSE.txt for details). http://opensource.org/licenses/MIT ============================================================================== DEPENDENCIES ============================================================================== Python 2.7+ (www.python.org) ============================================================================== TESTING ============================================================================== Unit testing: 1. Copy make.include.template to make.include (do only once) 2. Edit make.include to update to the location of your python executable. 3. Run unit testing from base directory of the pyxlate installation: make -C test Other example tests: python convert.py test/try1.py ruby python convert.py test/try2.py ruby python convert.py test/try3.py ruby python convert.py test/try4.py ruby ============================================================================== OUTPUT EMITTERS ============================================================================== Output emitters act as string templating for writing code in the target languages. The output emitters included in this package are: lib/python/pyxlate/perl.py lib/python/pyxlate/ruby.py lib/python/pyxlate/tcl.py All of the translation code to translate into a particular language are fully encapsulated into the respective output emitter file. No other files are needed to translate into a target language. As such, creating an output emitter for a new language is as simple as copying an existing output emitter and changing the outputted text to match the new language's syntax. ============================================================================== PYTHON BUILD-IN FUNCTIONS ============================================================================== The following are built-in Python functions and need special handling at each language's template as Call.<name> to be supported. abs() divmod() input() open() staticmethod() all() enumerate() int() ord() str() any() eval() isinstance() pow() sum() basestring() execfile() issubclass() print() super() bin() file() iter() property() tuple() bool() filter() len() range() type() bytearray() float() list() raw_input() unichr() callable() format() locals() reduce() unicode() chr() frozenset() long() reload() vars() classmethod() getattr() map() repr() xrange() cmp() globals() max() reversed() zip() compile() hasattr() memoryview() round() __import__() complex() hash() min() set() apply() delattr() help() next() setattr() buffer() dict() hex() object() slice() coerce() dir() id() oct() sorted() intern() ============================================================================== OVERALL FLOW ============================================================================== The conversion follows the following flow: 1. The "Source" class is populated with Python's AST (parsed by the ast module). 2. The AST is traversed and Symbols are created. 3. The AST is traversed and types are computed, promoted, and checked (see "SYMBOLS AND TYPES" section for more details). 4. The AST is converted into the target syntax using an output emitter class that derives from the "Target" class. ============================================================================== SYMBOLS AND TYPES ============================================================================== Symbols are created for variable assignments, function declarations, and class declarations. A built-in pxlate.Symbol class manages the symbols. Types are handled through a multi-pass process: - Static type computation - Automatic type promotion - Checking types Type rules ------------------------------------------------------------------------------ - Only objects can be used to call methods - List slice indexes must be integers - Function calls must only be performed on function symbols - "if" conditions must evaluate to boolean - Left and right sides of assignment must have compatible types - Function call argument types must match function declaration types - Function call return assignments must match return() type from the function - All return() statements in a function definition have the same type - Operands of arithmetic operation must have compatible types - Unary operators must have the proper type Static Types ------------------------------------------------------------------------------ None NoneType True, False bool <#> int <#>.<#> float "<string>" str {} dict [] list () tuple Derived Types ------------------------------------------------------------------------------ <symbol> same type as <symbol> not <expr> bool -<expr> same type as <expr> a[<value>] type stored in tuple/list/dict f(<args>) same type as return for function f() <expr> BinOp <expr> left type chosen (will validate against right type) <expr> Compare <expr> bool ============================================================================== RESTRICTIONS ============================================================================== - No embedded classes or functions (classes defined within classes or functions defined within functions. - Variable type must remain the same throughout the code for a given context. In other words, do not set a=1 and then a="foo".