fb3c278e50
P3 Task 11 (WRITE & COMPILE phase; device run pending MuMu availability). - integration_test/p3_flow_test.dart: login -> album (zh+en) -> category -> invite -> enqueue 3 real JPEGs -> queue completed -> server history (sourceDeviceId) -> ov public API sees 3 -> hide via API + UI sync -> DIO fault-gate offline (waitingNetwork -> retry -> 4 completed) -> password change (session kept) -> relogin -> in-app locale smoke. - integration_test/p3_background_test.dart: IT_PHASE=prepare/verify spec for HOME-background continuation and force-stop kill-restart recovery (2 x ~14MB noise JPEGs give a deterministic mid-flight window). - helpers: dart-define config, fault-injecting DIO adapter, app harness (picker/notification/locale provider overrides), UI step library with live-binding polling (no pumpAndSettle). - scripts/run-mobile-it.sh: device detect (exit 2), backend ensure (compose + api/ov/worker/sync, exit 3), idempotent per-run user seed (no DB reset), APK build/install + adb push of testdata, phase 1 / --background phase 2 orchestration with server-side confirmed-count truth via curl. - services/api seed:it script (create-if-absent staff accounts). - debug-only network security config: cleartext HTTP permitted to 10.0.2.2/127.0.0.1/localhost only (release unaffected). - testdata: 3 x ~120KB + 2 x ~14MB generated JPEGs. Co-Authored-By: Claude Code <noreply@anthropic.com>
67 lines
2.6 KiB
Dart
67 lines
2.6 KiB
Dart
/// P3 Task 11 集成测试配置(dart-define 注入)。
|
||
///
|
||
/// 所有值经 `--dart-define KEY=value` 由 `scripts/run-mobile-it.sh` 传入:
|
||
/// 账号由脚本端 `seed-it-users` 预置(每次运行全新账号,避免污染共享
|
||
/// dev 库——集成测试【不做 DB reset】,靠账号 + 相册名时间戳隔离)。
|
||
library;
|
||
|
||
/// 一次集成测试运行的全部外部输入。
|
||
class ItConfig {
|
||
const ItConfig._();
|
||
|
||
/// 主账号(本次运行专属,脚本经 seed-it-users 新建)。
|
||
static const String mainAccount = String.fromEnvironment('IT_MAIN_ACCOUNT');
|
||
|
||
/// 主账号密码。
|
||
static const String mainPassword = String.fromEnvironment(
|
||
'IT_MAIN_PASSWORD',
|
||
);
|
||
|
||
/// 受邀协作者账号(脚本预建;密码不需要——App 侧仅邀请不登录它)。
|
||
static const String staffAccount = String.fromEnvironment('IT_STAFF_ACCOUNT');
|
||
|
||
/// ov 公开端点(viewer 侧 API 检查用;默认模拟器宿主回环 8081)。
|
||
static const String ovBase = String.fromEnvironment(
|
||
'OV_BASE',
|
||
defaultValue: 'http://10.0.2.2:8081',
|
||
);
|
||
|
||
/// ADB 推送的小图目录(设备端绝对路径;见 run-mobile-it.sh 的 push 步骤)。
|
||
static const String sourceDir = String.fromEnvironment(
|
||
'IT_SOURCE_DIR',
|
||
defaultValue: '/data/local/tmp/photolive-it',
|
||
);
|
||
|
||
/// 大图文件名(后台/杀进程场景用,同一目录下)。
|
||
static const String largeFileA = 'it_large_a.jpg';
|
||
static const String largeFileB = 'it_large_b.jpg';
|
||
|
||
/// 本次运行戳(脚本生成;相册名/账号后缀,保证唯一)。
|
||
static const String runStamp = String.fromEnvironment('IT_RUN_STAMP');
|
||
|
||
/// 修改密码场景的新密码(每轮不同:旧密码 + 固定后缀,≥8 位)。
|
||
static String get rotatedPassword => '$mainPassword-rot8';
|
||
|
||
/// 断言入参齐备(缺 dart-define 时给出可读失败而非空账号静默跑挂)。
|
||
static void assertValid() {
|
||
final missing = <String>[
|
||
if (mainAccount.isEmpty) 'IT_MAIN_ACCOUNT',
|
||
if (mainPassword.isEmpty) 'IT_MAIN_PASSWORD',
|
||
if (staffAccount.isEmpty) 'IT_STAFF_ACCOUNT',
|
||
if (runStamp.isEmpty) 'IT_RUN_STAMP',
|
||
];
|
||
if (missing.isNotEmpty) {
|
||
throw StateError(
|
||
'缺少 dart-define:${missing.join(', ')}(请经 scripts/run-mobile-it.sh '
|
||
'运行,脚本负责生成账号与戳)',
|
||
);
|
||
}
|
||
}
|
||
|
||
/// 本次运行的相册标题(zh)。
|
||
static String get albumTitleZh => '集成测试相册 $runStamp';
|
||
|
||
/// 本次运行的相册标题(en)。
|
||
static String get albumTitleEn => 'IT Album $runStamp';
|
||
}
|