correspond.settings#

Where correspond keeps state and reads configuration, and how it finds a secret.

  • The data root: the data_dir argument, else $CORRESPOND_DATA_DIR, else data_dir in the config file, else ~/.local/share/correspond (%LOCALAPPDATA%\correspond on Windows). Each kind of state has its own folder under it (cursors/, webinbox/, telegram/); nothing is written into a repository.

  • The config file: $CORRESPOND_CONFIG, else ~/.config/correspond/config.toml ($XDG_CONFIG_HOME; %APPDATA% on Windows). One table per channel:

    [ntfy]
    url = "https://ntfy.example.org"
    topic_keychain_service = "my-ntfy-topic"
    
  • A value comes from its environment variable, else the channel’s table in the config file, else its default. A secret is never read from the config file: it comes from its environment variable, else (on macOS) a Keychain item whose service name is <key>_keychain_service in the config (default correspond-<channel>-<key>).

Nothing here prints or logs a value; mask() is for showing that one is set.

Functions

channel_config(channel, *[, config])

The [channel] table of the config file ({} when absent).

config_path()

$CORRESPOND_CONFIG, else ~/.config/correspond/config.toml.

data_dir([data_dir])

The data root: the argument, else $CORRESPOND_DATA_DIR, else data_dir in the config, else ~/.local/share/correspond.

keychain_available()

Whether a Keychain lookup can happen here (macOS with the security tool).

keychain_get(service, *[, run])

A generic password from the macOS Keychain, or "" when absent, not on macOS, or slow.

keychain_service(channel, key, *[, config])

The macOS Keychain service a secret is looked up under.

load_config([path])

The parsed config file, or {} when there is none.

mask(value)

Enough of a secret to recognise it, never enough to use it.

correspond.settings.channel_config(channel, *, config=None)[source]#

The [channel] table of the config file ({} when absent).

Return type:

dict

correspond.settings.config_path()[source]#

$CORRESPOND_CONFIG, else ~/.config/correspond/config.toml.

Return type:

Path

correspond.settings.data_dir(data_dir=None)[source]#

The data root: the argument, else $CORRESPOND_DATA_DIR, else data_dir in the config, else ~/.local/share/correspond.

The environment variable and the config value must be absolute paths: a relative one would put state wherever the current directory happens to be (a repository, say).

>>> data_dir("state").is_absolute()
True
Return type:

Path

correspond.settings.keychain_available()[source]#

Whether a Keychain lookup can happen here (macOS with the security tool).

Return type:

bool

correspond.settings.keychain_get(service, *, run=<function run>)[source]#

A generic password from the macOS Keychain, or "" when absent, not on macOS, or slow.

Return type:

str

correspond.settings.keychain_service(channel, key, *, config=None)[source]#

The macOS Keychain service a secret is looked up under.

>>> keychain_service("telegram", "token", config={})
'correspond-telegram-token'
Return type:

str

correspond.settings.load_config(path=None)[source]#

The parsed config file, or {} when there is none. A broken file raises, naming it.

Return type:

dict

correspond.settings.mask(value)[source]#

Enough of a secret to recognise it, never enough to use it.

>>> mask("example-topic-3f9a"), mask("short"), mask(None)
('ex…9a', '…', '(not set)')
Return type:

str