Beispiel #1
0
        //获取主账户最大可下单数量
        public static int GetAccountCount(Order order)
        {
            Account account = AccountRA.Get("A_" + order.account_id);

            if (order.type_enum == OrderTypeEnum.Buy && !string.IsNullOrWhiteSpace(account.limit_no_buying) && account.limit_no_buying.Contains(order.code))
            {
                return(0);
            }

            if (account.status_enum == StatusEnum.Forbidden)
            {
                return(0);
            }
            if (account.status_order_enum == StatusOrderEnum.Forbidden)
            {
                return(0);
            }
            if (order.type_enum == OrderTypeEnum.Buy && account.status_order_enum == StatusOrderEnum.NoBuying)
            {
                return(0);
            }

            if (order.type_enum == OrderTypeEnum.Buy)
            {
                decimal count = account.capital_initial / order.price;
                if (account.limit_ratio_single > 0)
                {
                    count = Math.Min(count, account.capital_initial * account.limit_ratio_single / order.price);
                }

                BlockInfo block = StockInfoBiz.GetBlock(order.code);
                if (block.block_type_enum == BlockEnum.gem)
                {
                    if (account.limit_ratio_gem_single > 0)
                    {
                        count = Math.Min(count, account.capital_initial * account.limit_ratio_gem_single / order.price);
                    }
                    if (account.limit_ratio_gem_total > 0)
                    {
                        count = Math.Min(count, (account.capital_initial * account.limit_ratio_gem_total - account.capital_stock_value_gem) / order.price);
                    }
                }

                string[]         keys = TradeRA.KeySearch("G_*_U_" + order.unit_id + "_A_" + order.account_id);
                AccountGroupItem item = AccountGroupRA.Get(keys[0]);
                if (item.capital_available > 0)
                {
                    count = Math.Min(count, (item.capital_available - item.capital_stock_value) / order.price);
                }
                return((int)Math.Ceiling(count / 100) * 100);
            }
            else
            {
                return(PositionRA.GetSellable(order.unit_id, order.code, order.account_id));
            }
        }
Beispiel #2
0
        public void Order(Order order)
        {
            string request_id = FuncHelper.GetUniqueID().ToString();

            order.account_id = account_id;
            order.name       = StockInfoBiz.GetStock(order.code).name;
            order.time_dt    = DateTime.Now;
            OrderRA.Add(order, "O_" + request_id + "_T_" + order.trade_no + "_U_" + order.unit_id + "_F");

            JY.Order(new JY.Order(order.code, order.type, order.count, order.price, request_id));
            MonitorRA.Increment("account_" + account_id, "order_count");
        }
Beispiel #3
0
        public static void Close()
        {
            TradeBiz.Stop();
            HQBiz.Save();
            SaveOrder();

            Dictionary <int, decimal[]> dic = new Dictionary <int, decimal[]>();

            SaveDeal(ref dic);
            SavePosition();
            SaveAccountCapital();
            SaveUnitCapital(dic);

            StockInfoBiz.RefreshBlockList();
        }
Beispiel #4
0
        //检查系统和用户是否满足下单条件
        public static ApiResultEnum CheckStatus(Order model)
        {
            StatusOrderEnum status_order = (StatusOrderEnum)int.Parse(UserRA.Get(model.user_id.ToString(), "status_order"));

            if (status_order == StatusOrderEnum.Forbidden)
            {
                return(ApiResultEnum.Order_User_Forbidden_Order);
            }
            if (model.type_enum == OrderTypeEnum.Buy && status_order == StatusOrderEnum.NoBuying)
            {
                return(ApiResultEnum.Order_User_NoBuying_Order);
            }

            StatusTradeEnum status_trade = (StatusTradeEnum)MonitorRA.GetStatusTrade();

            if (status_trade == StatusTradeEnum.Closed)
            {
                return(ApiResultEnum.Order_Closed);
            }
            else if (status_trade == StatusTradeEnum.Pause)
            {
                return(ApiResultEnum.Order_Paused);
            }

            BlockInfo block = StockInfoBiz.GetBlock(model.code);

            if (block == null)
            {
                return(ApiResultEnum.Order_Code_Error);
            }
            if (model.price == 0)
            {
                return(ApiResultEnum.Order_Price_Error);
            }
            if (model.count == 0)
            {
                return(ApiResultEnum.Order_Count_Error);
            }

            return(ApiResultEnum.Success);
        }
