From dadf0cbd5da477e16af7732f60f3eedcd11de7e7 Mon Sep 17 00:00:00 2001 From: Liuyf Date: Mon, 24 Feb 2025 18:00:48 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20jpush=20=E7=BB=9F=E4=B8=80android?= =?UTF-8?q?=E5=92=8Cios=20=E6=8E=A8=E9=80=81token=E4=B8=8A=E6=8A=A5?= =?UTF-8?q?=E9=80=BB=E8=BE=91?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- ios/Podfile.lock | 49 +++++++++-- lib/mine/mine/starLockMine_logic.dart | 2 +- lib/mine/mineSet/mineSet/mineSet_logic.dart | 4 +- lib/network/api.dart | 5 +- lib/network/api_provider.dart | 10 ++- lib/network/api_repository.dart | 14 +-- lib/tools/push/xs_jPhush.dart | 98 +++++++++++++++------ lib/tools/storage.dart | 2 + pubspec.lock | 4 +- pubspec.yaml | 2 +- 10 files changed, 140 insertions(+), 50 deletions(-) diff --git a/ios/Podfile.lock b/ios/Podfile.lock index 33ab3865..7f321307 100644 --- a/ios/Podfile.lock +++ b/ios/Podfile.lock @@ -74,8 +74,6 @@ PODS: - SDWebImage - SwiftyGif - EMASRest (11.1.1.2) - - fast_rsa (0.6.0): - - Flutter - file_picker (0.0.1): - DKImagePickerController/PhotoGallery - Flutter @@ -128,12 +126,16 @@ PODS: - flutter_bugly (0.0.1): - Bugly (= 2.6.1) - Flutter + - flutter_foreground_task (0.0.1): + - Flutter - flutter_local_notifications (0.0.1): - Flutter - flutter_native_contact_picker (0.0.1): - Flutter - flutter_pcm_sound (0.0.1): - Flutter + - flutter_screen_recording (0.0.1): + - Flutter - flutter_voice_processor (1.1.1): - Flutter - ios-voice-processor (~> 1.1.0) @@ -146,6 +148,8 @@ PODS: - fluwx/pay (0.0.1): - Flutter - WechatOpenSDK-XCFramework (~> 2.0.4) + - gallery_saver (0.0.1): + - Flutter - google_maps_flutter_ios (0.0.1): - Flutter - GoogleMaps (< 9.0) @@ -215,6 +219,18 @@ PODS: - JPush (= 5.3.0) - just_audio (0.0.1): - Flutter + - libwebp (1.3.2): + - libwebp/demux (= 1.3.2) + - libwebp/mux (= 1.3.2) + - libwebp/sharpyuv (= 1.3.2) + - libwebp/webp (= 1.3.2) + - libwebp/demux (1.3.2): + - libwebp/webp + - libwebp/mux (1.3.2): + - libwebp/demux + - libwebp/sharpyuv (1.3.2) + - libwebp/webp (1.3.2): + - libwebp/sharpyuv - nanopb (3.30910.0): - nanopb/decode (= 3.30910.0) - nanopb/encode (= 3.30910.0) @@ -257,6 +273,9 @@ PODS: - video_player_avfoundation (0.0.1): - Flutter - FlutterMacOS + - video_thumbnail (0.0.1): + - Flutter + - libwebp - webview_flutter_wkwebview (0.0.1): - Flutter - WechatOpenSDK-XCFramework (2.0.4) @@ -274,19 +293,21 @@ DEPENDENCIES: - camera_avfoundation (from `.symlinks/plugins/camera_avfoundation/ios`) - connectivity_plus (from `.symlinks/plugins/connectivity_plus/darwin`) - device_info_plus (from `.symlinks/plugins/device_info_plus/ios`) - - fast_rsa (from `.symlinks/plugins/fast_rsa/ios`) - file_picker (from `.symlinks/plugins/file_picker/ios`) - firebase_analytics (from `.symlinks/plugins/firebase_analytics/ios`) - firebase_core (from `.symlinks/plugins/firebase_core/ios`) - Flutter (from `Flutter`) - flutter_blue_plus (from `.symlinks/plugins/flutter_blue_plus/ios`) - flutter_bugly (from `.symlinks/plugins/flutter_bugly/ios`) + - flutter_foreground_task (from `.symlinks/plugins/flutter_foreground_task/ios`) - flutter_local_notifications (from `.symlinks/plugins/flutter_local_notifications/ios`) - flutter_native_contact_picker (from `.symlinks/plugins/flutter_native_contact_picker/ios`) - flutter_pcm_sound (from `.symlinks/plugins/flutter_pcm_sound/ios`) + - flutter_screen_recording (from `.symlinks/plugins/flutter_screen_recording/ios`) - flutter_voice_processor (from `.symlinks/plugins/flutter_voice_processor/ios`) - fluttertoast (from `.symlinks/plugins/fluttertoast/ios`) - fluwx (from `.symlinks/plugins/fluwx/ios`) + - gallery_saver (from `.symlinks/plugins/gallery_saver/ios`) - google_maps_flutter_ios (from `.symlinks/plugins/google_maps_flutter_ios/ios`) - image_gallery_saver (from `.symlinks/plugins/image_gallery_saver/ios`) - image_picker_ios (from `.symlinks/plugins/image_picker_ios/ios`) @@ -306,6 +327,7 @@ DEPENDENCIES: - umeng_common_sdk (from `.symlinks/plugins/umeng_common_sdk/ios`) - url_launcher_ios (from `.symlinks/plugins/url_launcher_ios/ios`) - video_player_avfoundation (from `.symlinks/plugins/video_player_avfoundation/darwin`) + - video_thumbnail (from `.symlinks/plugins/video_thumbnail/ios`) - webview_flutter_wkwebview (from `.symlinks/plugins/webview_flutter_wkwebview/ios`) SPEC REPOS: @@ -334,6 +356,7 @@ SPEC REPOS: - ios-voice-processor - JCore - JPush + - libwebp - nanopb - PromisesObjC - SDWebImage @@ -366,8 +389,6 @@ EXTERNAL SOURCES: :path: ".symlinks/plugins/connectivity_plus/darwin" device_info_plus: :path: ".symlinks/plugins/device_info_plus/ios" - fast_rsa: - :path: ".symlinks/plugins/fast_rsa/ios" file_picker: :path: ".symlinks/plugins/file_picker/ios" firebase_analytics: @@ -380,18 +401,24 @@ EXTERNAL SOURCES: :path: ".symlinks/plugins/flutter_blue_plus/ios" flutter_bugly: :path: ".symlinks/plugins/flutter_bugly/ios" + flutter_foreground_task: + :path: ".symlinks/plugins/flutter_foreground_task/ios" flutter_local_notifications: :path: ".symlinks/plugins/flutter_local_notifications/ios" flutter_native_contact_picker: :path: ".symlinks/plugins/flutter_native_contact_picker/ios" flutter_pcm_sound: :path: ".symlinks/plugins/flutter_pcm_sound/ios" + flutter_screen_recording: + :path: ".symlinks/plugins/flutter_screen_recording/ios" flutter_voice_processor: :path: ".symlinks/plugins/flutter_voice_processor/ios" fluttertoast: :path: ".symlinks/plugins/fluttertoast/ios" fluwx: :path: ".symlinks/plugins/fluwx/ios" + gallery_saver: + :path: ".symlinks/plugins/gallery_saver/ios" google_maps_flutter_ios: :path: ".symlinks/plugins/google_maps_flutter_ios/ios" image_gallery_saver: @@ -424,6 +451,8 @@ EXTERNAL SOURCES: :path: ".symlinks/plugins/url_launcher_ios/ios" video_player_avfoundation: :path: ".symlinks/plugins/video_player_avfoundation/darwin" + video_thumbnail: + :path: ".symlinks/plugins/video_thumbnail/ios" webview_flutter_wkwebview: :path: ".symlinks/plugins/webview_flutter_wkwebview/ios" @@ -451,7 +480,6 @@ SPEC CHECKSUMS: DKImagePickerController: 946cec48c7873164274ecc4624d19e3da4c1ef3c DKPhotoGallery: b3834fecb755ee09a593d7c9e389d8b5d6deed60 EMASRest: 8df6f87836767a9415ad5cc4af739bc9d215b475 - fast_rsa: a1fed69b074093d2e2e3fefae6b821a071649d4c file_picker: ce3938a0df3cc1ef404671531facef740d03f920 Firebase: 9f574c08c2396885b5e7e100ed4293d956218af9 firebase_analytics: 1a66fe8d4375eccff44671ea37897683a78b2675 @@ -463,12 +491,15 @@ SPEC CHECKSUMS: Flutter: e0871f40cf51350855a761d2e70bf5af5b9b5de7 flutter_blue_plus: 4837da7d00cf5d441fdd6635b3a57f936778ea96 flutter_bugly: bf35df32a9c5d50b8aacdd35bd8ddc5b55150dae + flutter_foreground_task: 21ef182ab0a29a3005cc72cd70e5f45cb7f7f817 flutter_local_notifications: 4cde75091f6327eb8517fa068a0a5950212d2086 flutter_native_contact_picker: bd430ba0fbf82768bb50c2c52a69a65759a8f907 flutter_pcm_sound: de0572ca4f99091cc2abfcc31601b8a4ddd33c0e + flutter_screen_recording: f56d857cef9c6338f74909a15f60b3e5dc5ffb38 flutter_voice_processor: 2b89b93d69b02227ae3fd58589ee0bcfa3ca2a82 fluttertoast: e9a18c7be5413da53898f660530c56f35edfba9c - fluwx: c18fd6c16b03a2187cd07d6e48e32a7801962849 + fluwx: daa284756ce53442b3d0417ceeda66e981906811 + gallery_saver: 9fc173c9f4fcc48af53b2a9ebea1b643255be542 google_maps_flutter_ios: f135b968a67c05679e0a53538e900b5c174b0d99 GoogleAppMeasurement: 6e49ffac7d3f2c3ded9cc663f912a13b67bbd0de GoogleMaps: 20d7b12be49a14287f797e88e0e31bc4156aaeb4 @@ -480,6 +511,7 @@ SPEC CHECKSUMS: JPush: b71f497a3c1b825c7843fd97f290b05d5cd75f2e jpush_flutter: c87be254790933c0363684169ef9d3d279a5adc5 just_audio: baa7252489dbcf47a4c7cc9ca663e9661c99aafa + libwebp: 1786c9f4ff8a279e4dac1e8f385004d5fc253009 nanopb: fad817b59e0457d11a5dfbde799381cd727c1275 network_info_plus: 6d0c3eb8367b8164fa3fb0c19875e3f59d49697f open_filex: 6e26e659846ec990262224a12ef1c528bb4edbe4 @@ -498,9 +530,10 @@ SPEC CHECKSUMS: umeng_common_sdk: a8abd7f86dfd013dbbeeae587ee143760c6582f2 url_launcher_ios: 5334b05cef931de560670eeae103fd3e431ac3fe video_player_avfoundation: 7c6c11d8470e1675df7397027218274b6d2360b3 + video_thumbnail: c4e2a3c539e247d4de13cd545344fd2d26ffafd1 webview_flutter_wkwebview: 2a23822e9039b7b1bc52e5add778e5d89ad488d1 WechatOpenSDK-XCFramework: 36fb2bea0754266c17184adf4963d7e6ff98b69f PODFILE CHECKSUM: 728f9c851a19709391c77c54ed3556e484b54db6 -COCOAPODS: 1.16.2 +COCOAPODS: 1.14.3 diff --git a/lib/mine/mine/starLockMine_logic.dart b/lib/mine/mine/starLockMine_logic.dart index 9e69a978..9380e65d 100755 --- a/lib/mine/mine/starLockMine_logic.dart +++ b/lib/mine/mine/starLockMine_logic.dart @@ -24,7 +24,7 @@ class StarLockMineLogic extends BaseGetXController { //删除账号请求 Future userLogoutRequest() async { - final LoginEntity entity = await ApiRepository.to.userLogout(deviceld: ''); + final LoginEntity entity = await ApiRepository.to.userLogout(storageNonce: ''); if (entity.errorCode!.codeIsSuccessful) {} } diff --git a/lib/mine/mineSet/mineSet/mineSet_logic.dart b/lib/mine/mineSet/mineSet/mineSet_logic.dart index 33b0f61a..8778dfc0 100755 --- a/lib/mine/mineSet/mineSet/mineSet_logic.dart +++ b/lib/mine/mineSet/mineSet/mineSet_logic.dart @@ -130,7 +130,7 @@ class MineSetLogic extends BaseGetXController { } }); final LoginEntity entity = - await ApiRepository.to.userLogout(deviceld: getPushDeviceID); + await ApiRepository.to.userLogout(storageNonce: getPushDeviceID); final String getMobile = (await Storage.getMobile())!; if (entity.errorCode!.codeIsSuccessful) { ApmHelper.instance.logout(); @@ -169,6 +169,8 @@ class MineSetLogic extends BaseGetXController { ///退出登录 void logOut() async { + final XSJPushProvider jpushProvider = XSJPushProvider(); + await jpushProvider.resetJPushService(); Storage.clearAll(); } diff --git a/lib/network/api.dart b/lib/network/api.dart index c51b05f6..8a04dc74 100755 --- a/lib/network/api.dart +++ b/lib/network/api.dart @@ -67,8 +67,7 @@ abstract class Api { final String getWifiServiceIpURL = '/wifiLock/getWifiServiceIp'; // 获取Wifi锁服务器 final String updateLockSettingUrl = '/v2/lockSetting/updateLockSetting'; // 锁设置里面所有的设置 - final String deviceNetworkConfiguration = - '/deviceNetwork/setting'; // 设备网络配置 + final String deviceNetworkConfiguration = '/deviceNetwork/setting'; // 设备网络配置 final String getDeviceNetworkConfiguration = '/deviceNetwork/getNetworkInfo'; // 设备网络配置 final String roomQueryDateUrl = '/room/queryDate'; // 获取网关时间 @@ -195,6 +194,7 @@ abstract class Api { final String setAppUnlockMustOnlineURL = '/room/setAppUnlockMustOnline'; //APP开锁时需手机联网的锁 final String userLogoutURL = '/v2/user/logout'; //退出登录 + final String userLogout3URL = '/v3/user/logout'; //退出登录 final String deleteAccountURL = '/user/delete'; //删除账号 final String getUserInfoURL = '/user/getUserInfo'; //获取个人信息 final String sendValidationCodeAuthURL = @@ -214,6 +214,7 @@ abstract class Api { final String unbindPhoneTokenURL = '/user/unbindPhoneToken'; //获取解绑手机号Token final String unbindEmailTokenURL = '/user/unbindEmailToken'; //获取解绑邮箱Token final String pushBindAppIdURL = '/user/bindAppId'; //推送绑定APP设备 + final String bindPushTokenURL = '/user/bindPushToken'; //推送绑定APP设备 final String messageListURL = '/notifications/list'; //消息列表 final String readMessageURL = '/notifications/markAsRead'; //读取消息 diff --git a/lib/network/api_provider.dart b/lib/network/api_provider.dart index a758294c..c69dce39 100755 --- a/lib/network/api_provider.dart +++ b/lib/network/api_provider.dart @@ -1950,8 +1950,8 @@ class ApiProvider extends BaseProvider { })); //退出登录 - Future userLogout(String deviceld) => - post(userLogoutURL.toUrl, jsonEncode({'deviceld': deviceld})); + Future userLogout(String storageNonce) => + post(userLogout3URL.toUrl, jsonEncode({'storageNonce': storageNonce})); //删除账号 Future deleteAccount( @@ -2115,6 +2115,12 @@ class ApiProvider extends BaseProvider { pushBindAppIdURL.toUrl, jsonEncode({'deviceId': deviceId, 'deviceType': deviceType})); + //推送channel绑定 + Future pushBindChannels( + String storageNonce, List> channels) => + post(bindPushTokenURL.toUrl, + jsonEncode({'storageNonce': storageNonce, 'channels': channels})); + // 消息列表 Future messageListLoadData(String pageNo, String pageSize) => post( messageListURL.toUrl, diff --git a/lib/network/api_repository.dart b/lib/network/api_repository.dart index 7c97ae82..5b0b5cef 100755 --- a/lib/network/api_repository.dart +++ b/lib/network/api_repository.dart @@ -1871,8 +1871,8 @@ class ApiRepository { } // 退出登录 - Future userLogout({required String deviceld}) async { - final res = await apiProvider.userLogout(deviceld); + Future userLogout({required String storageNonce}) async { + final res = await apiProvider.userLogout(storageNonce); return LoginEntity.fromJson(res.body); } @@ -2170,6 +2170,13 @@ class ApiRepository { return MineUnbindPhoneOrEmailEntity.fromJson(res.body); } + //推送channel绑定 + Future pushBindChannels( + String storageNonce, List> channels) async { + final res = await apiProvider.pushBindChannels(storageNonce, channels); + return MineUnbindPhoneOrEmailEntity.fromJson(res.body); + } + // 消息列表 Future messageListLoadData( {required String pageNo, required String pageSize}) async { @@ -2731,7 +2738,4 @@ class ApiRepository { ); return DeviceNetwork.fromJson(res.body); } - - - } diff --git a/lib/tools/push/xs_jPhush.dart b/lib/tools/push/xs_jPhush.dart index 3ce9adf3..11b16951 100755 --- a/lib/tools/push/xs_jPhush.dart +++ b/lib/tools/push/xs_jPhush.dart @@ -1,3 +1,5 @@ +import 'dart:async'; +import 'dart:convert'; import 'dart:io'; import 'package:flutter/foundation.dart'; @@ -13,11 +15,37 @@ import 'package:star_lock/tools/storage.dart'; import '../../app_settings/app_settings.dart'; class XSJPushProvider { + static const Map channelTypeMapping = { + 1: 'xiaomi', + 2: 'huawei', + 3: 'meizu', + 4: 'oppo', + 5: 'vivo', + 6: 'honor', + 7: 'apns', + 8: 'fcm', + 9: 'jiguang' + }; final JPush jpush = JPush(); + late Completer> _jpushRegistrationIdCompleter; + late Completer> _vendorTokenCompleter; + + Future resetJPushService() async { + debugPrint("resetJPushService start"); + jpush.setup( + appKey: '', + channel: 'flutter_channel', + production: F.isProductionEnv, + debug: !F.isProductionEnv, + ); + } // appKey: 251fc8074820d122b6de58d2--鑫泓佳AppKey // appKey: 7ff37d174c1a568a89e98dad--sky Future initJPushService() async { + debugPrint("initJPushService start"); + _jpushRegistrationIdCompleter = Completer>(); + _vendorTokenCompleter = Completer>(); final String? data = await Storage.getString(saveUserLoginData); if (data == null || data.isEmpty) { AppLog.log('No user data found.'); @@ -34,25 +62,49 @@ class XSJPushProvider { production: F.isProductionEnv, debug: !F.isProductionEnv, ); - jpush.applyPushAuthority( const NotificationSettingsIOS(sound: true, alert: true, badge: false), ); addJPushEventHandler(); AppLog.log('JPush initialized.'); - - final String rid = await jpush.getRegistrationID(); - AppLog.log('flutter get registration id : $rid'); - pushBindDeviceID(rid); + debugPrint("initJPushService end"); } + static const int CMD_GET_REGISTRATION_ID = 2005; //getRegistrationID 异步回调 + static const int CMD_GET_TOKEN = 10000; //厂商 token 注册回调 + //极光推送事件处理方法 void addJPushEventHandler() { jpush.addEventHandler( - onCommandResult: (Map message) async { - AppLog.log('onCommandResult: $message'); - debugPrint("addJPushEventHandler onCommandResult:$message"); + onCommandResult: (Map data) async { + AppLog.log('onCommandResult: $data'); + debugPrint("addJPushEventHandler onCommandResult:$data"); + final int cmdCode = data['cmd']; + switch (cmdCode) { + case CMD_GET_REGISTRATION_ID: + await Storage.setString(pushDeviceID, data['message']); + AppLog.log('flutter get registration id : ${data['message']}'); + _jpushRegistrationIdCompleter.complete({ + 'channel': 'jiguang', + 'channelToken': data['message'] + }); + // final String? channel2TokenStr = + // await Storage.getString(vendorPushChannelInfo); + // if (Platform.isAndroid && channel2TokenStr != null) { + // _vendorTokenCompleter.complete(jsonDecode(channel2TokenStr)); + // } + break; + case CMD_GET_TOKEN: + final Map channel2Token = { + 'channel': channelTypeMapping[data['platform']], + 'channelToken': data['token'] + }; + await Storage.setString( + vendorPushChannelInfo, jsonEncode(channel2Token)); + _vendorTokenCompleter.complete(channel2Token); + break; + } }, onReceiveNotification: (Map message) async { AppLog.log('onReceiveNotification: $message'); @@ -79,32 +131,22 @@ class XSJPushProvider { debugPrint("addJPushEventHandler onInAppMessageShow:$message"); }, onConnected: (Map message) async { - //绑定设备id - final String rid = await jpush.getRegistrationID(); - AppLog.log('onConnected registration id : $rid'); - debugPrint("addJPushEventHandler onConnected:$message"); - await Storage.setString(pushDeviceID, rid); - await pushBindDeviceID(rid); - return Future.value(); }, ); - - // Remove the incorrect addEventHandler call + bindPushChannels(); } - Future pushBindDeviceID(String deviceID) async { + // jpush 统一推送通道设备绑定 + Future bindPushChannels() async { try { - if (deviceID.isEmpty) { - AppLog.log('Device ID is empty.'); - //绑定设备id - final String rid = await jpush.getRegistrationID(); - AppLog.log('onConnected registration id : $rid'); - deviceID = rid; - } - await Storage.setString(pushDeviceID, deviceID); - final MineUnbindPhoneOrEmailEntity entity = await ApiRepository.to - .pushBindAppId(deviceID, Platform.isAndroid ? 10 : 20); + debugPrint("await PushChannels start"); + var channels = await Future.wait( + [_jpushRegistrationIdCompleter.future, _vendorTokenCompleter.future]); + final String? registrationId = await Storage.getString(pushDeviceID); + debugPrint("await PushChannels end"); + final MineUnbindPhoneOrEmailEntity entity = + await ApiRepository.to.pushBindChannels(registrationId!, channels); if (entity.errorCode!.codeIsSuccessful) { AppLog.log('绑定成功'); } else { diff --git a/lib/tools/storage.dart b/lib/tools/storage.dart index cf4e9666..eb251a53 100755 --- a/lib/tools/storage.dart +++ b/lib/tools/storage.dart @@ -25,6 +25,7 @@ const String isAgreeCamera = 'isAgreeCamera'; //是否同意获取相机/相册 const String isShowUpdateVersion = 'isShowUpdateVersion'; //是否更新弹窗 const String saveLockAlias = 'saveLockAlias'; //锁别名 const String pushDeviceID = 'pushDeviceID'; //推送设备ID +const String vendorPushChannelInfo = 'pushChannelInfo'; //推送设备ID const String saveIsVip = 'saveIsVip'; //是否是VIP const String saveUserLoginData = 'userLoginData'; @@ -37,6 +38,7 @@ const String relayInfo = 'relayInfo'; //星图中继服务器信息 const String lockNetWorkInfo = 'lockNetWorkInfo'; //锁板配网信息 const String appVersionHistoryUrl = 'appVersionHistoryUrl'; //是否同意隐私协议弹窗 + class Storage { factory Storage() => _instance; diff --git a/pubspec.lock b/pubspec.lock index 40584305..dd6aba4d 100644 --- a/pubspec.lock +++ b/pubspec.lock @@ -992,8 +992,8 @@ packages: dependency: "direct main" description: path: "." - ref: "807ddb8e396c2dce16919df84efe795072404dde" - resolved-ref: "807ddb8e396c2dce16919df84efe795072404dde" + ref: ed2bd31147ccc929d9b9cf47205c2b8142a6d3f2 + resolved-ref: ed2bd31147ccc929d9b9cf47205c2b8142a6d3f2 url: "git@code-internal.star-lock.cn:StarlockTeam/jpush_flutter.git" source: git version: "2.5.8" diff --git a/pubspec.yaml b/pubspec.yaml index 885185dc..7d0cc89b 100755 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -214,7 +214,7 @@ dependencies: jpush_flutter: git: url: git@code-internal.star-lock.cn:StarlockTeam/jpush_flutter.git - ref: 807ddb8e396c2dce16919df84efe795072404dde + ref: ed2bd31147ccc929d9b9cf47205c2b8142a6d3f2 #视频播放器 video_player: ^2.9.2