app scaffold

This commit is contained in:
Guangfei.Zhao
2026-08-17 15:29:55 +08:00
commit 681688dfae
301 changed files with 18414 additions and 0 deletions
@@ -0,0 +1,77 @@
import 'package:core_analytics/core_analytics.dart';
import 'package:flutter_test/flutter_test.dart';
void main() {
group('AnalyticsEvent 命名约定', () {
// 13 §三:snake_case,结果类过去式,动作类现在式。事件名一旦上线不再改,
// 所以这条测试的作用是在「加新事件」时挡住拼写风格漂移。
const List<String> all = <String>[
AnalyticsEvent.scanSucceeded,
AnalyticsEvent.scanFailed,
AnalyticsEvent.h5Closed,
AnalyticsEvent.h5Failed,
AnalyticsEvent.h5FirstPaint,
AnalyticsEvent.supportClicked,
AnalyticsEvent.apiFailed,
AnalyticsEvent.appColdStart,
AnalyticsEvent.logout,
AnalyticsEvent.sessionRestoreFailed,
];
test('全部是 snake_case', () {
for (final String e in all) {
expect(
RegExp(r'^[a-z][a-z0-9]*(_[a-z0-9]+)*$').hasMatch(e),
isTrue,
reason: '$e 不是 snake_case',
);
}
});
test('没有重名', () {
expect(all.toSet().length, all.length);
});
test('客户端事件表就是这 10 条', () {
// 多一条少一条都要先回到 13 §三的判据:这件事会不会产生一次后端请求?
expect(all.length, 10);
});
});
group('NoopAnalytics', () {
test('所有方法都不抛异常', () {
const Analytics analytics = NoopAnalytics();
expect(
() => analytics
..track(AnalyticsEvent.appColdStart)
..registerSuperProperties(<String, Object?>{'storeId': 1})
..identify('u1')
..reset(),
returnsNormally,
);
});
});
group('RecordingAnalytics', () {
test('记录事件与参数副本', () {
final RecordingAnalytics analytics = RecordingAnalytics();
final Map<String, Object?> params = <String, Object?>{AnalyticsParam.mode: 'vin'};
analytics.track(AnalyticsEvent.scanSucceeded, params);
params[AnalyticsParam.mode] = 'plate';
expect(analytics.events.single.event, AnalyticsEvent.scanSucceeded);
// 存的是副本,调用方后续修改不会污染已记录的事件。
expect(analytics.events.single.params[AnalyticsParam.mode], 'vin');
});
test('reset 同时清掉用户与超级属性', () {
final RecordingAnalytics analytics = RecordingAnalytics()
..identify('u1')
..registerSuperProperties(<String, Object?>{AnalyticsSuperProperty.storeId: 7})
..reset();
expect(analytics.currentUserId, isNull);
expect(analytics.superProperties, isEmpty);
});
});
}