91 lines
2.2 KiB
Python
91 lines
2.2 KiB
Python
import logging
|
|
import sys
|
|
|
|
logging.basicConfig(
|
|
level=logging.INFO,
|
|
format="%(asctime)s [%(levelname)s] %(name)s: %(message)s",
|
|
)
|
|
logger = logging.getLogger(__name__)
|
|
|
|
|
|
def _process_filing(filing: dict):
|
|
from signals.filter_engine import process_filing
|
|
from alerts.slack_alert import send_slack_alert
|
|
import config
|
|
|
|
signal = process_filing(filing)
|
|
if signal is None:
|
|
return
|
|
|
|
logger.info(
|
|
f"Signal: {signal['ticker']} score={signal['score']} cluster={signal['cluster_size']}"
|
|
)
|
|
|
|
if config.SLACK_WEBHOOK_URL:
|
|
send_slack_alert(signal)
|
|
|
|
if config.ALPACA_KEY and config.ALPACA_SECRET:
|
|
from broker.alpaca_client import execute_signal
|
|
execute_signal(signal)
|
|
|
|
|
|
def _close_expired_positions():
|
|
import config
|
|
if config.ALPACA_KEY and config.ALPACA_SECRET:
|
|
from broker.alpaca_client import close_expired_positions
|
|
close_expired_positions()
|
|
|
|
|
|
def cmd_run():
|
|
from db.db import init_db
|
|
from ingestion.edgar_poller import run_poller
|
|
|
|
init_db()
|
|
logger.info("Database initialized")
|
|
|
|
def on_new_filing(filing: dict):
|
|
_process_filing(filing)
|
|
_close_expired_positions()
|
|
|
|
run_poller(on_new_filing=on_new_filing)
|
|
|
|
|
|
def cmd_backtest():
|
|
from backtest.backtest import run_backtest, print_summary
|
|
import config
|
|
|
|
logger.info("Running backtest...")
|
|
summary = run_backtest(
|
|
db_path=config.DB_PATH,
|
|
holding_days=config.HOLDING_PERIOD_DAYS,
|
|
min_score=config.SCORE_ALERT_THRESHOLD,
|
|
min_cluster_size=config.MIN_CLUSTER_SIZE,
|
|
)
|
|
print_summary(summary)
|
|
|
|
|
|
def cmd_fetch_once():
|
|
from db.db import init_db
|
|
from ingestion.edgar_poller import fetch_and_store_new_filings
|
|
|
|
init_db()
|
|
filings = fetch_and_store_new_filings()
|
|
logger.info(f"Fetched and stored {len(filings)} new filings")
|
|
|
|
for filing in filings:
|
|
_process_filing(filing)
|
|
|
|
|
|
COMMANDS = {
|
|
"run": cmd_run,
|
|
"backtest": cmd_backtest,
|
|
"fetch-once": cmd_fetch_once,
|
|
}
|
|
|
|
if __name__ == "__main__":
|
|
cmd = sys.argv[1] if len(sys.argv) > 1 else "run"
|
|
if cmd not in COMMANDS:
|
|
print(f"Usage: python main.py [{' | '.join(COMMANDS)}]")
|
|
sys.exit(1)
|
|
COMMANDS[cmd]()
|