import 'dart:convert'; /// 本地解析 JWT 的 exp 字段,判断是否已过期。 /// /// 目的:App 启动时立刻发现"登录已过期",不必先发一次请求才报错。 /// 注意:只做本地时间判断,不校验签名——签名的真伪由后端负责。 /// 返回 false(视为未过期)的条件:token 不是标准 JWT 格式或没有 exp 字段, /// 避免因格式差异把正常登录态误判为过期。 bool isJwtExpired(String? token, {Duration leeway = const Duration(seconds: 30)}) { if (token == null || token.isEmpty) return true; final parts = token.split('.'); if (parts.length != 3) return false; try { final payload = utf8.decode(base64Url.decode(base64Url.normalize(parts[1]))); final claims = jsonDecode(payload); if (claims is! Map) return false; final exp = claims['exp']; if (exp is! num) return false; // 无 exp 字段 → 不做本地判断 final expireAt = DateTime.fromMillisecondsSinceEpoch(exp.toInt() * 1000); return expireAt.isBefore(DateTime.now().add(leeway)); } catch (_) { return false; } }