添加websocket支持

hmxc
张萌 3 years ago
parent b111df6e2f
commit c83d98dc28

@ -26,6 +26,7 @@ void main() async {
MainInitialize.initTheme();
await MainInitialize.initJPush();
MainInitialize.initWechat();
MainInitialize.initWebSocket();
runApp(MyApp());
}

@ -1,5 +1,7 @@
import 'dart:io';
import 'package:aku_community/utils/websocket/fire_dialog.dart';
import 'package:aku_community/utils/websocket/web_socket_util.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
@ -76,4 +78,16 @@ class MainInitialize {
if (kIsWeb || Platform.isMacOS) return;
registerWxApi(appId: AppConfig.wechatAppId);
}
static initWebSocket() {
WebSocketUtil().initWebSocket(
consolePrint: false,
onReceiveMes: (message) async {
await FireDialog.fireAlarm(message);
},
onError: (e) {
LoggerData.addData(e);
},
);
}
}

@ -27,6 +27,7 @@ class _OpeningCodePageState extends State<OpeningCodePage> {
late String _qrCode;
late bool _overDate;
late EasyRefreshController _refreshController;
static const int seconds = 300; //
Timer? _overDateTimer;
@override
void initState() {
@ -46,7 +47,8 @@ class _OpeningCodePageState extends State<OpeningCodePage> {
await NetUtil().get(API.manager.getDoorQrCode, params: {
"startTime":
DateUtil.formatDate(_currentTime, format: 'yyyy/MM/dd HH:mm:ss'),
"endTime": DateUtil.formatDate(_currentTime.add(Duration(minutes: 30)),
"endTime": DateUtil.formatDate(
_currentTime.add(Duration(seconds: seconds)),
format: 'yyyy/MM/dd HH:mm:ss'),
});
if ((baseModel.status ?? false) && baseModel.data != null) {
@ -62,12 +64,10 @@ class _OpeningCodePageState extends State<OpeningCodePage> {
}
startTimer() {
_overDateTimer = Timer.periodic(Duration(minutes: 1), (timer) {
if (timer.tick >= 5) {
_overDate = true;
endTimer();
setState(() {});
}
_overDateTimer = Timer.periodic(Duration(seconds: seconds), (timer) {
_overDate = true;
endTimer();
setState(() {});
});
}

@ -1,3 +1,4 @@
import 'package:aku_community/utils/websocket/web_socket_util.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
@ -106,6 +107,7 @@ class _TabNavigatorState extends State<TabNavigator>
return false;
}
//app
WebSocketUtil().closeWebSocket();
return true;
},
child: TabBarView(

@ -1,5 +1,6 @@
import 'dart:io';
import 'package:aku_community/utils/websocket/web_socket_util.dart';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
@ -32,6 +33,8 @@ class UserProvider extends ChangeNotifier {
await updateProfile();
await updateUserDetail();
await appProvider.updateHouses(await HouseFunc.passedHouses);
WebSocketUtil().setUser(userInfoModel!.id.toString());
WebSocketUtil().startWebSocket();
notifyListeners();
}
@ -47,6 +50,7 @@ class UserProvider extends ChangeNotifier {
NetUtil().dio!.options.headers.remove('App-Admin-Token');
HiveStore.appBox!.delete('token');
HiveStore.appBox!.delete('login');
WebSocketUtil().closeWebSocket();
notifyListeners();
}

@ -1,11 +1,8 @@
import 'dart:convert';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:aku_community/utils/websocket/fire_dialog.dart';
import 'package:get/get.dart';
import 'package:aku_community/utils/headers.dart';
class MessageParser {
final Map<String, dynamic> message;
@ -27,34 +24,7 @@ class MessageParser {
switch (type) {
case '1':
await fireAlarm(subTitle);
await FireDialog.fireAlarm(subTitle);
}
}
///
fireAlarm(String content) async {
await Get.dialog(
CupertinoAlertDialog(
title: Text('发生火灾'),
content: Column(
children: [
Text(subTitle),
10.hb,
Icon(
CupertinoIcons.bell_fill,
color: Colors.red,
size: 48.w,
),
],
),
actions: [
CupertinoDialogAction(
child: Text('确认'),
onPressed: () => Get.back(),
),
],
),
barrierDismissible: false,
);
}
}

@ -0,0 +1,33 @@
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:get/get.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:aku_community/extensions/num_ext.dart';
class FireDialog {
static fireAlarm(String content) async {
await Get.dialog(
CupertinoAlertDialog(
title: Text('发生火灾'),
content: Column(
children: [
Text(content),
10.hb,
Icon(
CupertinoIcons.bell_fill,
color: Colors.red,
size: 48.w,
),
],
),
actions: [
CupertinoDialogAction(
child: Text('确认'),
onPressed: () => Get.back(),
),
],
),
barrierDismissible: false,
);
}
}

@ -0,0 +1,208 @@
import 'dart:async';
import 'package:bot_toast/bot_toast.dart';
import 'package:power_logger/power_logger.dart';
import 'package:web_socket_channel/io.dart';
import 'package:web_socket_channel/web_socket_channel.dart';
const String baseUri = 'wss://test.kaidalai.cn/websocket/app';
enum SOCKETSTATUS {
CONNECTED, //
BREAKOFF, //
CLOSED, //
}
class WebSocketUtil {
static final WebSocketUtil _socket = WebSocketUtil._();
//
WebSocketUtil._();
//
factory WebSocketUtil() => _socket;
IOWebSocketChannel? _webSocket;
///
String _user = 'admin';
///
SOCKETSTATUS _socketStatus = SOCKETSTATUS.CLOSED;
///
Timer? _heartTimer;
///
Duration _heartDuration = Duration(seconds: 30);
///
int _reconnectCount = 0;
///
int _reconnectTimes = 30;
///
Timer? _reconnectTimer;
///
Function(dynamic e)? onError;
///
Function? onStart;
///
Function(String message)? onReceiveMes;
///
Function? onClosed;
///
bool _consolePrint = true;
///websocket
void initWebSocket(
{Duration? heartDuration,
bool? consolePrint,
Function? onStart,
Function(String message)? onReceiveMes,
Function? onClosed,
Function(dynamic e)? onError}) {
this.onStart = onStart;
this.onReceiveMes = onReceiveMes;
this.onClosed = onClosed;
this.onError = onError;
if (consolePrint != null) {
this._consolePrint = consolePrint;
}
if (heartDuration != null) {
this._heartDuration = heartDuration;
}
print('——————————webSocket init ——————————');
}
///
void setUser(String user) {
this._user = user;
}
///websocket
void startWebSocket() {
closeWebSocket();
try {
_webSocket = IOWebSocketChannel.connect(Uri.parse('$baseUri/$_user'));
print('webSocket已连接服务器$baseUri/$_user');
_socketStatus = SOCKETSTATUS.CONNECTED;
endReconnect();
onStart?.call();
_webSocket!.stream.listen(
(event) => webSocketReceiveMessage(event as String),
onError: webSocketOnError,
onDone: webSocketClosed);
initHeartBeat();
} catch (e) {
BotToast.showText(text: 'webSocket连接失败');
onError?.call(e);
LoggerData.addData(e);
}
}
//
webSocketReceiveMessage(message) {
if (message == '心跳正常') {
_dPrint('心跳正常————————${DateTime.now()}');
} else {
onReceiveMes?.call(message);
}
}
//
webSocketClosed() {
closeWebSocket();
onClosed?.call();
}
//
webSocketOnError(e) {
WebSocketChannelException ex = e;
_socketStatus = SOCKETSTATUS.BREAKOFF;
onError?.call(ex.message);
print('——————连接断开,开始重连');
startReconnect();
}
//
void startReconnect() {
endReconnect();
_reconnectTimer = Timer.periodic(Duration(milliseconds: 5000), (timer) {
_reconnectCount++;
print('——————第${_reconnectCount}次重连');
startWebSocket();
if (_reconnectCount >= _reconnectTimes) {
print('——————重连失败');
closeWebSocket();
}
});
}
//
void endReconnect() {
_reconnectTimer?.cancel();
_reconnectTimer = null;
_reconnectCount = 0;
}
///
void initHeartBeat() {
destoryHeart();
_heartTimer = Timer.periodic(_heartDuration, (timer) {
sentHeart();
});
}
//
void sentHeart() {
sendMessage('heartbeat');
}
///
void destoryHeart() {
_heartTimer?.cancel();
_heartTimer = null;
}
///websocket
void closeWebSocket() {
if (_webSocket != null) {
_webSocket!.sink.close();
print('——————websocket连接已关闭');
}
endReconnect();
destoryHeart();
_socketStatus = SOCKETSTATUS.CLOSED;
}
///websocket
void sendMessage(message) {
if (_webSocket != null) {
switch (_socketStatus) {
case SOCKETSTATUS.CONNECTED:
_dPrint('发送中:' + message);
_webSocket!.sink.add(message);
break;
case SOCKETSTATUS.CLOSED:
print('连接已关闭');
break;
case SOCKETSTATUS.BREAKOFF:
print('发送失败');
break;
default:
break;
}
}
}
//print
void _dPrint(dynamic data) {
if (this._consolePrint) {
print(data);
}
}
}

@ -36,6 +36,8 @@ dependencies:
#用户存储路径
path_provider: ^2.0.1
#webscoket
web_socket_channel: ^2.1.0
#支付宝支付功能
tobias: ^2.1.0

Loading…
Cancel
Save