BTCTrader / broker-api-docs

The documentation for BTCTrader's white label exchange platform API. Use this documentation to access the APIs of BTCTurk other BTCTrader partners.

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Private Socket Messages

fatihmecidiye opened this issue · comments

.NETCore kullanarak geliştirdiğim projede websockete bağlanmak ve login olmak için gönderdiğim mesajlar sonrasında aşağıdaki yanıtları alıyorum. Ancak private socket mesajlarını (UserTrade, OrderInsert, OrderDelete vb.) alamıyorum. Trade channelına subscribe olduğumda ise public trade mesajları geliyor. Doğru şekilde private channellara subscribe olma konusunda yardımcı olursanız sevinirim.

[991,{"type":991,"current":"6.0.0","min":"2.3.0"}]
[114,{"type":114,"id":586 9906,"ok":true,"message":null}]
private readonly string _apiKey;
    private readonly string _secretKey;
    private readonly IMediator _mediator;

    public BtcTurkPrivateWebsocket(string apiKey, string secretKey, IMediator mediator)
    {
        _apiKey = apiKey;
        _secretKey = secretKey;
        _mediator = mediator;
    }

    public async Task Initialize()
    {
        Task.Run(() =>
        {
            while (true)
            {
                Task.Delay(TimeSpan.FromSeconds(3)).Wait();

                try
                {
                    GetPrivateSocketMessages().Wait();
                }
                catch (Exception e)
                {
                    LoggingUtility.LogException(e);
                    //log here
                }
            }
        }).Wait();
    }

    private async Task GetPrivateSocketMessages()
    {
        Uri uri = new Uri("wss://ws-feed-pro.btcturk.com");
        ClientWebSocket client = new ClientWebSocket();

        await client.ConnectAsync(uri, CancellationToken.None);

        string publicKey = _apiKey;
        string privateKey = _secretKey;
        long nonce = 20000;
        string baseString = $"{publicKey}{nonce}";
        string signature = ComputeHash(privateKey, baseString);
        long timestamp = ToUnixTime(DateTime.UtcNow);
        object[] hmacMessageObject = { 114, new { type = 114, publicKey = publicKey, timestamp = timestamp, nonce = nonce, signature = signature } };
        string message = JsonSerializer.Serialize(hmacMessageObject);

        await client.SendAsync(buffer: new ArraySegment<byte>(array: Encoding.UTF8.GetBytes(message),
                offset: 0,
                count: message.Length),
            messageType: WebSocketMessageType.Text,
            endOfMessage: true,
            cancellationToken: CancellationToken.None);

        while (true)
        {
            try
            {
                string resultMessage = await ReceiveMessageAsync(client);
                Console.WriteLine(resultMessage);
                int? messageId = SocketMessageId(resultMessage);

                if (messageId == null || messageId == 991)
                {
                    continue;
                }

                if (messageId == 114)
                {
                    UserLogin? userLoginResult = await GetResponseAsync<UserLogin>(resultMessage);
                    if (!userLoginResult.Ok)
                    {
                        throw new ApplicationException("Problem occurred during authentication.");
                    }
                }

                switch (messageId)
                {
                    case 423:
                        UserTrade? userTrade = await GetResponseAsync<UserTrade>(resultMessage);
                        //Message handlers for private socket messages
                        //BtcTurkAPI > Handlers > UserTradeHandler
                        await _mediator.Publish(userTrade);
                        break;

                    case 441:
                        OrderMatched? orderMatched = await GetResponseAsync<OrderMatched>(resultMessage);
                        await _mediator.Publish(orderMatched);
                        break;

                    case 451:
                        OrderInserted? orderInserted = await GetResponseAsync<OrderInserted>(resultMessage);
                        await _mediator.Publish(orderInserted);
                        break;

                    case 452:
                        OrderDeleted? orderDeleted = await GetResponseAsync<OrderDeleted>(resultMessage);
                        await _mediator.Publish(orderDeleted);
                        break;

                    case 453:
                        OrderUpdated? orderUpdated = await GetResponseAsync<OrderUpdated>(resultMessage);
                        await _mediator.Publish(orderUpdated);
                        break;
                }
            }
            catch (Exception e)
            {
                // log here
                break;
            }
        }
    }

    private static string ComputeHash(string privateKey, string baseString)
    {
        var key = Convert.FromBase64String(privateKey);
        string hashString;

        using (var hmac = new HMACSHA256(key))
        {
            var hash = hmac.ComputeHash(Encoding.UTF8.GetBytes(baseString));
            hashString = Convert.ToBase64String(hash);
        }

        return hashString;
    }

    private static long ToUnixTime(DateTime date)
    {
        var epoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc);
        return Convert.ToInt64((date - epoch).TotalMilliseconds);
    }

    private async Task<string> ReceiveMessageAsync(ClientWebSocket client)
    {
        byte[] buffer = new byte[1024 * 16];

        WebSocketReceiveResult result;
        StringBuilder resultMessageBuilder = new StringBuilder();

        do
        {
            result = await client.ReceiveAsync(new ArraySegment<byte>(buffer), CancellationToken.None);
            string bufferMessage = Encoding.UTF8.GetString(buffer, 0, result.Count);

            resultMessageBuilder.Append(bufferMessage);
        } while (!result.EndOfMessage);

        return resultMessageBuilder.ToString();
    }

    private int? SocketMessageId(string resultMessage)
    {
        if (string.IsNullOrWhiteSpace(resultMessage))
        {
            return null;
        }

        JArray resultArray = JArray.Parse(resultMessage);

        if (resultArray.Count == 0)
        {
            return 0;
        }

        return resultArray.First().Value<int>();
    }

    private Task<T?> GetResponseAsync<T>(string resultMessage)
    {
        JArray resultArray = JArray.Parse(resultMessage);

        if (resultArray.Count == 0)
        {
            return Task.FromResult<T?>(default);
        }

        return Task.FromResult(resultArray.Last().ToObject<T>());
    }