# Android 后台授权检查:旧会话与新登录隔离 状态:本地源码候选修复,未发布APK,未在手机安装。版本号仍为1.0.3;此前1.0.3已签名候选包不包含本次修复,不可将其旧哈希作为本次修复后的二进制证据。 ## 复现与原因 原UcvlAuthorizationGuard在检查开始时发现保存的令牌不等于该VPN的令牌,会调用与401/403相同的revoke回调。该回调虽然不清除较新的令牌,却无条件发送AUTHORIZATION_REVOKED广播,使新登录界面被退回登录页。成功或暂时性失败的旧请求还要等下一轮60秒检查才停止旧隧道;旧401/403回包遇到新令牌时则直接返回,没有调用停止旧隧道回调。 隔离复现:新增lateSuccessMustNotRevokeNewLogin,在授权请求中模拟令牌由old变为new。原代码执行4项测试,3通过、该项真实失败;证据android-auth-before-20260917.json/.log。全部为合成令牌和回调,不是生产网络或真实用户账号复现。 ## 修复 - 将sessionChanged(只停止旧VPN)与revoke(当前令牌确实被401/403拒绝)分离。 - 请求前、成功/临时失败后立即核对会话,发生变化不等待下一次60秒轮询。 - 旧401/403响应属于已替换会话时停止旧隧道,但不撤销新令牌。 - CoreVpnService只有确认仍属于同一令牌时才清除令牌并发出撤销广播;替换/退出会话仅停止旧服务。 - 协程取消继续向上传播,不把取消视为账号撤销;保持临时断网不撤销同一会话的策略。 这不是新增自动换节点功能,也不声称修复了Activity所有网络请求或所有换网问题。 ## 验证 独立ASCII临时副本:`C:/Users/Administrator/AppData/Local/Temp/ucvl-auth-20260917-907433b0081d432aa9a6d763f8bb061b`。使用已有JDK21、Android SDK37、Gradle9.4.1缓存,全程--offline、--no-daemon;没有启动模拟器或读取签名私钥。 1. 原代码定向回归:4项,1项失败(预期暴露缺陷)。 2. 修复后定向回归:10项全部通过,0跳过。覆盖同会话撤销、临时离线、旧401/403、旧成功响应、预先替换/退出、取消、持续检查;成功和临时失败的会话变更需在1秒上限内退出,不等60秒。 3. 全量`:app:testPlaystoreReleaseUnitTest`:**41项全部通过,0失败、0错误、0跳过**。包括授权10、桥接5、版本解析7和其余19项;修复后的主应用Kotlin及测试Kotlin编译通过。 4. 没有运行assemble、签名、APK安装、VPN授权、换网或真实服务广播/UI仪器测试。不等于Android实机、Codex长连接或全平台验收。 定向复测证据android-auth-after-20260917.json/.log,全量证据android-auth-full-20260917.json/.log。复现工具`tools/Test-SessionGuard-Isolated.ps1`,首次不要删除原源码/旧安装,测试仅复制到专用临时目录;不会连接公司生产API。 本次源文件SHA256: | 文件 | SHA256 | | --- | --- | | UcvlAuthorizationGuard.kt | 5C7B01D602EB0F5B45BBE88D7F12E3BC70FED4296AE5B6578C2F25A918FD87C4 | | CoreVpnService.kt | 4F55A79F7179D26AF622998C9A70A0D2C64BC1C60B56DDC9E10BA06EE921D850 | | UcvlAuthorizationGuardTest.kt | ACB7BD96F1D1766D59B4D42DC12295621EDEE98E9DCCF78FE566B83770ADF919 | 下一步:在专用Android设备/模拟器做真实service生命周期、重新登录后旧响应/撤销广播、断网恢复验证,再在实体手机补VPN及长连接验收,之后方可决定发布。当前旧候选APK、公司Git公开版本、Windows现用安装、生产后台/节点均未修改,没有员工通知。