diff --git a/src/langs/common/enum.js b/src/langs/common/enum.js index 08308bb..fa1e5e5 100644 --- a/src/langs/common/enum.js +++ b/src/langs/common/enum.js @@ -22,7 +22,8 @@ class SymbolEnum extends Enum { 'REVERSE', 'CONCAT', 'JUDGE', - 'RISK' + 'RISK', + 'YIELD' ], { name: 'symbol', ignoreCase: true }); } assign() { @@ -161,7 +162,8 @@ class TypeEnum extends Enum { 'list', 'object', 'readable', - 'writable' + 'writable', + 'iterator' ], { name: 'types', ignoreCase: true }); } } diff --git a/src/langs/common/items.js b/src/langs/common/items.js index 9918d8f..e81c371 100644 --- a/src/langs/common/items.js +++ b/src/langs/common/items.js @@ -266,6 +266,14 @@ class GrammerReturn extends Grammer { } } +class GrammerYield extends Grammer { + constructor(expr = '', type = '') { + super(); + this.type = type; // null | grammer + this.expr = expr; + } +} + class GrammerLoop extends Grammer { constructor(type = '') { super(); @@ -539,6 +547,7 @@ module.exports = { GrammerCondition, GrammerException, GrammerReturnType, + GrammerYield, Behavior, BehaviorToMap, diff --git a/src/langs/python/combinator.js b/src/langs/python/combinator.js index 493eff8..3d09b35 100644 --- a/src/langs/python/combinator.js +++ b/src/langs/python/combinator.js @@ -1673,6 +1673,17 @@ class Combinator extends CombinatorBase { } } + grammerYield(emitter, gram) { + emitter.emit('yield '); + if (gram.type === 'grammer') { + this.grammer(emitter, gram.expr, false, false); + } else if (gram.type === 'string') { + emitter.emit('\'\''); + } else { + this.grammer(emitter, gram.expr, false, false); + } + } + grammerContinue(emitter, gram) { emitter.emit('continue'); } diff --git a/src/langs/python/config.js b/src/langs/python/config.js index 99f4450..ab15409 100644 --- a/src/langs/python/config.js +++ b/src/langs/python/config.js @@ -67,7 +67,8 @@ module.exports = { 'WRITABLE': 'BinaryIO', 'any': 'Any', 'dict': 'Dict', - 'list': 'List' + 'list': 'List', + 'iterator': 'Iterator' }, typeMap: { 'string': 'str', @@ -94,7 +95,8 @@ module.exports = { 'uint64': 'int', 'any': 'any', 'void': 'None', - 'null': 'None' + 'null': 'None', + 'iterator': 'Iterator' }, type: { // 'long': 'base', @@ -110,7 +112,8 @@ module.exports = { 'dict': 'complex', 'list': 'complex', 'READABLE': 'custom', - 'WRITABLE': 'custom' + 'WRITABLE': 'custom', + 'iterator': 'complex' }, exceptionMap: { 'BASE': 'Exception', diff --git a/src/langs/python2/combinator.js b/src/langs/python2/combinator.js index 1429ce6..9f46cf4 100644 --- a/src/langs/python2/combinator.js +++ b/src/langs/python2/combinator.js @@ -1532,6 +1532,17 @@ class Combinator extends CombinatorBase { } } + grammerYield(emitter, gram) { + emitter.emit('yield '); + if (gram.type === 'grammer') { + this.grammer(emitter, gram.expr, false, false); + } else if (gram.type === 'string') { + emitter.emit('\'\''); + } else { + this.grammer(emitter, gram.expr, false, false); + } + } + grammerContinue(emitter, gram) { emitter.emit('continue'); } diff --git a/src/resolver/client.js b/src/resolver/client.js index b524f16..79c2b16 100644 --- a/src/resolver/client.js +++ b/src/resolver/client.js @@ -25,6 +25,7 @@ const { GrammerCondition, GrammerException, GrammerReturnType, + GrammerYield, BehaviorRetry, BehaviorToMap, @@ -920,6 +921,31 @@ class ClientResolver extends BaseResolver { tryGram.setFinally(finallyGram); } node = tryGram; + } else if (stmt.type === 'yield') { + node = new GrammerYield(); + if (typeof stmt.expr === 'undefined') { + node.type = 'null'; + } else if (stmt.expr.type === 'null') { + node.type = 'null'; + } else if (stmt.expr.type === 'call') { + let val = this.renderGrammerValue(null, stmt.expr); + node.expr = val; + node.type = 'grammer'; + } else if (_isBasicType(stmt.expr.type)) { + node.type = stmt.expr.type; + node.expr = this.renderGrammerValue(null, stmt.expr); + } else { + node.expr = this.renderGrammerValue(null, stmt.expr); + node.type = 'grammer'; + } + if (stmt.expectedType && stmt.expectedType.type === 'model') { + let expected = ''; + if (stmt.expectedType.moduleName) { + expected += `${stmt.expectedType.moduleName}.`; + } + expected += stmt.expectedType.name; + node.expr = new BehaviorToModel(node.expr, expected); + } } else { debug.stack(stmt); } diff --git a/tests/expected/python2/iterator/tea_python_tests/__init__.py b/tests/expected/python2/iterator/tea_python_tests/__init__.py new file mode 100644 index 0000000..5becc17 --- /dev/null +++ b/tests/expected/python2/iterator/tea_python_tests/__init__.py @@ -0,0 +1 @@ +__version__ = "1.0.0" diff --git a/tests/expected/python2/iterator/tea_python_tests/client.py b/tests/expected/python2/iterator/tea_python_tests/client.py new file mode 100644 index 0000000..3630ce7 --- /dev/null +++ b/tests/expected/python2/iterator/tea_python_tests/client.py @@ -0,0 +1,32 @@ +# -*- coding: utf-8 -*- +# This file is auto-generated, don't edit it. Thanks. +from __future__ import unicode_literals + +from Tea.converter import TeaConverter + + +class Client(object): + def __init__(self): + pass + + def test_1(self): + raise Exception('Un-implemented') + + def test_2(self): + it = self.test_1() + for test in it: + yield test + + def test_3(self, iter): + it = iter + str = '' + for i in it: + str = '%s, %s' % (TeaConverter.to_unicode(str), TeaConverter.to_unicode(i)) + return str + + def test_4(self, test): + pass + + def test_5(self, iter): + # test3(iter); + self.test_4(iter) diff --git a/tests/expected/python3/iterator/tea_python_tests/__init__.py b/tests/expected/python3/iterator/tea_python_tests/__init__.py new file mode 100644 index 0000000..5becc17 --- /dev/null +++ b/tests/expected/python3/iterator/tea_python_tests/__init__.py @@ -0,0 +1 @@ +__version__ = "1.0.0" diff --git a/tests/expected/python3/iterator/tea_python_tests/client.py b/tests/expected/python3/iterator/tea_python_tests/client.py new file mode 100644 index 0000000..f81e5ec --- /dev/null +++ b/tests/expected/python3/iterator/tea_python_tests/client.py @@ -0,0 +1,70 @@ +# -*- coding: utf-8 -*- +# This file is auto-generated, don't edit it. Thanks. +from typing import Any + + +class Client: + def __init__(self): + pass + + def test_1(self) -> Iterator: + raise Exception('Un-implemented') + + async def test_1_async(self) -> Iterator: + raise Exception('Un-implemented') + + def test_2(self) -> Iterator: + it = self.test_1() + for test in it: + yield test + + async def test_2_async(self) -> Iterator: + it = await self.test_1_async() + for test in it: + yield test + + def test_3( + self, + iter: Iterator, + ) -> str: + it = iter + str = '' + for i in it: + str = f'{str}, {i}' + return str + + async def test_3_async( + self, + iter: Iterator, + ) -> str: + it = iter + str = '' + for i in it: + str = f'{str}, {i}' + return str + + def test_4( + self, + test: Any, + ) -> None: + pass + + async def test_4_async( + self, + test: Any, + ) -> None: + pass + + def test_5( + self, + iter: Iterator, + ) -> None: + # test3(iter); + self.test_4(iter) + + async def test_5_async( + self, + iter: Iterator, + ) -> None: + # test3(iter); + await self.test_4_async(iter) diff --git a/tests/fixtures/iterator/Darafile b/tests/fixtures/iterator/Darafile new file mode 100644 index 0000000..3329a3a --- /dev/null +++ b/tests/fixtures/iterator/Darafile @@ -0,0 +1,6 @@ +{ + "scope": "darabonba", + "name": "main", + "version": "0.0.1", + "main": "./main.dara" +} \ No newline at end of file diff --git a/tests/fixtures/iterator/main.dara b/tests/fixtures/iterator/main.dara new file mode 100644 index 0000000..9996111 --- /dev/null +++ b/tests/fixtures/iterator/main.dara @@ -0,0 +1,26 @@ +init(){} + +async function test1(): iterator[string]; +async function test2(): iterator[string]{ + var it:iterator[string] = test1(); + for(var test : it) { + yield test; + } +} + +async function test3(iter: iterator[string]): string{ + var it = iter; + var str : string = ''; + for (var i : it) { + str = `${str}, ${i}`; + } + return str; +} + +async function test4(test: any): void{ +} + +async function test5(iter: iterator[string]): void{ + // test3(iter); + test4(iter); +} \ No newline at end of file diff --git a/tests/python2.tests.js b/tests/python2.tests.js index c4c4b4d..8fa3e3e 100644 --- a/tests/python2.tests.js +++ b/tests/python2.tests.js @@ -278,4 +278,23 @@ describe('Python Generator', function () { }); }); + + it('iterator should ok', function () { + check('iterator', [ + 'tea_python_tests/client.py' + ], + { + python2: { + package: 'tea_python_tests', + clientName: 'client', + packageInfo: { + name: 'tea_python_tests', + desc: 'Generate setup.py', + github: 'https://github.com/', + author: 'Alibaba', + email: 'sdk-team@alibabacloud.com' + } + } + }); + }); }); \ No newline at end of file diff --git a/tests/python3.tests.js b/tests/python3.tests.js index 46b4ad7..cd1e5f9 100644 --- a/tests/python3.tests.js +++ b/tests/python3.tests.js @@ -290,4 +290,23 @@ describe('Python Generator', function () { } }); }); + + it('iterator should ok', function () { + check('iterator', [ + 'tea_python_tests/client.py' + ], + { + python: { + package: 'tea_python_tests', + clientName: 'client', + packageInfo: { + name: 'tea_python_tests', + desc: 'Generate setup.py', + github: 'https://github.com/', + author: 'Alibaba', + email: 'sdk-team@alibabacloud.com' + } + } + }); + }); }); \ No newline at end of file