def get_all_config(): import os, sys cur_dir = os.path.dirname(os.path.abspath(__file__)) + os.sep + os.pardir + os.sep # sys.path.insert(0, os.path.join(cur_dir, "..")) sys.path.append(os.path.join(cur_dir)) try: import game_config from models.config import Config as ConfigModel except: import settings settings.set_evn('dev_new', '1') # settings.set_evn('dev', 'h1') import game_config from models.config import Config as ConfigModel # from apps.config import game_config common_config_name_list = game_config.config_name_list # game_config_name_list = game_config.all_config_name_list config_dict = {} for config_key, config_sub_func, is_show_in_admin, is_modifable, xls_table_name, need_download, _ in game_config.config_name_list: _c = ConfigModel.get(config_key) config_dict[config_key] = _c.value filename = cur_dir + '/test/local_config.py' f = open(filename, 'w') d = str(config_dict) f.write('config='+d) f.close() return filename
def upload(self, file_name, xl=None): """ 上传一个文件 :param file_name: :param xl: :return: """ self.locked = True save_list = [] warning_msg = [] data = trans_config(file_name, xl) if not data: self.locked = False return save_list, [] cv = ConfigVersion.get() for config_name, m, config in data: check_warning = config.pop('check_warning', []) if check_warning: warning_msg.extend(check_warning) if cv.versions.get(config_name) == m: continue c = Config.get(config_name) c.update_config(config, m, save=True) cv.update_version(config_name, m) save_list.append(config_name) if save_list: cv.save() self.locked = False return save_list, warning_msg
def reload(self): """ 更新进程配置 :return: """ self.locked = True cm = ConfigMd5.get() if cm.ver_md5 == self.ver_md5: self.locked = False return False cv = ConfigVersion.get() if cv.versions and cv.versions == self.versions: self.locked = False return False cv_save = False for name, v in mapping_config.iteritems(): # 配置 转换 if name in []: pass cv_version = cv.versions.get(name) if cv_version and self.versions.get(name) == cv_version: continue c = Config.get(name) if cv_version and c.version != cv_version: if settings.CONFIG_SWITCH: cv.versions[name] = c.version cv_save = True if v[0]: # 加载的策划配置的xlsx setattr(self, name, make_readonly(c.value)) if cv_version: # 设置服务器版本号 self.versions[name] = cv_version elif cv_version: setattr(self, name, make_readonly(c.value)) # 设置服务器版本号 self.versions[name] = cv_version if cv_save: cv.save() self.ver_md5 = cm.ver_md5
def select(req, **kwargs): """# config: docstring args: req: --- arg returns: 0 --- """ config_key = req.get_argument('config_key', '') c = Config.get(config_key) config_data = c.value last_update_time = c.last_update_time if not config_data and config_key: config_data = getattr(game_config, config_key) refresh_text = req.get_argument('config_refresh_text', '') flag = int(req.get_argument('config_refresh_flag', 0)) res_flag = int(req.get_argument('test_res_version_flag', -1)) white_ip = req.get_argument('white_ip', '-1') version_dirs = os.path.join(settings.BASE_ROOT, 'logs', 'client_resource') msg = kwargs.get('msg', '') return render(req, 'admin/config/index.html', **{ 'mapping_config': mapping_config, 'config_key': config_key, 'config_data': config_data, 'config_refresh_flag': 1, 'config_refresh_text': refresh_text, 'last_update_time': last_update_time, 'test_res_version_flag': 1, # resource.hot_update_switch, 'can_hot_update_ip': 1, # resource.can_hot_update_ip, 'limit_version': 1, # resource.limit_version, 'recent_version': 1, # resource.recent_version, 'msg': msg, })
class Mail: def __init__(self): """ """ self.config = Config() self.host = self.config.get("MailHost") self.security = self.config.get("MailSecurity") self.port = self.config.get("MailPort") self.user = self.config.get("MailUser") self.receiver_address = self.config.get("MailReceiver") self.sender_address = self.config.get("MailSender") self.password = self.config.get("MailPassword") def send_mail(self, subject, message): """ :param subject: :param message: :return: """ if self.config.get("SendMail") == "1": msg = MIMEMultipart('alternative') msg['Subject'] = subject msg['From'] = self.sender_address msg['To'] = self.receiver_address part1 = MIMEText(message, 'plain') part2 = MIMEText(message, 'html') msg.attach(part1) msg.attach(part2) server = smtplib.SMTP(self.host, self.port) server.login(self.user, self.password) server.sendmail(self.sender_address, [self.receiver_address], msg.as_string()) server.quit()
class BinanceAPI: """ Verwaltet Methoden für die Zugriffe auf die Binance API """ # noinspection PyTypeChecker def __init__(self): self.closes = [] self.rsi_overbought = 70 self.rsi_oversold = 15 self.rsi_period = 21 self.config = Config() self.client = Client(self.config.get("Binance_api_key"), self.config.get("Binance_api_secret")) self.socket_manager = BinanceSocketManager(self.client) self.connection_key = self.socket_manager.start_kline_socket( self.config.get("Symbol"), self.process_message, interval=self.get_interval()) def write_file(self, path, content): """ :param path: :param content: :return: """ with open(path, "w") as file: file.write(content) def read_file(self, path): """ :param path: :return: """ if os.path.isfile(path): with open(path, "r") as file: return str(file.read()) return "" def set_last_bought(self, close): """ writes the last bought value into a text file :param close: :return: """ self.write_file(os.path.join("last_bought.txt"), str(float(close))) def get_last_order_id(self): """ gibt die id der letzten order zurück :return: """ return self.read_file(os.path.join("last_order_id.txt")) def set_last_order_id(self, order_id): """ setzt die id der letzten order :param order_id: string :return: None """ self.write_file(os.path.join("last_order_id.txt"), str(order_id)) def get_last_bought(self): """ gibt den preis der letzten kauforder zurück :return: """ if (self.read_file(os.path.join("last_bought.txt"))) != "": return float(self.read_file(os.path.join("last_bought.txt"))) return 0.0 def set_in_position(self, position): """ schreibt die aktuelle position :param position: :return: """ self.write_file(os.path.join("position.txt"), str(int(position))) def get_in_position(self): """ gibt zurück ob wir in position sind :return: """ if self.read_file(os.path.join("position.txt")) != "": return bool(int(self.read_file(os.path.join("position.txt")))) return 0 def start_socket(self): """ startet den websocket :return: None """ dataframe = self.get_candles() for close in dataframe['close']: self.closes.append(close) self.socket_manager.start() debug_logger.debug("socket started") mail = Mail() debug_logger.debug( "**************************************** TRADING BOT STARTED ****************************************" ) mail.send_mail("Tradingbot started", "Tradingbot started") def restart_socket(self): """ startet den socket neu :return: None """ debug_logger.debug("restarting socket") self.socket_manager.stop_socket(self.connection_key) self.start_socket() debug_logger.debug("socket restarted") mail = Mail() mail.send_mail("Tradingbot socket restarted", "Tradingbot socket restarted") def check_last_order_status(self): """ überprüft den status der letzten order :return: None """ order_id = self.get_last_order_id() order = self.client.get_order(symbol=self.config.get("Symbol"), orderId=order_id) """ order wurde durchgeführt """ if order["status"] == "FILLED": self.set_last_order_id("") if order["side"] == "SELL": self.set_in_position(False) self.set_last_bought(0.0) self.send_sell_filled_mail(order["price"], order["origQty"]) debug_logger.debug( "************************************ Verkauforder ausgeführt: {0} Menge: {1} ************************************" .format(order["price"], order["origQty"])) if order["side"] == "BUY": self.set_last_bought(order["price"]) self.set_in_position(True) self.send_buy_filled_mail(order["price"], order["origQty"]) debug_logger.debug( "************************************ Kauforder ausgeführt: {0} Menge: {1} ************************************" .format(order["price"], order["origQty"])) """ order wurde abgebrochen """ if order["status"] == "CANCELLED": self.set_last_order_id("") if order["side"] == "SELL": self.send_sell_cancelled_mail(order["price"], order["origQty"]) debug_logger.debug( "************************************ Verkauforder abgebrochen: {0} Menge: {1} ************************************" .format(order["price"], order["origQty"])) if order["side"] == "BUY": self.send_buy_cancelled_mail(order["price"], order["origQty"]) debug_logger.debug( "************************************ Kauforder abgebrochen: {0} Menge: {1} ************************************" .format(order["price"], order["origQty"])) def process_message(self, msg): """ Hier werden die Indikatoren berechnet. - MACD - Bollinger Bänder - Stochastik RSI :param msg: dict :return: None """ if msg['e'] == 'error': """ Beim Fehler den Fehler loggen und den socket neustarten """ debug_logger.debug(json.dumps(msg)) self.restart_socket() else: """ Response vom Websocket auswerten """ json_message = msg candle = json_message["k"] is_candle_closed = candle["x"] close = float(candle["c"]) """ nur in die berechnung gehen wenn die kerze geschlossen ist und der liste hinzugefügt werden kann """ if is_candle_closed: should_sell = 0 should_buy = 0 debug_logger.debug("---------------------------") self.closes.append(close) # die liste auf 800 kerzen beschränken while len(self.closes) > 500: self.closes.pop(0) # aus der liste einen numpy array zaubern np_closes = numpy.array(self.closes) fastk, fastd = talib.STOCHRSI(np_closes, timeperiod=14, fastk_period=5, fastd_period=3, fastd_matype=0) # macd berechnen ShortEMA = talib.EMA(np_closes, 9) LongEMA = talib.EMA(np_closes, 18) MACD = ShortEMA - LongEMA signal = talib.EMA(MACD, 5) # bollinger bänder berechnen upperband, middleband, lowerband = talib.BBANDS(np_closes, timeperiod=18, nbdevup=2, nbdevdn=2, matype=0) upperband_crossed = numpy.where((np_closes > upperband), 1, 0) lowerband_crossed = numpy.where((np_closes < lowerband), 1, 0) # preis durchschnitt und max/min berechnen in dem getraded werden soll max_price = numpy.amax(np_closes) lowest_price = numpy.amin(np_closes) average_price = numpy.average(np_closes) last_upperband_crossed = upperband_crossed[-1] last_lowerband_crossed = lowerband_crossed[-1] last_macd = MACD[-1] last_signal = signal[-1] last_fastk = fastk[-1] last_fastd = fastd[-1] if self.get_last_order_id() != "": self.check_last_order_status() if last_macd > last_signal: should_buy += 1 if last_lowerband_crossed: should_buy += 1 if last_macd < last_signal: should_sell += 1 if last_upperband_crossed: should_sell += 1 if last_fastd > 90 and last_fastk > 90: should_buy += 1 if last_fastd <= 20 and last_fastk <= 20: should_sell += 1 debug_logger.debug( "last_upperband_crossed {}".format(last_upperband_crossed)) debug_logger.debug( "last_lowerband_crossed {}".format(last_lowerband_crossed)) debug_logger.debug("last_macd {}".format(last_macd)) debug_logger.debug("last_signal {}".format(last_signal)) debug_logger.debug("fastk {}".format(last_fastk)) debug_logger.debug("fastd {}".format(last_fastd)) debug_logger.debug("unterer preisbereich {}".format( lowest_price < close < average_price)) debug_logger.debug("oberer preisbereich {}".format( max_price > close > average_price)) debug_logger.debug("buy {}".format(should_buy)) debug_logger.debug("sell {}".format(should_sell)) if should_sell == 3 and max_price > close > average_price and self.get_last_bought( ) + 5 < close and self.get_last_order_id() == "": if self.get_in_position(): self.sell(close) else: debug_logger.debug( "it is overbought but we dont own anything so nothing to do" ) if should_buy == 3 and lowest_price < close < average_price and self.get_last_order_id( ) == "": if self.get_in_position(): debug_logger.debug( "it is oversold, but you already own it, nothing to do" ) else: self.buy(close) def get_order_type(self): order_type = self.config.get("OrderType") if order_type == "0": order_type = self.client.ORDER_TYPE_MARKET if order_type == "1": order_type = self.client.ORDER_TYPE_LIMIT return order_type def backtest(self): """ :return: None """ dataframe = self.get_historical_candles() dates = list() for close in dataframe["close"]: self.closes.append(close) while len(self.closes) > 500: self.closes.pop(0) for date in dataframe['datetime']: dates.append(date) while len(dates) > 500: dates.pop(0) np_closes = numpy.array(self.closes) ShortEMA = talib.EMA(np_closes, 9) LongEMA = talib.EMA(np_closes, 18) fastk, fastd = talib.STOCHRSI(np_closes, timeperiod=14, fastk_period=5, fastd_period=3, fastd_matype=0) MACD = ShortEMA - LongEMA signal = talib.EMA(MACD, 5) upperband, middleband, lowerband = talib.BBANDS(np_closes, timeperiod=20, nbdevup=2, nbdevdn=2, matype=0) upperband_crossed = numpy.where((np_closes > upperband), 1, 0) lowerband_crossed = numpy.where((np_closes < lowerband), 1, 0) max_price = numpy.amax(np_closes) lowest_price = numpy.amin(np_closes) average_price = numpy.average(np_closes) last_bought = self.get_last_bought() in_position = self.get_in_position() bought = list() sold = list() last_upperband_crossed = False last_lowerband_crossed = False for i in range(0, len(np_closes)): should_sell = 0 should_buy = 0 buy = False sell = False last_macd = MACD[i] last_signal = signal[i] last_fastk = fastk[i] last_fastd = fastd[i] if upperband_crossed[i] and not last_upperband_crossed: last_upperband_crossed = True last_lowerband_crossed = False if lowerband_crossed[i] and not last_lowerband_crossed: last_upperband_crossed = False last_lowerband_crossed = True close = np_closes[i] if last_macd > last_signal: should_buy += 1 if last_lowerband_crossed: should_buy += 1 if last_macd < last_signal: should_sell += 1 if last_upperband_crossed: should_sell += 1 print("-------------------------------------------------------") print("last_upperband_crossed {}".format(last_upperband_crossed)) print("last_lowerband_crossed {}".format(last_lowerband_crossed)) print("last_macd {}".format(last_macd)) print("last_signal {}".format(last_signal)) print("fastk {}".format(last_fastk)) print("fastd {}".format(last_fastd)) print("unterer preisbereich {}".format(close > lowest_price and close < average_price)) print("oberer preisbereich {}".format(close < max_price and close > average_price)) print("buy {}".format(should_buy)) print("sell {}".format(should_sell)) if should_sell == 3 and max_price > close > average_price and last_bought + 10 < close: if in_position: print("****************** sell *********************") sold.append(close) in_position = False last_bought = 0.0 sell = True if should_buy == 3 and lowest_price < close < average_price: if not in_position: print("****************** buy *********************") bought.append(close) in_position = True last_bought = close buy = True if not sell: sold.append(numpy.nan) if not buy: bought.append(numpy.nan) plt.figure(1) plt.subplot(311) plt.plot(dates, upperband, color='yellow') plt.plot(dates, middleband, color='black') plt.plot(dates, lowerband, color='green') plt.plot(dates, sold, color='red', marker='o') plt.plot(dates, bought, color='green', marker='o') plt.plot(dates, np_closes, color='blue') plt.subplot(313) plt.plot(dates, fastk, label="macd", color='red') plt.plot(dates, fastd, label="signal", color='green') plt.show() def sell(self, close): """ :param close: :return: """ try: price, quantity = self.get_sell_value(close) order = self.client.create_order( symbol=self.config.get("Symbol"), side=self.client.SIDE_SELL, type=self.get_order_type(), timeInForce=self.client.TIME_IN_FORCE_GTC, quantity=quantity, price=price) self.set_last_order_id(order["orderId"]) self.send_sell_mail(close) debug_logger.debug( " **************************** SELL: {} **************************** " .format(close)) debug_logger.debug(json.dumps(order)) except Exception as error: debug_logger.debug(error) mail = Mail() mail.send_mail("Fehler", error) return False def get_sell_value(self, close): """ :param close: :return: """ new_close = close + ((close / 100) / 10) quantity = float(self.config.get("Quantity")) new_quantity = quantity - ((quantity / 100) / 10) return round(new_close, 2), round(new_quantity, 8) def buy(self, close): """ :param close: :return: """ try: price, quantity = self.get_buy_value(close) order = self.client.create_order( symbol=self.config.get("Symbol"), side=self.client.SIDE_BUY, type=self.get_order_type(), timeInForce=self.client.TIME_IN_FORCE_GTC, quantity=quantity, price=price) self.set_last_order_id(order["orderId"]) self.send_buy_mail(close) debug_logger.debug( " **************************** BUY: {} **************************** " .format(close)) debug_logger.debug(json.dumps(order)) except Exception as error: debug_logger.debug(error) mail = Mail() mail.send_mail("Fehler", error) return False def get_buy_value(self, close): """ :param close: :return: """ new_close = close - ((close / 100) / 10) quantity = float(self.config.get("Quantity")) new_quantity = quantity + ((quantity / 100) / 10) return round(new_close, 2), round(new_quantity, 8) def get_interval(self): """ :return: """ interval_seconds = int(self.config.get("Interval")) if interval_seconds == 60: return self.client.KLINE_INTERVAL_1MINUTE if interval_seconds == 180: return self.client.KLINE_INTERVAL_3MINUTE if interval_seconds == 300: return self.client.KLINE_INTERVAL_5MINUTE if interval_seconds == 900: return self.client.KLINE_INTERVAL_15MINUTE if interval_seconds == 1800: return self.client.KLINE_INTERVAL_30MINUTE if interval_seconds == 3600: return self.client.KLINE_INTERVAL_1HOUR if interval_seconds == 4 * 3600: return self.client.KLINE_INTERVAL_4HOUR if interval_seconds == 24 * 3600: return self.client.KLINE_INTERVAL_1DAY def get_price_for_symbol(self): """ :return: """ return self.client.get_avg_price(symbol=self.config.get("Symbol")) def send_buy_mail(self, close): """ :param close: :return: """ price, quantity = self.get_buy_value(close) subject = "Tradingbot: Kaufe" message = "Ich setze eine Kauforder:" message += "Preis: {0}</br>".format(price) message += "Menge: {0}</br>".format(quantity) mail = Mail() mail.send_mail(subject, message) def send_buy_filled_mail(self, price, quantity): """ :param price: :param quantity: :return: """ subject = "Tradingbot: Gekauft" message = "Kauforder erfolgreich:" message += "Preis: {0}</br>".format(price) message += "Menge: {0}</br>".format(quantity) mail = Mail() mail.send_mail(subject, message) def send_buy_cancelled_mail(self, price, quantity): """ :param price: :param quantity: :return: """ subject = "Tradingbot: Kauf abgebrochen" message = "Die letzte Kauforder wurde abgebrochen:" message += "Preis: {0}</br>".format(price) message += "Menge: {0}</br>".format(quantity) mail = Mail() mail.send_mail(subject, message) def send_sell_mail(self, close): """ :param close: :return: """ price, quantity = self.get_sell_value(close) subject = "Tradingbot: Verkaufe" message = "Ich setze eine Verkauforder:" message += "Preis: {0}</br>".format(price) message += "Menge: {0}</br>".format(quantity) mail = Mail() mail.send_mail(subject, message) def send_sell_filled_mail(self, price, quantity): """ :param price: :param quantity: :return: """ subject = "Tradingbot: Verkauft" message = "Die letzte Verkauforder war erfolgreich:" message += "Preis: {0}</br>".format(price) message += "Menge: {0}</br>".format(quantity) mail = Mail() mail.send_mail(subject, message) def send_sell_cancelled_mail(self, price, quantity): """ :param price: :param quantity: :return: """ subject = "Tradingbot: Verkauf abgebrochen" message = "Die letzte Verkauforder wurde abgebrochen:" message += "Preis: {0}</br>".format(price) message += "Menge: {0}</br>".format(quantity) mail = Mail() mail.send_mail(subject, message) def get_candles(self): record = self.client.get_klines(symbol=self.config.get("Symbol"), interval=self.get_interval()) myList = [] try: for item in record: n_item = [] int_ts = int(item[0] / 1000) # nur neue timestamps anhängen n_item.append(int_ts) # open time n_item.append(float(item[1])) # open n_item.append(float(item[2])) # high n_item.append(float(item[3])) # low n_item.append(float(item[4])) # close n_item.append(float(item[5])) # volume n_item.append(int(item[6] / 1000)) # close_time n_item.append(float(item[7])) # quote_assetv n_item.append(int(item[8])) # trades n_item.append(float(item[9])) # taker_b_asset_v n_item.append(float(item[10])) # taker_b_quote_v n_item.append(datetime.fromtimestamp(n_item[0])) myList.append(n_item) except Exception as error: debug_logger.debug(error) new_ohlc = pd.DataFrame(myList, columns=[ 'open_time', 'open', 'high', 'low', 'close', 'volume', 'close_time', 'quote_assetv', 'trades', 'taker_b_asset_v', 'taker_b_quote_v', 'datetime' ]) return new_ohlc def get_historical_candles(self): record = self.client.get_historical_klines(self.config.get("Symbol"), self.get_interval(), "1 week ago UTC") myList = [] try: for item in record: n_item = [] int_ts = int(item[0] / 1000) # nur neue timestamps anhängen n_item.append(int_ts) # open time n_item.append(float(item[1])) # open n_item.append(float(item[2])) # high n_item.append(float(item[3])) # low n_item.append(float(item[4])) # close n_item.append(float(item[5])) # volume n_item.append(int(item[6] / 1000)) # close_time n_item.append(float(item[7])) # quote_assetv n_item.append(int(item[8])) # trades n_item.append(float(item[9])) # taker_b_asset_v n_item.append(float(item[10])) # taker_b_quote_v n_item.append(datetime.fromtimestamp(n_item[0])) myList.append(n_item) except Exception as error: debug_logger.debug(error) new_ohlc = pd.DataFrame(myList, columns=[ 'open_time', 'open', 'high', 'low', 'close', 'volume', 'close_time', 'quote_assetv', 'trades', 'taker_b_asset_v', 'taker_b_quote_v', 'datetime' ]) return new_ohlc