import 'package:proto_socket/proto_socket.dart';
import '../gen/proto/iop/control.pb.dart';
import 'parser_map.dart';

class ClientWireClient extends WsProtobufClient {
  ClientWireClient(
    dynamic ws, {
    int heartbeatIntervalTime = 5000,
    int heartbeatWaitTime = 5000,
  }) : super(
         ws,
         heartbeatIntervalTime,
         heartbeatWaitTime,
         Map.from(clientParserMap),
       );

  /// Connect to the Control Plane Wire endpoint and return a ClientWireClient.
  static Future<ClientWireClient> connect(
    String host,
    int port, {
    String path = '/client',
    bool secure = false,
  }) async {
    final ws = secure
        ? await WsProtobufClient.connectSecure(host, port, path: path)
        : await WsProtobufClient.connect(host, port, path: path);
    return ClientWireClient(ws);
  }

  /// Parse a full WebSocket URL and connect.
  static Future<ClientWireClient> connectToUrl(String urlString) async {
    final uri = Uri.parse(urlString);
    final host = uri.host.isEmpty ? 'localhost' : uri.host;
    final isSecure = uri.scheme == 'wss';
    final defaultPort = isSecure ? 443 : 80;
    final port = uri.hasPort ? uri.port : defaultPort;
    final path = uri.path.isEmpty ? '/' : uri.path;

    final ws = isSecure
        ? await WsProtobufClient.connectSecure(host, port, path: path)
        : await WsProtobufClient.connect(host, port, path: path);
    return ClientWireClient(ws);
  }

  /// Sends a Hello request to the Control Plane.
  Future<ClientHelloResponse> hello({
    required String clientId,
    required String clientVersion,
    Duration timeout = const Duration(seconds: 3),
  }) async {
    return await sendRequest<ClientHelloRequest, ClientHelloResponse>(
      ClientHelloRequest()
        ..clientId = clientId
        ..clientVersion = clientVersion,
      timeout: timeout,
    );
  }
}
