| | |
| | | from db.redis_manager_delegate import RedisUtils |
| | | from third_data import kpl_block_util, kpl_api, kpl_util |
| | | from settings.trade_setting import MarketSituationManager |
| | | from third_data.kpl_data_constant import LimitUpCodesBlockRecordManager |
| | | from third_data.kpl_data_constant import LimitUpCodesBlockRecordManager, ContainsLimitupCodesBlocksManager |
| | | from third_data.third_blocks_manager import BlockMapManager |
| | | from utils import global_util, tool, buy_condition_util |
| | | from log_module import async_log_util |
| | |
| | | |
| | | from log_module.log import logger_kpl_block_can_buy, logger_kpl_jx_out, logger_kpl_jx_in, logger_debug |
| | | from third_data.kpl_util import KPLPlatManager |
| | | from trade import trade_manager, l2_trade_util, trade_constant |
| | | from trade import l2_trade_util, trade_constant |
| | | |
| | | # 代码精选板块管理 |
| | | from utils.kpl_data_db_util import KPLLimitUpDataUtil |
| | |
| | | |
| | | # 开盘啦禁止交易板块管理 |
| | | class KPLPlateForbiddenManager: |
| | | __redisManager = redis_manager.RedisManager(3) |
| | | """ |
| | | 不能买的板块管理 |
| | | """ |
| | | __redis_manager = redis_manager.RedisManager(3) |
| | | __kpl_forbidden_plates_cache = set() |
| | | |
| | | __instance = None |
| | |
| | | def __load_datas(cls): |
| | | __redis = cls.__get_redis() |
| | | try: |
| | | __kpl_forbidden_plates_cache = RedisUtils.smembers(__redis, "kpl_forbidden_plates") |
| | | cls.__kpl_forbidden_plates_cache = RedisUtils.smembers(__redis, "kpl_forbidden_plates") |
| | | finally: |
| | | RedisUtils.realse(__redis) |
| | | |
| | | @classmethod |
| | | def __get_redis(cls): |
| | | return cls.__redisManager.getRedis() |
| | | return cls.__redis_manager.getRedis() |
| | | |
| | | def save_plate(self, plate): |
| | | self.__kpl_forbidden_plates_cache.add(plate) |
| | | RedisUtils.sadd(self.__get_redis(), "kpl_forbidden_plates", plate) |
| | | RedisUtils.expire(self.__get_redis(), "kpl_forbidden_plates", tool.get_expire()) |
| | | |
| | | def delete_plate(self, plate): |
| | | self.__kpl_forbidden_plates_cache.discard(plate) |
| | | RedisUtils.srem(self.__get_redis(), "kpl_forbidden_plates", plate) |
| | | RedisUtils.expire(self.__get_redis(), "kpl_forbidden_plates", tool.get_expire()) |
| | | |
| | | def list_all(self): |
| | |
| | | |
| | | def list_all_cache(self): |
| | | return self.__kpl_forbidden_plates_cache |
| | | |
| | | def is_in_cache(self, plate): |
| | | if self.__kpl_forbidden_plates_cache and plate in self.__kpl_forbidden_plates_cache: |
| | | return True |
| | | return False |
| | | |
| | | |
| | | class LimitUpCodesPlateKeyManager: |
| | |
| | | |
| | | # 实时开盘啦市场数据 |
| | | class RealTimeKplMarketData: |
| | | # 流入缓存 |
| | | # 流入缓存 [ID, 板块名称, 板块涨幅, 流入金额] |
| | | top_in_list_cache = [] |
| | | # 流出缓存 |
| | | top_out_list_cache = [] |
| | |
| | | __top_jx_out_blocks = [] |
| | | # 精选板块流入金额 |
| | | __jx_blocks_in_money_dict = {} |
| | | # 市场行情热度,默认为60 |
| | | __market_strong = 60 |
| | | |
| | | @classmethod |
| | | def get_jingxuan_in_block_threshold_count(cls): |
| | | """ |
| | | 获取买精选流入前几 |
| | | @return: |
| | | """ |
| | | score = 60 |
| | | if cls.__market_strong is not None: |
| | | score = int(cls.__market_strong) |
| | | for info in constant.RADICAL_BUY_TOP_IN_COUNT_BY_MARKET_STRONG: |
| | | if info[0] <= score < info[1]: |
| | | return info[2] |
| | | return 10 |
| | | |
| | | @classmethod |
| | | def set_market_jingxuan_blocks(cls, datas): |
| | | """ |
| | | 设置精选流入数据 |
| | | @param datas: |
| | | @param datas:[(板块编号,板块名称,涨幅, 板块流入金额)] |
| | | @return: |
| | | """ |
| | | # blocks = set() |
| | | # 老版本实现方式 |
| | | # for data in datas: |
| | | # if data[3] <= 0: |
| | | # break |
| | | # blocks.add(data[1]) |
| | | # cls.__top_jx_blocks = blocks |
| | | # 流入阈值 |
| | | # THRESHOLD_MONEY = 50 * (tool.trade_time_sub(tool.get_now_time_str(), "09:30:00") // 60) + 1000 |
| | | # THRESHOLD_MONEY = min(THRESHOLD_MONEY, 10000) |
| | | # THRESHOLD_MONEY = max(THRESHOLD_MONEY, 1000) |
| | | # THRESHOLD_MONEY = THRESHOLD_MONEY * 10000 |
| | | THRESHOLD_MONEY = 0 |
| | | # 最大数量 |
| | | # MAX_COUNT = cls.get_jingxuan_in_block_threshold_count() |
| | | |
| | | cls.top_in_list_cache = datas |
| | | blocks = set() |
| | | count = 0 |
| | |
| | | cls.__jx_blocks_in_money_dict[data[1]] = data[3] |
| | | if data[1] in constant.KPL_INVALID_BLOCKS: |
| | | continue |
| | | if data[3] < 5e7: |
| | | if data[3] < THRESHOLD_MONEY: |
| | | continue |
| | | # 过滤出来为同一个板块就只算1个数量 |
| | | fb = BlockMapManager().filter_blocks({data[1]}) |
| | | if blocks & fb: |
| | | continue |
| | | |
| | | for b in fb: |
| | | fblock_money[b] = data[3] |
| | | blocks |= fb |
| | | count += 1 |
| | | if count >= 10: |
| | | break |
| | | |
| | | # 如果该原因没有涨停票要往后移一位 |
| | | has_code = False |
| | | for b in fb: |
| | | if ContainsLimitupCodesBlocksManager().get_block_codes(b): |
| | | has_code = True |
| | | break |
| | | if has_code: |
| | | count += 1 |
| | | if count == 10: |
| | | strong = cls.get_market_strong() |
| | | if strong is None: |
| | | strong = 60 |
| | | THRESHOLD_MONEY = int((1 - strong / 200) * data[3]) |
| | | # if count >= MAX_COUNT: |
| | | # break |
| | | # 记录精选流出日志 |
| | | async_log_util.info(logger_kpl_jx_in, f"原数据:{datas[:20]} 板块:{blocks}") |
| | | async_log_util.info(logger_kpl_jx_in, f"原数据:{datas[:50]} 板块:{blocks}") |
| | | blocks = list(blocks) |
| | | blocks.sort(key=lambda x: fblock_money.get(x), reverse=True) |
| | | cls.__top_jx_blocks = blocks |
| | |
| | | cls.__top_jx_out_blocks = list(blocks) |
| | | |
| | | @classmethod |
| | | def set_market_strong(cls, strong): |
| | | """ |
| | | 设置市场行情强度 |
| | | @param strong: |
| | | @return: |
| | | """ |
| | | cls.__market_strong = strong |
| | | |
| | | @classmethod |
| | | def get_market_strong(cls): |
| | | return cls.__market_strong |
| | | |
| | | @classmethod |
| | | def get_top_market_jingxuan_blocks(cls): |
| | | return cls.__top_jx_blocks |
| | | |
| | | @classmethod |
| | | def get_top_market_jingxuan_out_blocks(cls): |
| | | return cls.__top_jx_out_blocks |
| | | |
| | | @classmethod |
| | | def get_block_info_at_block_in(cls, b): |
| | | """ |
| | | 获取板块的净流入情况 |
| | | @param b: |
| | | @return: (板块名称,身位,流入金额) |
| | | """ |
| | | for i in range(0, len(cls.top_in_list_cache)): |
| | | if cls.top_in_list_cache[i][1] == b: |
| | | return b, i, cls.top_in_list_cache[i][3] |
| | | return b, -1, 0 |
| | | |
| | | @classmethod |
| | | def set_top_5_industry(cls, datas): |
| | |
| | | __TargetCodePlateKeyManager = TargetCodePlateKeyManager() |
| | | __LimitUpCodesPlateKeyManager = LimitUpCodesPlateKeyManager() |
| | | __CodesHisReasonAndBlocksManager = CodesHisReasonAndBlocksManager() |
| | | __CodesTradeStateManager = trade_manager.CodesTradeStateManager() |
| | | __can_buy_compute_result_dict = {} |
| | | |
| | | @classmethod |
| | | def __remove_from_l2(cls, code, msg): |
| | | # 根据身位移除代码 |
| | | # return |
| | | # 下过单的代码不移除 |
| | | if trade_manager.CodesTradeStateManager().get_trade_state_cache(code) != trade_constant.TRADE_STATE_NOT_TRADE: |
| | | # 只要下过单的就不移除 |
| | | return |
| | | l2_trade_util.forbidden_trade(code, msg=msg) |
| | | logger_kpl_block_can_buy.info(msg) |
| | | |
| | | # 是否需要积极买 |
| | | @classmethod |
| | |
| | | @classmethod |
| | | def __compute_can_buy_blocks(cls, code, current_limit_up_datas, limit_up_record_datas, |
| | | yesterday_current_limit_up_codes, before_blocks_dict, |
| | | current_limit_up_block_codes_dict, high_level_general_code_blocks): |
| | | current_limit_up_block_codes_dict, high_level_general_code_blocks, codes_delegate, |
| | | codes_success): |
| | | # 根据代码泛化板块获取泛化板块的代码集合 |
| | | high_level_general_block_codes = {} |
| | | for c in high_level_general_code_blocks: |
| | |
| | | high_level_general_block_codes) |
| | | if not blocks_compute_results: |
| | | return False, True, f"没有找到板块", [], keys, [] |
| | | codes_delegate = set(cls.__CodesTradeStateManager.get_codes_by_trade_states_cache( |
| | | {trade_constant.TRADE_STATE_BUY_DELEGATED, trade_constant.TRADE_STATE_BUY_PLACE_ORDER})) |
| | | codes_success = set(cls.__CodesTradeStateManager.get_codes_by_trade_states_cache( |
| | | {trade_constant.TRADE_STATE_BUY_SUCCESS})) |
| | | |
| | | codes = codes_delegate | codes_success |
| | | # 统计成交代码的板块 |
| | | trade_codes_blocks_dict = {} |
| | |
| | | @classmethod |
| | | def update_can_buy_blocks(cls, code, current_limit_up_datas, limit_up_record_datas, |
| | | latest_current_limit_up_records, |
| | | before_blocks_dict, current_limit_up_block_codes_dict): |
| | | before_blocks_dict, current_limit_up_block_codes_dict, delegate_codes, deal_codes): |
| | | yesterday_current_limit_up_codes = set() |
| | | yesterday_current_limit_up_records_dict = {} |
| | | yesterday_current_limit_up_records = latest_current_limit_up_records[0][1] |
| | |
| | | yesterday_current_limit_up_codes, |
| | | before_blocks_dict, |
| | | current_limit_up_block_codes_dict, |
| | | high_level_general_code_blocks) |
| | | high_level_general_code_blocks, |
| | | delegate_codes, |
| | | deal_codes) |
| | | # 保存板块计算结果 |
| | | cls.__can_buy_compute_result_dict[code] = ( |
| | | can_buy_blocks, unique, msg, can_buy_strong_blocks, keys, active_buy_blocks) |
| | | |
| | | |
| | | if __name__ == "__main__": |
| | | pass |
| | | RealTimeKplMarketData.set_market_strong(120) |
| | | print(RealTimeKplMarketData.get_jingxuan_in_block_threshold_count()) |