import 'dart:convert'; import 'dart:io'; import 'package:web_socket_channel/web_socket_channel.dart'; import 'package:web_socket_channel/status.dart' as status; import 'package:flutter/scheduler.dart'; import "dart:async"; import 'package:flutter/src/foundation/print.dart'; class CustomWSChannel { /* created custom class for web socket handler with support for reconnect */ late WebSocketChannel channel; // to store the websocketchannel bool isAlive = false; // boolean flag to check if we are connected to the websocket bool isConnected = false; int reconnectAttempts = 0; // to keep track of how many times we have tried to reconnect late Uri serverUri; int delay; // to set amount of delay between reconnects int pingInterval; // pings to the server after every pingInterval time and if pong is not received close the socket Timer pingScheduler=Timer(Duration.zero, () { }); void Function(dynamic) onMessage; // function which is called everytime we receive an message from the server void Function(String, dynamic) onErrorShowMessage; // triggered everytime an error occur void Function() onConnect; // function which is called everytime we are connected to the server CustomWSChannel(serverUrl, {this.delay = 5, this.pingInterval = 5000, required this.onConnect, required this.onMessage, required this.onErrorShowMessage}) { serverUri = Uri.parse(serverUrl); connect(); } get sink => channel.sink; get ready => channel.ready; // Future isConnected() async{ // try{ // await channel.ready; // return true; // } // catch(e){ // debugFn("we are not connected"); // return false; // } // } void ping() { // send ping // channel. channel.sink.add(jsonEncode({"route": "get_pong"})); } void handlepong() { // isAlive = true; isConnected = true; } void onDone() async { isConnected = false; isAlive = false; debugPrint("onDone called"); pingScheduler.cancel(); await channel.sink.close(); debugFn("Reconnecting in $delay seconds, attempt $reconnectAttempts "); // channel = null; await Future.delayed(Duration(seconds: delay)); connect(); } void onError(error) { debugFn("Error while connecting.", e: error); reconnectAttempts += 1; } void connect() async { final Timer connectTimeout; try { channel = WebSocketChannel.connect(serverUri); channel.stream.listen(onMessage, onDone: onDone, onError: onError); // channel.stream.listen(onMessage, onError:onError); connectTimeout = Timer(const Duration(seconds: 5),(){ debugPrint('connectTimeout'); channel.sink.close(); // channel. // onDone(); }); debugPrint('before channel.ready'); await channel.ready; debugPrint('after channel.ready'); connectTimeout.cancel(); // await channel.sink.done; // await channel.stream.drain(); // channel.stream. debugPrint('Reconnected successfully'); // isAlive = true; // isConnected = true; // onConnect(); // pingScheduler = // Timer.periodic(Duration(milliseconds: pingInterval), (timer) async { // if(isAlive==false) return onDone(); // ping(); // // set isAlive False // isAlive = false; // }); } catch (e) { debugFn("can't connect to the server", e: e); } } void debugFn(String s, {e = ""}) { // print("space"); // print("Custom Message:"+s); // print("Custom Error:"+e.toString()); onErrorShowMessage(s, e); } }