refactor: telegram config via pos config telegram; fix listener pipe + entertainment bugs

- Drop sender 'config'/'config set' subcommand — redundant with 'pos config
  telegram' (same POS_CONFIG registry: masked token input/display, chat-id
  validation, chmod 600); sender/listener error hints now point there.
- Listener: load_map now uses a \x1f delimiter, so mapped /commands
  containing '|' are no longer truncated at the first pipe.
- entertainment send: forward extra plugin args (previously dropped); pass
  '--' before the message so leading '-' plugin output isn't parsed as an
  option.
- write_config_key/cfg_write: replace unescaped sed writes with grep-v+append
  so values with &, |, \ round-trip safely.
- sync_systemd: daemon-reload after removing timer units.
- config-ui: 'digits' validation accepts negative group/supergroup chat ids.
This commit is contained in:
Your Name
2026-08-09 12:22:12 +00:00
parent 97e9d57f45
commit 4d8f70d770
12 changed files with 53 additions and 102 deletions
+10 -9
View File
@@ -29,7 +29,7 @@ Commands:
Push the mapped /commands to the bot's "/" menu (setMyCommands)
--run Run the polling loop in the foreground (used by the service)
Config: $CONFIG_FILE (TELEGRAM_BOT_TOKEN, TELEGRAM_CHAT_ID)
Config: $CONFIG_FILE (TELEGRAM_BOT_TOKEN, TELEGRAM_CHAT_ID — edit with 'pos config telegram')
Map: $MAP_FILE — '/cmd=bash command' per line (optional
'/cmd::short description=bash command' shown in the bot menu)
@@ -76,8 +76,9 @@ load_config() {
# ── command map (MAP_FILE) ──────────────────────────────────────
# Lines: /cmd=bash command, or /cmd::description=bash command. Keys keep the
# leading slash; read via awk so values may contain '='. The map is re-read
# per message — edits apply without restarting the listener.
# leading slash; read via awk so values may contain '='. Entries are emitted
# with a \x1f (unit separator) delimiter so bash commands may contain pipes.
# The map is re-read per message — edits apply without restarting the listener.
map_entries() {
[ -f "$MAP_FILE" ] || return 0
@@ -90,7 +91,7 @@ map_entries() {
cmd="$left"
desc=""
fi
printf '%s|%s|%s\n' "$cmd" "$desc" "${line#*=}"
printf '%s\x1f%s\x1f%s\n' "$cmd" "$desc" "${line#*=}"
done
}
@@ -132,8 +133,8 @@ MAP_CMDS=(); MAP_VALS=(); MAP_DESCS=(); MAP_N=0
load_map() {
MAP_CMDS=(); MAP_VALS=(); MAP_DESCS=(); MAP_N=0
[ -f "$MAP_FILE" ] || return 0
local i=0 line cmd desc value
while IFS='|' read -r cmd desc value; do
local i=0 cmd desc value
while IFS=$'\x1f' read -r cmd desc value; do
[ -n "$cmd" ] || continue
i=$((i + 1))
MAP_CMDS[$i]="$cmd"; MAP_DESCS[$i]="$desc"; MAP_VALS[$i]="$value"
@@ -182,7 +183,7 @@ build_commands_json() {
sync_bot_commands() {
load_config
[ -n "${TELEGRAM_BOT_TOKEN:-}" ] || { warn "no bot token — run 'pos communication telegram config set TELEGRAM_BOT_TOKEN=...' first"; return 1; }
[ -n "${TELEGRAM_BOT_TOKEN:-}" ] || { warn "no bot token — run 'pos config telegram' first"; return 1; }
command -v jq &>/dev/null || { warn "jq not found — cannot sync bot commands"; return 1; }
local json n
json="$(build_commands_json)"
@@ -462,8 +463,8 @@ handle_message() {
run_daemon() {
command -v jq &>/dev/null || err "jq not found (install jq — in preinstall PACKAGES)"
load_config
[ -n "${TELEGRAM_BOT_TOKEN:-}" ] || err "No bot token — run 'pos communication telegram config set TELEGRAM_BOT_TOKEN=...'"
[ -n "${TELEGRAM_CHAT_ID:-}" ] || err "No chat id — run 'pos communication telegram config set TELEGRAM_CHAT_ID=...'"
[ -n "${TELEGRAM_BOT_TOKEN:-}" ] || err "No bot token — run 'pos config telegram'"
[ -n "${TELEGRAM_CHAT_ID:-}" ] || err "No chat id — run 'pos config telegram'"
sync_bot_commands || true
local offset=0
+6 -56
View File
@@ -1,8 +1,8 @@
#!/usr/bin/env bash
set -euo pipefail
# POS: communication telegram-sender — Send Telegram messages/files/links/stickers via Bot API (send, test, config set)
# POS: communication telegram-sender — Send Telegram messages/files/links/stickers via Bot API (send, test)
# POS_FLAGS: --type --caption --parse-mode --no-preview --token --chat-id --markdown
# POS_SUBCMDS: send test config
# POS_SUBCMDS: send test
# POS_CONFIG: telegram | telegram.env | TELEGRAM_BOT_TOKEN=secret:Bot token from @BotFather | TELEGRAM_CHAT_ID=digits:Numeric chat id from @userinfobot
CONFIG_DIR="$HOME/.config/linux_post_install"
@@ -18,8 +18,6 @@ Send Telegram messages via the Bot API.
Commands:
send <value> [options] Send a message, link, or media (auto-detects the type)
test Send a test message using the current config
config Show current config (token masked)
config set KEY=VALUE Set TELEGRAM_BOT_TOKEN or TELEGRAM_CHAT_ID
Types (auto-detected when --type is omitted):
message Plain text (default)
@@ -41,8 +39,8 @@ Options:
--token <t> Override token for one send
--chat-id <id> Override chat id for one send
Config file: $CONFIG_FILE
Keys: TELEGRAM_BOT_TOKEN | TELEGRAM_CHAT_ID
Config: $CONFIG_FILE (TELEGRAM_BOT_TOKEN, TELEGRAM_CHAT_ID)
edit it with 'pos config telegram'
Precedence: CLI flags > environment > config file.
@@ -75,20 +73,10 @@ load_config() {
done < <(grep -E '^[A-Z_]+=' "$CONFIG_FILE" || true)
}
mask_token() {
local t="$1"
[ -z "$t" ] && { echo "(not set)"; return; }
if [ "${#t}" -le 12 ]; then
echo "${t:0:4}... (${#t} chars)"
else
echo "${t:0:6}...${t: -4} (${#t} chars)"
fi
}
send_request() {
local endpoint="$1"; shift
[ -z "${TELEGRAM_BOT_TOKEN:-}" ] && err "No bot token — run 'pos communication telegram config set TELEGRAM_BOT_TOKEN=...'"
[ -z "${TELEGRAM_CHAT_ID:-}" ] && err "No chat id — run 'pos communication telegram config set TELEGRAM_CHAT_ID=...'"
[ -z "${TELEGRAM_BOT_TOKEN:-}" ] && err "No bot token — run 'pos config telegram'"
[ -z "${TELEGRAM_CHAT_ID:-}" ] && err "No chat id — run 'pos config telegram'"
curl -fsS -m 60 -X POST "$API/bot${TELEGRAM_BOT_TOKEN}/${endpoint}" "$@" >/dev/null
}
@@ -211,37 +199,6 @@ cmd_send() {
echo "[+] $type${auto:+ (auto-detected)} sent to chat ${TELEGRAM_CHAT_ID}"
}
cmd_config() {
load_config
echo "Config: $CONFIG_FILE"
echo " TELEGRAM_BOT_TOKEN = $(mask_token "${TELEGRAM_BOT_TOKEN:-}")"
echo " TELEGRAM_CHAT_ID = ${TELEGRAM_CHAT_ID:-}"
}
cmd_config_set() {
local kv="$1"
local key="${kv%%=*}"
local val="${kv#*=}"
case "$key" in
TELEGRAM_BOT_TOKEN|TELEGRAM_CHAT_ID) ;;
*) err "Unknown key '$key' (allowed: TELEGRAM_BOT_TOKEN, TELEGRAM_CHAT_ID)" ;;
esac
[ -z "$val" ] && err "No value given (expected $key=...)"
mkdir -p "$CONFIG_DIR"
if [ -f "$CONFIG_FILE" ]; then
if grep -q "^${key}=" "$CONFIG_FILE"; then
sed -i "s|^${key}=.*|${key}=${val}|" "$CONFIG_FILE"
else
echo "${key}=${val}" >>"$CONFIG_FILE"
fi
else
echo "${key}=${val}" >"$CONFIG_FILE"
fi
chmod 600 "$CONFIG_FILE"
echo "[+] $key saved to $CONFIG_FILE"
}
cmd="${1:-}"
case "$cmd" in
@@ -255,13 +212,6 @@ case "$cmd" in
send_message "Test message from pos $(date '+%Y-%m-%d %H:%M:%S')"
echo "[+] test message sent to chat ${TELEGRAM_CHAT_ID}"
;;
config)
shift
case "${1:-}" in
set) shift; [ $# -eq 1 ] || usage; cmd_config_set "$1" ;;
*) cmd_config ;;
esac
;;
*)
echo "ERROR: Unknown telegram command '$cmd'"
echo "Run 'pos communication telegram-sender --help' for usage."
+4 -4
View File
@@ -25,7 +25,7 @@ that stdout is what gets sent.
Modes:
(default) Send the plugin output to Telegram (silent)
--print Print the output locally instead of sending
--markdown Send with Markdown parse_mode (via pos communication telegram)
--markdown Send with Markdown parse_mode (via pos communication telegram sender)
Available plugins:
$plugins
@@ -69,7 +69,7 @@ dir="$(plugin_dir)"
script="$(resolve_plugin "$dir" "$plugin")"
rc=0
output="$( "$script" "$@" )" || rc=$?
output="$( "$script" "${plugin_args[@]}" )" || rc=$?
if [ "$rc" -ne 0 ]; then
err "Plugin '$plugin' failed (exit $rc)"
fi
@@ -87,7 +87,7 @@ telegram="$(dirname "$0")/pos-communication-telegram-sender"
[ -n "$telegram" ] && [ -x "$telegram" ] || err "pos-communication-telegram-sender not found next to this script"
if [ "$MARKDOWN" -eq 1 ]; then
exec "$telegram" send "$output" --parse-mode markdown
exec "$telegram" send --parse-mode markdown -- "$output"
else
exec "$telegram" send "$output"
exec "$telegram" send -- "$output"
fi