修复用户列表
This commit is contained in:
parent
27f4e75cb8
commit
e842c41736
@ -20,6 +20,7 @@ import 'package:yumi/app/constants/sc_emoji_datas.dart';
|
||||
import 'package:yumi/shared/tools/sc_date_utils.dart';
|
||||
import 'package:yumi/shared/tools/sc_loading_manager.dart';
|
||||
import 'package:yumi/shared/tools/sc_message_utils.dart';
|
||||
import 'package:yumi/shared/tools/sc_user_id_utils.dart';
|
||||
import 'package:yumi/shared/data_sources/sources/repositories/sc_user_repository_impl.dart';
|
||||
import 'package:yumi/shared/business_logic/models/res/login_res.dart';
|
||||
import 'package:yumi/shared/business_logic/models/res/sc_vip_res.dart';
|
||||
@ -363,7 +364,8 @@ class _SCMessageChatPageState extends State<SCMessageChatPage> {
|
||||
_isSystemConversation ||
|
||||
SCGlobalConfig.isSystemUserId(userId) ||
|
||||
userId == null ||
|
||||
userId.isEmpty) {
|
||||
userId.isEmpty ||
|
||||
!scLooksLikeBackendUserId(userId)) {
|
||||
return;
|
||||
}
|
||||
SCLoadingManager.show();
|
||||
|
||||
@ -17,6 +17,7 @@ import 'package:yumi/shared/tools/sc_room_utils.dart';
|
||||
import 'package:yumi/shared/tools/sc_cp_relation_broadcast_assets.dart';
|
||||
import 'package:yumi/shared/tools/sc_cp_relation_notice_utils.dart';
|
||||
import 'package:yumi/shared/tools/sc_room_rocket_reward_popup_ack.dart';
|
||||
import 'package:yumi/shared/tools/sc_user_id_utils.dart';
|
||||
import 'package:yumi/shared/data_sources/sources/local/floating_screen_manager.dart';
|
||||
import 'package:yumi/shared/data_sources/sources/local/data_persistence.dart';
|
||||
import 'package:yumi/shared/data_sources/sources/local/user_manager.dart';
|
||||
@ -566,6 +567,18 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
|
||||
Future<bool> startConversation(V2TimConversation conversation) async {
|
||||
assert(conversation != null);
|
||||
final userId = conversation.userID?.trim() ?? "";
|
||||
if (conversation.type == ConversationType.V2TIM_C2C &&
|
||||
!_isSystemConversation(conversation) &&
|
||||
conversation.conversationID != "customer" &&
|
||||
conversation.conversationID != "article" &&
|
||||
!scLooksLikeBackendUserId(userId)) {
|
||||
_cpInviteLog(
|
||||
'skip startConversation reason=invalid_user_id '
|
||||
'userId=$userId conversationID=${conversation.conversationID}',
|
||||
);
|
||||
return false;
|
||||
}
|
||||
int eTime = DateTime.now().millisecondsSinceEpoch;
|
||||
if (eTime - sTime > 5000) {
|
||||
sTime = eTime;
|
||||
@ -731,6 +744,15 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
}
|
||||
return false;
|
||||
}
|
||||
final cpData = _decodeCpSystemMessageData(message);
|
||||
if (_isCpRelationInviteNoticeData(cpData) &&
|
||||
!scLooksLikeBackendUserId(peerId)) {
|
||||
_cpInviteLog(
|
||||
'skip C2C conversation sync reason=invalid_peer '
|
||||
'peerId=$peerId msgId=${message.msgID} sender=${message.sender}',
|
||||
);
|
||||
return false;
|
||||
}
|
||||
if ((message.userID?.trim() ?? "").isEmpty) {
|
||||
message.userID = peerId;
|
||||
}
|
||||
@ -769,7 +791,6 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
(conversation.unreadCount ?? 0) + (shouldIncrementUnread ? 1 : 0);
|
||||
conversationMap[conversationId] = conversation;
|
||||
|
||||
final cpData = _decodeCpSystemMessageData(message);
|
||||
if (cpData != null) {
|
||||
_cpInviteLog(
|
||||
'sync C2C conversation conversationId=$conversationId '
|
||||
@ -849,15 +870,15 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
data: data,
|
||||
);
|
||||
if (isSender) {
|
||||
if (userId.isNotEmpty && !currentIds.contains(userId)) {
|
||||
if (scLooksLikeBackendUserId(userId) && !currentIds.contains(userId)) {
|
||||
return userId;
|
||||
}
|
||||
return _cpInviteReceiverIdFromMessageData(data);
|
||||
}
|
||||
if (sender.isNotEmpty && !currentIds.contains(sender)) {
|
||||
if (scLooksLikeBackendUserId(sender) && !currentIds.contains(sender)) {
|
||||
return sender;
|
||||
}
|
||||
return _cpInviteInviterIdFromMessageData(data, invite);
|
||||
return _cpInviteInviterIdFromMessageData(data);
|
||||
}
|
||||
|
||||
String _c2cConversationDisplayName(
|
||||
@ -1614,7 +1635,8 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
SCSystemInvitMessageRes invite,
|
||||
) {
|
||||
final userId =
|
||||
_firstCpInviteValue([invite.actualAccount, invite.account]) ?? "";
|
||||
_firstCpInviteBackendUserId([invite.actualAccount, invite.account]) ??
|
||||
"";
|
||||
return SocialChatUserProfile(
|
||||
id: userId,
|
||||
account:
|
||||
@ -1657,7 +1679,7 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
for (final profile in profiles) {
|
||||
for (final value in [profile?.id, profile?.account]) {
|
||||
final text = value?.trim() ?? "";
|
||||
if (text.isNotEmpty && !result.contains(text)) {
|
||||
if (scLooksLikeBackendUserId(text) && !result.contains(text)) {
|
||||
result.add(text);
|
||||
}
|
||||
}
|
||||
@ -1676,12 +1698,9 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
);
|
||||
}
|
||||
|
||||
String _cpInviteInviterIdFromMessageData(
|
||||
Map<String, dynamic> data,
|
||||
SCSystemInvitMessageRes invite,
|
||||
) {
|
||||
String _cpInviteInviterIdFromMessageData(Map<String, dynamic> data) {
|
||||
final content = _cpInviteContentMap(data);
|
||||
return _firstCpInviteValue([
|
||||
return _firstCpInviteBackendUserId([
|
||||
data["userId"]?.toString(),
|
||||
data["inviterUserId"]?.toString(),
|
||||
data["inviterId"]?.toString(),
|
||||
@ -1696,26 +1715,13 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
content["senderId"]?.toString(),
|
||||
content["fromUserId"]?.toString(),
|
||||
content["applyUserId"]?.toString(),
|
||||
data["actualAccount"]?.toString(),
|
||||
data["applyActualAccount"]?.toString(),
|
||||
data["applyUserActualAccount"]?.toString(),
|
||||
data["inviterActualAccount"]?.toString(),
|
||||
data["account"]?.toString(),
|
||||
content["applyActualAccount"]?.toString(),
|
||||
content["applyUserActualAccount"]?.toString(),
|
||||
content["inviterActualAccount"]?.toString(),
|
||||
content["applyUserAccount"]?.toString(),
|
||||
invite.actualAccount,
|
||||
invite.account,
|
||||
content["actualAccount"]?.toString(),
|
||||
content["account"]?.toString(),
|
||||
]) ??
|
||||
"";
|
||||
}
|
||||
|
||||
String _cpInviteReceiverIdFromMessageData(Map<String, dynamic> data) {
|
||||
final content = _cpInviteContentMap(data);
|
||||
return _firstCpInviteValue([
|
||||
return _firstCpInviteBackendUserId([
|
||||
data["acceptUserId"]?.toString(),
|
||||
data["receiverId"]?.toString(),
|
||||
data["receiverUserId"]?.toString(),
|
||||
@ -1726,10 +1732,6 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
content["receiverUserId"]?.toString(),
|
||||
content["targetUserId"]?.toString(),
|
||||
content["toUserId"]?.toString(),
|
||||
data["acceptActualAccount"]?.toString(),
|
||||
data["receiverActualAccount"]?.toString(),
|
||||
content["acceptActualAccount"]?.toString(),
|
||||
content["receiverActualAccount"]?.toString(),
|
||||
]) ??
|
||||
"";
|
||||
}
|
||||
@ -2019,6 +2021,30 @@ class RealTimeMessagingManager extends ChangeNotifier {
|
||||
return null;
|
||||
}
|
||||
|
||||
String? _firstCpInviteBackendUserId(Iterable<String?> values) {
|
||||
return scFirstBackendUserId(values);
|
||||
}
|
||||
|
||||
bool _isCpRelationInviteNoticeData(Map<String, dynamic>? data) {
|
||||
if (data == null) {
|
||||
return false;
|
||||
}
|
||||
final content = _cpInviteContentMap(data);
|
||||
final noticeType =
|
||||
_firstCpInviteValue([
|
||||
data["noticeType"]?.toString(),
|
||||
data["type"]?.toString(),
|
||||
content["noticeType"]?.toString(),
|
||||
content["type"]?.toString(),
|
||||
])?.toUpperCase() ??
|
||||
"";
|
||||
if (noticeType == SCSysytemMessageType.CP_BUILD.name) {
|
||||
return true;
|
||||
}
|
||||
return _cpInviteApplyIdFromData(data).isNotEmpty &&
|
||||
_cpInviteResultFromMessageData(data) != null;
|
||||
}
|
||||
|
||||
void _cpInviteLog(String message) {
|
||||
debugPrint('[CP][Invite] $message');
|
||||
}
|
||||
|
||||
17
lib/shared/tools/sc_user_id_utils.dart
Normal file
17
lib/shared/tools/sc_user_id_utils.dart
Normal file
@ -0,0 +1,17 @@
|
||||
bool scLooksLikeBackendUserId(String? value) {
|
||||
final text = value?.trim() ?? "";
|
||||
if (text.isEmpty) {
|
||||
return false;
|
||||
}
|
||||
return RegExp(r'^\d{15,}$').hasMatch(text);
|
||||
}
|
||||
|
||||
String? scFirstBackendUserId(Iterable<String?> values) {
|
||||
for (final value in values) {
|
||||
final text = value?.trim() ?? "";
|
||||
if (scLooksLikeBackendUserId(text)) {
|
||||
return text;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
@ -22,6 +22,7 @@ import 'package:yumi/shared/data_sources/models/enum/sc_sysytem_message_type.dar
|
||||
import 'package:yumi/shared/tools/sc_date_utils.dart';
|
||||
import 'package:yumi/shared/data_sources/sources/repositories/sc_user_repository_impl.dart';
|
||||
import 'package:yumi/shared/business_logic/models/res/login_res.dart';
|
||||
import 'package:yumi/shared/tools/sc_user_id_utils.dart';
|
||||
import 'package:yumi/services/audio/rtm_manager.dart';
|
||||
|
||||
import '../../../modules/chat/chat_route.dart';
|
||||
@ -340,6 +341,9 @@ class _MessageConversationListPageState
|
||||
continue;
|
||||
}
|
||||
final userId = conversation.userID!.trim();
|
||||
if (!scLooksLikeBackendUserId(userId)) {
|
||||
continue;
|
||||
}
|
||||
if (_conversationUserCache.containsKey(userId) ||
|
||||
_loadingConversationUserIds.contains(userId)) {
|
||||
continue;
|
||||
@ -367,6 +371,7 @@ class _MessageConversationListPageState
|
||||
final userId = conversation.userID?.trim() ?? "";
|
||||
return conversation.type == ConversationType.V2TIM_C2C &&
|
||||
userId.isNotEmpty &&
|
||||
scLooksLikeBackendUserId(userId) &&
|
||||
!SCGlobalConfig.isSystemConversationId(conversation.conversationID) &&
|
||||
!SCGlobalConfig.isSystemUserId(userId) &&
|
||||
conversation.conversationID != "customer" &&
|
||||
@ -411,18 +416,11 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
_effectiveUserId.isNotEmpty;
|
||||
|
||||
String get _effectiveUserId {
|
||||
final cpInviteProfile = _cpInvitePeerProfileFromLastMessage();
|
||||
final cpInvitePeerId =
|
||||
_firstCpInviteValue([
|
||||
return scFirstBackendUserId([
|
||||
conversation.userID,
|
||||
_cpInvitePeerUserIdFromLastMessage(),
|
||||
cpInviteProfile?.id,
|
||||
cpInviteProfile?.account,
|
||||
]) ??
|
||||
"";
|
||||
if (cpInvitePeerId.isNotEmpty) {
|
||||
return cpInvitePeerId;
|
||||
}
|
||||
return conversation.userID?.trim() ?? "";
|
||||
}
|
||||
|
||||
String get _displayAvatar {
|
||||
@ -528,6 +526,9 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
}*/
|
||||
return GestureDetector(
|
||||
onTap: () async {
|
||||
if (_isC2CConversation && _effectiveUserId.isEmpty) {
|
||||
return;
|
||||
}
|
||||
final routeConversation = _routeConversation();
|
||||
if (_isC2CConversation && (routeConversation.userID?.isEmpty ?? true)) {
|
||||
return;
|
||||
@ -768,19 +769,17 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
final messageUserId =
|
||||
_firstCpInviteValue([message?.userID, conversation.userID]) ?? "";
|
||||
if (isCurrentInviter) {
|
||||
return _firstCpInviteValue([
|
||||
return _firstCpInviteBackendUserId([
|
||||
peerProfile?.id,
|
||||
currentIds.contains(messageUserId) ? null : messageUserId,
|
||||
_cpInviteReceiverIdFromData(data),
|
||||
peerProfile?.account,
|
||||
]) ??
|
||||
"";
|
||||
}
|
||||
return _firstCpInviteValue([
|
||||
return _firstCpInviteBackendUserId([
|
||||
currentIds.contains(sender) ? null : sender,
|
||||
peerProfile?.id,
|
||||
_cpInviteInviterIdFromData(data),
|
||||
peerProfile?.account,
|
||||
]) ??
|
||||
"";
|
||||
}
|
||||
@ -869,7 +868,7 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
"profile",
|
||||
]);
|
||||
return _cpInviteProfileOrNull(
|
||||
id: _firstCpInviteValue([
|
||||
id: _firstCpInviteBackendUserId([
|
||||
nested["id"]?.toString(),
|
||||
nested["userId"]?.toString(),
|
||||
data["userId"]?.toString(),
|
||||
@ -886,20 +885,21 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
content["senderId"]?.toString(),
|
||||
content["fromUserId"]?.toString(),
|
||||
content["applyUserId"]?.toString(),
|
||||
nested["actualAccount"]?.toString(),
|
||||
data["actualAccount"]?.toString(),
|
||||
data["applyActualAccount"]?.toString(),
|
||||
data["applyUserActualAccount"]?.toString(),
|
||||
data["inviterActualAccount"]?.toString(),
|
||||
content["applyActualAccount"]?.toString(),
|
||||
content["applyUserActualAccount"]?.toString(),
|
||||
content["inviterActualAccount"]?.toString(),
|
||||
]),
|
||||
account: _firstCpInviteValue([
|
||||
nested["account"]?.toString(),
|
||||
data["account"]?.toString(),
|
||||
data["applyUserAccount"]?.toString(),
|
||||
content["applyUserAccount"]?.toString(),
|
||||
nested["actualAccount"]?.toString(),
|
||||
data["actualAccount"]?.toString(),
|
||||
data["applyActualAccount"]?.toString(),
|
||||
data["applyUserActualAccount"]?.toString(),
|
||||
data["inviterActualAccount"]?.toString(),
|
||||
content["actualAccount"]?.toString(),
|
||||
content["applyActualAccount"]?.toString(),
|
||||
content["applyUserActualAccount"]?.toString(),
|
||||
content["inviterActualAccount"]?.toString(),
|
||||
]),
|
||||
nickname: _firstCpInviteValue([
|
||||
nested["userNickname"]?.toString(),
|
||||
@ -943,7 +943,7 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
"targetUserProfile",
|
||||
]);
|
||||
return _cpInviteProfileOrNull(
|
||||
id: _firstCpInviteValue([
|
||||
id: _firstCpInviteBackendUserId([
|
||||
nested["id"]?.toString(),
|
||||
nested["userId"]?.toString(),
|
||||
data["acceptUserId"]?.toString(),
|
||||
@ -956,11 +956,6 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
content["receiverUserId"]?.toString(),
|
||||
content["targetUserId"]?.toString(),
|
||||
content["toUserId"]?.toString(),
|
||||
nested["actualAccount"]?.toString(),
|
||||
data["acceptActualAccount"]?.toString(),
|
||||
data["receiverActualAccount"]?.toString(),
|
||||
content["acceptActualAccount"]?.toString(),
|
||||
content["receiverActualAccount"]?.toString(),
|
||||
]),
|
||||
account: _firstCpInviteValue([
|
||||
nested["account"]?.toString(),
|
||||
@ -968,6 +963,11 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
data["receiverAccount"]?.toString(),
|
||||
content["acceptAccount"]?.toString(),
|
||||
content["receiverAccount"]?.toString(),
|
||||
nested["actualAccount"]?.toString(),
|
||||
data["acceptActualAccount"]?.toString(),
|
||||
data["receiverActualAccount"]?.toString(),
|
||||
content["acceptActualAccount"]?.toString(),
|
||||
content["receiverActualAccount"]?.toString(),
|
||||
]),
|
||||
nickname: _firstCpInviteValue([
|
||||
nested["userNickname"]?.toString(),
|
||||
@ -1016,12 +1016,12 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
|
||||
String _cpInviteInviterIdFromData(Map<String, dynamic> data) {
|
||||
final profile = _cpInviteInviterProfileFromData(data);
|
||||
return _firstCpInviteValue([profile?.id, profile?.account]) ?? "";
|
||||
return _firstCpInviteBackendUserId([profile?.id]) ?? "";
|
||||
}
|
||||
|
||||
String _cpInviteReceiverIdFromData(Map<String, dynamic> data) {
|
||||
final profile = _cpInviteReceiverProfileFromData(data);
|
||||
return _firstCpInviteValue([profile?.id, profile?.account]) ?? "";
|
||||
return _firstCpInviteBackendUserId([profile?.id]) ?? "";
|
||||
}
|
||||
|
||||
Set<String> _cpInviteInviterIdentityValues(Map<String, dynamic> data) {
|
||||
@ -1161,4 +1161,8 @@ class _ConversationItemState extends State<ConversationItem> {
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
String? _firstCpInviteBackendUserId(Iterable<String?> values) {
|
||||
return scFirstBackendUserId(values);
|
||||
}
|
||||
}
|
||||
|
||||
20
test/sc_user_id_utils_test.dart
Normal file
20
test/sc_user_id_utils_test.dart
Normal file
@ -0,0 +1,20 @@
|
||||
import 'package:flutter_test/flutter_test.dart';
|
||||
import 'package:yumi/shared/tools/sc_user_id_utils.dart';
|
||||
|
||||
void main() {
|
||||
test('backend user id detector rejects display accounts', () {
|
||||
expect(scLooksLikeBackendUserId('323456'), isFalse);
|
||||
expect(scLooksLikeBackendUserId('223456'), isFalse);
|
||||
expect(scLooksLikeBackendUserId('4569421795454615555'), isTrue);
|
||||
});
|
||||
|
||||
test('first backend user id skips CP invite display accounts', () {
|
||||
final userId = scFirstBackendUserId([
|
||||
'323456',
|
||||
'223456',
|
||||
'4569421795454615555',
|
||||
]);
|
||||
|
||||
expect(userId, '4569421795454615555');
|
||||
});
|
||||
}
|
||||
Loading…
x
Reference in New Issue
Block a user