refactor(core): 平台上报收敛为单个请求头
去掉 device_info_plus 依赖与机型/系统版本,只保留 X-Client-Platform。
This commit is contained in:
1 parent
01a3b0101e
commit
935de13343
6 files changed
+19
-113
No files matched your search
+2
-5
@@ -117,17 +117,14 @@ class LumaDramaApp extends StatefulWidget {
|
||||
class _LumaDramaAppState extends State<LumaDramaApp> {
|
||||
late final AuthSessionStore _sessionStore = AuthSessionStore();
|
||||
|
||||
/// 设备画像只读一次:供拦截器在每次请求头里带上系统与机型。
|
||||
late final DeviceProfileReader _deviceProfile = DeviceProfileReader();
|
||||
|
||||
/// 全 App 共用一个 ApiClient:这样目录、账号、后续的互动/进度请求
|
||||
/// 都自动带 `Authorization` 与 `X-Device-Id`,401 的刷新重试也只有一处实现。
|
||||
/// 都自动带 `Authorization`、`X-Device-Id` 与平台头,401 的刷新重试也只有一处实现。
|
||||
late final ApiClient _apiClient = ApiClient(
|
||||
accessTokenReader: () => _auth.accessToken,
|
||||
tokenRefresher: () => _auth.refresh(),
|
||||
onUnauthorized: () => _auth.clear(),
|
||||
deviceIdReader: _sessionStore.deviceId,
|
||||
deviceProfileReader: _deviceProfile.read,
|
||||
platformReader: clientPlatform,
|
||||
);
|
||||
|
||||
late final AuthController _auth = AuthController(
|
||||
|
||||
@@ -5,7 +5,6 @@ import 'package:dio/dio.dart';
|
||||
import '../../config/app_config.dart';
|
||||
import 'api_exception.dart';
|
||||
import 'api_interceptors.dart';
|
||||
import 'device_profile.dart';
|
||||
import 'network_log_interceptor.dart';
|
||||
|
||||
/// `ApiException` 从这里也能拿到:历史调用方一律 `import 'api_client.dart'`,不必改 import。
|
||||
@@ -25,7 +24,7 @@ class ApiClient {
|
||||
this.tokenRefresher,
|
||||
this.onUnauthorized,
|
||||
this.deviceIdReader,
|
||||
this.deviceProfileReader,
|
||||
this.platformReader,
|
||||
}) : _fixedBaseUrl = baseUrl {
|
||||
_dio = Dio(
|
||||
BaseOptions(
|
||||
@@ -42,7 +41,7 @@ class ApiClient {
|
||||
AuthHeaderInterceptor(
|
||||
accessTokenReader: accessTokenReader,
|
||||
deviceIdReader: deviceIdReader,
|
||||
deviceProfileReader: deviceProfileReader,
|
||||
platformReader: platformReader,
|
||||
),
|
||||
const EnvelopeInterceptor(),
|
||||
NetworkLogInterceptor(),
|
||||
@@ -70,8 +69,8 @@ class ApiClient {
|
||||
/// 设备号(`X-Device-Id`):注册风控、后续下载绑定都要用
|
||||
final Future<String> Function()? deviceIdReader;
|
||||
|
||||
/// 设备画像(系统/机型版本):后台列表展示客户端系统用
|
||||
final Future<DeviceProfile> Function()? deviceProfileReader;
|
||||
/// 客户端平台(`X-Client-Platform`):后台区分 iOS / Android
|
||||
final String Function()? platformReader;
|
||||
|
||||
Future<Object?> get(String path, {Map<String, String>? query}) {
|
||||
return _request('GET', path, query: query);
|
||||
|
||||
@@ -5,7 +5,6 @@ import 'dart:convert';
|
||||
import 'package:dio/dio.dart';
|
||||
|
||||
import 'api_exception.dart';
|
||||
import 'device_profile.dart';
|
||||
import 'network_log_interceptor.dart';
|
||||
|
||||
/// 请求级开关:放在 `RequestOptions.extra` 里,由 `ApiClient` 写入、拦截器读取。
|
||||
@@ -36,7 +35,7 @@ class AuthHeaderInterceptor extends Interceptor {
|
||||
AuthHeaderInterceptor({
|
||||
this.accessTokenReader,
|
||||
this.deviceIdReader,
|
||||
this.deviceProfileReader,
|
||||
this.platformReader,
|
||||
});
|
||||
|
||||
/// 当前 access token;未登录返回 null 或空串。
|
||||
@@ -45,8 +44,8 @@ class AuthHeaderInterceptor extends Interceptor {
|
||||
/// 设备号(`X-Device-Id`):注册风控、下载绑定都用它。
|
||||
final Future<String> Function()? deviceIdReader;
|
||||
|
||||
/// 设备画像(系统/机型):后台判断客户端系统用,匿名请求同样要带。
|
||||
final Future<DeviceProfile> Function()? deviceProfileReader;
|
||||
/// 客户端平台(`X-Client-Platform`):后台区分 iOS / Android,匿名请求同样要带。
|
||||
final String Function()? platformReader;
|
||||
|
||||
@override
|
||||
Future<void> onRequest(
|
||||
@@ -62,9 +61,9 @@ class AuthHeaderInterceptor extends Interceptor {
|
||||
if (deviceId != null && deviceId.isNotEmpty) {
|
||||
options.headers['X-Device-Id'] = deviceId;
|
||||
}
|
||||
final profile = await deviceProfileReader?.call();
|
||||
if (profile != null) {
|
||||
options.headers.addAll(profile.headers);
|
||||
final platform = platformReader?.call() ?? '';
|
||||
if (platform.isNotEmpty) {
|
||||
options.headers['X-Client-Platform'] = platform;
|
||||
}
|
||||
handler.next(options);
|
||||
}
|
||||
|
||||
@@ -2,68 +2,14 @@
|
||||
|
||||
import 'dart:io' show Platform;
|
||||
|
||||
import 'package:device_info_plus/device_info_plus.dart';
|
||||
import 'package:flutter/foundation.dart';
|
||||
|
||||
/// 设备画像:随每个请求以请求头上报,供后台列表识别客户端系统。
|
||||
/// 客户端平台,后台只用来区分 iOS / Android。
|
||||
///
|
||||
/// 之前只有登录接口在 body 里带 `platform` / `osVersion`,匿名互动没有任何系统信息,
|
||||
/// 后台只能显示「—」。改成请求头后,点赞、收藏、评论、观看等接口都能带上。
|
||||
class DeviceProfile {
|
||||
const DeviceProfile({
|
||||
this.platform = '',
|
||||
this.osVersion = '',
|
||||
this.model = '',
|
||||
});
|
||||
|
||||
/// ANDROID / IOS / WEB;桌面端等无法归类时为空。
|
||||
final String platform;
|
||||
|
||||
/// 系统版本,Android 取 release(如 14),iOS 取 systemVersion(如 17.2)。
|
||||
final String osVersion;
|
||||
|
||||
/// 机型,Android 取 model(如 SM-G991B),iOS 取 utsname.machine(如 iPhone15,2)。
|
||||
final String model;
|
||||
|
||||
Map<String, String> get headers => {
|
||||
if (platform.isNotEmpty) 'X-Client-Platform': platform,
|
||||
if (osVersion.isNotEmpty) 'X-Client-Os': osVersion,
|
||||
if (model.isNotEmpty) 'X-Client-Model': model,
|
||||
};
|
||||
}
|
||||
|
||||
/// 读取一次并缓存设备画像:插件调用有开销,且整个进程内不会变。
|
||||
class DeviceProfileReader {
|
||||
DeviceProfileReader({DeviceInfoPlugin? plugin})
|
||||
: _plugin = plugin ?? DeviceInfoPlugin();
|
||||
|
||||
final DeviceInfoPlugin _plugin;
|
||||
Future<DeviceProfile>? _cached;
|
||||
|
||||
Future<DeviceProfile> read() => _cached ??= _load();
|
||||
|
||||
Future<DeviceProfile> _load() async {
|
||||
if (kIsWeb) return const DeviceProfile(platform: 'WEB');
|
||||
try {
|
||||
if (Platform.isAndroid) {
|
||||
final info = await _plugin.androidInfo;
|
||||
return DeviceProfile(
|
||||
platform: 'ANDROID',
|
||||
osVersion: info.version.release,
|
||||
model: info.model,
|
||||
);
|
||||
}
|
||||
if (Platform.isIOS) {
|
||||
final info = await _plugin.iosInfo;
|
||||
return DeviceProfile(
|
||||
platform: 'IOS',
|
||||
osVersion: info.systemVersion,
|
||||
model: info.utsname.machine,
|
||||
);
|
||||
}
|
||||
} catch (_) {
|
||||
// 插件不可用(widget 测试没有原生通道)时退化为 dart:io 能拿到的信息
|
||||
}
|
||||
return const DeviceProfile();
|
||||
}
|
||||
/// 系统版本、机型一律不上报:后台列表需要的只是「这台设备是安卓还是苹果」。
|
||||
String clientPlatform() {
|
||||
if (kIsWeb) return 'WEB';
|
||||
if (Platform.isAndroid) return 'ANDROID';
|
||||
if (Platform.isIOS) return 'IOS';
|
||||
return '';
|
||||
}
|
||||
@@ -113,22 +113,6 @@ packages:
|
||||
url: "https://pub.flutter-io.cn"
|
||||
source: hosted
|
||||
version: "1.0.9"
|
||||
device_info_plus:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
name: device_info_plus
|
||||
sha256: "86add5ef97215562d2e090535b0a16f197902b10c369c558a100e74ea06e8659"
|
||||
url: "https://pub.flutter-io.cn"
|
||||
source: hosted
|
||||
version: "9.0.3"
|
||||
device_info_plus_platform_interface:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: device_info_plus_platform_interface
|
||||
sha256: e1ea89119e34903dca74b883d0dd78eb762814f97fb6c76f35e9ff74d261a18f
|
||||
url: "https://pub.flutter-io.cn"
|
||||
source: hosted
|
||||
version: "7.0.3"
|
||||
dio:
|
||||
dependency: "direct main"
|
||||
description:
|
||||
@@ -721,22 +705,6 @@ packages:
|
||||
url: "https://pub.flutter-io.cn"
|
||||
source: hosted
|
||||
version: "3.2.0"
|
||||
win32:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: win32
|
||||
sha256: d7cb55e04cd34096cd3a79b3330245f54cb96a370a1c27adb3c84b917de8b08e
|
||||
url: "https://pub.flutter-io.cn"
|
||||
source: hosted
|
||||
version: "5.15.0"
|
||||
win32_registry:
|
||||
dependency: transitive
|
||||
description:
|
||||
name: win32_registry
|
||||
sha256: "21ec76dfc731550fd3e2ce7a33a9ea90b828fdf19a5c3bcf556fa992cfa99852"
|
||||
url: "https://pub.flutter-io.cn"
|
||||
source: hosted
|
||||
version: "1.1.5"
|
||||
xdg_directories:
|
||||
dependency: transitive
|
||||
description:
|
||||
|
||||
@@ -48,9 +48,6 @@ dependencies:
|
||||
sdk: flutter
|
||||
path_provider: 2.1.5
|
||||
html: ^0.15.6
|
||||
# 设备画像上报(系统版本 + 机型),后台列表据此展示客户端系统;
|
||||
# 用缓存里的 9.0.3,避免拉新版带来的原生构建变更。
|
||||
device_info_plus: 9.0.3
|
||||
|
||||
dev_dependencies:
|
||||
flutter_test:
|
||||
|
||||
Reference in new issue
Block a user