app-starlock/lib/talk/startChart/command/message_command.dart

433 lines
13 KiB
Dart
Raw Normal View History

import 'dart:convert';
import 'dart:typed_data';
import 'package:star_lock/talk/startChart/constant/message_type_constant.dart';
2024-11-28 14:57:49 +08:00
import 'package:star_lock/talk/startChart/constant/payload_type_constant.dart';
import 'package:star_lock/talk/startChart/constant/protocol_flag_constant.dart';
import 'package:star_lock/talk/startChart/entity/scp_message.dart';
import 'package:star_lock/talk/startChart/proto/gateway_reset.pb.dart';
2024-12-05 13:50:20 +08:00
import 'package:star_lock/talk/startChart/proto/generic.pb.dart';
import 'package:star_lock/talk/startChart/proto/talk_accept.pb.dart';
import 'package:star_lock/talk/startChart/proto/talk_data.pb.dart';
import 'package:star_lock/talk/startChart/proto/talk_expect.pb.dart';
2024-12-10 17:27:37 +08:00
import 'package:star_lock/talk/startChart/proto/talk_hangup.pb.dart';
2024-12-05 13:50:20 +08:00
import 'package:star_lock/talk/startChart/proto/talk_ping.pb.dart';
import 'package:star_lock/talk/startChart/proto/talk_reject.pb.dart';
import 'package:star_lock/talk/startChart/proto/talk_request.pb.dart';
2024-11-28 14:57:49 +08:00
class MessageCommand {
// 全局字典,用于存储每个 ToPeerId 对应的当前 messageId
static Map<String, int> _messageIdMap = {};
static int _maxIntValue = 9223372036854775807; // Dart 中 int 的最大值
// 获取并递增消息ID
static int getNextMessageId(String toPeerId, {bool increment = true}) {
if (_messageIdMap.containsKey(toPeerId)) {
if (increment) {
_messageIdMap[toPeerId] = _messageIdMap[toPeerId]! + 1;
// 如果 messageId 超过 int 的最大值,则重置为 1
if (_messageIdMap[toPeerId]! > _maxIntValue) {
_messageIdMap[toPeerId] = 1;
}
}
} else {
_messageIdMap[toPeerId] = 1;
}
return _messageIdMap[toPeerId]!;
}
2024-11-28 14:57:49 +08:00
/// 客户端去中继上线命令
static List<int> goOnlineRelay({
required String FromPeerId,
required String ToPeerId,
int? MessageId,
}) {
2024-11-28 14:57:49 +08:00
String serializedBytesString = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: [0],
PayloadCRC: 0,
PayloadLength: 0,
PayloadType: PayloadTypeConstant.goOnline,
2024-11-28 14:57:49 +08:00
).serialize();
return _hexToBytes(serializedBytesString);
}
// 回声测试消息
static List<int> echoMessage({
required String ToPeerId,
required String FromPeerId,
List<int>? payload,
int? SpTotal,
int? SpIndex,
int? MessageId,
2024-11-28 14:57:49 +08:00
}) {
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: SpTotal,
SpIndex: SpIndex,
2024-11-28 14:57:49 +08:00
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrcFromIntList(payload ?? []),
PayloadLength: payload?.length ?? 0,
PayloadType: PayloadTypeConstant.echoTest,
2024-11-28 14:57:49 +08:00
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
// 心跳消息
static List<int> heartbeatMessage({
required String FromPeerId,
required String ToPeerId,
int? MessageId,
}) {
String payload = 'hello';
2024-11-28 14:57:49 +08:00
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(_stringToUint8List(payload)),
PayloadLength: payload.length,
PayloadType: PayloadTypeConstant.heartbeat,
2024-11-28 14:57:49 +08:00
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
// 网关初始化
static List<int> gatewayResetMessage({
required int gatewayId,
required String FromPeerId,
required String ToPeerId,
required int time,
int? MessageId,
}) {
// 构建荷载
final gatewayResetReq = GatewayResetReq(
iD: gatewayId,
time: time,
);
// 构建荷载长度
final payload = gatewayResetReq.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadTypeConstant.gatewayReset,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
2024-12-05 13:50:20 +08:00
// 同意接听消息
static List<int> talkAcceptMessage({
required String FromPeerId,
required String ToPeerId,
int? MessageId,
}) {
2024-12-05 13:50:20 +08:00
final talkAcceptReq = TalkAcceptReq();
final payload = talkAcceptReq.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
2024-12-05 13:50:20 +08:00
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadTypeConstant.talkAccept,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
// 发送对话请求消息
static List<int> talkRequestMessage({
required String FromPeerId,
required String ToPeerId,
int? MessageId,
}) {
final talkReq = TalkReq();
final payload = talkReq.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadTypeConstant.callRequest,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
2024-12-05 13:50:20 +08:00
// 拒绝接听消息
static List<int> talkRejectMessage({
required String FromPeerId,
required String ToPeerId,
int? MessageId,
2024-12-05 13:50:20 +08:00
}) {
final talkReject = TalkReject();
final payload = talkReject.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
2024-12-05 13:50:20 +08:00
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadTypeConstant.talkReject,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
// 呼叫保持消息
static List<int> talkPingMessage({
required String FromPeerId,
required String ToPeerId,
int? MessageId,
2024-12-05 13:50:20 +08:00
}) {
final talkPing = TalkPing();
final payload = talkPing.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
2024-12-10 16:31:41 +08:00
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
2024-12-05 13:50:20 +08:00
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadTypeConstant.talkPing,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
2024-12-10 17:27:37 +08:00
// 通话中挂断
static List<int> talkHangupMessage({
required String FromPeerId,
required String ToPeerId,
int? MessageId,
2024-12-10 17:27:37 +08:00
}) {
final talkHangup = TalkHangup();
final payload = talkHangup.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
2024-12-10 17:27:37 +08:00
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadTypeConstant.talkHangup,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
2024-12-05 13:50:20 +08:00
// 音视频数据
static List<int> talkDataMessage({
required String FromPeerId,
required String ToPeerId,
required TalkData talkData,
int? MessageId,
2024-12-05 13:50:20 +08:00
}) {
final payload = talkData.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.RealTimeData,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
2024-12-05 13:50:20 +08:00
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadTypeConstant.talkData,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
// 预期接收消息
static List<int> talkExpectMessage({
required String FromPeerId,
required String ToPeerId,
required TalkExpect talkExpect,
int? MessageId,
}) {
final payload = talkExpect.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Req,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadTypeConstant.talkExpect,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
2024-12-05 13:50:20 +08:00
// GenericRespSuccess 消息
static List<int> genericRespSuccessMessage({
required String FromPeerId,
required String ToPeerId,
required int PayloadType,
int? MessageId,
2024-12-05 13:50:20 +08:00
}) {
final genericResp = GenericResp();
genericResp.message = 'ok';
genericResp.code = 0;
final payload = genericResp.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Resp,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
2024-12-05 13:50:20 +08:00
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadType,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
// GenericRespError 消息
static List<int> genericRespErrorMessage({
required String FromPeerId,
required String ToPeerId,
required int PayloadType,
int? MessageId,
2024-12-05 13:50:20 +08:00
}) {
final genericResp = GenericResp();
genericResp.message = 'error';
genericResp.code = -1;
final payload = genericResp.writeToBuffer();
ScpMessage message = ScpMessage(
ProtocolFlag: ProtocolFlagConstant.scp01,
MessageType: MessageTypeConstant.Resp,
MessageId: MessageId,
SpTotal: 1,
SpIndex: 1,
2024-12-05 13:50:20 +08:00
FromPeerId: FromPeerId,
ToPeerId: ToPeerId,
Payload: payload,
PayloadCRC: calculationCrc(payload),
PayloadLength: payload.length,
PayloadType: PayloadType,
);
String serializedBytesString = message.serialize();
return _hexToBytes(serializedBytesString);
}
2024-11-28 14:57:49 +08:00
// 辅助方法将16进制字符串转换为字节列表
static List<int> _hexToBytes(String hex) {
final bytes = <int>[];
for (int i = 0; i < hex.length; i += 2) {
bytes.add(int.parse(hex.substring(i, i + 2), radix: 16));
}
return bytes;
}
static int calculationCrc(Uint8List uint8Payload) {
// 使用自定义 CRC32 算法
final int crc32Value = _crc32Uint16(uint8Payload);
return crc32Value;
}
// 重载的方法,接受 List<int>
static int calculationCrcFromIntList(List<int> intList) {
// 将 List<int> 转换为 Uint8List
final Uint8List uint8Payload = Uint8List.fromList(intList);
// 调用现有的 calculationCrc 方法
return calculationCrc(uint8Payload);
}
// 将字符串转换为 Uint8List
static Uint8List _stringToUint8List(String input) {
return Uint8List.fromList(utf8.encode(input));
}
// 自定义 CRC32 实现
static int _crc32Uint16(Uint8List data) {
const int polynomial = 0xD5828281;
// 创建 CRC32 表
final List<int> table = List<int>.generate(256, (i) {
int crc = i;
for (int j = 0; j < 8; j++) {
if ((crc & 1) != 0) {
crc = (crc >> 1) ^ polynomial;
} else {
crc >>= 1;
}
}
return crc;
});
// 计算 CRC32 校验值
int crc = 0xFFFFFFFF;
for (final int byte in data) {
crc = (crc >> 8) ^ table[(crc ^ byte) & 0xFF];
}
crc ^= 0xFFFFFFFF;
// 返回 CRC32 的低 16 位
return crc & 0xFFFF;
}
2024-11-28 14:57:49 +08:00
}