diff --git a/.overcommit.yml b/.overcommit.yml deleted file mode 100644 index 6407a30..0000000 --- a/.overcommit.yml +++ /dev/null @@ -1,11 +0,0 @@ -# PreCommit: -# Pep8: -# enabled: true -# on_warn: fail # Treat all warnings as failures -# Pep257: -# enabled: true -# on_warn: fail -# command: ['pep257', '--ignore=D300,D400,D100,D203,D102,D202'] -# HardTabs: -# enabled: true -# on_warn: fail diff --git a/.travis.yml b/.travis.yml new file mode 100644 index 0000000..ebae6cc --- /dev/null +++ b/.travis.yml @@ -0,0 +1,4 @@ +language: python +python: + - "3.2" +script: python -m unittest discover tests diff --git a/LICENSE b/LICENSE index bb62f27..d81ea5c 100644 --- a/LICENSE +++ b/LICENSE @@ -1,6 +1,6 @@ The MIT License (MIT) -Copyright (c) 2015 Alexander Ivanov +Copyright (c) 2016 Alexander Ivanov Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in diff --git a/README.md b/README.md index 2a9a803..2b64695 100644 --- a/README.md +++ b/README.md @@ -1,47 +1,73 @@ -# pseudon +# pseudo -Pseudon is a library for generating code in different high level languages and a system for language algorithm translation: its goal is to be able to translate any code expressed in a certain "pseudon-translateable" subset of each supported language or as a pseudon AST to any of the supported target languages. +Pseudo is a library for generating code in different high level languages and a system for language translation: its goal is to be able to translate any code expressed in a certain "pseudo-translateable" subset of each supported language or as a pseudo AST to readable and idiomatic code in any of the supported target languages. + +Pseudo achieves that with translation on two layers: it uses the target language syntax and it can express standard library methods/api of language X using language Y's native standard library Supporting full-blown X to Y auto translation is hard. -However Pseudon support a very clear and somehow limited subset of a language: +However Pseudo support a very clear and somehow limited subset of a language: - * basic types: integer, float, string, boolean, nil + * basic types and collections and standard library methods for them + + * integer, float, string, boolean * lists * dicts - * standard library methods for the basic types + * sets + * tuples/structs(fixed length heterogeneous lists) + * fixed size arrays + * regular expressions + * functions with normal parameters (no default/keyword/vararg parameters) - * classes (only as a constructor + a collection of instance methods, no fancy metaprogramming etc supported) - * iteration (for-in loops / while) + * classes + * single inheritance + * polymorphism + * no dynamic instance variables + * basically a constructor + a collection of instance methods, no fancy metaprogramming etc supported + + * exception-based error handling with support for custom exceptions + (target languages support return-based error handling too) + + * io: print/input, file read/write, system and subprocess commands + + * iteration (for-in-range / for-each / iterating over several collections / while) * conditionals (if / else if / else) * standard math/logical operations - * basic exception-based error handling -Those constructs and entities have almost the same behavior and very same-spirited api in a lot of the dynamic languages which Pseudon would support. +Those constructs and entities have almost the same behavior and very same-spirited api in a lot of the languages which Pseudo would support. -##why -Supporting full-blown Ruby to Python/Perl to Javascript auto translation is hard. -However often we need to +## pseudo makes easier to: + * generate code for the same task/algorithm in different languages (parser generators etc) + * port a library/codebase + * develop core logic in one language and use it in other language codebases + * write a compiler/dsl + * bootstrap a codebase in another language / generate equivalent test suites in different languages * translate/support some algorithms in different languages - * translate/support some text/data processing tool in different languages - * generate code for the same task/algorithm in different languages + * translate/support some text/data processing/command tool in different languages + +## why + +Supporting full-blown Ruby to Python/Javascript to C++ auto translation is hard. +However often we need to just exress the core Often that code is(or can be) expressed in very similar way, with similar constructs and basic types and data structures. On that level -a lot of dynamic languages are very similar and the only real difference +a lot of languages are very similar and the only real difference is syntax and methods api. That's a feasible task for automatic translation -and actually the existance of `pseudon` is to fullfill the needs of other -existings projects. +and actually the existance of `pseudo` is to fullfill the needs of several other +existing projects. You can almost think of it in a "~json-for-algorithms" way: we express -our algorithm/function with standard basic types, collections and constructs in our favorite language -or in pseudon AST format and we can translate to any of the supported target languages +our algorithm/function with standard basic types, collections and constructs in our favorite language or in pseudo AST format and we can translate to any of the supported target languages. + +You can also use the "lodash-with-babylon-fishes" metaphor: we use e.g. Python or Ruby or Pseudo standard library and Pseudo maps uses the right equivalent idioms in the target language. + ## progress -close to v0.2, several fixes and finishing the api only left +close to v0.2, left: several fixes and finishing the api translation - [ ] python - [x] syntax tests passing @@ -88,16 +114,11 @@ v0.3/v0.4: ## Language support -Using pseudon's DSL it's really easy to add support for a new language, so soon we'll try to support -all most popular languages and even different versions of them (e.g. EcmaScript 6/7, Perl 5/6 Java 7 / 8) +Using pseudo's DSL it's easy to add support for a new language, so it's feasible to expect support for most popular languages and even different versions of them (e.g. EcmaScript 6/7, Perl 5/6 Java 7 / 8) ## How to translate back? -Each language is supposed to have its own pseudon generator. - -* [pseudon-python](https://github.com/alehander42/pseudon-python) -* [pseudon-ruby](https://github.com/alehander42/pseudon-ruby) -* [pseudon-js](https://github.com/alehander42/pseudon-js) (ecmascript 6) +Currently there are `python`, `js` and `c#` to `pseudo` compilers in the works ## Intermediate AST format @@ -105,22 +126,19 @@ The AST format uses basic data structures available in most languages. The nodes dictionaries with `type` key corresponding to the node type and `field_name` keys corresponding to the node fields, similar to the widely popular `estree` ecmascript format. -Pseudon can consume ast either serialized in `.pseudon.yaml` / `.pseudon.json` files or directly as -dictionary objects through it's `pseudon.generate(ast, output_lang)` API - -The first prototype of pseudon was using lisp-like code, but standard data formats seemed like the -more easy-to-approach for users solution +Pseudo can consume ast either serialized in `.pseudo.yaml` files or directly as +dictionary objects through it's `pseudo.generate(ast, output_lang)` API ## Implementation -The implementation goal is to be really clear and simple. If you dive in, you'll find out +The implementation goal is to make the definitions of new supported languages really clear and simple. If you dive in, you'll find out almost all the code/api transformations are defined using a declarative dsl with rare ocassions of edge case handling helpers. That has a lot of advantages: * Less bugs: the core transformation code is really generalized, it's reused as a dsl and its results are well tested * Easy to comprehend: it almost looks like a config file * Easy to add support for other languages: I was planning to support just python and c# in the initial version but it is so easy to add support for a language similar to the current supported ones, that I -added support for 5 more. -* Easy to test: there is a simple test dsl too which helps all language tests to share input examples and I mean [just look](pseudon/tests/test_javascript.py) at it +added support for 4 more. +* Easy to test: there is a simple test dsl too which helps all language tests to share input examples [like that](pseudo/tests/test_ruby.py) ## Target language specific docs diff --git a/TODO.md b/TODO.md deleted file mode 100644 index 0f28701..0000000 --- a/TODO.md +++ /dev/null @@ -1,5 +0,0 @@ -todo ----- - -* python generator -* php generator diff --git a/ast.html b/ast.html deleted file mode 100644 index 2a084e2..0000000 --- a/ast.html +++ /dev/null @@ -1,1056 +0,0 @@ -ast

program

-

contains a module of code, corresponding to a single file/snippet

-
Module
-  code: list[Function / Class / Expression]
-
- -
42
-
- -
type: module
-code:
-  - type: integer
-    value: 42
-
- -

local

-

contains a local name value, written in snake_case by convention

-
Local
-  name: str
-
- -
e
-
- -
type: local
-name: 'e'
-
- -

integer

-

contains an integer