Beispiel #5
0
        public static void AdjustPosition(Position position, Deal deal, decimal order_price, int type)
        {
            string key_unit     = "U_" + deal.unit_id;
            string key_position = "P_" + deal.code + "_A_" + deal.account_id + "_U_" + deal.unit_id;

            //更新单元余额和冻结
            if (deal.type_enum == OrderTypeEnum.Buy)
            {
                UnitRA.UpdateCapitalDealBuy(order_price * deal.count, type == 0, key_unit);
            }
            else if (deal.type_enum == OrderTypeEnum.Sell)
            {
                UnitRA.UpdateCapitalDealSell(deal.price * deal.count, key_unit);
            }

            //更新持仓
            decimal amount = deal.money + deal.commission;

            if (position != null)
            {
                if (deal.type == 0)
                {
                    position.price_cost = Math.Round((position.price_cost * position.count + amount) / (deal.count + position.count), 6);
                    position.count      = position.count + deal.count;
                    if (type == 0 || type == 1)
                    {
                        position.price_cost_today_buy = Math.Round((amount + position.price_cost_today_buy * position.count_today_buy) / (deal.count + position.count_today_buy), 6);
                        position.count_today_buy      = deal.count + position.count_today_buy;
                    }
                    PositionRA.UpdateBuy(position, key_position);
                }
                else
                {
                    position.count = position.count - deal.count;
                    if (type == 0 || type == 1)
                    {
                        position.price_cost_today_sell = Math.Round((amount + position.price_cost_today_sell * position.count_today_sell) / (deal.count + position.count_today_sell), 6);
                        position.count_today_sell      = deal.count + position.count_today_sell;
                    }
                    PositionRA.UpdateSell(position, key_position);
                }
            }
            else
            {
                HQItem    hq    = HQService.Get(deal.code);
                BlockInfo block = StockInfoBiz.GetBlock(deal.code);
                if (block == null)
                {
                    return;
                }

                position = new Position()
                {
                    code         = deal.code,
                    name         = deal.name,
                    unit_id      = deal.unit_id,
                    account_id   = deal.account_id,
                    block_enum   = block.block_type_enum,
                    price_latest = hq != null ? hq.Last : 0
                };
                if (deal.type == 0)
                {
                    position.price_cost = Math.Round(amount / deal.count, 6);
                    position.count      = deal.count;
                    if (type == 0 || type == 1)
                    {
                        position.price_cost_today_buy = position.price_cost;
                        position.count_today_buy      = position.count;
                    }
                    else if (type == 2)
                    {
                        position.count_sellable = position.count;
                    }
                }
                else
                {
                    position.price_cost = Math.Round(amount / deal.count, 6);
                    position.count      = position.count_sellable = -deal.count;
                    if (type == 0 || type == 1)
                    {
                        position.price_cost_today_sell = position.price_cost;
                        position.count_today_sell      = deal.count;
                    }
                }
                PositionRA.Add(position, key_position);
            }
            RunCalculateValue();
        }
Beispiel #6
0
        public static ApiResultEnum Order(Order order)
        {
            ApiResultEnum result = LimitBiz.CheckStatus(order);

            if (result != ApiResultEnum.Success)
            {
                return(result);
            }
            result = LimitBiz.CheckUnit(order);
            if (result != ApiResultEnum.Success)
            {
                return(result);
            }

            Dictionary <int, int> order_items;

            if (order.account_id == 0)
            {
                order_items = LimitBiz.GetOrderAccount(order);
            }
            else
            {
                order_items = new Dictionary <int, int>()
                {
                    { order.account_id, order.count }
                }
            };
            if (order_items.Count == 0)
            {
                return(ApiResultEnum.Order_Unit_No_Account);
            }
            if (order_items.Sum(i => i.Value) == 0)
            {
                return(ApiResultEnum.Order_Group_Negative_Amount);
            }

            int order_count = 0;

            order.trade_no    = FuncHelper.GetUniqueID().ToString();
            order.trade_count = order.count;
            foreach (var kvp in order_items)
            {
                if (kvp.Value == 0)
                {
                    continue;
                }

                order.account_id = kvp.Key;
                order.count      = kvp.Value;
                result           = LimitBiz.CheckAccount(order);
                if (result != ApiResultEnum.Success)
                {
                    continue;
                }

                BlockInfo block = StockInfoBiz.GetBlock(order.code);
                order.price = Math.Round(order.price, block.@decimal);
                jybizs[order.account_id].Order(order);
                order_count += order.count;
            }

            if (order_count == 0)
            {
                return(result);
            }
            if (order_count < order.count)
            {
                return(ApiResultEnum.Success_Portion);
            }
            return(ApiResultEnum.Success);
        }
