Env Vars / docs-site/
v0.3.5 VOPI build

Environment variables

All DISCORD_VOICE_LIVE_* env vars the plugin reads. Defaults shown in bold.

Required

VarDescription
DISCORD_BOT_TOKENDiscord bot token
GEMINI_API_KEYGoogle Gemini API key
DISCORD_VOICE_LIVE_USER_IDYour Discord snowflake — the bridge listens to this user

Core

VarDefaultDescription
GEMINI_MODELgemini-3.1-flash-live-previewPrimary Gemini Live model
GEMINI_LIVE_MODEL_FALLBACKSComma-separated fallback models, tried in order if primary fails
DISCORD_VOICE_LIVE_VOICEen-US-JennyNeuralTTS voice (criterion #3 — high-pitched female)
DISCORD_VOICE_LIVE_PORT18943Sidecar HTTP control port
DISCORD_VOICE_LIVE_ALLOWED_SPEAKERSemptyComma-separated list of user IDs the bridge accepts audio from. Empty = listen to the channel.
DISCORD_VOICE_LIVE_AUTO_LEAVE_QUIET_SECONDS900Idle timeout (15 min) before the bridge auto-leaves
DISCORD_VOICE_LIVE_AUTO_LEAVE_MIN_UPTIME_SECONDS30Don't auto-leave within the first 30s of a session (avoids killing right after start)
DISCORD_VOICE_LIVE_LEAVE_PHRASES(built-in list)Phrases that trigger /voice-live-leave (e.g. "stop", "hang up", "bye", "exit voice")
DISCORD_VOICE_LIVE_GREETINGOptional greeting text on first turn
DISCORD_VOICE_LIVE_CLEAR_ON_INTERRUPTtrueWhen user interrupts the model, clear the audio queue
DISCORD_VOICE_LIVE_NOTES_DIR~/.hermes/voice-live-notes/Where to write per-call notes
DISCORD_VOICE_LIVE_KEEP_AUTOSTART_FILEfalseIf true, the autostart file is not deleted after use
DISCORD_VOICE_LIVE_AUTOSTARTfalseAuto-join the channel in voice-live-autostart.json on gateway boot
DISCORD_VOICE_LIVE_AUTOSTART_FILE~/.hermes/voice-live-autostart.jsonPath to the autostart file
DISCORD_VOICE_LIVE_GUILD_IDGuild ID for autostart; required if autostart is enabled
DISCORD_VOICE_LIVE_CHANNEL_IDVoice channel ID for autostart; required if autostart is enabled

Voice output

VarDefaultDescription
GEMINI_AUDIO_STREAM_IDLE_END_SECONDS0.25Time of audio silence before the model considers the user turn ended
DISCORD_VOICE_LIVE_OUTPUT_PREROLL_MS200Pre-roll audio before first byte lands in Discord
DISCORD_VOICE_LIVE_OUTPUT_TAIL_PAD_MS120Tail padding after last byte (prevents click on natural ends)
DISCORD_VOICE_LIVE_OUTPUT_FADE_IN_MS60Fade-in on each chunk (prevents click on joins)
DISCORD_VOICE_LIVE_OUTPUT_READ_WAIT_SECONDS0.05How long LiveAudioSource.read() blocks waiting for the next chunk

Idle prompts

VarDefaultDescription
DISCORD_VOICE_LIVE_IDLE_PROMPT_SECONDS120Seconds of inactivity before the model generates a nudge
DISCORD_VOICE_LIVE_IDLE_PROMPT_GRACE_SECONDS30Initial grace period after session start before nudging
DISCORD_VOICE_LIVE_IDLE_PROMPT_TEXT(built-in)The nudge prompt injected after idle timeout

SFX library

See sfx-library.md for full list. Highlights:

VarDefaultDescription
DISCORD_VOICE_LIVE_SFX_ENABLEDtrueMaster enable
DISCORD_VOICE_LIVE_SFX_DIR~/.hermes/voice-users/sfx/Default sfx directory
DISCORD_VOICE_LIVE_SFX_<SLOT>per-slotPer-slot WAV path override
DISCORD_VOICE_LIVE_SFX_<SLOT>_VOLUMEper-slotPer-slot volume (0.0-1.5)

Slots: TOOL_INIT, ERROR, NOTIFICATION, TRANSITION.

Typing sfx (legacy single-slot)

VarDefaultDescription
DISCORD_VOICE_LIVE_TYPING_SOUNDtrueEnable the keyboard click sfx on tool calls
DISCORD_VOICE_LIVE_TYPING_SFX~/.hermes/voice-live-typing.wavPath to the WAV
DISCORD_VOICE_LIVE_TYPING_SFX_VOLUME0.35Volume
DISCORD_VOICE_LIVE_TYPING_SYNTH_FALLBACKfalseIf true and the WAV is missing, generate a synthetic click instead of going silent

Video

VarDefaultDescription
  • DISCORD_VOICE_LIVE_VIDEO_MAX_FPS | 1 | Hard cap on feeder frame rate. Gemini rejects faster anyway. |
  • DISCORD_VOICE_LIVE_VIDEO_MAX_BYTES | 524288 | Per-frame JPEG size cap (512 KB). |
  • DISCORD_VOICE_LIVE_VIDEO_WHEN_RECENT_AUDIO_SECONDS | 8 | Drop frames if no voice activity in the last N seconds. |
  • DISCORD_VOICE_LIVE_VIDEO_INITIALIZED_QUIET_THRESHOLD_S | 30 | Webhook announce fires only when a frame is accepted after at least this many seconds of silence. |
  • DISCORD_VOICE_LIVE_VIDEO_ENABLED | true | Allow video frame input |
  • DISCORD_VOICE_LIVE_VIDEO_STATE_DETECTION | true | Auto-react to video enable/disable |
  • DISCORD_VOICE_LIVE_VIDEO_STATE_POLL_INTERVAL_SECONDS | 2.0 | Poll interval for video state changes |

Tool enable/disable

VarDefaultDescription
DISCORD_VOICE_LIVE_LOCAL_TOOLStrueAll local tools (umbrella)
DISCORD_VOICE_LIVE_WEB_TOOLStrueWeb search / extract
DISCORD_VOICE_LIVE_SPOTIFY_TOOLStrueSpotify playback
DISCORD_VOICE_LIVE_GITHUB_TOOLStrueGitHub repo / issue / PR tools
DISCORD_VOICE_LIVE_HA_TOOLStrueHome Assistant
DISCORD_VOICE_LIVE_OPENCODE_TOOLStrueOpencode delegation
DISCORD_VOICE_LIVE_SYSINSPECT_TOOLStrueSystem inspection
DISCORD_VOICE_LIVE_EMAIL_TOOLStrueEmail read / send / reply / brief

Webhooks

See webhooks.md. One env var per event class, all start with DISCORD_VOICE_LIVE_WEBHOOK_<CLASS>.

VarDefaultDescription
DISCORD_VOICE_LIVE_WEBHOOK_THROTTLE_SECONDS60Default throttle window when throttle_key is set

Email brief

See email-brief.md.

VarDefaultDescription
DISCORD_VOICE_LIVE_EMAIL_BRIEF_ENABLEDtrueEnable the scheduler
DISCORD_VOICE_LIVE_EMAIL_BRIEF_INTERVAL_SECONDS180030 min default
DISCORD_VOICE_LIVE_EMAIL_BRIEF_LIMIT8Max emails per brief

Per-email reminder loop

VarDefaultDescription
DISCORD_VOICE_LIVE_EMAIL_REMINDER_ENABLEDtrueEnable per-email pings
DISCORD_VOICE_LIVE_EMAIL_REMINDER_POLL_SECONDS1202 min poll interval
DISCORD_VOICE_LIVE_EMAIL_REMINDER_MAX_PER_HOUR3Cap pings per hour to avoid spam

Notification system

VarDefaultDescription
DISCORD_VOICE_LIVE_NOTIFY_TIMEOUT10HTTP timeout for webhook delivery (s)

Honcho integration

VarDefaultDescription
VOICE_LIVE_HONCHO_CONTEXTtrueInject Honcho context into the system prompt
VOICE_LIVE_HONCHO_MAX_CHARS1200Cap Honcho context block size
VOICE_LIVE_HONCHO_PEER(user_id)Override the Honcho peer name

Opencode delegation

VarDefaultDescription
OPENCODE_BIN~/.local/bin/opencodePath to opencode binary
OPENCODE_DEFAULT_MODEL(opencode default)Model passed to opencode
OPENCODE_TMUX_SESSIONvoice-opencodeTmux session name
DISCORD_VOICE_LIVE_OPENCODE_WATCHERtrueWatch opencode tmux sessions for status changes
DISCORD_VOICE_LIVE_OPENCODE_WATCHER_POLL_SECONDS2.0Poll interval
DISCORD_VOICE_LIVE_OPENCODE_WATCHER_INITIAL_DELAY_SECONDS5Delay before first poll after session start
DISCORD_VOICE_LIVE_OPENCODE_WATCHER_MIN_VOICE_GAP_SECONDS10Minimum gap between narrations to avoid spam

Misc

VarDefaultDescription
VOICE_USERS_DIR~/.hermes/voice-users/Per-user profile directory
VOICE_OWNER_DISCORD_ID(env)Used for owner-only commands
HERMES_PYTHONpython3Python interpreter for subprocess calls
GOOGLE_API_BIN(auto-detected)Path to google_api.py for email + Google Workspace
HASS_URLhttp://homeassistant.local:8123Home Assistant base URL
HASS_TOKENHome Assistant long-lived access token