-
Integer
-  value: int
-
- -
42
-
- -
type: integer
-value: 42
-
\ No newline at end of file diff --git a/bin/pseudon b/bin/pseudo similarity index 73% rename from bin/pseudon rename to bin/pseudo index 6395a22..c798859 100755 --- a/bin/pseudon +++ b/bin/pseudo @@ -4,14 +4,14 @@ import sys import os import types sys.path.append(os.path.dirname(os.path.dirname(os.path.realpath(__file__)))) -import pseudon -import pseudon.loader +import pseudo +import pseudo.loader import yaml from subprocess import call USAGE = ''' -pseudon + +pseudo + where can be: py / python @@ -26,10 +26,10 @@ where can be: api can be either a .pseudo.yaml intemediate file or -a python / ruby / js / swift file using pseudon-translateable subset of the +a python / ruby / js / swift file using pseudo-translateable subset of the language -however, if it's a source file(not an intermediate one) pseudon expects -that pseudon-python for python or pseudon- for language is installed +however, if it's a source file(not an intermediate one) pseudo expects +that pseudo-python for python or pseudo- for language is installed and accessible from path ''' # js = js_generator.JSGenerator @@ -59,7 +59,7 @@ if __name__ == '__main__': input_filename = sys.argv[1] output_formats = sys.argv[2:] - intermediate_code = pseudon.loader.load_input(input_filename, call) + intermediate_code = pseudo.loader.load_input(input_filename, call) base, _, ext = input_filename.rpartition('.') if ext == 'yaml': base = base.partition('.')[0] @@ -68,7 +68,7 @@ if __name__ == '__main__': f.write(intermediate_code) exit() - # typed = pseudon.type_engine.TypeEngine().inference(converted) + # typed = pseudo.type_engine.TypeEngine().inference(converted) # if output_formats[0] == 'typed': # print(typed) @@ -80,16 +80,16 @@ if __name__ == '__main__': # print(api) # exit() - # converted = pseudon.loader.as_tree(intermediate_code) + # converted = pseudo.loader.as_tree(intermediate_code) # if output_formats[0] == 'all': # formats = SUPPORTED_FORMATS # generators = GENERATORS # else: for format in output_formats: - if format in pseudon.SUPPORTED_FORMATS: - output_source = pseudon.generate(pseudon.loader.as_tree(intermediate_code), format) - with open('%s.%s' % (base, pseudon.FILE_EXTENSIONS[format]), 'w') as f: + if format in pseudo.SUPPORTED_FORMATS: + output_source = pseudo.generate(pseudo.loader.as_tree(intermediate_code), format) + with open('%s.%s' % (base, pseudo.FILE_EXTENSIONS[format]), 'w') as f: f.write(output_source) else: print('%s is not supported' % format) diff --git a/ast.md b/docs/ast.md similarity index 89% rename from ast.md rename to docs/ast.md index 5fd6832..33d3515 100644 --- a/ast.md +++ b/docs/ast.md @@ -423,10 +423,10 @@ args: [] ## standard_call -a call to a standard pseudon function -pseudon standard functions are divided in namespaces, they in a combination with standard methods (below) represent the pseudon standard library -the standard library corresponds to the only pseudon-translateable native functions and methods(builtin in the input/target language or its standard library) -if you want support for other functions/methods, please follow the [extend pseudon guide](docs/extend_pseudon_guide.md) +a call to a standard pseudo function +pseudo standard functions are divided in namespaces, they in a combination with standard methods (below) represent the pseudo standard library +the standard library corresponds to the only pseudo-translateable native functions and methods(builtin in the input/target language or its standard library) +if you want support for other functions/methods, please follow the [extend pseudo guide](docs/extend_pseudo_guide.md) the namespaces currently are `global`(no namespace/top namespace) `math`, `io`, `system` you can read more in [standard library reference](docs/library_reference.md) @@ -454,9 +454,9 @@ args: ## standard_method_call -a pseudon standard library method call -the standard library corresponds to the only pseudon-translateable native functions and methods(builtin in the input/target language or its standard library) -if you want support for other functions/methods, please follow the [extend pseudon guide](docs/extend_pseudon_guide.md) +a pseudo standard library method call +the standard library corresponds to the only pseudo-translateable native functions and methods(builtin in the input/target language or its standard library) +if you want support for other functions/methods, please follow the [extend pseudo guide](docs/extend_pseudo_guide.md) you can read more in [standard library reference](docs/library_reference.md) @@ -479,11 +479,11 @@ receiver: type: local name: f args: [] - pseudon_type: List[Int] + pseudo_type: List[Int] message: slice_from args: - type: int value: 1 -pseudon_type: List[Int] +pseudo_type: List[Int] ``` diff --git a/docs/extend_pseudo_guide.md b/docs/extend_pseudo_guide.md new file mode 100644 index 0000000..3946f20 --- /dev/null +++ b/docs/extend_pseudo_guide.md @@ -0,0 +1,7 @@ +# extend pseudo + +## add support for a language as a target + +## compile a subset of a language to pseudo + +## add functions/methods/types to standard library \ No newline at end of file diff --git a/docs/extend_pseudon_guide.md b/docs/extend_pseudon_guide.md deleted file mode 100644 index b53c1d6..0000000 --- a/docs/extend_pseudon_guide.md +++ /dev/null @@ -1,7 +0,0 @@ -# extend pseudon - -## add support for a language as a target - -## compile a subset of a language to pseudon - -## add functions/methods/types to standard library \ No newline at end of file diff --git a/docs/library_reference.md b/docs/library_reference.md index 8b0bb37..96f2c81 100644 --- a/docs/library_reference.md +++ b/docs/library_reference.md @@ -59,7 +59,7 @@ the logarithm of x to the given base display(*args: Any) -> Void ``` -displays the contents on the screen using the native print function. `display` is the only pseudon +displays the contents on the screen using the native print function. `display` is the only pseudo function accepting a variable number of args diff --git a/examples/a.yaml b/examples/a.yaml deleted file mode 100644 index 7b77889..0000000 --- a/examples/a.yaml +++ /dev/null @@ -1,58 +0,0 @@ -type: 'program' -code: - - type: 'class' - name: 'Converter' - parent: ~ - methods: - - type: 'constructor' - args: - - type: 'local_label' - name: 'a' - type_hint: 'String' - body: - - type: 'ivar_assignment' - ivar: 'a' - value: - - type: 'local_label' - name: 'a' - - type: 'ivar_assignment' - ivar: 'options' - value: - - type: 'dictionary' - pairs: [] - - type: 'method' - name: 'convert' - args: - - type: 'local_label' - name: 'depth' - type_hint: 'Int' - body: - - type: 'explicitreturn' - value: - type: 'list_comp' - iter: ['a'] - iterable: - type: 'ivar' - name: 'a' - body: - type: 'format' - template: '%d%s' - args: - - type: 'local_label' - name: 'depth' - - type: 'local_label' - name: 'a' - - - type: 'assignment' - slot: - type: 'local_label' - value: - type: 'new_instance' - of_class: 'Converter' - args: [] - - type: 'method_call' - receiver: - type: 'local_label' - name: 'f' - message: 'convert' - args: [] diff --git a/examples/add.py b/examples/add.py deleted file mode 100644 index a9b889f..0000000 --- a/examples/add.py +++ /dev/null @@ -1,2 +0,0 @@ -def add(e: int): - return e + 1 diff --git a/examples/add.rb b/examples/add.rb deleted file mode 100644 index e69de29..0000000 diff --git a/examples/parse.pseudon.yaml b/examples/parse.pseudon.yaml index 44961d2..54dbc78 100644 --- a/examples/parse.pseudon.yaml +++ b/examples/parse.pseudon.yaml @@ -3,7 +3,7 @@ definitions: - type: function_definition name: parse params: [z] - pseudon_type: Int + pseudo_type: Int block: - type: local_assignment local: ast diff --git a/progress.md b/progress.md deleted file mode 100644 index 04ab33a..0000000 --- a/progress.md +++ /dev/null @@ -1,9 +0,0 @@ -## progress - -- [ ] api translation -- [ ] return-based error handling translation middleware (for `go`, `c`) -- [ ] code generation - - [ ] base generator - - [ ] dsl - - \ No newline at end of file diff --git a/pseudon/__init__.py b/pseudo/__init__.py similarity index 60% rename from pseudon/__init__.py rename to pseudo/__init__.py index fb5076e..bb3943e 100644 --- a/pseudon/__init__.py +++ b/pseudo/__init__.py @@ -1,21 +1,21 @@ -'''pseudon is translating asts''' -import pseudon.api_translators -import pseudon.api_translators.ruby_translator -import pseudon.api_translators.python_translator -import pseudon.api_translators.js_translator -import pseudon.api_translators.csharp_translator -import pseudon.api_translators.cpp_translator -import pseudon.api_translators.golang_translator -import pseudon.api_translators.php_translator +'''pseudo is translating asts''' +import pseudo.api_translators +import pseudo.api_translators.ruby_translator +import pseudo.api_translators.python_translator +import pseudo.api_translators.js_translator +import pseudo.api_translators.csharp_translator +import pseudo.api_translators.cpp_translator +import pseudo.api_translators.golang_translator +import pseudo.api_translators.php_translator -import pseudon.generators -import pseudon.generators.ruby_generator -import pseudon.generators.python_generator -import pseudon.generators.js_generator -import pseudon.generators.csharp_generator -import pseudon.generators.cpp_generator -import pseudon.generators.golang_generator -import pseudon.generators.php_generator +import pseudo.generators +import pseudo.generators.ruby_generator +import pseudo.generators.python_generator +import pseudo.generators.js_generator +import pseudo.generators.csharp_generator +import pseudo.generators.cpp_generator +import pseudo.generators.golang_generator +import pseudo.generators.php_generator SUPPORTED_FORMATS = {'js', 'javascript', 'py', 'python', 'rb', 'ruby', 'php', 'go', 'golang', 'cs', 'csharp', 'cpp'} FILE_EXTENSIONS = {'js': 'js', 'javascript': 'js', 'py': 'py', 'python': 'py', 'rb': 'rb', 'ruby': 'rb', 'php': 'php', 'go': 'go', 'golang': 'go', 'cs': 'cs', 'csharp': 'cs', 'cpp': 'cpp'} @@ -25,7 +25,7 @@ API_TRANSLATORS = { format: getattr( getattr( - pseudon.api_translators, + pseudo.api_translators, '%s_translator' % NAMES[format].lower()), '%sTranslator' % NAMES[format]) for format in SUPPORTED_FORMATS @@ -34,16 +34,16 @@ GENERATORS = { format: getattr( getattr( - pseudon.generators, + pseudo.generators, '%s_generator' % NAMES[format].lower()), '%sGenerator' % NAMES[format]) for format in SUPPORTED_FORMATS } -def generate(pseudon_ast, language): +def generate(pseudo_ast, language): '''generate output code in the given language''' - translated_ast = API_TRANSLATORS[language](pseudon_ast).api_translate() + translated_ast = API_TRANSLATORS[language](pseudo_ast).api_translate() # print(language, API_TRANSLATORS[language].functions['io']['display']) # input() return GENERATORS[language]().generate(translated_ast) diff --git a/pseudon/api_handlers.py b/pseudo/api_handlers.py similarity index 100% rename from pseudon/api_handlers.py rename to pseudo/api_handlers.py diff --git a/pseudon/api_translator.py b/pseudo/api_translator.py similarity index 89% rename from pseudon/api_translator.py rename to pseudo/api_translator.py index 2e1cf66..5678344 100644 --- a/pseudon/api_translator.py +++ b/pseudo/api_translator.py @@ -1,9 +1,9 @@ -from pseudon.tree_transformer import TreeTransformer -from pseudon.types import * -from pseudon.env import Env -from pseudon.pseudon_tree import Node, to_node, method_call, call, local -from pseudon.errors import PseudonStandardLibraryError, PseudonDSLError -from pseudon.api_handlers import LeakingNode, NormalLeakingNode, BizarreLeakingNode +from pseudo.tree_transformer import TreeTransformer +from pseudo.types import * +from pseudo.env import Env +from pseudo.pseudo_tree import Node, to_node, method_call, call, local +from pseudo.errors import PseudoStandardLibraryError, PseudoDSLError +from pseudo.api_handlers import LeakingNode, NormalLeakingNode, BizarreLeakingNode import copy TYPES = {'List', 'Dictionary', 'Set', 'Tuple', 'Regexp', 'Array', 'String'} @@ -12,7 +12,7 @@ def to_op(op, reversed=False): ''' create a function that transforms a method to a binary op - often we need to convert a pseudon method + often we need to convert a pseudo method .() to a binary op that's a decorator that helps for that @@ -61,11 +61,11 @@ def _placeholder(self, receiver, *args, equivalent) which should return a Node - Nodes: Nodes can be either the official pseudon nodes or in special cases + Nodes: Nodes can be either the official pseudo nodes or in special cases with `_` when they describe syntax typical only for the target language of the translator - helpers: quite useful helpers from pseudon.pseudon_tree are + helpers: quite useful helpers from pseudo.pseudo_tree are `method_call(receiver: str/Node, message: str, args: [Node])` which helps with method call nodes with normal `local` name object receivers @@ -142,11 +142,11 @@ def transform_standard_method_call(self, node, in_block=False, assignment=None): node.receiver = self.transform(node.receiver) if l not in self.methods: - raise PseudonStandardLibraryError( - 'pseudon doesn\'t recognize %s as a standard type' % l) + raise PseudoStandardLibraryError( + 'pseudo doesn\'t recognize %s as a standard type' % l) elif node.message not in self.methods[l]: - raise PseudonStandardLibraryError( - 'pseudon doesn\'t have a %s#%s method' % (l, node.message)) + raise PseudoStandardLibraryError( + 'pseudo doesn\'t have a %s#%s method' % (l, node.message)) x = self.methods[l][node.message] if isinstance(x, type) and issubclass(x, LeakingNode): @@ -181,14 +181,14 @@ def leaking(self, z, module, name, node, context, *data): leaked_nodes = z.as_assignment(z.temp_name(data[0])) exp = local(z.temp_name(data[0]), node.pseudo_type) if exp is None or exp.pseudo_type == 'Void': - raise PseudonTypeError("pseudo can't handle values with void type in expression: %s?%s" % (module, name)) + raise PseudoTypeError("pseudo can't handle values with void type in expression: %s?%s" % (module, name)) self.leaked_nodes += leaked_nodes return exp elif context == 'assignment': if isinstance(z, NormalLeakingNode): leaked_nodes, exp = z.as_expression() if exp is None or exp.pseudo_type == 'Void': - raise PseudonTypeError("pseudo can't handle values with void type in expression: %s?%s" % (module, name)) + raise PseudoTypeError("pseudo can't handle values with void type in expression: %s?%s" % (module, name)) self.leaked_nodes += leaked_nodes return assignment(data[0], exp) else: @@ -203,11 +203,11 @@ def transform_standard_call(self, node, in_block=False, assignment=None): namespace = node.namespace or 'global' node.args = [self.transform(arg) for arg in node.args] if namespace not in self.functions: - raise PseudonStandardLibraryError( - 'pseudon doesn\'t have a %s namespace' % namespace) + raise PseudoStandardLibraryError( + 'pseudo doesn\'t have a %s namespace' % namespace) elif node.function not in self.functions[namespace]: - raise PseudonStandardLibraryError( - 'pseudon doesn\'t have a %s:%s function' % (namespace, node.function)) + raise PseudoStandardLibraryError( + 'pseudo doesn\'t have a %s:%s function' % (namespace, node.function)) x = self.functions[namespace][node.function] if isinstance(x, type) and issubclass(x, LeakingNode): @@ -282,7 +282,7 @@ def _expand_api(self, api, receiver, args, pseudo_type, equivalent): else: return call(call_api, args, pseudo_type=pseudo_type) else: - raise PseudonDSLError('%s not supported by api dsl' % str(api)) + raise PseudoDSLError('%s not supported by api dsl' % str(api)) def _parse_part(self, part, receiver, args, equivalent): if part[0] == '%': # %{v} @@ -294,7 +294,7 @@ def _parse_part(self, part, receiver, args, equivalent): if receiver: return receiver else: - raise PseudonDSLError( + raise PseudoDSLError( '%{self} not working for functions with api dsl') elif inside == 'equivalent': return typename(equivalent) diff --git a/pseudon/api_translators/__init__.py b/pseudo/api_translators/__init__.py similarity index 100% rename from pseudon/api_translators/__init__.py rename to pseudo/api_translators/__init__.py diff --git a/pseudon/api_translators/cpp_api_handlers.py b/pseudo/api_translators/cpp_api_handlers.py similarity index 94% rename from pseudon/api_translators/cpp_api_handlers.py rename to pseudo/api_translators/cpp_api_handlers.py index a3326d3..193a206 100644 --- a/pseudon/api_translators/cpp_api_handlers.py +++ b/pseudo/api_translators/cpp_api_handlers.py @@ -1,5 +1,5 @@ -from pseudon.pseudon_tree import Node, call, method_call, local, assignment, to_node -from pseudon.api_handlers import BizarreLeakingNode, NormalLeakingNode +from pseudo.pseudo_tree import Node, call, method_call, local, assignment, to_node +from pseudo.api_handlers import BizarreLeakingNode, NormalLeakingNode class Read(BizarreLeakingNode): ''' diff --git a/pseudon/api_translators/cpp_translator.py b/pseudo/api_translators/cpp_translator.py similarity index 93% rename from pseudon/api_translators/cpp_translator.py rename to pseudo/api_translators/cpp_translator.py index abea80a..e8b94e2 100644 --- a/pseudon/api_translators/cpp_translator.py +++ b/pseudo/api_translators/cpp_translator.py @@ -1,7 +1,7 @@ -from pseudon.types import * -from pseudon.api_translator import ApiTranslator -from pseudon.pseudon_tree import Node, method_call, call, to_node -from pseudon.api_translators.cpp_api_handlers import Read, Slice, ReadFile +from pseudo.types import * +from pseudo.api_translator import ApiTranslator +from pseudo.pseudo_tree import Node, method_call, call, to_node +from pseudo.api_translators.cpp_api_handlers import Read, Slice, ReadFile class CppTranslator(ApiTranslator): ''' diff --git a/pseudon/api_translators/csharp_api_handlers.py b/pseudo/api_translators/csharp_api_handlers.py similarity index 50% rename from pseudon/api_translators/csharp_api_handlers.py rename to pseudo/api_translators/csharp_api_handlers.py index ce7db36..81ac5cf 100644 --- a/pseudon/api_translators/csharp_api_handlers.py +++ b/pseudo/api_translators/csharp_api_handlers.py @@ -1,5 +1,5 @@ -from pseudon.pseudon_tree import Node, call, method_call, local, assignment, to_node -from pseudon.api_handlers import BizarreLeakingNode, NormalLeakingNode +from pseudo.pseudo_tree import Node, call, method_call, local, assignment, to_node +from pseudo.api_handlers import BizarreLeakingNode, NormalLeakingNode def expand_slice(receiver, from_, to, pseudo_type=None): return method_call(method_call(receiver, 'Take', [to], pseudo_type), 'Drop', [from_], pseudo_type) diff --git a/pseudon/api_translators/csharp_translator.py b/pseudo/api_translators/csharp_translator.py similarity index 88% rename from pseudon/api_translators/csharp_translator.py rename to pseudo/api_translators/csharp_translator.py index 28f226f..3622da3 100644 --- a/pseudon/api_translators/csharp_translator.py +++ b/pseudo/api_translators/csharp_translator.py @@ -1,7 +1,7 @@ -from pseudon.types import * -from pseudon.api_translator import ApiTranslator -from pseudon.pseudon_tree import Node, method_call, call -from pseudon.api_translators.csharp_api_handlers import expand_slice +from pseudo.types import * +from pseudo.api_translator import ApiTranslator +from pseudo.pseudo_tree import Node, method_call, call +from pseudo.api_translators.csharp_api_handlers import expand_slice class CSharpTranslator(ApiTranslator): ''' diff --git a/pseudon/api_translators/go_api_handlers.py b/pseudo/api_translators/go_api_handlers.py similarity index 92% rename from pseudon/api_translators/go_api_handlers.py rename to pseudo/api_translators/go_api_handlers.py index 595e448..1977e3b 100644 --- a/pseudon/api_translators/go_api_handlers.py +++ b/pseudo/api_translators/go_api_handlers.py @@ -1,5 +1,5 @@ -from pseudon.pseudon_tree import Node, call, method_call, local, assignment, attr, to_node -from pseudon.api_handlers import BizarreLeakingNode, NormalLeakingNode +from pseudo.pseudo_tree import Node, call, method_call, local, assignment, attr, to_node +from pseudo.api_handlers import BizarreLeakingNode, NormalLeakingNode def expand_push(receiver, element): return Node( @@ -18,7 +18,7 @@ def expand_map(receiver, function, assignment, pseudo_type): return Node('block', block=[Node('_go_multi_assignment', name=local('result'), value=Node('_go_make_slice', - type=receiver.pseudon_type, + type=receiver.pseudo_type, length=call('len', receiver))), for_each_with_index_statement( [iter, 'j'], @@ -37,7 +37,7 @@ def expand_filter(receiver, test, assignment, pseudo_type): Node('_go_multi_assignment', name=local('result'), value=Node('_go_make_slice', - type=receiver.pseudon_type, + type=receiver.pseudo_type, length=call('len', receiver))), for_each_with_index_statement( [iter, 'j'], diff --git a/pseudon/api_translators/golang_translator.py b/pseudo/api_translators/golang_translator.py similarity index 87% rename from pseudon/api_translators/golang_translator.py rename to pseudo/api_translators/golang_translator.py index c5c129f..93476f1 100644 --- a/pseudon/api_translators/golang_translator.py +++ b/pseudo/api_translators/golang_translator.py @@ -1,7 +1,7 @@ -from pseudon.types import * -from pseudon.api_translator import ApiTranslator, to_op -from pseudon.pseudon_tree import Node, method_call, call, if_statement, for_each_with_index_statement, assignment, attr -from pseudon.api_translators.go_api_handlers import expand_insert, expand_slice, expand_map, expand_filter, Read +from pseudo.types import * +from pseudo.api_translator import ApiTranslator, to_op +from pseudo.pseudo_tree import Node, method_call, call, if_statement, for_each_with_index_statement, assignment, attr +from pseudo.api_translators.go_api_handlers import expand_insert, expand_slice, expand_map, expand_filter, Read class GolangTranslator(ApiTranslator): ''' diff --git a/pseudon/api_translators/js_translator.py b/pseudo/api_translators/js_translator.py similarity index 94% rename from pseudon/api_translators/js_translator.py rename to pseudo/api_translators/js_translator.py index 8155c65..26062f0 100644 --- a/pseudon/api_translators/js_translator.py +++ b/pseudo/api_translators/js_translator.py @@ -1,6 +1,6 @@ -from pseudon.types import * -from pseudon.api_translator import ApiTranslator -from pseudon.pseudon_tree import Node, method_call, call +from pseudo.types import * +from pseudo.api_translator import ApiTranslator +from pseudo.pseudo_tree import Node, method_call, call class JSTranslator(ApiTranslator): diff --git a/pseudon/api_translators/php_translator.py b/pseudo/api_translators/php_translator.py similarity index 90% rename from pseudon/api_translators/php_translator.py rename to pseudo/api_translators/php_translator.py index f6302a3..35ff610 100644 --- a/pseudon/api_translators/php_translator.py +++ b/pseudo/api_translators/php_translator.py @@ -1,6 +1,6 @@ -from pseudon.types import * -from pseudon.api_translator import ApiTranslator -from pseudon.pseudon_tree import Node, call, local +from pseudo.types import * +from pseudo.api_translator import ApiTranslator +from pseudo.pseudo_tree import Node, call, local class PHPTranslator(ApiTranslator): diff --git a/pseudon/api_translators/python_api_handlers.py b/pseudo/api_translators/python_api_handlers.py similarity index 94% rename from pseudon/api_translators/python_api_handlers.py rename to pseudo/api_translators/python_api_handlers.py index f289120..3c5ed44 100644 --- a/pseudon/api_translators/python_api_handlers.py +++ b/pseudo/api_translators/python_api_handlers.py @@ -1,5 +1,5 @@ -from pseudon.pseudon_tree import Node, call, method_call, local, assignment, to_node -from pseudon.api_handlers import BizarreLeakingNode, NormalLeakingNode +from pseudo.pseudo_tree import Node, call, method_call, local, assignment, to_node +from pseudo.api_handlers import BizarreLeakingNode, NormalLeakingNode def expand_map(receiver, func): if func.type == 'lambda': diff --git a/pseudon/api_translators/python_translator.py b/pseudo/api_translators/python_translator.py similarity index 92% rename from pseudon/api_translators/python_translator.py rename to pseudo/api_translators/python_translator.py index 6ac16ce..9a93b39 100644 --- a/pseudon/api_translators/python_translator.py +++ b/pseudo/api_translators/python_translator.py @@ -1,7 +1,7 @@ -from pseudon.types import * -from pseudon.api_translator import ApiTranslator, to_op -from pseudon.pseudon_tree import Node, method_call, call, to_node, local, assignment_updated -from pseudon.api_translators.python_api_handlers import expand_map, expand_filter, expand_slice, expand_set_slice, ReadFile, WriteFile +from pseudo.types import * +from pseudo.api_translator import ApiTranslator, to_op +from pseudo.pseudo_tree import Node, method_call, call, to_node, local, assignment_updated +from pseudo.api_translators.python_api_handlers import expand_map, expand_filter, expand_slice, expand_set_slice, ReadFile, WriteFile class PythonTranslator(ApiTranslator): ''' diff --git a/pseudon/api_translators/ruby_api_handlers.py b/pseudo/api_translators/ruby_api_handlers.py similarity index 84% rename from pseudon/api_translators/ruby_api_handlers.py rename to pseudo/api_translators/ruby_api_handlers.py index bda7c88..1b5a685 100644 --- a/pseudon/api_translators/ruby_api_handlers.py +++ b/pseudo/api_translators/ruby_api_handlers.py @@ -1,4 +1,4 @@ -from pseudon.pseudon_tree import Node, call, method_call, local, assignment, to_node +from pseudo.pseudo_tree import Node, call, method_call, local, assignment, to_node def expand_slice(receiver, from_=None, to=None, pseudo_type=None): if from_: diff --git a/pseudon/api_translators/ruby_translator.py b/pseudo/api_translators/ruby_translator.py similarity index 90% rename from pseudon/api_translators/ruby_translator.py rename to pseudo/api_translators/ruby_translator.py index 890fef2..ece8e0e 100644 --- a/pseudon/api_translators/ruby_translator.py +++ b/pseudo/api_translators/ruby_translator.py @@ -1,7 +1,7 @@ -from pseudon.types import * -from pseudon.api_translator import ApiTranslator -from pseudon.pseudon_tree import Node, to_node -from pseudon.api_translators.ruby_api_handlers import expand_slice +from pseudo.types import * +from pseudo.api_translator import ApiTranslator +from pseudo.pseudo_tree import Node, to_node +from pseudo.api_translators.ruby_api_handlers import expand_slice class RubyTranslator(ApiTranslator): ''' diff --git a/pseudon/code_generator.py b/pseudo/code_generator.py similarity index 97% rename from pseudon/code_generator.py rename to pseudo/code_generator.py index d97c0a3..11f3bcb 100644 --- a/pseudon/code_generator.py +++ b/pseudo/code_generator.py @@ -1,7 +1,7 @@ # base generator with common functionality import re -from pseudon.pseudon_tree import Node -from pseudon.code_generator_dsl import Placeholder, Newline, Action, Function, SubTemplate, SubElement, PseudonType, Whitespace, Offset, INTERNAL_WHITESPACE, NEWLINE +from pseudo.pseudo_tree import Node +from pseudo.code_generator_dsl import Placeholder, Newline, Action, Function, SubTemplate, SubElement, PseudoType, Whitespace, Offset, INTERNAL_WHITESPACE, NEWLINE PASS_REGEX = re.compile(r'\n[ \t]*\n([ \t]*pass)') LINE_FIRS = re.compile(r'^( +)') @@ -339,7 +339,7 @@ def % if placeholder[0] == '#': q = Function(placeholder[1:]) elif placeholder[0] == '@': - q = PseudonType(placeholder[1:].split('.')) + q = PseudoType(placeholder[1:].split('.')) elif placeholder[0] == '.': q = SubTemplate(label, placeholder[1:]) elif '.' in placeholder: @@ -392,7 +392,7 @@ def safe_double(self, node, indent): return s def render_type(self, type): - return PseudonType(type).expand_type(type, self) + return PseudoType(type).expand_type(type, self) def offset(self, depth): return self._single_indent * depth diff --git a/pseudon/code_generator_dsl.py b/pseudo/code_generator_dsl.py similarity index 96% rename from pseudon/code_generator_dsl.py rename to pseudo/code_generator_dsl.py index 2d657c0..6b68862 100644 --- a/pseudon/code_generator_dsl.py +++ b/pseudo/code_generator_dsl.py @@ -1,12 +1,12 @@ import yaml -from pseudon.pseudon_tree import Node +from pseudo.pseudo_tree import Node Iterable = (list, tuple, set) class FragmentGenerator: @property def y(self): result = yaml.dump(self) - return result.replace('!python/object:pseudon.code_generator_dsl.', '') + return result.replace('!python/object:pseudo.code_generator_dsl.', '') # we can't set __str__ and __repr__ because this makes yaml.dump insane :( # and i like yaml.dump, I don't want it to be insane, even if that's cute @@ -31,7 +31,7 @@ def expand(self, generator, node, depth): return str(content) -class PseudonType(FragmentGenerator): +class PseudoType(FragmentGenerator): def __init__(self, placeholder): self.placeholder = placeholder diff --git a/pseudon/env.py b/pseudo/env.py similarity index 100% rename from pseudon/env.py rename to pseudo/env.py diff --git a/pseudo/errors.py b/pseudo/errors.py new file mode 100644 index 0000000..9d25b62 --- /dev/null +++ b/pseudo/errors.py @@ -0,0 +1,11 @@ +class PseudoError(Exception): + pass + +class PseudoStandardLibraryError(PseudoError): + pass + +class PseudoDSLError(PseudoError): + pass + +class PseudoTypeError(PseudoError): + pass \ No newline at end of file diff --git a/pseudon/generators/__init__.py b/pseudo/generators/__init__.py similarity index 100% rename from pseudon/generators/__init__.py rename to pseudo/generators/__init__.py diff --git a/pseudon/generators/cpp_generator.py b/pseudo/generators/cpp_generator.py similarity index 96% rename from pseudon/generators/cpp_generator.py rename to pseudo/generators/cpp_generator.py index b9cc9ee..399c9e5 100644 --- a/pseudon/generators/cpp_generator.py +++ b/pseudo/generators/cpp_generator.py @@ -1,7 +1,7 @@ -from pseudon.code_generator import CodeGenerator, switch -from pseudon.middlewares import DeclarationMiddleware, CppPointerMiddleware, CppDisplayExceptionMiddleware -from pseudon.pseudon_tree import Node, local -from pseudon.code_generator_dsl import PseudonType +from pseudo.code_generator import CodeGenerator, switch +from pseudo.middlewares import DeclarationMiddleware, CppPointerMiddleware, CppDisplayExceptionMiddleware +from pseudo.pseudo_tree import Node, local +from pseudo.code_generator_dsl import PseudoType class CppGenerator(CodeGenerator): '''Cpp code generator''' @@ -228,7 +228,7 @@ def header(self, node, indent): def params(self, node, indent): return ', '.join( '%s %s' % ( - PseudonType('').expand_type(k.pseudo_type, self), + PseudoType('').expand_type(k.pseudo_type, self), k.name) for j, k in enumerate(node.params) ) def anon_block(self, node, indent): diff --git a/pseudon/generators/csharp_generator.py b/pseudo/generators/csharp_generator.py similarity index 98% rename from pseudon/generators/csharp_generator.py rename to pseudo/generators/csharp_generator.py index 98f1c11..93f365e 100644 --- a/pseudon/generators/csharp_generator.py +++ b/pseudo/generators/csharp_generator.py @@ -1,6 +1,6 @@ -from pseudon.code_generator import CodeGenerator, switch -from pseudon.middlewares import DeclarationMiddleware, NameMiddleware -from pseudon.pseudon_tree import Node, local +from pseudo.code_generator import CodeGenerator, switch +from pseudo.middlewares import DeclarationMiddleware, NameMiddleware +from pseudo.pseudo_tree import Node, local class CSharpGenerator(CodeGenerator): '''CSharp code generator''' diff --git a/pseudon/generators/golang_generator.py b/pseudo/generators/golang_generator.py similarity index 94% rename from pseudon/generators/golang_generator.py rename to pseudo/generators/golang_generator.py index ade43ac..18c00be 100644 --- a/pseudon/generators/golang_generator.py +++ b/pseudo/generators/golang_generator.py @@ -1,7 +1,7 @@ -from pseudon.code_generator import CodeGenerator, switch -from pseudon.middlewares import GoConstructorMiddleware, TupleMiddleware, DeclarationMiddleware # GoErrorHandlingMiddleware #, GoTupleMiddleware -from pseudon.code_generator_dsl import PseudonType -from pseudon.pseudon_tree import Node, local +from pseudo.code_generator import CodeGenerator, switch +from pseudo.middlewares import GoConstructorMiddleware, TupleMiddleware, DeclarationMiddleware # GoErrorHandlingMiddleware #, GoTupleMiddleware +from pseudo.code_generator_dsl import PseudoType +from pseudo.pseudo_tree import Node, local class GolangGenerator(CodeGenerator): '''Go generator''' @@ -216,7 +216,7 @@ class % : Exception ) def params(self, node, depth): - return ', '.join('%s %s' % (q.name, PseudonType('').expand_type(q.pseudo_type, self)) for q in node.params) + return ', '.join('%s %s' % (q.name, PseudoType('').expand_type(q.pseudo_type, self)) for q in node.params) def dependencies(self, node, depth): if len(node.dependencies) == 1: diff --git a/pseudon/generators/java_generator.py b/pseudo/generators/java_generator.py similarity index 85% rename from pseudon/generators/java_generator.py rename to pseudo/generators/java_generator.py index 1abd5d5..5dfbe17 100644 --- a/pseudon/generators/java_generator.py +++ b/pseudo/generators/java_generator.py @@ -1,4 +1,4 @@ -from pseudon.code_generator import CodeGenerator +from pseudo.code_generator import CodeGenerator class JavaGenerator(CodeGenerator): diff --git a/pseudon/generators/js_generator.py b/pseudo/generators/js_generator.py similarity index 98% rename from pseudon/generators/js_generator.py rename to pseudo/generators/js_generator.py index 13aedbc..32f8aff 100644 --- a/pseudon/generators/js_generator.py +++ b/pseudo/generators/js_generator.py @@ -1,6 +1,6 @@ import re -from pseudon.code_generator import CodeGenerator, switch -from pseudon.middlewares import DeclarationMiddleware +from pseudo.code_generator import CodeGenerator, switch +from pseudo.middlewares import DeclarationMiddleware JS_NAME = re.compile(r'[a-zA-Z][a-zA-Z_0-9]*') diff --git a/pseudon/generators/php_generator.py b/pseudo/generators/php_generator.py similarity index 94% rename from pseudon/generators/php_generator.py rename to pseudo/generators/php_generator.py index d9bf889..d3eeaa5 100644 --- a/pseudon/generators/php_generator.py +++ b/pseudo/generators/php_generator.py @@ -1,4 +1,4 @@ -from pseudon.code_generator import CodeGenerator +from pseudo.code_generator import CodeGenerator class PHPGenerator(CodeGenerator): diff --git a/pseudon/generators/python_generator.py b/pseudo/generators/python_generator.py similarity index 99% rename from pseudon/generators/python_generator.py rename to pseudo/generators/python_generator.py index d7586ce..86011d0 100644 --- a/pseudon/generators/python_generator.py +++ b/pseudo/generators/python_generator.py @@ -1,4 +1,4 @@ -from pseudon.code_generator import CodeGenerator, switch +from pseudo.code_generator import CodeGenerator, switch EXPRESSION_TYPES = ['call', 'implicit_return', 'method_call', 'explicit_return'] diff --git a/pseudon/generators/ruby_generator.py b/pseudo/generators/ruby_generator.py similarity index 99% rename from pseudon/generators/ruby_generator.py rename to pseudo/generators/ruby_generator.py index 7c94ff8..9b614a2 100644 --- a/pseudon/generators/ruby_generator.py +++ b/pseudo/generators/ruby_generator.py @@ -1,4 +1,4 @@ -from pseudon.code_generator import CodeGenerator, switch +from pseudo.code_generator import CodeGenerator, switch import re SHORT_SYNTAX = re.compile(r'[a-zA-Z_][a-zA-Z0-9_]*') diff --git a/pseudon/helpers.py b/pseudo/helpers.py similarity index 100% rename from pseudon/helpers.py rename to pseudo/helpers.py diff --git a/pseudon/loader.py b/pseudo/loader.py similarity index 77% rename from pseudon/loader.py rename to pseudo/loader.py index 2921749..47f1a88 100644 --- a/pseudon/loader.py +++ b/pseudo/loader.py @@ -1,16 +1,16 @@ import types import yaml -from pseudon.pseudon_tree import Node +from pseudo.pseudo_tree import Node COMMANDS = { 'py': lambda filename: ['pseudo-python', filename], 'rb': lambda filename: ['pseudo-ruby', filename], - 'js': lambda filename: ['pseudon-javascript', filename], - 'swift': lambda filename: ['pseudon-swift', filename], - 'java': lambda filename: ['pseudon-java', filename], - 'cs': lambda filename: ['pseudon-csharp', filename], - 'go': lambda filename: ['pseudon-golang', filename] + 'js': lambda filename: ['pseudo-javascript', filename], + 'swift': lambda filename: ['pseudo-swift', filename], + 'java': lambda filename: ['pseudo-java', filename], + 'cs': lambda filename: ['pseudo-csharp', filename], + 'go': lambda filename: ['pseudo-golang', filename] } diff --git a/pseudo/middlewares/__init__.py b/pseudo/middlewares/__init__.py new file mode 100644 index 0000000..5bb12f7 --- /dev/null +++ b/pseudo/middlewares/__init__.py @@ -0,0 +1,7 @@ +from pseudo.middlewares.declaration_middleware import DeclarationMiddleware +from pseudo.middlewares.go_constructor_middleware import GoConstructorMiddleware +from pseudo.middlewares.tuple_middleware import TupleMiddleware +from pseudo.middlewares.name_middleware import NameMiddleware +from pseudo.middlewares.cpp_pointer_middleware import CppPointerMiddleware +from pseudo.middlewares.cpp_display_exception_middleware import CppDisplayExceptionMiddleware +# go_error_handling_middleware import GoErrorHandlingMiddleware diff --git a/pseudon/middlewares/cpp_display_exception_middleware.py b/pseudo/middlewares/cpp_display_exception_middleware.py similarity index 84% rename from pseudon/middlewares/cpp_display_exception_middleware.py rename to pseudo/middlewares/cpp_display_exception_middleware.py index 4487ead..361c9e9 100644 --- a/pseudon/middlewares/cpp_display_exception_middleware.py +++ b/pseudo/middlewares/cpp_display_exception_middleware.py @@ -1,5 +1,5 @@ -from pseudon.middlewares.middleware import Middleware -from pseudon.pseudon_tree import Node, method_call +from pseudo.middlewares.middleware import Middleware +from pseudo.pseudo_tree import Node, method_call class CppDisplayExceptionMiddleware(Middleware): ''' diff --git a/pseudon/middlewares/cpp_pointer_middleware.py b/pseudo/middlewares/cpp_pointer_middleware.py similarity index 92% rename from pseudon/middlewares/cpp_pointer_middleware.py rename to pseudo/middlewares/cpp_pointer_middleware.py index 4480116..c6dc1be 100644 --- a/pseudon/middlewares/cpp_pointer_middleware.py +++ b/pseudo/middlewares/cpp_pointer_middleware.py @@ -1,5 +1,5 @@ -from pseudon.middlewares.middleware import Middleware -from pseudon.pseudon_tree import Node, method_call +from pseudo.middlewares.middleware import Middleware +from pseudo.pseudo_tree import Node, method_call BUILTIN_SIMPLE = {'Int', 'String', 'Void', 'Exception', 'Float', 'Boolean', 'CppIterator', 'ifstream', 'istreambuf_iterator'} diff --git a/pseudon/middlewares/declaration_middleware.py b/pseudo/middlewares/declaration_middleware.py similarity index 97% rename from pseudon/middlewares/declaration_middleware.py rename to pseudo/middlewares/declaration_middleware.py index d85604d..c45215c 100644 --- a/pseudon/middlewares/declaration_middleware.py +++ b/pseudo/middlewares/declaration_middleware.py @@ -1,4 +1,4 @@ -from pseudon.middlewares.middleware import Middleware +from pseudo.middlewares.middleware import Middleware class DeclarationMiddleware(Middleware): ''' diff --git a/pseudon/middlewares/go_constructor_middleware.py b/pseudo/middlewares/go_constructor_middleware.py similarity index 94% rename from pseudon/middlewares/go_constructor_middleware.py rename to pseudo/middlewares/go_constructor_middleware.py index c6faa41..27b5f44 100644 --- a/pseudon/middlewares/go_constructor_middleware.py +++ b/pseudo/middlewares/go_constructor_middleware.py @@ -1,6 +1,6 @@ -from pseudon.middlewares.middleware import Middleware -from pseudon.pseudon_tree import Node, assignment -from pseudon.tree_transformer import TreeTransformer +from pseudo.middlewares.middleware import Middleware +from pseudo.pseudo_tree import Node, assignment +from pseudo.tree_transformer import TreeTransformer class GoConstructorMiddleware(Middleware): ''' diff --git a/pseudon/middlewares/go_error_handling_middleware.py b/pseudo/middlewares/go_error_handling_middleware.py similarity index 95% rename from pseudon/middlewares/go_error_handling_middleware.py rename to pseudo/middlewares/go_error_handling_middleware.py index de9576e..2634dce 100644 --- a/pseudon/middlewares/go_error_handling_middleware.py +++ b/pseudo/middlewares/go_error_handling_middleware.py @@ -1,4 +1,4 @@ -from pseudon.middlewares.middleware import Middleware +from pseudo.middlewares.middleware import Middleware class GoErrorHandlingMiddleware(Middleware): ''' @@ -69,7 +69,7 @@ def transform_f(self, node, in_block=False, assignment=None): def transform_custom_exception(self, node, in_block=False, assignment=None): if node.base: - raise PseudonTypeError("pseudo go generator doesn't support custom exceptions with inheritance") + raise PseudoTypeError("pseudo go generator doesn't support custom exceptions with inheritance") return node def transform_call(self, node, in_block=False, assignment=False): diff --git a/pseudo/middlewares/middleware.py b/pseudo/middlewares/middleware.py new file mode 100644 index 0000000..dc10ac5 --- /dev/null +++ b/pseudo/middlewares/middleware.py @@ -0,0 +1,4 @@ +from pseudo.tree_transformer import TreeTransformer + +class Middleware(TreeTransformer): + pass diff --git a/pseudon/middlewares/name_middleware.py b/pseudo/middlewares/name_middleware.py similarity index 98% rename from pseudon/middlewares/name_middleware.py rename to pseudo/middlewares/name_middleware.py index 866bb4c..f8e366e 100644 --- a/pseudon/middlewares/name_middleware.py +++ b/pseudo/middlewares/name_middleware.py @@ -1,4 +1,4 @@ -from pseudon.middlewares.middleware import Middleware +from pseudo.middlewares.middleware import Middleware class NameMiddleware(Middleware): ''' diff --git a/pseudon/middlewares/tuple_middleware.py b/pseudo/middlewares/tuple_middleware.py similarity index 88% rename from pseudon/middlewares/tuple_middleware.py rename to pseudo/middlewares/tuple_middleware.py index 01587a0..75c731b 100644 --- a/pseudon/middlewares/tuple_middleware.py +++ b/pseudo/middlewares/tuple_middleware.py @@ -1,7 +1,7 @@ -from pseudon.middlewares.middleware import Middleware -from pseudon.pseudon_tree import Node, assignment -from pseudon.tree_transformer import TreeTransformer -from pseudon.helpers import safe_serialize_type +from pseudo.middlewares.middleware import Middleware +from pseudo.pseudo_tree import Node, assignment +from pseudo.tree_transformer import TreeTransformer +from pseudo.helpers import safe_serialize_type class TupleMiddleware(Middleware): ''' diff --git a/pseudon/parser.py b/pseudo/parser.py similarity index 100% rename from pseudon/parser.py rename to pseudo/parser.py diff --git a/pseudon/pseudon_tree.py b/pseudo/pseudo_tree.py similarity index 96% rename from pseudon/pseudon_tree.py rename to pseudo/pseudo_tree.py index e8bd4fe..0efc59c 100644 --- a/pseudon/pseudon_tree.py +++ b/pseudo/pseudo_tree.py @@ -2,7 +2,7 @@ class Node: ''' - A pseudon tree node + A pseudo tree node Example: Node('local', name='l') ''' @@ -17,7 +17,7 @@ def __init__(self, type, **fields): @property def y(self): result = yaml.dump(self) - return result.replace('!python/object:pseudon.pseudon_tree.', '') + return result.replace('!python/object:pseudo.pseudo_tree.', '') def node_representer(dumper, data): return dumper.represent_scalar('!%s' % type(data).__name__, ) diff --git a/pseudon/tree_transformer.py b/pseudo/tree_transformer.py similarity index 97% rename from pseudon/tree_transformer.py rename to pseudo/tree_transformer.py index 7b348ca..05a9607 100644 --- a/pseudon/tree_transformer.py +++ b/pseudo/tree_transformer.py @@ -1,4 +1,4 @@ -from pseudon.pseudon_tree import Node +from pseudo.pseudo_tree import Node class TreeTransformer: diff --git a/pseudon/type_engine.py b/pseudo/type_engine.py similarity index 80% rename from pseudon/type_engine.py rename to pseudo/type_engine.py index c37a549..5300102 100644 --- a/pseudon/type_engine.py +++ b/pseudo/type_engine.py @@ -1,7 +1,7 @@ -from pseudon.tree_transformer import TreeTransformer -from pseudon.env import Env -import pseudon.types -from pseudon.types import * +from pseudo.tree_transformer import TreeTransformer +from pseudo.env import Env +import pseudo.types +from pseudo.types import * from pprint import pprint @@ -10,7 +10,7 @@ class TypeEngine(TreeTransformer): def __init__(self): self.env = Env() self.scope = 'static' - self.types = pseudon.types.TYPES + self.types = pseudo.types.TYPES def inference(self, tree): # go thru stuff @@ -21,7 +21,7 @@ def inference(self, tree): def transform_function(self, node): print(node.__dict__) self.env.values[node.name] = self.to_type(node.type_hint[-1]) - node.pseudon_type = [self.to_type( + node.pseudo_type = [self.to_type( arg.type_hint) for arg in node.args] + [self.env.values[node.name]] self.env = self.env.child_env( {arg.name: self.to_type(arg.type_hint) for arg in node.args}) @@ -31,12 +31,12 @@ def transform_function(self, node): def transform_assignment(self, node): self.transform(node.right) - self.env[node.left.name] = node.right.pseudon_type - node.left.pseudon_type = node.right.pseudon_type + self.env[node.left.name] = node.right.pseudo_type + node.left.pseudo_type = node.right.pseudo_type return node def transform_int(self, node): - node.pseudon_type = Int + node.pseudo_type = Int return node def to_type(self, type_hint): diff --git a/pseudon/types.py b/pseudo/types.py similarity index 92% rename from pseudon/types.py rename to pseudo/types.py index 3ee8a45..9b56d67 100644 --- a/pseudon/types.py +++ b/pseudo/types.py @@ -1,4 +1,4 @@ -class PseudonType: +class PseudoType: def is_compatible_with(self, other): return self.child_of(other) or other.child_of(self) @@ -12,7 +12,7 @@ def child_of(self, other): return False -class SimpleType(PseudonType): +class SimpleType(PseudoType): def __init__(self, label, parent=None): self.label = label @@ -28,7 +28,7 @@ def __hash__(self): return hash(repr(self)) -class Any(PseudonType): +class Any(PseudoType): def __eq__(self, other): return True @@ -40,11 +40,11 @@ def __hash__(self): return hash(repr(self)) -class Unknown(PseudonType): +class Unknown(PseudoType): pass -class GenericType(PseudonType): +class GenericType(PseudoType): def __init__(self, label, generic_args, parent=None): self.label = label @@ -58,7 +58,7 @@ def __eq__(self, other): return self.label == other.label and self.generic_args == other.generic_args -class CustomType(PseudonType): +class CustomType(PseudoType): def __init__(self, label, fields=None, parent=None): self.label = label @@ -72,7 +72,7 @@ def __eq__(self, other): return self.label == other.label -class GenericInstance(PseudonType): +class GenericInstance(PseudoType): def __init__(self, generic, args): self.generic = generic diff --git a/pseudon/untitled.py b/pseudo/untitled.py similarity index 100% rename from pseudon/untitled.py rename to pseudo/untitled.py diff --git a/pseudon/errors.py b/pseudon/errors.py deleted file mode 100644 index 4b50ddd..0000000 --- a/pseudon/errors.py +++ /dev/null @@ -1,11 +0,0 @@ -class PseudonError(Exception): - pass - -class PseudonStandardLibraryError(PseudonError): - pass - -class PseudonDSLError(PseudonError): - pass - -class PseudonTypeError(PseudonError): - pass \ No newline at end of file diff --git a/pseudon/middlewares/__init__.py b/pseudon/middlewares/__init__.py deleted file mode 100644 index c5444f2..0000000 --- a/pseudon/middlewares/__init__.py +++ /dev/null @@ -1,7 +0,0 @@ -from pseudon.middlewares.declaration_middleware import DeclarationMiddleware -from pseudon.middlewares.go_constructor_middleware import GoConstructorMiddleware -from pseudon.middlewares.tuple_middleware import TupleMiddleware -from pseudon.middlewares.name_middleware import NameMiddleware -from pseudon.middlewares.cpp_pointer_middleware import CppPointerMiddleware -from pseudon.middlewares.cpp_display_exception_middleware import CppDisplayExceptionMiddleware -# go_error_handling_middleware import GoErrorHandlingMiddleware diff --git a/pseudon/middlewares/middleware.py b/pseudon/middlewares/middleware.py deleted file mode 100644 index 2bfbfa5..0000000 --- a/pseudon/middlewares/middleware.py +++ /dev/null @@ -1,4 +0,0 @@ -from pseudon.tree_transformer import TreeTransformer - -class Middleware(TreeTransformer): - pass diff --git a/tests/suite.py b/tests/suite.py index 299e337..9147899 100644 --- a/tests/suite.py +++ b/tests/suite.py @@ -1,6 +1,6 @@ import re -from pseudon.pseudon_tree import Node, to_node, call, method_call, local, typename, assignment -from pseudon import generate +from pseudo.pseudo_tree import Node, to_node, call, method_call, local, typename, assignment +from pseudo import generate SNAKE_CASE_REGEX = re.compile(r'(_\[a-z])') diff --git a/tests/test_cpp.py b/tests/test_cpp.py index 3d4431c..519ae1d 100644 --- a/tests/test_cpp.py +++ b/tests/test_cpp.py @@ -1,7 +1,7 @@ import unittest import textwrap -from pseudon import generate -from pseudon.pseudon_tree import Node +from pseudo import generate +from pseudo.pseudo_tree import Node import suite as suite #v diff --git a/tests/test_csharp.py b/tests/test_csharp.py index 1997769..5fe8bfe 100644 --- a/tests/test_csharp.py +++ b/tests/test_csharp.py @@ -1,7 +1,7 @@ import unittest import textwrap -from pseudon import generate -from pseudon.pseudon_tree import Node +from pseudo import generate +from pseudo.pseudo_tree import Node import suite #v diff --git a/tests/test_go.py b/tests/test_go.py index 819f854..1eec9f0 100644 --- a/tests/test_go.py +++ b/tests/test_go.py @@ -1,7 +1,7 @@ import unittest import textwrap -from pseudon import generate -from pseudon.pseudon_tree import Node +from pseudo import generate +from pseudo.pseudo_tree import Node import suite as suite def dedent_with_tabs(source): diff --git a/tests/test_javascript.py b/tests/test_javascript.py index 1d29d2d..69d4e32 100644 --- a/tests/test_javascript.py +++ b/tests/test_javascript.py @@ -1,7 +1,7 @@ import unittest import textwrap -from pseudon import generate -from pseudon.pseudon_tree import Node +from pseudo import generate +from pseudo.pseudo_tree import Node import suite #v diff --git a/tests/test_ruby.py b/tests/test_ruby.py index 7e9f1d9..438f6db 100644 --- a/tests/test_ruby.py +++ b/tests/test_ruby.py @@ -1,7 +1,7 @@ import unittest import textwrap -from pseudon import generate -from pseudon.pseudon_tree import Node +from pseudo import generate +from pseudo.pseudo_tree import Node import suite #v diff --git a/vote.md b/vote.md deleted file mode 100644 index b8b0660..0000000 --- a/vote.md +++ /dev/null @@ -1,15 +0,0 @@ -attr :python :ruby :java -property:js :php -member :cs :php -field :java :cpp -slot :smalltalk -ivar :smalltalk :ruby - -:python attr -:ruby attr slot -:js property -:php property member -:cs member -:java attr field -:cpp field -:smalltalk slot ivar diff --git a/wiki.md b/wiki.md deleted file mode 100644 index a74fe1c..0000000 --- a/wiki.md +++ /dev/null @@ -1,70 +0,0 @@ -## types - -pseudon supports fully dynamic languages so we don't **require** any type signatures. -however most of our use cases have been for pure algorithms or for generating code -for a certain taks. in both cases the code isn't too dynamic and you can easily apply -type signatures to it. most of the time it's useful for pseudon to have at least some awareness about -the types of the names in the ast in order to translate into the right standard -target language methods/functions. we group the cases in 3 categories: - -* custom class attributes / methods - -e.g. -```ruby -Person.name -Person.age = 2 -Person.full_name({capitalize: false}) -``` - -the custom classes themselves should be defined somewhere in the input code and their -attributes and methods will always be translated by Pseudon to something equivalent, so -everything is pretty straightforward - -* sequences - -e.g. -```python -'w' + 'a' -[2] + [4] -2 + 4 -``` - -here it's quite important to know if we do integer addition, list or string concatenation. -For example in php those 3 should translate to - -```php -"w" . "a"; -array_concat([2], [4]); -2 + 4; -``` - -so you can see why do we need to be aware of them. It was a very complicated decision, because the easiest thing for Pseudon is to leave the responsibillity of type hinting everything to `xlang-pseudon` clients. -The worry was the Pseudon can apply that logic once, but then you have different clients emitting incompatible code and all of them depending on the central implementation to have internal knowledge about the quirks of each of them. That's why currently each of the clients is expected to either use it's language -type system or to infer types of the pseudon-translateable code itself. -That may sound hard but the type system for pseudon is pretty basic and soft. -Also that's already implemented in `pseudon-python`, `pseudon-ruby` and `pseudon-js`, and soon in -`pseudon-php`, so if anybody is interested in developing `pseudon-` -one can always take a look to those implementations or to ask in the issues/maintainer email. - - -function('fib', ['n'], [ - if_statement( - comparison('>', 'n', 1), [ - math_op('+', call('fib', [math_op('-', 'fib', 1)]), call('fib', [math_op('-', 'fib', 2)])) - ], [ - 1 - ])]) - -basically you have functions with the same name as node types and they initialize -node fields by order given in `ast.md` (usually the same order as in code, except for binary operators) - -strings and numbers can be used as shortcuts: wherever pseudon expects a node and sees a literal, -it converts it to a node with `local`/`typename` for strings and `int`/`float` type for numbers - -BEWARE: string nodes can be only created with string('value') - - - - - -