diff --git a/es2panda/binder/binder.cpp b/es2panda/binder/binder.cpp index f3b2a0285e926609d79696632b2e16d159496a76..36f298a5c956b33adb488c35aa260f28d51c15e7 100644 --- a/es2panda/binder/binder.cpp +++ b/es2panda/binder/binder.cpp @@ -561,12 +561,14 @@ void Binder::BuildClassDefinition(ir::ClassDefinition *classDef) classDef->Ident()->SetParent(classDef); } - ResolveReference(classDef, classDef->Ctor()); - for (auto *stmt : classDef->Body()) { ResolveReference(classDef, stmt); } + // ResolveReference of ctor is after the classBody to ensure that + // the parent of the astNode added in the transformer is set correctly. + ResolveReference(classDef, classDef->Ctor()); + for (auto *iter : classDef->IndexSignatures()) { ResolveReference(classDef, iter); } diff --git a/es2panda/parser/parserImpl.cpp b/es2panda/parser/parserImpl.cpp index 9f60a3e509210f16e888142c903a5cbfbb35f147..5adcebbc4b7a6940fa234595ae8ac24bdc352309 100644 --- a/es2panda/parser/parserImpl.cpp +++ b/es2panda/parser/parserImpl.cpp @@ -2672,7 +2672,8 @@ static bool IsConstructor(ir::Statement *stmt) return def->Kind() == ir::MethodDefinitionKind::CONSTRUCTOR; } -ir::MethodDefinition *ParserImpl::CreateImplicitConstructor(bool hasSuperClass, bool isDeclare) +ir::MethodDefinition *ParserImpl::CreateImplicitConstructor(ir::Expression *superClass, + bool hasSuperClass, bool isDeclare) { ArenaVector params(Allocator()->Adapter()); ArenaVector statements(Allocator()->Adapter()); @@ -2681,18 +2682,20 @@ ir::MethodDefinition *ParserImpl::CreateImplicitConstructor(bool hasSuperClass, auto *scope = Binder()->Allocator()->New(Allocator(), paramScope); if (hasSuperClass) { - util::StringView argsStr = "args"; - params.push_back(AllocNode(ir::AstNodeType::REST_ELEMENT, - AllocNode(argsStr))); - paramScope->AddParamDecl(Allocator(), params.back()); + if (Extension() != ScriptExtension::TS || !superClass->IsNullLiteral()) { + util::StringView argsStr = "args"; + params.push_back(AllocNode(ir::AstNodeType::REST_ELEMENT, + AllocNode(argsStr))); + paramScope->AddParamDecl(Allocator(), params.back()); - ArenaVector callArgs(Allocator()->Adapter()); - auto *superExpr = AllocNode(); - callArgs.push_back(AllocNode(ir::AstNodeType::SPREAD_ELEMENT, - AllocNode(argsStr))); + ArenaVector callArgs(Allocator()->Adapter()); + auto *superExpr = AllocNode(); + callArgs.push_back(AllocNode(ir::AstNodeType::SPREAD_ELEMENT, + AllocNode(argsStr))); - auto *callExpr = AllocNode(superExpr, std::move(callArgs), nullptr, false); - statements.push_back(AllocNode(callExpr)); + auto *callExpr = AllocNode(superExpr, std::move(callArgs), nullptr, false); + statements.push_back(AllocNode(callExpr)); + } } auto *body = AllocNode(scope, std::move(statements)); @@ -2943,15 +2946,13 @@ ir::ClassDefinition *ParserImpl::ParseClassDefinition(bool isDeclaration, bool i lexer::SourcePosition classBodyEndLoc = lexer_->GetToken().End(); if (ctor == nullptr) { - ctor = CreateImplicitConstructor(hasSuperClass, isDeclare); + ctor = CreateImplicitConstructor(superClass, hasSuperClass, isDeclare); ctor->SetRange({startLoc, classBodyEndLoc}); hasConstructorFuncBody = !isDeclare; } lexer_->NextToken(); - if (!isDeclare && !hasConstructorFuncBody) { - ThrowSyntaxError("Constructor implementation is missing.", ctor->Start()); - } + ValidateClassConstructor(ctor, properties, superClass, isDeclare, hasConstructorFuncBody, hasSuperClass); auto *classDefinition = AllocNode( classCtx.GetScope(), identNode, typeParamDecl, superTypeParams, std::move(implements), ctor, superClass, @@ -2965,6 +2966,105 @@ ir::ClassDefinition *ParserImpl::ParseClassDefinition(bool isDeclaration, bool i return classDefinition; } +void ParserImpl::ValidateClassConstructor(ir::MethodDefinition *ctor, + ArenaVector &properties, + ir::Expression *superClass, + bool isDeclare, bool hasConstructorFuncBody, bool hasSuperClass) +{ + if (!hasConstructorFuncBody) { + if (isDeclare) { + return; + } + ThrowSyntaxError("Constructor implementation is missing.", ctor->Start()); + } + + if (Extension() != ScriptExtension::TS || !hasSuperClass) { + return; + } + + bool hasSuperCall = false; + FindSuperCallInConstructor(ctor, &hasSuperCall); + if (hasSuperCall) { + if (superClass->IsNullLiteral()) { + ThrowSyntaxError("A constructor cannot contain a super call when its class extends null.", ctor->Start()); + } + + if (SuperCallShouldBeFirst(ctor, properties)) { + ir::Statement *firstStat = nullptr; + ASSERT(ctor->Function()->Body()->IsBlockStatement()); + ir::BlockStatement *blockStat = ctor->Function()->Body()->AsBlockStatement(); + for (auto iter = blockStat->Statements().begin(); iter != blockStat->Statements().end();) { + if ((*iter)->IsExpressionStatement() && + (*iter)->AsExpressionStatement()->GetExpression()->IsStringLiteral()) { + iter++; + } else { + firstStat = *iter; + break; + } + } + + if (firstStat == nullptr || !firstStat->IsExpressionStatement() || + !firstStat->AsExpressionStatement()->GetExpression()->IsCallExpression() || + !firstStat->AsExpressionStatement()->GetExpression()->AsCallExpression() + ->Callee()->IsSuperExpression()) { + ThrowSyntaxError("A super call must be the first statement in the constructor when a class contains " + "initialized properties, parameter properties, or private identifiers.", + ctor->Start()); + } + } + } else if (!superClass->IsNullLiteral()) { + ThrowSyntaxError("Constructors for derived classes must contain a super call.", ctor->Start()); + } +} + +bool ParserImpl::SuperCallShouldBeFirst(ir::MethodDefinition *ctor, ArenaVector &properties) +{ + for (const auto *property : properties) { + if (property->IsClassProperty() && (property->AsClassProperty()->Value() != nullptr || + property->AsClassProperty()->Key()->IsTSPrivateIdentifier())) { + return true; + } + } + + for (const auto ¶m : ctor->Function()->Params()) { + if (param->IsTSParameterProperty() && + (param->AsTSParameterProperty()->Accessibility() != ir::AccessibilityOption::NO_OPTS || + param->AsTSParameterProperty()->Readonly())) { + return true; + } + } + return false; +} + +void ParserImpl::FindSuperCallInConstructor(const ir::AstNode *parent, bool *hasSuperCall) +{ + parent->Iterate([this, hasSuperCall](auto *childNode) { + FindSuperCallInConstructorChildNode(childNode, hasSuperCall); + }); +} + +void ParserImpl::FindSuperCallInConstructorChildNode(const ir::AstNode *childNode, bool *hasSuperCall) +{ + if (*hasSuperCall) { + return; + } + switch (childNode->Type()) { + case ir::AstNodeType::CALL_EXPRESSION: { + if (childNode->AsCallExpression()->Callee()->IsSuperExpression()) { + *hasSuperCall = true; + } + break; + } + case ir::AstNodeType::CLASS_DEFINITION: { + break; + } + default: { + FindSuperCallInConstructor(childNode, hasSuperCall); + break; + } + } +} + ir::TSEnumDeclaration *ParserImpl::ParseEnumMembers(ir::Identifier *key, const lexer::SourcePosition &enumStart, bool isExport, bool isDeclare, bool isConst) { diff --git a/es2panda/parser/parserImpl.h b/es2panda/parser/parserImpl.h index 6d50ea02a0179b2fbb594c756c24de61bd24a834..dce95144f822681725d7c5ae65b909bd06b7a26c 100644 --- a/es2panda/parser/parserImpl.h +++ b/es2panda/parser/parserImpl.h @@ -305,7 +305,8 @@ private: ir::Statement *ParseClassElement(const ArenaVector &properties, ArenaVector *indexSignatures, bool hasSuperClass, bool isDeclare, bool isAbstractClass); - ir::MethodDefinition *CreateImplicitConstructor(bool hasSuperClass, bool isDeclare = false); + ir::MethodDefinition *CreateImplicitConstructor(ir::Expression *superClass, + bool hasSuperClass, bool isDeclare = false); ir::MethodDefinition *CheckClassMethodOverload(ir::Statement *property, ir::MethodDefinition **ctor, bool isDeclare, lexer::SourcePosition errorInfo, ir::MethodDefinition *lastOverload, bool implExists, bool isAbstract = false); @@ -313,6 +314,13 @@ private: ir::ClassDefinition *ParseClassDefinition(bool isDeclaration, bool idRequired = true, bool isDeclare = false, bool isAbstract = false); + void ValidateClassConstructor(ir::MethodDefinition *ctor, + ArenaVector &properties, + ir::Expression *superClass, + bool isDeclare, bool hasConstructorFuncBody, bool hasSuperClass); + void FindSuperCallInConstructor(const ir::AstNode *parent, bool *hasSuperCall); + void FindSuperCallInConstructorChildNode(const ir::AstNode *childNode, bool *hasSuperCall); + bool SuperCallShouldBeFirst(ir::MethodDefinition *ctor, ArenaVector &properties); void ValidateAccessor(ExpressionParseFlags flags, lexer::TokenFlags currentTokenFlags); void CheckPropertyKeyAsycModifier(ParserStatus *methodStatus); ir::Property *ParseShorthandProperty(const lexer::LexerPosition *startPos); diff --git a/es2panda/parser/transformer/transformer.cpp b/es2panda/parser/transformer/transformer.cpp index a5d5f46ba31aaaab5f0d40bbbbee34a6d11a1759..1f66e0dfb1c15e9b38f984afe1b2db7c4dfd8efb 100644 --- a/es2panda/parser/transformer/transformer.cpp +++ b/es2panda/parser/transformer/transformer.cpp @@ -551,6 +551,23 @@ util::StringView Transformer::CreatePrivatePropertyBindName(util::StringView nam return uniqueName; } +size_t Transformer::GetInsertPosForConstructor(ir::ClassDefinition *node) +{ + size_t insertPos = 0; + ir::BlockStatement *blockStat = node->Ctor()->Function()->Body()->AsBlockStatement(); + for (auto iter = blockStat->Statements().begin(); iter != blockStat->Statements().end();) { + if ((*iter)->IsExpressionStatement() && + (*iter)->AsExpressionStatement()->GetExpression()->IsStringLiteral()) { + iter++; + insertPos++; + } else { + break; + } + } + + return (node->Super() == nullptr || node->Super()->IsNullLiteral()) ? insertPos : (insertPos + 1); +} + std::vector Transformer::VisitInstanceProperty(ir::ClassDefinition *node) { /* @@ -582,7 +599,7 @@ std::vector Transformer::VisitInstanceProperty(ir::Cl auto ctorScopeCtx = binder::LexicalScope::Enter(Binder(), node->Ctor()->Function()->Scope()); ir::BlockStatement *blockStat = node->Ctor()->Function()->Body()->AsBlockStatement(); - size_t insertPos = (node->Super() == nullptr) ? 0 : 1; + size_t insertPos = GetInsertPosForConstructor(node); for (auto *it : addToCtor) { if (it->IsComputed()) { computedProps.push_back(AllocNode(it->Key())); @@ -631,7 +648,7 @@ void Transformer::VisitTSParameterProperty(ir::ClassDefinition *node) return; } auto blockStatement = body->AsBlockStatement(); - size_t insertPos = (node->Super() == nullptr) ? 0 : 1; + size_t insertPos = GetInsertPosForConstructor(node); for (auto *it : func->Params()) { if (!it->IsTSParameterProperty()) { continue; @@ -2006,14 +2023,15 @@ void Transformer::CheckTransformedAstNode(const ir::AstNode *parent, ir::AstNode if (!(*passed)) { return; } - if (childNode->IsClassProperty() && childNode->AsClassProperty()->IsStatic()) { + if (childNode->IsClassProperty() && + (childNode->AsClassProperty()->IsStatic() || childNode->AsClassProperty()->Value() != nullptr)) { return; } if (childNode->IsDecorator()) { return; } if (childNode->Parent() != parent) { - std::cout << "Illegal ast structure after transforme." << std::endl; + std::cout << "Illegal ast structure after transform." << std::endl; *passed = false; return; } diff --git a/es2panda/parser/transformer/transformer.h b/es2panda/parser/transformer/transformer.h index 80b6ae1907c37586ac954a0f76c401efdc6e0725..f9b2153dd4a7b2499ab00812b6f82d4f817bc63d 100644 --- a/es2panda/parser/transformer/transformer.h +++ b/es2panda/parser/transformer/transformer.h @@ -110,6 +110,7 @@ private: util::StringView name); void VisitPrivateProperty(ir::ClassDefinition *node); void VisitComputedProperty(ir::ClassDefinition *node); + size_t GetInsertPosForConstructor(ir::ClassDefinition *node); ir::VariableDeclaration *CreateVariableDeclarationWithIdentify(util::StringView name, VariableParsingFlags flags, diff --git a/es2panda/test/compiler/ts/cases/conformance/classes/test-ts-classes-22-expected.txt b/es2panda/test/compiler/ts/cases/conformance/classes/test-ts-classes-22-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..ce013625030ba8dba906f756967f9e9ca394464a --- /dev/null +++ b/es2panda/test/compiler/ts/cases/conformance/classes/test-ts-classes-22-expected.txt @@ -0,0 +1 @@ +hello diff --git a/es2panda/test/compiler/ts/cases/conformance/classes/test-ts-classes-22.ts b/es2panda/test/compiler/ts/cases/conformance/classes/test-ts-classes-22.ts new file mode 100644 index 0000000000000000000000000000000000000000..1801a6d79ae1718a318a164005072b793f335db6 --- /dev/null +++ b/es2panda/test/compiler/ts/cases/conformance/classes/test-ts-classes-22.ts @@ -0,0 +1,27 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base { } +class A extends Base { + prop:number; + constructor() { + let a = "hello"; + print(a); + super(); + this.prop=1; + } +} +new A(); \ No newline at end of file diff --git a/es2panda/test/parser/ts/test-class-constructor10-expected.txt b/es2panda/test/parser/ts/test-class-constructor10-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..84804e53a77375c9254b19322af0625e6c5e7e5f --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor10-expected.txt @@ -0,0 +1 @@ +SyntaxError: A super call must be the first statement in the constructor when a class contains initialized properties, parameter properties, or private identifiers. [test-class-constructor10.ts:20:5] diff --git a/es2panda/test/parser/ts/test-class-constructor10.ts b/es2panda/test/parser/ts/test-class-constructor10.ts new file mode 100644 index 0000000000000000000000000000000000000000..0437c35dcbb7f1a19c6e1048dc346a860b9b65ad --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor10.ts @@ -0,0 +1,24 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base { } +class A extends Base { + prop: number = 1; + constructor() { + print("hello"); + super(); + } +} diff --git a/es2panda/test/parser/ts/test-class-constructor11-expected.txt b/es2panda/test/parser/ts/test-class-constructor11-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..90c1c74a99d3547c75a8e5b5e68c8e95002f0ba1 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor11-expected.txt @@ -0,0 +1 @@ +SyntaxError: A super call must be the first statement in the constructor when a class contains initialized properties, parameter properties, or private identifiers. [test-class-constructor11.ts:19:5] diff --git a/es2panda/test/parser/ts/test-class-constructor11.ts b/es2panda/test/parser/ts/test-class-constructor11.ts new file mode 100644 index 0000000000000000000000000000000000000000..f5ed5a70df1f960271b155357b0f5d7aa174220c --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor11.ts @@ -0,0 +1,23 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base { } +class A extends Base { + constructor(public prop: number) { + print("hello"); + super(); + } +} diff --git a/es2panda/test/parser/ts/test-class-constructor12-expected.txt b/es2panda/test/parser/ts/test-class-constructor12-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..394098a7a62f1e6a12b2a73fb9e4747d38235e13 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor12-expected.txt @@ -0,0 +1 @@ +SyntaxError: A super call must be the first statement in the constructor when a class contains initialized properties, parameter properties, or private identifiers. [test-class-constructor12.ts:19:5] diff --git a/es2panda/test/parser/ts/test-class-constructor12.ts b/es2panda/test/parser/ts/test-class-constructor12.ts new file mode 100644 index 0000000000000000000000000000000000000000..c7f36dba82180cd6cf7b10a68b756ff25dae0c0d --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor12.ts @@ -0,0 +1,23 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base { } +class A extends Base { + constructor(readonly prop: number) { + print("hello"); + super(); + } +} diff --git a/es2panda/test/parser/ts/test-class-constructor13-expected.txt b/es2panda/test/parser/ts/test-class-constructor13-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..1f18b7f7f5570887faf149283345fbf862e12c44 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor13-expected.txt @@ -0,0 +1 @@ +SyntaxError: A super call must be the first statement in the constructor when a class contains initialized properties, parameter properties, or private identifiers. [test-class-constructor13.ts:20:5] diff --git a/es2panda/test/parser/ts/test-class-constructor13.ts b/es2panda/test/parser/ts/test-class-constructor13.ts new file mode 100644 index 0000000000000000000000000000000000000000..f706bc0f1fb7217fb8e4d72dc97b547d4956c27d --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor13.ts @@ -0,0 +1,24 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base { } +class A extends Base { + #prop:number; + constructor() { + print("hello"); + super(); + } +} diff --git a/es2panda/test/parser/ts/test-class-constructor14-expected.txt b/es2panda/test/parser/ts/test-class-constructor14-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..12fd24998b3d79b4cd2144ace3877c52c2bb2da5 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor14-expected.txt @@ -0,0 +1 @@ +SyntaxError: Constructors for derived classes must contain a super call. [test-class-constructor14.ts:19:5] diff --git a/es2panda/test/parser/ts/test-class-constructor14.ts b/es2panda/test/parser/ts/test-class-constructor14.ts new file mode 100644 index 0000000000000000000000000000000000000000..fe2dc24900f5873d6c7cf7cececb65e944093b93 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor14.ts @@ -0,0 +1,23 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base { } +class A extends Base { + constructor() { + let a = "hello"; + print(a); + } +} diff --git a/es2panda/test/parser/ts/test-class-constructor15-expected.txt b/es2panda/test/parser/ts/test-class-constructor15-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..30ef365866e2a812b83083cbd3042c4a407cee01 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor15-expected.txt @@ -0,0 +1 @@ +SyntaxError: A constructor cannot contain a super call when its class extends null. [test-class-constructor15.ts:18:5] diff --git a/es2panda/test/parser/ts/test-class-constructor15.ts b/es2panda/test/parser/ts/test-class-constructor15.ts new file mode 100644 index 0000000000000000000000000000000000000000..5d814bce3d8c6463404ee4936a64700cc161cd95 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor15.ts @@ -0,0 +1,21 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class A extends null { + constructor() { + super(); + } +} diff --git a/es2panda/test/parser/ts/test-class-constructor16-expected.txt b/es2panda/test/parser/ts/test-class-constructor16-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..ae4535ba558c9366f31235a98cf18ef090ba781b --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor16-expected.txt @@ -0,0 +1,150 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "loc": { + "start": { + "line": 17, + "column": 7 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "superClass": { + "type": "NullLiteral", + "value": null, + "loc": { + "start": { + "line": 17, + "column": 17 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + "implements": [], + "constructor": { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": null, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 24 + } + } + }, + "body": [], + "indexSignatures": [], + "loc": { + "start": { + "line": 17, + "column": 22 + }, + "end": { + "line": 17, + "column": 24 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 24 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 18, + "column": 1 + } + } +} diff --git a/es2panda/test/parser/ts/test-class-constructor16.ts b/es2panda/test/parser/ts/test-class-constructor16.ts new file mode 100644 index 0000000000000000000000000000000000000000..9c11fda8c0653fcff4b7b15ead0ba3ffb48ef442 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor16.ts @@ -0,0 +1,17 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class A extends null {} diff --git a/es2panda/test/parser/ts/test-class-constructor17-expected.txt b/es2panda/test/parser/ts/test-class-constructor17-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..2a2c278af24f2a8bedc354969361d48430de88c9 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor17-expected.txt @@ -0,0 +1 @@ +SyntaxError: Constructors for derived classes must contain a super call. [test-class-constructor17.ts:20:5] diff --git a/es2panda/test/parser/ts/test-class-constructor17.ts b/es2panda/test/parser/ts/test-class-constructor17.ts new file mode 100644 index 0000000000000000000000000000000000000000..abc26d83587f6c10816080be777a2756e1628849 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor17.ts @@ -0,0 +1,23 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base { } + +class D extends Base { + constructor() { + var a = class Inner extends Base { constructor() { super(); } } + } +} diff --git a/es2panda/test/parser/ts/test-class-constructor6-expected.txt b/es2panda/test/parser/ts/test-class-constructor6-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..0a3ef172bbb16d16add5e595deedbe9102c27b53 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor6-expected.txt @@ -0,0 +1 @@ +SyntaxError: Constructor implementation is missing. [test-class-constructor6.ts:19:5] diff --git a/es2panda/test/parser/ts/test-class-constructor6.ts b/es2panda/test/parser/ts/test-class-constructor6.ts new file mode 100644 index 0000000000000000000000000000000000000000..e5b1b8699faddb9a7f1c6d7919379c921db96e07 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor6.ts @@ -0,0 +1,20 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base {} +class A extends Base { + constructor(); +} diff --git a/es2panda/test/parser/ts/test-class-constructor7-expected.txt b/es2panda/test/parser/ts/test-class-constructor7-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..eefe44b72206c41181429f4e80d645e58a580290 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor7-expected.txt @@ -0,0 +1,258 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "Base", + "loc": { + "start": { + "line": 17, + "column": 7 + }, + "end": { + "line": 17, + "column": 11 + } + } + }, + "superClass": null, + "implements": [], + "constructor": { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": null, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 14 + } + } + }, + "body": [], + "indexSignatures": [], + "loc": { + "start": { + "line": 17, + "column": 12 + }, + "end": { + "line": 17, + "column": 14 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 14 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "loc": { + "start": { + "line": 18, + "column": 15 + }, + "end": { + "line": 18, + "column": 16 + } + } + }, + "superClass": { + "type": "Identifier", + "name": "Base", + "loc": { + "start": { + "line": 18, + "column": 25 + }, + "end": { + "line": 18, + "column": 29 + } + } + }, + "implements": [], + "constructor": { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 19, + "column": 16 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": null, + "generator": false, + "async": false, + "expression": false, + "params": [], + "loc": { + "start": { + "line": 19, + "column": 16 + }, + "end": { + "line": 19, + "column": 19 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 16 + }, + "end": { + "line": 19, + "column": 19 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 19, + "column": 19 + } + } + }, + "body": [], + "indexSignatures": [], + "loc": { + "start": { + "line": 18, + "column": 30 + }, + "end": { + "line": 20, + "column": 2 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 9 + }, + "end": { + "line": 20, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 21, + "column": 1 + } + } +} diff --git a/es2panda/test/parser/ts/test-class-constructor7.ts b/es2panda/test/parser/ts/test-class-constructor7.ts new file mode 100644 index 0000000000000000000000000000000000000000..54836b51d672511c11af6c86d496d07b74c3340f --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor7.ts @@ -0,0 +1,20 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base {} +declare class A extends Base { + constructor(); +} diff --git a/es2panda/test/parser/ts/test-class-constructor8-expected.txt b/es2panda/test/parser/ts/test-class-constructor8-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..a12e5c163837b8817e791b1fa1c950289c65f551 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor8-expected.txt @@ -0,0 +1 @@ +SyntaxError: Constructors for derived classes must contain a super call. [test-class-constructor8.ts:19:5] diff --git a/es2panda/test/parser/ts/test-class-constructor8.ts b/es2panda/test/parser/ts/test-class-constructor8.ts new file mode 100644 index 0000000000000000000000000000000000000000..78ef0a584e9c2182e6a0b55e6d663b4ef1ddfef9 --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor8.ts @@ -0,0 +1,20 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base {} +class A extends Base { + constructor() {} +} diff --git a/es2panda/test/parser/ts/test-class-constructor9-expected.txt b/es2panda/test/parser/ts/test-class-constructor9-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..03595b2cdcaafcddbf2d034908d457a2ba6166ae --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor9-expected.txt @@ -0,0 +1 @@ +SyntaxError: Constructors for derived classes must contain a super call. [test-class-constructor9.ts:19:5] diff --git a/es2panda/test/parser/ts/test-class-constructor9.ts b/es2panda/test/parser/ts/test-class-constructor9.ts new file mode 100644 index 0000000000000000000000000000000000000000..debed6631d0c0bf6a8864c0e718aa4c9e6e693aa --- /dev/null +++ b/es2panda/test/parser/ts/test-class-constructor9.ts @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base {} +class A extends Base { + constructor() { + print("hello"); + } +} diff --git a/es2panda/test/parser/ts/transformed_cases/test-class-constructor1-transformed-expected.txt b/es2panda/test/parser/ts/transformed_cases/test-class-constructor1-transformed-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..e8d49b83ccb0457936d6c1c2efab90a614e5b55e --- /dev/null +++ b/es2panda/test/parser/ts/transformed_cases/test-class-constructor1-transformed-expected.txt @@ -0,0 +1,296 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "A", + "loc": { + "start": { + "line": 17, + "column": 7 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "superClass": { + "type": "NullLiteral", + "value": null, + "loc": { + "start": { + "line": 17, + "column": 17 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + "implements": [], + "constructor": { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": null, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "AssignmentExpression", + "operator": "=", + "left": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "property": { + "type": "Identifier", + "name": "prop1", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "right": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 18, + "column": 21 + }, + "end": { + "line": 18, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 19, + "column": 2 + } + } + }, + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "prop1", + "loc": { + "start": { + "line": 18, + "column": 5 + }, + "end": { + "line": 18, + "column": 10 + } + } + }, + "value": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 18, + "column": 21 + }, + "end": { + "line": 18, + "column": 22 + } + } + }, + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "TSNumberKeyword", + "loc": { + "start": { + "line": 18, + "column": 12 + }, + "end": { + "line": 18, + "column": 18 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 5 + }, + "end": { + "line": 18, + "column": 22 + } + } + } + ], + "indexSignatures": [], + "loc": { + "start": { + "line": 17, + "column": 22 + }, + "end": { + "line": 19, + "column": 2 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 19, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 20, + "column": 1 + } + } +} +Transformed AST structure check passed. diff --git a/es2panda/test/parser/ts/transformed_cases/test-class-constructor1.ts b/es2panda/test/parser/ts/transformed_cases/test-class-constructor1.ts new file mode 100644 index 0000000000000000000000000000000000000000..90a305c65cb9f37859e6dc92936aaab23def081c --- /dev/null +++ b/es2panda/test/parser/ts/transformed_cases/test-class-constructor1.ts @@ -0,0 +1,19 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class A extends null { + prop1: number = 1; +} diff --git a/es2panda/test/parser/ts/transformed_cases/test-class-constructor2-transformed-expected.txt b/es2panda/test/parser/ts/transformed_cases/test-class-constructor2-transformed-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..ee5671404cb9a8a87ea3a681210a428ef5eced36 --- /dev/null +++ b/es2panda/test/parser/ts/transformed_cases/test-class-constructor2-transformed-expected.txt @@ -0,0 +1,323 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "B", + "loc": { + "start": { + "line": 17, + "column": 7 + }, + "end": { + "line": 17, + "column": 8 + } + } + }, + "superClass": { + "type": "NullLiteral", + "value": null, + "loc": { + "start": { + "line": 17, + "column": 17 + }, + "end": { + "line": 17, + "column": 21 + } + } + }, + "implements": [], + "constructor": { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 19, + "column": 16 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": null, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "StringLiteral", + "value": "use strict", + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 20, + "column": 9 + }, + "end": { + "line": 20, + "column": 22 + } + } + }, + { + "type": "ExpressionStatement", + "expression": { + "type": "AssignmentExpression", + "operator": "=", + "left": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "property": { + "type": "Identifier", + "name": "prop", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "right": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 18, + "column": 20 + }, + "end": { + "line": 18, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 19, + "column": 19 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 16 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 19, + "column": 16 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 5 + }, + "end": { + "line": 21, + "column": 6 + } + } + }, + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "prop", + "loc": { + "start": { + "line": 18, + "column": 5 + }, + "end": { + "line": 18, + "column": 9 + } + } + }, + "value": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 18, + "column": 20 + }, + "end": { + "line": 18, + "column": 21 + } + } + }, + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "TSNumberKeyword", + "loc": { + "start": { + "line": 18, + "column": 11 + }, + "end": { + "line": 18, + "column": 17 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 18, + "column": 5 + }, + "end": { + "line": 18, + "column": 21 + } + } + } + ], + "indexSignatures": [], + "loc": { + "start": { + "line": 17, + "column": 22 + }, + "end": { + "line": 22, + "column": 2 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 22, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 23, + "column": 1 + } + } +} +Transformed AST structure check passed. diff --git a/es2panda/test/parser/ts/transformed_cases/test-class-constructor2.ts b/es2panda/test/parser/ts/transformed_cases/test-class-constructor2.ts new file mode 100644 index 0000000000000000000000000000000000000000..8774beefe3e79dd6493a6304a30c845641ae5909 --- /dev/null +++ b/es2panda/test/parser/ts/transformed_cases/test-class-constructor2.ts @@ -0,0 +1,22 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class B extends null { + prop: number = 1; + constructor() { + "use strict"; + } +} diff --git a/es2panda/test/parser/ts/transformed_cases/test-class-constructor3-transformed-expected.txt b/es2panda/test/parser/ts/transformed_cases/test-class-constructor3-transformed-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..5f80a5ec4afdfcefaec7295040e5d96149082760 --- /dev/null +++ b/es2panda/test/parser/ts/transformed_cases/test-class-constructor3-transformed-expected.txt @@ -0,0 +1,486 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "Base", + "loc": { + "start": { + "line": 17, + "column": 7 + }, + "end": { + "line": 17, + "column": 11 + } + } + }, + "superClass": null, + "implements": [], + "constructor": { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": null, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 14 + } + } + }, + "body": [], + "indexSignatures": [], + "loc": { + "start": { + "line": 17, + "column": 12 + }, + "end": { + "line": 17, + "column": 14 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 14 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "B", + "loc": { + "start": { + "line": 19, + "column": 7 + }, + "end": { + "line": 19, + "column": 8 + } + } + }, + "superClass": { + "type": "Identifier", + "name": "Base", + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 19, + "column": 21 + } + } + }, + "implements": [], + "constructor": { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "loc": { + "start": { + "line": 21, + "column": 5 + }, + "end": { + "line": 21, + "column": 16 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": null, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "StringLiteral", + "value": "use strict", + "loc": { + "start": { + "line": 22, + "column": 9 + }, + "end": { + "line": 22, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 9 + }, + "end": { + "line": 22, + "column": 22 + } + } + }, + { + "type": "ExpressionStatement", + "expression": { + "type": "CallExpression", + "callee": { + "type": "Super", + "loc": { + "start": { + "line": 23, + "column": 9 + }, + "end": { + "line": 23, + "column": 14 + } + } + }, + "arguments": [], + "optional": false, + "loc": { + "start": { + "line": 23, + "column": 9 + }, + "end": { + "line": 23, + "column": 16 + } + } + }, + "loc": { + "start": { + "line": 23, + "column": 9 + }, + "end": { + "line": 23, + "column": 17 + } + } + }, + { + "type": "ExpressionStatement", + "expression": { + "type": "AssignmentExpression", + "operator": "=", + "left": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "property": { + "type": "Identifier", + "name": "prop", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "right": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 20, + "column": 20 + }, + "end": { + "line": 20, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 21, + "column": 19 + }, + "end": { + "line": 24, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 16 + }, + "end": { + "line": 24, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 21, + "column": 16 + }, + "end": { + "line": 24, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 5 + }, + "end": { + "line": 24, + "column": 6 + } + } + }, + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "prop", + "loc": { + "start": { + "line": 20, + "column": 5 + }, + "end": { + "line": 20, + "column": 9 + } + } + }, + "value": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 20, + "column": 20 + }, + "end": { + "line": 20, + "column": 21 + } + } + }, + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "TSNumberKeyword", + "loc": { + "start": { + "line": 20, + "column": 11 + }, + "end": { + "line": 20, + "column": 17 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 5 + }, + "end": { + "line": 20, + "column": 21 + } + } + } + ], + "indexSignatures": [], + "loc": { + "start": { + "line": 19, + "column": 22 + }, + "end": { + "line": 25, + "column": 2 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 1 + }, + "end": { + "line": 25, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 26, + "column": 1 + } + } +} +Transformed AST structure check passed. diff --git a/es2panda/test/parser/ts/transformed_cases/test-class-constructor3.ts b/es2panda/test/parser/ts/transformed_cases/test-class-constructor3.ts new file mode 100644 index 0000000000000000000000000000000000000000..141a3b3b2b518b98975656fe46fa7de05248e01c --- /dev/null +++ b/es2panda/test/parser/ts/transformed_cases/test-class-constructor3.ts @@ -0,0 +1,25 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base {} + +class B extends Base { + prop: number = 1; + constructor() { + "use strict"; + super(); + } +} diff --git a/es2panda/test/parser/ts/transformed_cases/test-class-constructor4-transformed-expected.txt b/es2panda/test/parser/ts/transformed_cases/test-class-constructor4-transformed-expected.txt new file mode 100644 index 0000000000000000000000000000000000000000..69d7527d4de1040d3efe01c9667ebb320dce346e --- /dev/null +++ b/es2panda/test/parser/ts/transformed_cases/test-class-constructor4-transformed-expected.txt @@ -0,0 +1,784 @@ +{ + "type": "Program", + "statements": [ + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "Base", + "loc": { + "start": { + "line": 17, + "column": 7 + }, + "end": { + "line": 17, + "column": 11 + } + } + }, + "superClass": null, + "implements": [], + "constructor": { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": null, + "generator": false, + "async": false, + "expression": false, + "params": [], + "body": { + "type": "BlockStatement", + "statements": [], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 15 + } + } + }, + "body": [], + "indexSignatures": [], + "loc": { + "start": { + "line": 17, + "column": 12 + }, + "end": { + "line": 17, + "column": 15 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 17, + "column": 1 + }, + "end": { + "line": 17, + "column": 15 + } + } + }, + { + "type": "ClassDeclaration", + "definition": { + "id": { + "type": "Identifier", + "name": "B", + "loc": { + "start": { + "line": 19, + "column": 7 + }, + "end": { + "line": 19, + "column": 8 + } + } + }, + "superClass": { + "type": "Identifier", + "name": "Base", + "loc": { + "start": { + "line": 19, + "column": 17 + }, + "end": { + "line": 19, + "column": 21 + } + } + }, + "implements": [], + "constructor": { + "type": "MethodDefinition", + "key": { + "type": "Identifier", + "name": "constructor", + "loc": { + "start": { + "line": 22, + "column": 5 + }, + "end": { + "line": 22, + "column": 16 + } + } + }, + "kind": "constructor", + "static": false, + "optional": false, + "computed": false, + "value": { + "type": "FunctionExpression", + "function": { + "type": "ScriptFunction", + "id": null, + "generator": false, + "async": false, + "expression": false, + "params": [ + { + "type": "TSParameterProperty", + "accessibility": "public", + "readonly": false, + "static": false, + "export": false, + "parameter": { + "type": "AssignmentPattern", + "left": { + "type": "Identifier", + "name": "prop3", + "typeAnnotation": { + "type": "TSNumberKeyword", + "loc": { + "start": { + "line": 22, + "column": 31 + }, + "end": { + "line": 22, + "column": 37 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 24 + }, + "end": { + "line": 22, + "column": 29 + } + } + }, + "right": { + "type": "NumberLiteral", + "value": 3, + "loc": { + "start": { + "line": 22, + "column": 40 + }, + "end": { + "line": 22, + "column": 41 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 24 + }, + "end": { + "line": 22, + "column": 41 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 17 + }, + "end": { + "line": 22, + "column": 41 + } + } + } + ], + "body": { + "type": "BlockStatement", + "statements": [ + { + "type": "ExpressionStatement", + "expression": { + "type": "StringLiteral", + "value": "use strict", + "loc": { + "start": { + "line": 23, + "column": 9 + }, + "end": { + "line": 23, + "column": 21 + } + } + }, + "loc": { + "start": { + "line": 23, + "column": 9 + }, + "end": { + "line": 23, + "column": 22 + } + } + }, + { + "type": "ExpressionStatement", + "expression": { + "type": "CallExpression", + "callee": { + "type": "Super", + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 14 + } + } + }, + "arguments": [], + "optional": false, + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 16 + } + } + }, + "loc": { + "start": { + "line": 24, + "column": 9 + }, + "end": { + "line": 24, + "column": 17 + } + } + }, + { + "type": "ExpressionStatement", + "expression": { + "type": "AssignmentExpression", + "operator": "=", + "left": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "property": { + "type": "Identifier", + "name": "prop3", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "right": { + "type": "Identifier", + "name": "prop3", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + { + "type": "ExpressionStatement", + "expression": { + "type": "AssignmentExpression", + "operator": "=", + "left": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "property": { + "type": "Identifier", + "name": "prop1", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "right": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 20, + "column": 21 + }, + "end": { + "line": 20, + "column": 22 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + { + "type": "ExpressionStatement", + "expression": { + "type": "AssignmentExpression", + "operator": "=", + "left": { + "type": "MemberExpression", + "object": { + "type": "ThisExpression", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "property": { + "type": "Identifier", + "name": "###B#prop2#1", + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "computed": false, + "optional": false, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "right": { + "type": "NumberLiteral", + "value": 2, + "loc": { + "start": { + "line": 21, + "column": 22 + }, + "end": { + "line": 21, + "column": 23 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + }, + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 1, + "column": 1 + } + } + } + ], + "loc": { + "start": { + "line": 22, + "column": 43 + }, + "end": { + "line": 25, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 16 + }, + "end": { + "line": 25, + "column": 6 + } + } + }, + "loc": { + "start": { + "line": 22, + "column": 16 + }, + "end": { + "line": 25, + "column": 6 + } + } + }, + "overloads": [], + "decorators": [], + "loc": { + "start": { + "line": 22, + "column": 5 + }, + "end": { + "line": 25, + "column": 6 + } + } + }, + "body": [ + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "prop1", + "loc": { + "start": { + "line": 20, + "column": 5 + }, + "end": { + "line": 20, + "column": 10 + } + } + }, + "value": { + "type": "NumberLiteral", + "value": 1, + "loc": { + "start": { + "line": 20, + "column": 21 + }, + "end": { + "line": 20, + "column": 22 + } + } + }, + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "TSNumberKeyword", + "loc": { + "start": { + "line": 20, + "column": 12 + }, + "end": { + "line": 20, + "column": 18 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 20, + "column": 5 + }, + "end": { + "line": 20, + "column": 22 + } + } + }, + { + "type": "ClassProperty", + "key": { + "type": "Identifier", + "name": "###B#prop2#1", + "loc": { + "start": { + "line": 21, + "column": 5 + }, + "end": { + "line": 21, + "column": 11 + } + } + }, + "value": { + "type": "NumberLiteral", + "value": 2, + "loc": { + "start": { + "line": 21, + "column": 22 + }, + "end": { + "line": 21, + "column": 23 + } + } + }, + "static": false, + "readonly": false, + "declare": false, + "optional": false, + "computed": false, + "typeAnnotation": { + "type": "TSNumberKeyword", + "loc": { + "start": { + "line": 21, + "column": 13 + }, + "end": { + "line": 21, + "column": 19 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 21, + "column": 5 + }, + "end": { + "line": 21, + "column": 23 + } + } + } + ], + "indexSignatures": [], + "loc": { + "start": { + "line": 19, + "column": 22 + }, + "end": { + "line": 26, + "column": 2 + } + } + }, + "decorators": [], + "loc": { + "start": { + "line": 19, + "column": 1 + }, + "end": { + "line": 26, + "column": 2 + } + } + } + ], + "loc": { + "start": { + "line": 1, + "column": 1 + }, + "end": { + "line": 27, + "column": 1 + } + } +} +Transformed AST structure check passed. diff --git a/es2panda/test/parser/ts/transformed_cases/test-class-constructor4.ts b/es2panda/test/parser/ts/transformed_cases/test-class-constructor4.ts new file mode 100644 index 0000000000000000000000000000000000000000..5b751f1603ee5df95f73aa0c0044c2b388aa792a --- /dev/null +++ b/es2panda/test/parser/ts/transformed_cases/test-class-constructor4.ts @@ -0,0 +1,26 @@ +/* + * Copyright (c) 2023 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + + +class Base { } + +class B extends Base { + prop1: number = 1; + #prop2: number = 2; + constructor(public prop3: number = 3) { + "use strict"; + super(); + } +} diff --git a/es2panda/test/test_tsc_ignore_list.txt b/es2panda/test/test_tsc_ignore_list.txt index bf0b3458775bcd583329dd49a4004bc6f261157c..1278c2e6e6b5397a0961d27f368debee8d542be9 100644 --- a/es2panda/test/test_tsc_ignore_list.txt +++ b/es2panda/test/test_tsc_ignore_list.txt @@ -40,3 +40,6 @@ es2panda/test/TypeScript/tests/cases/conformance/interfaces/interfaceDeclaration es2panda/test/TypeScript/tests/cases/conformance/parser/ecmascript5/RegressionTests/parser579071.ts es2panda/test/TypeScript/tests/cases/conformance/scanner/ecmascript3/scannerES3NumericLiteral2.ts es2panda/test/TypeScript/tests/cases/conformance/types/members/objectTypeWithStringNamedNumericProperty.ts +es2panda/test/TypeScript/tests/cases/conformance/classes/constructorDeclarations/superCalls/emitStatementsBeforeSuperCall.ts +es2panda/test/TypeScript/tests/cases/conformance/classes/constructorDeclarations/superCalls/emitStatementsBeforeSuperCallWithDefineFields.ts +es2panda/test/TypeScript/tests/cases/conformance/classes/members/privateNames/privateNameBadSuperUseDefineForClassFields.ts