| // Copyright (c) 2023, the Dart project authors. Please see the AUTHORS file |
| // for details. All rights reserved. Use of this source code is governed by a |
| // BSD-style license that can be found in the LICENSE file. |
| |
| import 'package:test_reflective_loader/test_reflective_loader.dart'; |
| |
| import '../rule_test_support.dart'; |
| |
| main() { |
| defineReflectiveSuite(() { |
| defineReflectiveTests(ImplicitReopenTest); |
| defineReflectiveTests(ImplicitReopenInducedModifierTest); |
| }); |
| } |
| |
| @reflectiveTest |
| class ImplicitReopenInducedModifierTest extends LintRuleTest { |
| @override |
| bool get addMetaPackageDep => true; |
| |
| @override |
| String get lintRule => 'implicit_reopen'; |
| |
| test_inducedFinal() async { |
| await assertDiagnostics(r''' |
| final class F {} |
| sealed class S extends F {} |
| base class C extends S {} |
| ''', [ |
| lint(56, 1), |
| ]); |
| } |
| |
| test_inducedFinal_base_interface() async { |
| await assertDiagnostics(r''' |
| base class C {} |
| interface class D {} |
| sealed class E extends D implements C {} |
| base class B extends E {} |
| ''', [ |
| lint(89, 1), |
| ]); |
| } |
| |
| test_inducedFinal_baseMixin_interface() async { |
| await assertDiagnostics(r''' |
| interface class D {} |
| base mixin G {} |
| sealed class H extends D with G {} |
| base class B extends H {} |
| ''', [ |
| lint(83, 1), |
| ]); |
| } |
| |
| test_inducedFinal_interface_base_ok() async { |
| await assertDiagnostics(r''' |
| interface class S {} |
| base class I {} |
| sealed class A extends S implements I {} |
| class C extends A {} |
| ''', [ |
| // No lint. |
| error(CompileTimeErrorCode.SUBTYPE_OF_BASE_IS_NOT_BASE_FINAL_OR_SEALED, |
| 84, 1), |
| ]); |
| } |
| |
| test_inducedFinal_mixin_finalClass() async { |
| await assertDiagnostics(r''' |
| final class S {} |
| mixin M {} |
| sealed class A extends S with M {} |
| base class B extends A {} |
| ''', [ |
| lint(74, 1), |
| ]); |
| } |
| |
| test_inducedInterface() async { |
| await assertDiagnostics(r''' |
| interface class I {} |
| sealed class S extends I {} |
| class C extends S {} |
| ''', [ |
| lint(55, 1), |
| ]); |
| } |
| |
| test_inducedInterface_base() async { |
| await assertDiagnostics(r''' |
| interface class I {} |
| sealed class S extends I {} |
| base class C extends S {} |
| ''', [ |
| lint(60, 1), |
| ]); |
| } |
| |
| test_inducedInterface_base_mixin_interface() async { |
| await assertDiagnostics(r''' |
| interface class S {} |
| mixin M {} |
| sealed class A extends S with M {} |
| base class C extends A {} |
| ''', [ |
| lint(78, 1), |
| ]); |
| } |
| |
| test_inducedInterface_mixin_interface() async { |
| await assertDiagnostics(r''' |
| interface class S {} |
| mixin M {} |
| sealed class A extends S with M {} |
| class C extends A {} |
| ''', [ |
| lint(73, 1), |
| ]); |
| } |
| |
| test_inducedInterface_twoLevels() async { |
| await assertDiagnostics(r''' |
| interface class I {} |
| sealed class S extends I {} |
| sealed class S2 extends S {} |
| class C extends S2 {} |
| ''', [ |
| lint(84, 1), |
| ]); |
| } |
| |
| test_subtypingFinalError_ok() async { |
| await assertDiagnostics(r''' |
| final class F {} |
| sealed class S extends F {} |
| class C extends S {} |
| ''', [ |
| // No lint. |
| error(CompileTimeErrorCode.SUBTYPE_OF_FINAL_IS_NOT_BASE_FINAL_OR_SEALED, |
| 51, 1), |
| ]); |
| } |
| } |
| |
| @reflectiveTest |
| class ImplicitReopenTest extends LintRuleTest { |
| @override |
| bool get addMetaPackageDep => true; |
| |
| @override |
| String get lintRule => 'implicit_reopen'; |
| |
| test_class_classFinal_ok() async { |
| await assertDiagnostics(r''' |
| final class F {} |
| |
| class C extends F {} |
| ''', [ |
| // No lint. |
| error(CompileTimeErrorCode.SUBTYPE_OF_FINAL_IS_NOT_BASE_FINAL_OR_SEALED, |
| 24, 1), |
| ]); |
| } |
| |
| test_class_classInterface() async { |
| await assertDiagnostics(r''' |
| interface class I {} |
| |
| class C extends I {} |
| ''', [ |
| lint(28, 1), |
| ]); |
| } |
| |
| test_class_classInterface_outsideLib_ok() async { |
| newFile('$testPackageLibPath/a.dart', r''' |
| interface class I {} |
| '''); |
| |
| await assertDiagnostics(r''' |
| import 'a.dart'; |
| |
| class C extends I {} |
| ''', [ |
| // No lint. |
| error(CompileTimeErrorCode.INTERFACE_CLASS_EXTENDED_OUTSIDE_OF_LIBRARY, |
| 34, 1), |
| ]); |
| } |
| |
| test_class_classInterface_reopened_ok() async { |
| await assertNoDiagnostics(r''' |
| import 'package:meta/meta.dart'; |
| |
| interface class I {} |
| |
| @reopen |
| class C extends I {} |
| '''); |
| } |
| |
| test_classBase_classFinal() async { |
| await assertDiagnostics(r''' |
| final class F {} |
| |
| base class B extends F {} |
| ''', [ |
| lint(29, 1), |
| ]); |
| } |
| |
| test_classBase_classInterface() async { |
| await assertDiagnostics(r''' |
| interface class I {} |
| |
| base class B extends I {} |
| ''', [ |
| lint(33, 1), |
| ]); |
| } |
| |
| test_classFinal_classInterface_ok() async { |
| await assertNoDiagnostics(r''' |
| interface class I {} |
| |
| final class C extends I {} |
| '''); |
| } |
| |
| test_classMixin_classInterface_ok() async { |
| await assertDiagnostics(r''' |
| interface class I {} |
| |
| mixin class M extends I {} |
| ''', [ |
| // No lint. |
| error(CompileTimeErrorCode.MIXIN_CLASS_DECLARATION_EXTENDS_NOT_OBJECT, 44, |
| 1), |
| ]); |
| } |
| |
| test_classTypeAlias_class_classInterface() async { |
| await assertDiagnostics(r''' |
| interface class I {} |
| mixin M {} |
| class C = I with M; |
| ''', [ |
| lint(38, 1), |
| ]); |
| } |
| |
| test_classTypeAlias_classBase_classFinal() async { |
| await assertDiagnostics(r''' |
| final class C {} |
| mixin M {} |
| base class D = C with M; |
| ''', [ |
| lint(39, 1), |
| ]); |
| } |
| |
| test_classTypeAlias_classBase_classFinal_reopened() async { |
| await assertNoDiagnostics(r''' |
| import 'package:meta/meta.dart'; |
| |
| final class C {} |
| mixin M {} |
| @reopen |
| base class D = C with M; |
| '''); |
| } |
| |
| test_mixin_classInterface_ok() async { |
| await assertDiagnostics(r''' |
| interface class I {} |
| |
| mixin M extends I {} |
| ''', [ |
| // No lint. |
| error(ParserErrorCode.EXPECTED_INSTEAD, 30, 7), |
| ]); |
| } |
| } |