Repository navigation
Expand file tree
/
Copy path.env.example
More file actions
123 lines (105 loc) · 7.37 KB
/
Copy path.env.example
File metadata and controls
123 lines (105 loc) · 7.37 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
# =============================================================================
# mimir-stellar/telegram-bot — copy to .env and fill in. Never commit .env.
# =============================================================================
# ── Profiles (optional) ──────────────────────────────────────────────────────
# MIMIR_PROFILE=mock selects the local mock profile for anything below that is
# left unset: loopback RPC (127.0.0.1:8420), fixture contract ids, an isolated
# data/cursor.mock.json, and placeholder Telegram values so config validation
# passes without credentials. Explicit variables always win over profile
# defaults, and any other profile name fails fast at startup. Leave unset for
# normal Testnet operation — see README "Local mock profile".
# MIMIR_PROFILE=mock
# ── Telegram ─────────────────────────────────────────────────────────────────
# Bot token from @BotFather (/newbot). Required.
BOT_TOKEN=
# Where notifications are posted. A negative id is a group/channel
# (e.g. -1001234567890); a positive id is a private chat. Required.
# See the README for how to find it.
TELEGRAM_CHAT_ID=
# Optional per-contract destinations. When omitted, both sources use
# TELEGRAM_CHAT_ID for backwards-compatible single-chat deployments.
# TELEGRAM_MARKET_CHAT_ID=
# TELEGRAM_SQUAD_CHAT_ID=
# Optional allowlist for the /status command. Comma-separated list of chat ids
# or @channelusernames. When set, /status is silently ignored in any chat not
# on the list. When absent or empty, /status works in any chat the bot can see.
# Example: ALLOWED_CHAT_IDS=-1001234567890,-1009876543210,@mypublicchannel
# ALLOWED_CHAT_IDS=
# ── Mimir Soroban contracts (Stellar Testnet) ────────────────────────────────
# The live deployment the bot watches. These are the same contract ids the
# Mimir app reads as NEXT_PUBLIC_STELLAR_MARKET_CONTRACT_ID /
# NEXT_PUBLIC_STELLAR_SQUAD_CONTRACT_ID — this repo is not a Next.js app, so
# there is no NEXT_PUBLIC_ prefix here. Both are required.
MARKET_CONTRACT_ID=CDV6JXIJCALSXQELCS6YUEWJWG5DFXQK5PJ5I7MWI6KVMQJBC5DLPKZI
SQUAD_CONTRACT_ID=CBPGVXHXLULUBVZ24D6XNSUX7NH45HYXGWHAJFWTBHXYNO72KDRKCDFY
# ── Network ──────────────────────────────────────────────────────────────────
# Soroban RPC is the only endpoint the poller needs: events are read with
# `getEvents`. Horizon is kept for the explorer/tx links and future account
# reads. The passphrase must match the RPC's own getNetwork().passphrase.
STELLAR_RPC_URL=https://soroban-testnet.stellar.org
STELLAR_HORIZON_URL=https://horizon-testnet.stellar.org
STELLAR_NETWORK_PASSPHRASE=Test SDF Network ; September 2015
# Optional explorer origin (no trailing slash required). Defaults to stellar.expert.
# STELLAR_EXPLORER_BASE_URL=https://stellar.expert/explorer
# ── Poller ───────────────────────────────────────────────────────────────────
# How often to ask the RPC for new events. Minimum 5000. Testnet closes a
# ledger about every 5s, so anything under ~15s mostly polls empty pages.
POLL_INTERVAL_MS=30000
# On a cold start with no data/cursor.json, how far back to look before
# tailing. Keep it small — this is a notifier, not a backfiller. ~5 ledgers/25s.
# START_LOOKBACK_LEDGERS=60
# Where the last-seen cursor is persisted. Needs to survive restarts; see the
# "Deployment" section of the README for persisting `data/` on an always-on host
# and the "Deploying on Railway" section for the volume-backed deployment.
# CURSOR_FILE=./data/cursor.json
# Exclusive lock so only one process owns the cursor / chat. Defaults next to
# the cursor file. A second live instance exits immediately with a clear error.
# INSTANCE_LOCK_FILE=./data/poller.lock
# Where the machine-readable status snapshot is written after every poll cycle.
# Read it with `npm start -- --status` (or `node dist/index.js --status`). It
# contains no secrets: the chat id is redacted and error strings are truncated.
# STATUS_FILE=./data/status.json
# Safety valve: most notifications sent in one poll cycle. The rest are
# skipped (logged, cursor commits after the page) so a burst cannot get the bot
# rate-limited by Telegram.
# MAX_NOTIFICATIONS_PER_CYCLE=20
# How many recent event ids to remember per contract so an event repeated by
# an overlapping page, a resumed cursor, or a restart is not posted twice.
# Oldest ids are evicted first, so the window never grows with history; 0
# disables deduplication.
# EVENT_DEDUP_WINDOW=256
# On SIGTERM/SIGINT, how long to wait for the cycle already in progress before
# flushing the cursor file and exiting. Notifications that have not been sent
# yet are dropped (counted, logged) so the drain stays inside this budget.
# 0 exits without waiting — safe for the file, but the restart resumes from the
# last completed cycle. Raise it if your RPC regularly takes longer than 10s.
# SHUTDOWN_TIMEOUT_MS=10000
# ── Health endpoint (local HTTP) ─────────────────────────────────────────────
# Loopback-only by default. Supervisors / deploy probes hit GET /health.
# Set HEALTH_PORT=0 to disable the listener (e.g. one-shot tooling).
# Note: For Docker deployments, set HEALTH_HOST=0.0.0.0 to expose it outside the container.
# HEALTH_HOST=127.0.0.1
# HEALTH_PORT=8787
# After the first successful poll, mark degraded if no success within this
# many milliseconds. 0 disables the stale check.
# HEALTH_STALE_MS=90000
# ── Railway (persistent-volume deployment) ───────────────────────────────────
# Railway injects `PORT`; when HEALTH_PORT is unset the health endpoint binds
# that port, so the deploy healthcheck (railway.json -> GET /health) probes the
# right listener with no override. The probe arrives via the container's
# network, not loopback, so override the loopback-only default to bind it:
# HEALTH_HOST=0.0.0.0
#
# The volume is declared in railway.json (requiredMountPath="/app/data") but a
# volume is never created by config: attach one at /app/data from the Railway
# dashboard or CLI (`railway volume add --mount-path /app/data`) before the
# first deploy. CURSOR_FILE keeps its default ./data/cursor.json, which resolves
# to /app/data/cursor.json in Railway's /app working directory — no code change.
# RAILWAY_VOLUME_NAME / RAILWAY_VOLUME_MOUNT_PATH are injected automatically.
#
# CaC (`railway.json`) is deprecated in favour of Railway Infrastructure as Code
# (`.railway/railway.ts`) with a hard cutoff of 2026-12-01; this file documents
# the current behaviour and simplifies migrating to IaC. See the README.
# ── Channel Preview Mode ─────────────────────────────────────────────────────
# When true, notifications sent to Telegram are formatted with a preview badge.
# CHANNEL_PREVIEW_MODE=false