예제 #1
0
        private void MinuteCandleByTicks()
        {
            // 설정값
            var coinName    = Coin.Ticker;
            var candleType  = CandleType.Name;
            var candleCount = CandleCount;
            var feeRate     = FeeRate;
            var tradeRate   = TradeRate;
            var triggerRate = TriggerRate;

            // 해당 코인 보유금액이 있으면 매도 없으면 매수
            var candles = ApiData.getCandle <List <Candle> >(coinName, candleType, candleCount);   // 캔들 조회
            //var currCandle = candles.First();                                                 // 현재 캔들
            //var currPrice = currCandle.Close;                                                 // 현재가
            var ticker    = ApiData.getTicker(coinName).FirstOrDefault();
            var currPrice = (ticker != null) ? ticker.Value <double>("trade_price") : 0D;        // 현재가

            //var orderChance = GetOrderChance(ApiData, coinName, currPrice);                   // 주문 가능 정보
            var orderChance    = GetBalance(ApiData, coinName, currPrice, StartKRW);
            var krwBalance     = orderChance.KRWBalance;                                        // 보유 현금
            var coinBalance    = orderChance.CoinBalance;                                       // 코인 보유금
            var coinVol        = orderChance.CoinVol;                                           // 보유 코인 수량
            var avgPrice       = orderChance.AvgBuyPrice;                                       // 매수 평단가
            var coinBuyBalance = avgPrice * coinVol;                                            // 코인 매수금
            var minTradeKRW    = Settings.Default.minTradeKRW;                                  // 최소 거래 금액

            // 분봉 N개를 기준으로 직전 시가 에서 현재 금액 등낙률을 가져온다.
            var prevCandle    = candles[1];                                                     // 직전 캔들
            var lastCandle    = candles.Last();                                                 // 마지막 캔들
            var prevPrice     = prevCandle.Low;                                                 // 직전저가
            var highPrice     = candles.GetRange(1, candles.Count - 1).Max(x => x.High);        // 최고가
            var changePrice   = (currPrice - prevPrice);                                        // 변동가
            var changeRate    = (changePrice / currPrice) * 100;                                // 변동율
            var candlesChange = (currPrice - highPrice);                                        // 캔들 변동가
            var candlesRate   = (candlesChange / highPrice) * 100;                              // 캔들 변동율
            var profit        = coinBalance - coinBuyBalance;                                   // 수익
            //var tradeProfitRate = (avgPrice == 0) ? 0D : (profit / avgPrice) * 100;           // 수익율
            var targetProfit = coinBuyBalance + (coinBuyBalance * ((triggerRate / candleCount) + (feeRate * 2)) / 100);
            //var targetPrice = avgPrice + targetProfit;
            //var target = coinBuyPrice

            var result  = null as JObject;
            var args    = new object[] { coinName, currPrice, prevPrice, highPrice, changeRate, candlesRate, avgPrice, targetProfit };
            var buyTs   = DateTime.Now - LastBuyDate;
            var sellTs  = DateTime.Now - LastSellDate;
            var minutes = sellTs.TotalMinutes;

            WriteCurrent("{0} : 현재가 {1:N0}, 직전가 {2:N0}, 시작가 {3:N0}, 직전등락폭 {4:F6}, 등락폭 {5:F6}, 평단가 {6:N0}, 목표가 {7:N0}", args);

            if (StartKRW < minTradeKRW && krwBalance > minTradeKRW && coinBalance < minTradeKRW)
            {
                // 거래 시작 금액
                StartKRW = krwBalance;
            }

            try
            {
                if (coinBalance <= minTradeKRW && krwBalance <= minTradeKRW)
                {
                    // 보유현금과 보유 코인이 최소 거래금액 보다 적으면 거래 없음
                    WriteLog("#### 거래 불가 : 보유현금 {0}, 코인보유금 {1}, 최소 거래 금액 {2},", krwBalance, coinBalance, minTradeKRW);
                }
                else if (krwBalance > minTradeKRW &&
                         sellTs.TotalSeconds >= CandleType.Minute * 60 / 2 &&
                         candlesRate <= -(triggerRate + (feeRate * 2)) &&
                         changeRate >= (feeRate * 2))
                {
                    // BUY
                    // 보유현금이 최소 거래금액 보다 많음
                    // 수익율 초과하여 떨어지다 수수료율 2배 이상 상승 했을때 거래비율 만큼 산다.
                    var total = ToOrderPrice(krwBalance);
                    result      = React.executeDeal(true, false, coinName, 0, 0, total);
                    LastBuyDate = DateTime.Now;
                    WriteLog("#### {0} BUY : 금액 {1:N0}, 수량 {2:F6}", coinName, total, total / currPrice);
                }
                else if (coinBalance > minTradeKRW &&
                         (buyTs.TotalSeconds >= CandleType.Minute * 60 * candleCount / 2 ||
                          targetProfit <= coinBalance))
                {
                    // SELL
                    // 코인평가금 최소 거래금액 보다 많음
                    // 분봉 하나의 시간이 지나면 시장가에 전체 매도
                    // 현재가가 평단가 보다 (수익율/캔들수 + 수료율2배) 이상일때 전체 매도
                    var vol = coinVol;
                    vol          = Math.Truncate(vol * 100000) / 100000;
                    result       = React.executeDeal(false, false, coinName, vol, 0, 0);
                    LastSellDate = DateTime.Now;
                    WriteLog("#### {0} SELL : 금액 {1:N0}, 수량 {2:F6}", coinName, vol * currPrice, vol);
                }
            }
            catch (Exception ex)
            {
                WriteLog(ex.StackTrace);
            }

            if (result != null)
            {
                var uuid       = result.Value <string>("uuid");
                var coinProfit = GetOrderResult(ApiData, uuid, coinName, currPrice, StartKRW);

                //WriteLog("#### RESULT : {0}", result.ToString());

                //var coinProfit = GetBalance(ApiData, coinName, StartKRW);

                //txtProfitPrice.Text = coinProfit.KrwProfit.ToString("N0");
                //txtProfitRate.Text = coinProfit.KrwProfitRate.ToString("F6");
                var profits = new object[] { coinName, StartKRW, coinProfit.TotalBalance, coinProfit.KrwProfit, coinProfit.KrwProfitRate };
                WriteLog("#### {0} 수익 : 거래시작금액 {1:N0}, 현재평가 금액 {2:N0}, 수익금액 {3:N0}, 수익율 {4:F6}", profits);
            }
        }