Beispiel #7
0
        //检查单元是否满足下单条件
        public static ApiResultEnum CheckUnit(Order order)
        {
            Unit unit = UnitRA.Get("U_" + order.unit_id);

            if (unit == null || unit.user_id != order.user_id)
            {
                return(ApiResultEnum.Order_Unit_Null);
            }

            if (order.type_enum == OrderTypeEnum.Buy && !string.IsNullOrWhiteSpace(unit.limit_no_buying) && unit.limit_no_buying.Contains(order.code))
            {
                return(ApiResultEnum.Order_Unit_NoBuying_Code);
            }

            if (unit.status_enum == StatusEnum.Forbidden)
            {
                return(ApiResultEnum.Order_Unit_Forbidden);
            }
            if (unit.status_order_enum == StatusOrderEnum.Forbidden)
            {
                return(ApiResultEnum.Order_Unit_Forbidden_Order);
            }
            if (order.type_enum == OrderTypeEnum.Buy && unit.status_order_enum == StatusOrderEnum.NoBuying)
            {
                return(ApiResultEnum.Order_Unit_NoBuying_Order);
            }

            string[] keys = TradeRA.KeySearch("P_" + order.code + "_A_*_U_" + order.unit_id);
            if (unit.limit_stock_count > 0)
            {
                if (PositionRA.GetCodeCount(order.unit_id, order.code) > unit.limit_stock_count)
                {
                    return(ApiResultEnum.Order_Unit_Limit_Count);
                }
            }

            if (unit.limit_order_price_enum == OrderPriceLimitEnum.In5LeverPrice)
            {
                decimal price_min = DataBiz.GetPriceByPriceType(order.code, OrderPriceEnum.Buy5);
                decimal price_max = DataBiz.GetPriceByPriceType(order.code, OrderPriceEnum.Sell5);
                if (order.price < price_min || order.price > price_max)
                {
                    return(ApiResultEnum.Order_Unit_Limit_Price);
                }
            }

            if (order.type_enum == OrderTypeEnum.Buy)
            {
                if (unit.capital_available < order.price * order.count)
                {
                    return(ApiResultEnum.Order_Unit_Negative_Amount);
                }

                BlockInfo block = StockInfoBiz.GetBlock(order.code);
                if (block.block_type_enum == BlockEnum.mbm)
                {
                    if (unit.limit_ratio_mbm_single > 0 && order.price * order.count > unit.capital_scale * unit.limit_ratio_mbm_single)
                    {
                        return(ApiResultEnum.Order_Unit_Limit_MBM_Single);
                    }
                }
                else if (block.block_type_enum == BlockEnum.gem)
                {
                    if (unit.limit_ratio_gem_single > 0 && order.price * order.count > unit.capital_scale * unit.limit_ratio_gem_single)
                    {
                        return(ApiResultEnum.Order_Unit_Limit_GEM_Single);
                    }
                    if (unit.limit_ratio_gem_total > 0 && order.price * order.count + unit.capital_stock_value_gem > unit.capital_scale * unit.limit_ratio_gem_total)
                    {
                        return(ApiResultEnum.Order_Unit_Limit_GEM_Total);
                    }
                }
                else if (block.block_type_enum == BlockEnum.sme)
                {
                    if (unit.limit_ratio_sme_single > 0 && order.price * order.count > unit.capital_scale * unit.limit_ratio_sme_single)
                    {
                        return(ApiResultEnum.Order_Unit_Limit_SME_Single);
                    }
                    if (unit.limit_ratio_sme_total > 0 && order.price * order.count + unit.capital_stock_value_sme > unit.capital_scale * unit.limit_ratio_sme_total)
                    {
                        return(ApiResultEnum.Order_Unit_Limit_SME_Total);
                    }
                }
                else if (block.block_type_enum == BlockEnum.star)
                {
                    if (unit.limit_ratio_star_single > 0 && order.price * order.count > unit.capital_scale * unit.limit_ratio_star_single)
                    {
                        return(ApiResultEnum.Order_Unit_Limit_STAR_Single);
                    }
                    if (unit.limit_ratio_star_total > 0 && order.price * order.count + unit.capital_stock_value_star > unit.capital_scale * unit.limit_ratio_star_total)
                    {
                        return(ApiResultEnum.Order_Unit_Limit_STAR_Total);
                    }
                }
                if (block.block_type_enum == BlockEnum.sme || block.block_type_enum == BlockEnum.gem)
                {
                    if (unit.limit_ratio_smg_total > 0 && order.price * order.count + unit.capital_stock_value_sme + unit.capital_stock_value_gem > unit.capital_scale * unit.limit_ratio_smg_total)
                    {
                        return(ApiResultEnum.Order_Unit_Limit_SMG_Total);
                    }
                }
            }
            else
            {
                if (PositionRA.GetSellable(order.unit_id, order.code) < order.count)
                {
                    return(ApiResultEnum.Order_Unit_Negative_Position);
                }
            }
            return(ApiResultEnum.Success);
        }
