heimdall_test 0.4.0
heimdall_test: ^0.4.0 copied to clipboard
Architecture rules for Dart source trees inspired by ArchUnit.
example/heimdall_test_example.dart
import 'package:heimdall_test/heimdall_test.dart';
import 'package:test/test.dart';
void main() {
group('Package architecture', () {
late HeimdallProject project;
setUpAll(() {
project = const HeimdallFileImporter().importPath();
});
test('keeps source files parseable', () {
Heimdall.code().shouldParse().check(project).assertNoFindings();
});
test('does not import dart:mirrors', () {
Heimdall.code().shouldNotImportDartMirrors().check(project).assertNoFindings();
});
test('uses PascalCase for public types under src', () {
Heimdall.classes()
.that()
.resideInPath('src')
.and()
.arePublic()
.should()
.satisfy(_havePascalCaseName())
.as('public types should use PascalCase')
.check(project)
.assertNoFindings();
});
test('keeps source layers depending in the expected direction', () {
Heimdall.layers()
.layer('Public').definedBy(['heimdall_test.dart'])
.layer('Core').definedBy(['src/core.dart', 'src/core/(**)', 'src/mapper/(**)'])
.layer('Library').definedBy(['src/library_rules.dart', 'src/library/(**)'])
.layer('Plugins').definedBy(['src/plugins.dart'])
.whereLayer('Public').mayOnlyAccessLayers(['Core', 'Library', 'Plugins'])
.whereLayer('Core').mayOnlyAccessLayers(['Core'])
.whereLayer('Library').mayOnlyAccessLayers(['Core', 'Library'])
.whereLayer('Plugins').mayOnlyAccessLayers(['Core'])
.consideringOnlyDependenciesInLayers()
.asRule(description: 'package source layers')
.check(project)
.assertNoFindings();
});
});
}
HeimdallCondition<CompilationUnitMember> _havePascalCaseName() {
final pascalCase = RegExp(r'^[A-Z][A-Za-z0-9]*$');
return HeimdallCondition('have PascalCase names', (item, _) {
if (pascalCase.hasMatch(item.name)) return const [];
return [
HeimdallFinding(
filePath: item.sourcePath,
line: item.line,
message: '${item.name} should use PascalCase',
),
];
});
}