152 lines
7.1 KiB
Python
152 lines
7.1 KiB
Python
"""Konfigurasi proyek dari env / `.env`.
|
||
|
||
Bacaan tipe via `os.getenv`; nilai default = konstanta lama. Muat `.env` sekali
|
||
di sini supaya semua modul (get_voters, dashboard) berbagi sumber yang sama.
|
||
"""
|
||
|
||
import os
|
||
from decimal import Decimal
|
||
|
||
from dotenv import load_dotenv
|
||
|
||
load_dotenv()
|
||
|
||
# BP target
|
||
TARGET_BP = os.getenv('VEX_TARGET_BP', 'databisnisid')
|
||
|
||
# Node RPC publik Vexanium
|
||
API_NODE = os.getenv('VEX_API_NODE', 'https://v2.vexascan.com:2096')
|
||
|
||
# Node pool RPC (V58): CSV `VEX_API_NODES` — node utama + cadangan utk failover
|
||
# distribusi (fetch saldo, ABI/TAPOS, broadcast). Default = `API_NODE` +
|
||
# `https://api.databisnis.id` (node mainnet Vexanium terverifikasi, host sama
|
||
# dgn HYPERION_API tapi melayani juga /v1/chain). Dipakai `distribute.py`;
|
||
# scan/klaim tetap memakai `API_NODE` tunggal.
|
||
API_NODES = [
|
||
n.strip() for n in os.getenv(
|
||
'VEX_API_NODES', f'{API_NODE},https://api.databisnis.id').split(',')
|
||
if n.strip()
|
||
]
|
||
|
||
# Lokasi basis data SQLite (dipakai fetcher & dashboard)
|
||
DB_PATH = os.getenv('VEX_DB_PATH', 'voters.db')
|
||
|
||
# Backend basis data: 'sqlite' (default) atau 'mysql' (MariaDB/MySQL via PyMySQL)
|
||
DB_BACKEND = os.getenv('VEX_DB_BACKEND', 'sqlite')
|
||
|
||
# Koneksi MariaDB/MySQL (dipakai saat DB_BACKEND='mysql')
|
||
DB_HOST = os.getenv('VEX_DB_HOST', '127.0.0.1')
|
||
DB_PORT = int(os.getenv('VEX_DB_PORT', '3306'))
|
||
DB_USER = os.getenv('VEX_DB_USER', '')
|
||
DB_PASS = os.getenv('VEX_DB_PASS', '')
|
||
DB_NAME = os.getenv('VEX_DB_NAME', '')
|
||
|
||
# Syarat minimum stake (dalam VEX) untuk disimpan
|
||
MIN_STAKED_VEX = float(os.getenv('VEX_MIN_STAKED_VEX', '1000'))
|
||
|
||
# Dashboard: ukuran halaman list
|
||
PAGE_SIZE = int(os.getenv('DASH_PAGE_SIZE', '50'))
|
||
|
||
# Dashboard: host & port server Flask
|
||
DASH_HOST = os.getenv('DASH_HOST', '127.0.0.1')
|
||
DASH_PORT = int(os.getenv('DASH_PORT', '5000'))
|
||
|
||
# Dashboard: jumlah worker gunicorn (produksi)
|
||
DASH_WORKERS = int(os.getenv('DASH_WORKERS', '2'))
|
||
|
||
# Ambang batas vote "basi" (hari tanpa revote). Sejak V40 pemilih lewat batas
|
||
# ini TETAP disimpan di scan (basi dibuang hanya saat tampil/bayar): band
|
||
# kadaluarsa 28..31 hari tetap tampil (sorot VOTE ULANG), >31 hari disembunyikan.
|
||
VEX_STALE_DAYS = int(os.getenv('VEX_STALE_DAYS', '28'))
|
||
|
||
# Masa matang (hari): pemilih baru (revote < VEX_MATURITY_DAYS lalu) BELUM
|
||
# berhak reward (⊥ dibayar distribusi) hingga votenya berumur ≥ ambang ini.
|
||
VEX_MATURITY_DAYS = int(os.getenv('VEX_MATURITY_DAYS', '3'))
|
||
|
||
# Jendela "kadaluarsa" (hari SETELAH VEX_STALE_DAYS) yang masih tampil di
|
||
# dashboard (band sorot VOTE ULANG). Lewat 28+3 = 31 hari → disembunyikan.
|
||
VEX_EXPIRED_DAYS = int(os.getenv('VEX_EXPIRED_DAYS', '3'))
|
||
|
||
# Tag REVOTE (mint) bertahan (hari) sejak revote terakhir: hanya pemilih lama
|
||
# yang revote dalam `VEX_REVOTE_TAG_DAYS` terakhir diberi tag; setelah itu
|
||
# tampil sbg VALID biasa (tetap dibayar langsung — V42, ⊥ tunggu matang).
|
||
VEX_REVOTE_TAG_DAYS = int(os.getenv('VEX_REVOTE_TAG_DAYS', '1'))
|
||
|
||
# Jendela peringatan (hari SEBELUM VEX_STALE_DAYS): pemilih VALID yang
|
||
# `now − STALE < last_vote ≤ now − (STALE − WARN)` diberi badge `VOTE ULANG
|
||
# SEGERA` (segera kadaluarsa, masih dibayar).
|
||
VEX_WARN_DAYS = int(os.getenv('VEX_WARN_DAYS', '3'))
|
||
|
||
# Hyperion API untuk saldo liquid akun + verifikasi txid (balance BP,
|
||
# disajikan dashboard; verifikasi distribusi/klaim). `HYPERION_API` nama baru
|
||
# (V-rename); `DATABISNIS_API` masih dibaca utk backward-compat deploy lama.
|
||
HYPERION_API = (os.getenv('HYPERION_API')
|
||
or os.getenv('DATABISNIS_API')
|
||
or 'https://api.databisnis.id')
|
||
|
||
# Node pool Hyperion (V60): CSV `VEX_HYPERION_NODES` — host yang melayani
|
||
# `/v2/*` utk failover GET Hyperion (verifikasi txid, reward klaim, saldo
|
||
# liquid dashboard). Default = `HYPERION_API` (utama) + semua `API_NODES`
|
||
# (keduanya mainnet terverifikasi layani /v2, probe 2026-08-13), dedup,
|
||
# utama di depan. Dipakai `distribute._get_json` + dashboard `_get_liquid_vex`.
|
||
HYPERION_NODES = [
|
||
n.strip() for n in os.getenv(
|
||
'VEX_HYPERION_NODES',
|
||
','.join([HYPERION_API] + [n for n in API_NODES if n != HYPERION_API]),
|
||
).split(',') if n.strip()
|
||
]
|
||
|
||
# Dashboard: TTL cache (detik) untuk saldo liquid — gagal fetch juga di-cooldown
|
||
DASH_LIQUID_TTL = int(os.getenv('DASH_LIQUID_TTL', '60'))
|
||
|
||
# ————————————————— Distribusi profit-share (V19..V27) —————————————————
|
||
# Jam (lokal, TZ) run harian distribusi; key aktif BP via swarm secret/env.
|
||
# ⊥ env-able: konstanta chain Vexanium (token + chain_id untuk signing).
|
||
BP_PRIVATE_KEY = os.getenv('VEX_BP_PRIVATE_KEY', '')
|
||
DISTRIBUTE_HOUR = int(os.getenv('DISTRIBUTE_HOUR', '10'))
|
||
DISTRIBUTE_MAX_ATTEMPTS = int(os.getenv('DISTRIBUTE_MAX_ATTEMPTS', '3'))
|
||
# Jeda (detik) ANTAR kirim transfer antar pemilih (V63): send-loop distribusi
|
||
# tidur sebelum lanjut ke pemilih berikutnya — beri node/Hyperion waktu
|
||
# mengejar indeks + meratakan beban broadcast run panjang. Default 30.
|
||
DISTRIBUTE_SEND_DELAY = int(os.getenv('DISTRIBUTE_SEND_DELAY', '30'))
|
||
# Kill-switch distribusi (V35): default OFF — payout hanya jalan saat diset
|
||
# `true`. `--dry-run` tetap boleh jalan (read-only, ⊥ tanda tangan/tulis).
|
||
DISTRIBUTE_ENABLED = os.getenv(
|
||
'DISTRIBUTE_ENABLED', 'false').lower() in ('1', 'true', 'yes')
|
||
# Jadwal distribusi (V37/V44): hari `DISTRIBUTE_WEEKDAY` — satu nama (`sat`) atau
|
||
# CSV beberapa hari (`wed,sat`), jam `DISTRIBUTE_HOUR`; plus satu one-off
|
||
# `DISTRIBUTE_FIRST_RUN` (`YYYY-MM-DD`). Dipakai distribute_loop (via config,
|
||
# konsisten dgn dashboard V38). Default baked = launch pertama 2026-08-17
|
||
# (Senin) 10:00 lalu tiap Rabu & Sabtu; env tetap override. Setelah tanggal
|
||
# lewat → otomatis hanya mingguan (batas skip event masa lalu).
|
||
DISTRIBUTE_WEEKDAY = os.getenv('DISTRIBUTE_WEEKDAY', 'wed,sat')
|
||
DISTRIBUTE_FIRST_RUN = os.getenv('DISTRIBUTE_FIRST_RUN', '2026-08-17')
|
||
|
||
# ————————————————— Notifikasi Telegram (V30/V36) —————————————————
|
||
# Bot token tunggal; dua daftar chat id (CSV): KOMUNITAS (`..._COMMUNITY_...`)
|
||
# hanya brief mulai/selesai distribusi, INTERNAL (`..._INTERNAL_...`) detail
|
||
# distribusi + semua kegagalan + klaim reward (⊥ komunitas). Kosong → kanal
|
||
# itu senyap.
|
||
TELEGRAM_BOT_TOKEN = os.getenv('TELEGRAM_BOT_TOKEN', '')
|
||
TELEGRAM_COMMUNITY_CHAT_IDS = [
|
||
c.strip() for c in os.getenv('TELEGRAM_COMMUNITY_CHAT_IDS', '').split(',')
|
||
if c.strip()
|
||
]
|
||
TELEGRAM_INTERNAL_CHAT_IDS = [
|
||
c.strip() for c in os.getenv('TELEGRAM_INTERNAL_CHAT_IDS', '').split(',')
|
||
if c.strip()
|
||
]
|
||
|
||
# ————————————————— Klaim reward BP (V32..V34) —————————————————
|
||
# Poll interval (detik) saat mendekati jendela klaim; fee wallet + persentase
|
||
# 10% dari reward yang baru diklaim (floor 4 desimal).
|
||
CLAIM_RETRY_SECONDS = int(os.getenv('CLAIM_RETRY_SECONDS', '60'))
|
||
BP_FEE_WALLET = os.getenv('VEX_BP_FEE_WALLET', 'bpdbsjasprod')
|
||
BP_FEE_PERCENT = Decimal(os.getenv('VEX_BP_FEE_PERCENT', '0.10'))
|
||
|
||
# Kontrak token VEX = vex.token (⊥ eosio.token — tak ada di chain)
|
||
TOKEN_CONTRACT = 'vex.token'
|
||
VEX_SYMBOL = 'VEX'
|
||
VEX_PRECISION = 4
|
||
VEX_CHAIN_ID = 'f9f432b1851b5c179d2091a96f593aaed50ec7466b74f89301f957a83e56ce1f'
|