Beispiel #8
0
        //获取单元最大可下单数量
        public static int GetUnitCount(Order order)
        {
            Unit unit = UnitRA.Get("U_" + order.unit_id);

            if (unit == null)
            {
                return(0);
            }

            if (order.type_enum == OrderTypeEnum.Buy && !string.IsNullOrWhiteSpace(unit.limit_no_buying) && unit.limit_no_buying.Contains(order.code))
            {
                return(0);
            }

            if (unit.status_enum == StatusEnum.Forbidden)
            {
                return(0);
            }
            if (unit.status_order_enum == StatusOrderEnum.Forbidden)
            {
                return(0);
            }
            if (order.type_enum == OrderTypeEnum.Buy && unit.status_order_enum == StatusOrderEnum.NoBuying)
            {
                return(0);
            }

            string[] keys = TradeRA.KeySearch("P_" + order.code + "_A_*_U_" + order.unit_id);
            if (unit.limit_stock_count > 0)
            {
                if (PositionRA.GetCodeCount(order.unit_id, order.code) > unit.limit_stock_count)
                {
                    return(0);
                }
            }

            if (order.type_enum == OrderTypeEnum.Buy)
            {
                decimal   count = unit.capital_available / order.price;
                BlockInfo block = StockInfoBiz.GetBlock(order.code);
                if (block.block_type_enum == BlockEnum.mbm)
                {
                    if (unit.limit_ratio_mbm_single > 0)
                    {
                        count = Math.Min(count, unit.capital_scale * unit.limit_ratio_mbm_single / order.price);
                    }
                }
                else if (block.block_type_enum == BlockEnum.gem)
                {
                    if (unit.limit_ratio_gem_single > 0)
                    {
                        count = Math.Min(count, unit.capital_scale * unit.limit_ratio_gem_single / order.price);
                    }
                    if (unit.limit_ratio_gem_total > 0)
                    {
                        count = Math.Min(count, (unit.capital_scale * unit.limit_ratio_gem_total - unit.capital_stock_value_gem) / order.price);
                    }
                }
                else if (block.block_type_enum == BlockEnum.sme)
                {
                    if (unit.limit_ratio_sme_single > 0)
                    {
                        count = Math.Min(count, unit.capital_scale * unit.limit_ratio_sme_single / order.price);
                    }
                    if (unit.limit_ratio_sme_total > 0)
                    {
                        count = Math.Min(count, (unit.capital_scale * unit.limit_ratio_sme_total - unit.capital_stock_value_sme) / order.price);
                    }
                }
                else if (block.block_type_enum == BlockEnum.star)
                {
                    if (unit.limit_ratio_star_single > 0)
                    {
                        count = Math.Min(count, unit.capital_scale * unit.limit_ratio_star_single / order.price);
                    }
                    if (unit.limit_ratio_star_total > 0)
                    {
                        count = Math.Min(count, (unit.capital_scale * unit.limit_ratio_star_total - unit.capital_stock_value_star) / order.price);
                    }
                }
                if (block.block_type_enum == BlockEnum.sme || block.block_type_enum == BlockEnum.gem)
                {
                    if (unit.limit_ratio_smg_total > 0)
                    {
                        count = Math.Min(count, (unit.capital_scale * unit.limit_ratio_smg_total - unit.capital_stock_value_sme - unit.capital_stock_value_gem) / order.price);
                    }
                }
                return((int)Math.Ceiling(count / 100) * 100);
            }
            else
            {
                return(PositionRA.GetSellable(order.unit_id, order.code));
            }
        }
