You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Callstack is becoming a long-running Pi PBX/SMS service, but deployment configuration is still scattered: server.py has hard-coded host/port defaults, ModemConfig is constructed manually, and the CLI only supports flags plus --sim-pin-env. A small redacted environment/config loader would make installs repeatable without encouraging users to paste SIM PINs, API keys, or modem details into code or logs.
This is intentionally narrower than dashboard/realtime work: provide one safe configuration path that server.py and CLI commands can share.
User journey
A user creates a local environment file or service manager environment:
Then they can run the same configuration through the server and CLI:
python server.py
callstack status
callstack send --to '<redacted test recipient>' --body 'test'
Invalid values fail before opening serial ports, and any diagnostic output redacts secrets.
API / UX sketch
Add a documented helper such as ModemConfig.from_env(prefix="CALLSTACK_") or load_modem_config_from_env(os.environ).
Add a small HTTP/server config helper for host, port, API-key source, and rate-limit settings if that does not fit ModemConfig.
CLI flags continue to override env-derived defaults.
API keys should be loaded from a file path or secret env var without ever printing the key values. Prefer CALLSTACK_API_KEYS_FILE; if CALLSTACK_API_KEYS is supported, docs must warn that process environments can be visible to local admins/tools.
CALLSTACK_SIM_PIN_ENV names the variable holding the PIN; do not print the value.
Technical approach
Keep ModemConfig focused on modem settings; if HTTP settings are needed, add a tiny dataclass near server.py or in a new module such as callstack/server_config.py.
Parse and validate numeric values (baudrate, command_timeout, reconnect_interval, HTTP port, rate limit) before constructing runtime services.
Make the loader pure/testable by passing a mapping rather than reading globals directly in tests.
Update server.py to use the loader instead of hard-coded ModemConfig() and constants where practical.
Update callstack/cli.py so env-derived defaults are used, with explicit flags still taking precedence.
Ensure repr()/errors/logging never include SIM PIN values, API keys, SMS bodies, phone numbers, or full webhook URLs.
Affected modules
callstack/config.py
callstack/cli.py
server.py
Optional new module: callstack/server_config.py
Tests: tests/test_config.py, tests/test_cli.py, tests/test_api_auth.py or a new tests/test_server_config.py
Docs: README configuration / HTTP server sections
Hardware / modem caveats
Defaults should remain compatible with the current SIMCOM-oriented /dev/ttyUSB2 and /dev/ttyUSB4 examples.
Env loading must not mask the need for safe discovery/capability work; it should only configure explicit ports or documented defaults.
SIM PIN/PUK handling is sensitive. This issue should support reading an existing SIM PIN secret by env var name, but it must not expose public PUK recovery or credential-bearing commands.
Acceptance criteria
A pure config loader maps documented CALLSTACK_* values to ModemConfig and server settings.
CLI commands use env-derived defaults, while explicit CLI flags still win.
server.py uses env/server config for host, port, API keys, and modem settings instead of relying solely on hard-coded constants.
Invalid numeric values fail with clear, non-secret errors before opening serial ports or starting the HTTP server.
API keys and SIM PIN values are never printed, logged, returned in JSON, or included in exception messages.
README documents a minimal systemd/container-friendly env example with redacted placeholders.
Existing tests for auth, CLI, and config continue to pass without real hardware.
Motivation
Callstack is becoming a long-running Pi PBX/SMS service, but deployment configuration is still scattered:
server.pyhas hard-coded host/port defaults,ModemConfigis constructed manually, and the CLI only supports flags plus--sim-pin-env. A small redacted environment/config loader would make installs repeatable without encouraging users to paste SIM PINs, API keys, or modem details into code or logs.This is intentionally narrower than dashboard/realtime work: provide one safe configuration path that
server.pyand CLI commands can share.User journey
A user creates a local environment file or service manager environment:
Then they can run the same configuration through the server and CLI:
Invalid values fail before opening serial ports, and any diagnostic output redacts secrets.
API / UX sketch
ModemConfig.from_env(prefix="CALLSTACK_")orload_modem_config_from_env(os.environ).ModemConfig.CALLSTACK_API_KEYS_FILE; ifCALLSTACK_API_KEYSis supported, docs must warn that process environments can be visible to local admins/tools.CALLSTACK_SIM_PIN_ENVnames the variable holding the PIN; do not print the value.Technical approach
ModemConfigfocused on modem settings; if HTTP settings are needed, add a tiny dataclass nearserver.pyor in a new module such ascallstack/server_config.py.baudrate,command_timeout,reconnect_interval, HTTP port, rate limit) before constructing runtime services.server.pyto use the loader instead of hard-codedModemConfig()and constants where practical.callstack/cli.pyso env-derived defaults are used, with explicit flags still taking precedence.repr()/errors/logging never include SIM PIN values, API keys, SMS bodies, phone numbers, or full webhook URLs.Affected modules
callstack/config.pycallstack/cli.pyserver.pycallstack/server_config.pytests/test_config.py,tests/test_cli.py,tests/test_api_auth.pyor a newtests/test_server_config.pyHardware / modem caveats
/dev/ttyUSB2and/dev/ttyUSB4examples.Acceptance criteria
CALLSTACK_*values toModemConfigand server settings.server.pyuses env/server config for host, port, API keys, and modem settings instead of relying solely on hard-coded constants.Exact gates
Non-goals
callstack doctorwork for discovery.