Flutter插件arch_test的使用详解
Flutter插件arch_test的使用详解
arch_test
是一个用于创建 Dart 应用程序架构测试的包。本文将详细介绍如何使用该插件,并提供一些示例代码。
开始使用
首先,你需要在 test
文件夹下的根目录创建一个测试文件,通常命名为 arch_test.dart
。
在这个文件中,你需要导入你的主库。如果不这样做,该包将无法找到任何来自你包的元素。
// 在 test/arch_test.dart 中
import 'package:my_package/main.dart';
void main() {
// 你将在这里编写测试
}
接下来,你需要导入 arch_test
的主文件,它提供了创建测试所需的所有方法和类。你可以通过传递一个 ArchRule
参数来运行测试。你可以以流式方式或普通对象的方式创建 ArchRule
。
// 在 test/arch_test.dart 中
import 'package:my_package/main.dart';
import 'package:arch_test/arch_test.dart';
void main() {
// 流式测试
archTest(classes.that
.areInsideFolder('entity')
.should
.extendClass<BaseEntity>(),
);
// 使用预定义帮助器作为普通对象创建 ArchRule
archTest(ArchRule(
selector: Selectors.classes,
filter: Filters.insideFolder('entity'),
validation: Validations.extendClass<BaseEntity>(),
));
}
当使用 archTest
时,它会自动加载你的包的结构,并根据你提供的 ArchRule
创建一个具有描述性名称的测试。例如,上述两个测试都将被命名为 classes THAT are inside folder "entity" SHOULD extend BaseEntity
。
包层
该包分为三个抽象层:
- 核心:负责将 Dart 镜像系统转换为内部且更友好的类层次结构。你可以使用这一层获得最大的测试灵活性,但你也将需要写更多的代码;
- 测试:提供标准化测试的基础类。这是一种更为结构化但仍然不是最简单和流畅的测试方法;
- 流式:提供一种简单且可读性高的方式来创建测试。这应该是你的首选测试方法。
你可以查看以下部分了解如何使用这些层。
核心
核心层提供包的基本模型和组件,将你的包源代码转换为这些模型。
你可以看到有哪些模型,以及它们的字段和层次结构:
组件包括 DartPackageLoader
,它负责加载包的代码结构,以及 DartElementFinder
,它用于查找包内代码结构中的元素。
// 导入你的包的主文件,
// 否则 DartPackageLoader 将无法找到你的代码
import 'package:my_package/main.dart';
import 'package:test/test.dart';
// 如果你想只导入核心层可以这样做
import 'package:arch_test/core.dart';
void main() {
late DartPackage package;
setUp(() async {
package = await DartPackageLoader.instance.loadCurrentPackage();
});
test('所有实体应继承 BaseEntity', () {
final entities = findEntities();
for (final entity in entities) {
expect(entity.superClass, isNotNull, reason: '实体应该继承 BaseEntity');
expect(entity.superClass!.name, 'BaseEntity', reason: '实体应该继承 BaseEntity');
}
});
List<DartClass> findEntities() {
// 简单的方法
return DartElementFinder.instance.findByMatcher(
matcher: (el) => el is DartClass && !el.isEnum,
source: package,
).where((cls) => cls.library.split('/').contains('entities'));
/* 复杂的方法
final entities = [];
final entityLibraries = package.libraries
.where((lib) => lib.name.split('/').contains('entities')
.toList();
for (final entityLibrary in entityLibraries) {
for (final cls in entityLibrary.classes) {
if (!cls.isEnum) {
entities.add(cls);
}
}
}
return entities;
*/
}
}
如果你想要更多关于如何使用核心进行测试的例子,请参阅 testing_with_core 示例。
测试
测试层提供了一些类来标准化你创建和描述测试的方式,以及你的架构违规。这些类包括 ArchRule
、Selector
、Filter
和 Validation
。
ArchRule
定义了基本的测试结构,使用 Selector
查询要测试的元素(例如类、方法、库等),使用 Filter
过滤查询的元素,并使用 Validation
验证这些元素是否遵循你定义的架构。你还可以使用 and
和 or
方法组合多个过滤器或验证。
此层还提供了一些预定义的 Selector
、Filter
和 Validation
,以帮助你编写更简洁的代码,并提供了一个 archTest
方法来帮助你减少样板代码并标准化测试名称。
// 导入你的包的主文件,
// 否则 DartPackageLoader 将无法找到你的代码
import 'package:my_package/main.dart';
import 'package:test/test.dart';
// 如果你不使用 archTest 方法,则需要导入 core
import 'package:arch_test/core.dart';
import 'package:arch_test/testing.dart';
void main() {
// 使用预定义的
archTest(ArchRule<DartClass>(
selector: Selectors.classes,
filter: Filters.insideFolder('entities'),
validation: Validations.extendClass<BaseEntity>(),
));
// 编写所有内容
test('位于 "entities" 文件夹内的类应继承 BaseEntity', () async {
final package = await DartPackageLoader.instance.loadCurrentPackage();
ArchRule(
selector: Selector(
(package) => DartElementFinder.instance.findByMatcher(
matcher: (el) => el is DartClass && !el.isEnum,
source: package,
),
description: 'classes',
),
filter: Filter(
(el) => el.library.split('/').contains('entities'),
description: 'are inside folder "entities"',
),
validation: Validation(
(el, addViolation) {
if (el.superClass == null) {
addViolation('Does not have super class');
}
if (el.superClass.name != 'BaseEntity') {
addViolation('Should extend BaseEntity');
}
},
description: 'should extend BaseEntity',
),
).validate(package);
});
}
这是一个使用 ArchRule
的失败测试示例输出:
在包 my_package 中发现了以下违规:
SomeEntity(位于 package:my_package/path/to/some_entity.dart:1:1)的违规:
- Does not have super class
- Should extend BaseEntity
如果你想要更多关于如何使用测试进行测试的例子,请参阅 testing_with_testing 示例。
流式
流式层提供了一种流式 API 来创建 ArchRule
。
你可以使用以下顶级常量开始你的规则:classes
、enums
、methods
和 libraries
。从那里你可以使用 that
和 should
添加过滤器和验证到你的测试,以及使用 and
和 or
组合它们。注意 that
和 should
是可调用类,所以你可以在流式 API 中使用自定义类。
// 导入你的包的主文件,
// 否则 DartPackageLoader 将无法找到你的代码
import 'package:my_package/main.dart';
// 如果你不使用 archTest 方法,则需要导入 testing
import 'package:arch_test/testing.dart';
import 'package:arch_test/fluent.dart';
void main() {
// 使用预定义的
archTest(classes.that.areInsideFolder('entities').should.extendClass<BaseEntity>());
// 编写并组合自定义过滤器/验证
archTest(classes
.that(Filter((el) => el.name.endsWith('Entity'), description: 'have name ending with Entity'))
.and(Filter((el) => el.name != 'BaseEntity'), description: 'are not BaseEntity'))
.should(Validation((el, addViolation) {
if (el.superClass == null || el.superClass.name != 'BaseEntity') {
addViolation('Should extend BaseEntity');
}
}, description: 'should extend BaseEntity'))
.or(Validation((el, addViolation) {
if (el.library.split('/').contains('entities')) {
addViolation('Should be outside of "entities" folder');
}
}, description: 'should be outside of "entities" folder')),
);
}
更多关于Flutter插件arch_test的使用详解的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html
更多关于Flutter插件arch_test的使用详解的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html
针对您提到的Flutter未知功能插件arch_test
的潜在使用,由于arch_test
并非一个广为人知的官方或广泛使用的Flutter插件,我无法提供确切的文档或广泛认可的用例。不过,我可以基于插件名称和可能的用途,给出一个假设性的代码示例,展示如何在Flutter项目中集成并使用一个假设的架构测试插件。
请注意,以下代码是基于假设的,因为arch_test
的具体实现和功能未知。这个示例旨在展示如何集成和使用一个假想的架构测试插件。
假设的arch_test
插件功能
假设arch_test
插件用于验证Flutter应用的架构是否符合某些最佳实践,比如依赖注入、MVVM模式等。
集成步骤
-
在
pubspec.yaml
中添加依赖dependencies: flutter: sdk: flutter arch_test: ^1.0.0 # 假设版本号
-
运行
flutter pub get
flutter pub get
-
使用插件进行架构测试
假设
arch_test
提供了一个名为verifyArchitecture
的方法,用于验证应用的架构。以下是一个简单的使用示例:import 'package:flutter_test/flutter_test.dart'; import 'package:arch_test/arch_test.dart'; // 假设的导入路径 void main() { testWidgets('verify app architecture', (WidgetTester tester) async { // 假设有一个用于测试的Widget await tester.pumpWidget(MyApp()); // 使用arch_test插件进行架构验证 await verifyArchitecture(tester.widget(find.byType(MyApp))); }); } class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { // 假设的应用架构 return MaterialApp( home: Scaffold( appBar: AppBar( title: Text('Flutter Demo'), ), body: Center( child: Text('Hello, World!'), ), ), ); } }
在上面的代码中,
verifyArchitecture
是一个假设的方法,用于检查MyApp
组件的架构是否符合arch_test
插件定义的标准。
注意事项
- 由于
arch_test
是一个假设的插件,上述代码中的verifyArchitecture
方法和其他细节都是虚构的。 - 在实际使用中,您需要参考
arch_test
插件的官方文档来了解其真实的功能和使用方法。 - 如果
arch_test
是一个私有或内部使用的插件,您可能需要联系插件的开发者或维护者以获取更多信息和支持。
希望这个假设性的示例能够帮助您理解如何在Flutter项目中集成和使用一个假设的架构测试插件。如果您有关于具体插件的更多信息或需求,请提供详细信息以便给出更准确的指导。