Beispiel #9
0
        //检查主账户是否满足下单条件
        public static ApiResultEnum CheckAccount(Order order)
        {
            Account account = AccountRA.Get("A_" + order.account_id);

            if (order.type_enum == OrderTypeEnum.Buy && !string.IsNullOrWhiteSpace(account.limit_no_buying) && account.limit_no_buying.Contains(order.code))
            {
                return(ApiResultEnum.Order_Account_NoBuying_Code);
            }

            if (account.status_enum == StatusEnum.Forbidden)
            {
                return(ApiResultEnum.Order_Account_Forbidden);
            }
            if (account.status_order_enum == StatusOrderEnum.Forbidden)
            {
                return(ApiResultEnum.Order_Account_Forbidden_Order);
            }
            if (order.type_enum == OrderTypeEnum.Buy && account.status_order_enum == StatusOrderEnum.NoBuying)
            {
                return(ApiResultEnum.Order_Account_NoBuying_Order);
            }

            if (order.type_enum == OrderTypeEnum.Buy)
            {
                if (account.limit_ratio_single > 0 && order.price * order.count > account.capital_initial * account.limit_ratio_single)
                {
                    return(ApiResultEnum.Order_Account_Limit_Single);
                }

                BlockInfo block = StockInfoBiz.GetBlock(order.code);
                if (block.block_type_enum == BlockEnum.gem)
                {
                    if (account.limit_ratio_gem_single > 0 && order.price * order.count > account.capital_initial * account.limit_ratio_gem_single)
                    {
                        return(ApiResultEnum.Order_Account_Limit_GEM_Single);
                    }
                    if (account.limit_ratio_gem_total > 0 && order.price * order.count + account.capital_stock_value_gem > account.capital_initial * account.limit_ratio_gem_total)
                    {
                        return(ApiResultEnum.Order_Account_Limit_GEM_Total);
                    }
                }

                string[]         keys = TradeRA.KeySearch("G_*_U_" + order.unit_id + "_A_" + order.account_id);
                AccountGroupItem item = AccountGroupRA.Get(keys[0]);
                if (item.capital_available > 0 && item.capital_available < order.price * order.count + item.capital_stock_value)
                {
                    return(ApiResultEnum.Order_Account_Negative_Amount);
                }
            }
            else
            {
                if (PositionRA.GetSellable(order.unit_id, order.code, order.account_id) < order.count)
                {
                    return(ApiResultEnum.Order_Account_Negative_Position);
                }
            }

            //风控通过进行冻结
            if (order.type_enum == OrderTypeEnum.Buy)
            {
                string key_unit = "U_" + order.unit_id;
                UnitRA.UpdateCapitalOrderBuy(order.price * order.count, key_unit);
            }
            else if (order.type_enum == OrderTypeEnum.Sell)
            {
                string key_position = "P_" + order.code + "_A_" + order.account_id + "_U_" + order.unit_id;
                PositionRA.UpdateSellableOrderSell(-order.count, key_position);
            }
            return(ApiResultEnum.Success);
        }