You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 

129 lines
4.0 KiB

from locale import currency
from glQiwiApi import QiwiWallet
from glQiwiApi.core.event_fetching import executor
from glQiwiApi.core.event_fetching.dispatcher import QiwiDispatcher
from glQiwiApi.core.event_fetching.executor import Context
from glQiwiApi.core.event_fetching.filters import ExceptionFilter
from glQiwiApi.qiwi.clients.wallet.types import Transaction, TransactionType, TransactionStatus
from glQiwiApi.qiwi.exceptions import QiwiAPIError
from backend_integration import BackendClient
from colors import *
import os, sys, asyncio
import ws
class Client:
wallet: QiwiWallet
qiwi_dp: QiwiDispatcher
backend: BackendClient
prices = {}
backend_checker_enabled = False
convert_map = {
"month":30*24*60*60,
"week":7*24*60*60,
"day":1*24*60*60
}
def __init__(self):
if not os.getenv("BACKEND_URL", "") or not os.getenv("SECRET_KEY", ""):
error("BACKEND_URL or SECRET_KEY is not setted!")
sys.exit(1)
if not os.getenv("QIWI_APIKEY", "") or not os.getenv("QIWI_PHONENUMBER", ""):
error("QIWI_APIKEY or QIWI_PHONENUMBER in not setted!")
sys.exit(2)
self.qiwi_dp = QiwiDispatcher()
self.wallet = QiwiWallet(api_access_token=os.getenv("QIWI_APIKEY"), phone_number=os.getenv("QIWI_PHONENUMBER"))
self.build_handler()
def run(self):
executor.start_polling(self.wallet, self.qiwi_dp, on_startup=self.on_startup)
async def on_startup(self, ctx: Context):
print(await self.wallet.get_balance())
await self.backend.pulse()
await self.update_prices_from_server()
asyncio.ensure_future(self.backend_checker(60))
async def backend_checker(self, timeout = 60):
if not self.backend_checker_enabled:
self.backend_checker_enabled = True
info(f"check backend every {timeout} seconds")
while True:
await self.backend.pulse(True)
await self.update_prices_from_server(True)
await asyncio.sleep(timeout)
def build_handler(self):
@self.qiwi_dp.transaction_handler()
async def handle_transaction(t: Transaction, ctx: Context):
if t.type != TransactionType.IN:
return
if t.status != TransactionStatus.SUCCESS:
return
########################################
currency = t.sum.currency
if str(currency) != "RUB":#643-rub code
warning(f"[{t.id}] currency not be rub, drop")
return
########################################
if not self.prices:
await self.update_prices_from_server()
########################################
money = t.sum.amount
seconds = self.price_checker(money)
if seconds == 0:
warning(f"[{t.id}] so smol donate {money} RUB")
return
########################################
splitted = t.comment.split()
steam2 = None
for maybe_steam in splitted:
if "STEAM_" in maybe_steam.upper() and ":" in maybe_steam:
steam2 = maybe_steam.upper()
break
if steam2 is None:
warning(f"[{t.id}] comment not contain steam {t.comment} RUB")
return
########################################
# add vip
info(f"Add vip {steam2}, amount {seconds}")
await self.backend.vip(steam2, seconds, f"rub={int(money)};", unique=f"qiwi_{t.id}")
async def update_prices_from_server(self, exit_if_error = True):
#info("Fetch prices from server backend")
prices = await self.backend.prices(exit_if_error)
self.update_prices(prices)
def update_prices(self, prices):
for price in prices:
if price["money_price"] == 0:
continue
self.prices.update({float(price["money_price"]):self.convert_map[price['period']]})
if not self.prices:
error("cannot get prices from server")
sys.exit(228)
#info(f"prices: {self.prices}")
def price_checker(self, amount):
seconds2give = 0
for rub, sec in self.prices.items():
if amount >= rub and seconds2give <= sec:
seconds2give = sec
return seconds2give
if __name__ == "__main__":
print("Build date: "+os.getenv("BUILDDATE", "not setted"))
def run():
client = Client()
client.backend = BackendClient()
client.run()
ws.SERVICE_NAME = "qiwipay"
ws.START_AFTER_CONNECT = run
wsc = ws.WS(os.getenv("BACKEND_URL"), os.getenv("SECRET_KEY"))
wsc.run()