From d0afe28486e583f1345fd5f36050d74c31d6f373 Mon Sep 17 00:00:00 2001 From: Toki Date: Sat, 1 Feb 2025 17:42:50 +0900 Subject: [PATCH] =?UTF-8?q?base=20socket=20class=20=EC=B6=94=EA=B0=80?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- lib/socket/socket_client.dart | 116 +++++++++++++++++++++++++++ lib/socket/web_socket_connector.dart | 15 ++++ pubspec.yaml | 1 + 3 files changed, 132 insertions(+) create mode 100644 lib/socket/socket_client.dart create mode 100644 lib/socket/web_socket_connector.dart diff --git a/lib/socket/socket_client.dart b/lib/socket/socket_client.dart new file mode 100644 index 0000000..b2b71b4 --- /dev/null +++ b/lib/socket/socket_client.dart @@ -0,0 +1,116 @@ +import 'dart:async'; +import 'dart:io'; +import 'dart:convert'; +import 'dart:typed_data'; + +class SocketClient { + SocketClient(this._ipAddress, this._port); + + static const int headerSize = 10; + static const int intSize = 4; + late final String _ipAddress; + late final int _port; + late Socket? _socket; + late List _byteList = []; + late int _total = -1; + + late Function? eventDisconnected; + late Function(String) eventReceiveMessage; + + void connect([void Function(bool result)? resultListener]) { + bool connected = false; + Socket.connect(_ipAddress, _port).then((socket) { + try { + _socket = socket; + _socket!.listen(_onMessage, onError: _onError, onDone: _onDone); + print('[SocketClient] Socket connected to $_ipAddress'); + connected = true; + } catch (e) { + print(e); + } + resultListener??(connected); + // ignore: argument_type_not_assignable_to_error_handler + }).catchError((AsyncError e) { + print('Unable to connect: $e'); + resultListener??(connected); + }); + } + + //extra: 6bytes의 커스텀 정보, 서버와 프로토콜이 맞춰져있어야함 + void send(String message, [List? extra]) { + final byteMessage = utf8.encode(message); + // final byteLength = ByteArray(4); + // byteLength.writeInt(byteMessage.length); + // final byteArray = byteLength.buffer.asUint8List(0, 4); + final byteLength = Uint8List(4); + final byteDataLength = byteLength.buffer.asByteData(); + byteDataLength.setInt32(0, byteMessage.length); + final byteArray = byteLength.buffer.asUint8List(0, 4); + final byteExtra = extra == null ? [0, 0, 0, 0, 0, 0] : extra; + final byteSend = byteArray + byteExtra + byteMessage; + _socket!.add(byteSend); + } + + void disconnect() { + eventDisconnected??(); + _socket!.close(); + _socket = null; + } + + void _onMessage(data) { + final byteData = data as Uint8List; + try { + final bytesRead = byteData.length; + //print('Data Recevied!! $bytesRead'); + + if (bytesRead > 0) { + _byteList += byteData; + } + _parsing(); + } on Exception catch (e) { + print(e); + print(utf8.decode(byteData)); + } + } + + void _parsing() { + if (_total < 0) { + if (_byteList.length >= headerSize) { + final bytesLength = Uint8List.fromList( + _byteList.getRange(0, intSize).toList(growable: false)); + final bytesExtra = Uint8List.fromList( + _byteList.getRange(intSize, headerSize).toList(growable: false)); + _total = bytesLength.buffer.asByteData().getInt32(0, Endian.big); + // _total = ByteArray.fromBuffer(bytesLength.buffer).readInt(); + print(_total); + if (_total == 0) { + _total = -1; + _byteList.clear(); + } else { + _parsing(); + } + } + } else { + if (_byteList.length >= _total + headerSize) { + _byteList.removeRange(0, headerSize); + final list = Uint8List.fromList( + _byteList.getRange(0, _total).toList(growable: false)); + final message = utf8.decode(list); + //print(message); + if (eventReceiveMessage != null) eventReceiveMessage(message); + _byteList = _byteList.getRange(_total, _byteList.length).toList(); + _total = -1; + _parsing(); + } + } + } + + void _onError(error, StackTrace trace) { + print('onError: $error'); + } + + void _onDone() { + print('Disconnected'); + eventDisconnected??(); + } +} diff --git a/lib/socket/web_socket_connector.dart b/lib/socket/web_socket_connector.dart new file mode 100644 index 0000000..f537bd7 --- /dev/null +++ b/lib/socket/web_socket_connector.dart @@ -0,0 +1,15 @@ +import 'package:web_socket_channel/html.dart'; + +class WebSocketConnector { + late HtmlWebSocketChannel _socket; + + Future connect() async { + _socket = + HtmlWebSocketChannel.connect('ws://127.0.0.1:9090/ws/view/'); + _socket.stream.listen((message) async { + print('Received message from server'); + print(message); + _socket.sink.add('this is from flutter'); + }); + } +} diff --git a/pubspec.yaml b/pubspec.yaml index 56a2973..306ab86 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -18,6 +18,7 @@ dependencies: color: ^3.0.0 protobuf: ^3.1.0 encrypt: ^5.0.3 + web_socket_channel: ^3.0.2 # subtitle_wrapper_package: ^2.1.1 # equatable: ^2.0.5