Commit Graph

101 Commits

Author SHA1 Message Date
Your Name 3536f267c7 refactor: move usb/nfs tools into new 'share' category
- rename bin/pos-usb-server -> pos-share-usb-server, pos-system-nfs-{client,server} -> pos-share-nfs-{client,server}
- update # POS: headers, usage strings, INTERACTIVE_CMDS, usage() EXAMPLES, notify-scope comment
- docs: new DOC/howto/share.md (USB+NFS consolidated), drop usb.md + system.md NFS sections,
  POS.md ### share section, HOWTO/README/AGENT_Context/README/DEV/AGENTS updates
- make gen && make check green
2026-08-11 14:52:18 -04:00
Your Name b74dfffd0b feat: Matrix/Synapse sender + listener — second notify platform (telegram,matrix)
pos communication matrix sender: send (plain/--markdown/--room), login
(password->access token via m.login.password), test. Implements the
lib/notify.sh sender contract, so NOTIFY_PLATFORM=telegram,matrix now
fans out for real; matrix.env config scope registered for pos config.

pos communication matrix listener: systemd user daemon long-polling
/sync (since token, compact m.room.message filter); reacts to own user's
messages (/ and ! both resolve), threaded m.in_reply_to replies, @quiet
marker, ai bridge with per-room session, interactive editor. Added to
INTERACTIVE_CMDS.

Docs: POS.md, howto/communication.md, HOWTO.md, usage EXAMPLES.
Verified against a mock homeserver (send shape, login, owner filter,
replies, exit codes, editor). make gen && make check green.
2026-08-09 20:19:07 +00:00
Your Name 6e437cace8 fix: pos tree truncated when a category's last tool has no subcommands 2026-08-09 18:41:26 +00:00
Your Name 13fffb5775 feat: add config/event-rules.template — ready-made eventer rule set
Starter rules for CPU (pinned coretemp chip), load, memory, disk space,
SMART/NVMe health, network, and top processes. All verified to parse and
evaluate via the event-trigger parser; howto references the template.
2026-08-09 18:21:41 +00:00
Your Name 06858e34bb fix: CPU temp rule example pins coretemp chip
A bare 'sensors -u | grep -m1 temp1_input' can match a non-CPU chip's
temp1_input first (e.g. acpitz case temp 27.8 vs coretemp 46.0), so the
rule silently never fires. Example in config/event.env and howto now
target coretemp-isa-0000 + 'Package id 0' explicitly; howto notes the
gotcha.
2026-08-09 18:14:55 +00:00
Your Name 2e72ad1a44 chore: regen docs for event-trigger run value logging 2026-08-09 18:12:10 +00:00
Your Name 577d49ac2d fix: report skipped rules in event-trigger run; add lm-sensors dep
- run now counts rules skipped because their check produced no number (or
  the line was unparseable) and reports both counts, so an all-skipped pass
  no longer reads as 'evaluated 0 rule(s)'.
- preinstall.sh installs lm-sensors — the sensor example rules in event.env
  need it; howto troubleshooting notes to check 'sensors -u' output for the
  real *_input key before adding a rule.
2026-08-09 17:31:59 +00:00
Your Name 030ec0b456 feat: pos system event-trigger — state-based threshold monitors (eventer)
Each line of event.env is an independent rule: ["msg" if ] <check> <op> <thr>.
Check runs on every pass; first numeric output compared float-safe; op is the
rightmost 'op threshold' pair so checks with their own >/< parse fine. Alerts
once on false->true + one recovery message on true->false (no repeats while
the condition holds); per-rule state keyed by rule-line hash in
~/.local/share/linux_post_install/eventer/state/.

Subcommands: run (timer entrypoint), config (interactive add/remove/edit with
check-validation), list (rules + live values), enable [interval] (systemd
user timer pos-event-trigger.timer; 5m..weekly or OnCalendar; graceful without
a user manager, loginctl enable-linger attempt), disable, status. --dry-run
honors the DEV.md convention. Alerts via lib/notify.sh (Telegram default).

New: bin/pos-system-event-trigger, lib/eventer-lib.sh, config/event.env
template (no-clobber via postinstall), install.sh lib install, INTERACTIVE_CMDS
entry. Docs: POS.md system row, HOWTO.md index, howto/event-trigger.md.
make gen && make check green; functional tests cover trigger/recovery/no-repeat,
float+unit parsing, editor add/remove/edit + validation + dry-run, timer
enable/disable/status, dispatcher routing.
2026-08-09 17:09:59 +00:00
Your Name 2e57634877 feat: harden pos media mp3/mp4 — smart format selection, metadata, dry-run
Both tools: yt-dlp calls via spawn (honor DRY_RUN; --dry-run prints the
command and skips dep checks), -o/--output, --no-playlist, --cookies (with
file check), clean ffmpeg/yt-dlp guards, POS_FLAGS for completion, full
embedded metadata (--embed-metadata --embed-chapters --embed-thumbnail
--no-overwrites; mp3 adds --convert-thumbnails jpg + artist-from-uploader
parse-metadata). mp3 gains --by-artist (~/Music/<artist>/<title>.mp3).

mp4: -f <id>/--best/--worst skip the prompt (mutual-exclusion validated),
and the interactive picker now shows a curated [audio]/[video]/[combo]
format table on stderr (stdout carries only the chosen id — ui_pick
lesson), validates the id against the real -F output, and defaults empty
input to best. Docs: howto/media.md rewritten.
2026-08-09 15:56:47 +00:00
Your Name 0146dbe5f9 feat: ai bridge answers about replied-to Telegram messages
Extract reply_to_message.text (fallback caption) from each getUpdates
result and pass it to handle_message; the ai bridge prefixes the prompt
with '[Reply context — the message you are replying to]', so replying to
a /status output and asking 'ai check this details' gives the model the
actual output. AI bridge only — mapped /commands unchanged; context rides
in the user turn so the session records what was analyzed. Docs:
howto/ai.md bridge section.
2026-08-09 15:43:06 +00:00
Your Name 310367f3b2 feat: ai sessions + Telegram-friendly replies (--system, markdown strip)
pos ai gemini: --session gives ask/chat persistent memory
(~/.local/share/linux_post_install/ai/<name>.json, capped 40 turns),
new 'sessions' subcommand to list/clear; --system injects a Gemini
systemInstruction on every turn without storing it in the session file.
Telegram listener keeps one session per chat (telegram-<chat_id>), clears
on 'ai /reset', passes a Telegram-voice system prompt (emojis welcome),
and strips markdown from replies before sendMessage since messages are
sent as plain text. Docs: howto/ai.md flags/sessions/bridge behavior.
2026-08-09 15:32:39 +00:00
Your Name 1832a88c71 fix: pos config secret values corrupted by stray newline in captured input
cfg_read_secret is invoked via $() inside _cfg_edit_one, so the echo that
advanced the cursor after hidden input landed on the capture pipe instead of
the terminal — every secret value stored with pos config on a real TTY got a
leading newline (e.g. AI_GEMINI_API_KEY="\n<key>"), which neither cfg_value
nor the ai/telegram load_config parsers could read back: the menu showed
'(not set)' and pos ai gemini kept demanding a key.

Fix: send that newline to stderr (>&2). Defense in depth: cfg_write and
write_config_key now strip CR and truncate multi-line pastes, and the readers
(cfg_value, ai + telegram load_config) strip CR. Reproduced and verified on a
pseudo-TTY; piped-stdin tests never caught it because non-TTY input skips the
stty/echo path.
2026-08-09 15:08:29 +00:00
Your Name 23eede637a feat: pos ai gemini — CLI + Telegram AI chat (ask, chat, models)
- bin/pos-ai-gemini: one-shot ask (stdout-only, pipe-friendly), interactive
  multi-turn chat REPL (q/Ctrl+C, /reset), models list; --model override,
  default gemini-2.5-flash; key via x-goog-api-key header, never printed.
- Config scope 'ai' (AI_GEMINI_API_KEY secret, AI_GEMINI_MODEL) in
  ~/.config/linux_post_install/ai.env via 'pos config ai'; config/ai.env
  template installed no-clobber by postinstall.
- Telegram listener: non-command text starting with 'ai ' (case-insensitive)
  is answered by Gemini via 'pos ai gemini ask'; owner-chat only, errors
  reply with the pos config ai hint. Future intents slot in as case arms.
- ai-gemini added to INTERACTIVE_CMDS (chat reads stdin).
- Docs: POS.md ai section + listener bridge, howto/ai.md, HOWTO/README
  index rows, bin/pos usage example; make gen refreshed context/completions.
2026-08-09 14:40:15 +00:00
Your Name 0acdf3b346 fix: listener daemon read config from wrong HOME
enable_service baked Environment=HOME=$HOME into the unit at enable
time; a stale/wrong shell HOME made the daemon read an empty
~/.config/linux_post_install/telegram_commands.env — commands showed in
the bot menu (synced from the editor's correct HOME) but replying said
"unknown command" and /help said none mapped. systemd user services
already set the correct HOME; stop pinning it.
2026-08-09 14:09:10 +00:00
Your Name 52413a6a68 feat: pos tree — print the CLI command tree
pos tree derives the hierarchy live from bin/pos-* filenames + # POS:
/# POS_SUBCMDS: headers, so it always matches what the dispatcher can
run. Category-less tool (like pos-config); --depth N limits nesting.

Also sharpen the agent-facing docs that the work exposed:
- AGENTS.md: drop the stale "one category-less exception" claim; document
  the category-less pattern (pos-config, pos-tree) and that gen only reads
  the text after the first em-dash in # POS: headers
- DEV.md: category-less vs categorized rule + header extraction note
- AGENT_Context "Adding a New Tool": new step 0 — pin the exact CLI verb
  and runtime context (dev/repo-only vs installed) before writing code
- POS.md: new config + tree sections; category-less tools get their own
  sections
- README: pos tree bullet following the pos X convention
2026-08-09 12:50:52 +00:00
Your Name 4d8f70d770 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.
2026-08-09 12:22:12 +00:00
Your Name 498979a78d feat: telegram listener pushes command list to bot menu via setMyCommands
Map entries may now carry a menu description (/cmd::desc=bash) shown in
the bot's "/" menu; it falls back to the bash command (~40 chars) when
omitted. The command list is pushed automatically after every map edit,
on --enable, and at daemon start, plus a manual --sync-commands flag
(wired into POS_FLAGS completion). Names are validated against Telegram's
lowercase [a-z0-9_] rule — invalid ones are skipped from the menu with a
warning but still resolve when typed; an empty map clears the menu.

Fixes found by unit-testing the sync path: map_has always returned false
(awk END{exit 1} overrode the match), map_set had a local cross-reference
that broke under set -u, and warn() leaked into the generated JSON (now
stderr). Docs + AGENT_TODO updated; make gen && make check pass.
2026-08-09 09:54:05 +00:00
Your Name 95917607cf fix: infinite loop in pos completion walk-up caused CPU hang on TAB
_pos_complete_tool walks up the key looking for a tool that declares
POS_FLAGS/POS_SUBCMDS; "${k%-*}" on a dash-free key returns it
unchanged, so once the walk hit a bare category (e.g. 'system' from
system-nfs-server) the while loop spun at 100% CPU. Any TAB at an
argument position of a tool without flags/subcmds froze the shell.
Stop the walk-up when no dash remains.

Also refresh AGENTS.md quick facts and regenerate doc file table
(completions/pos.bash 278->279 lines).
2026-08-09 09:24:50 +00:00
Your Name fe7708f142 ai need continue 2026-08-09 04:57:28 -04:00
Your Name cb82acb155 fix: cache pos config scopes for completion; stop per-TAB registry scan
pos config <TAB> re-scanned every tool's '# POS_CONFIG:' header per
keypress (dozens of subshells, greps, seds). On the loaded homelab box a
stuck completion wedged interactive shells at 69% CPU for ~an hour. make
gen now emits a static _pos_config_scopes array into completions/pos.bash
(no runtime scan; live-scan fallback if the cache is missing).
2026-08-09 04:31:07 -04:00
Your Name 0b7fdb4954 feat: pos config — interactive config editor driven by the POS_CONFIG registry
Add bin/pos-config + lib/config-ui.sh: reads the '# POS_CONFIG:' headers
across tools into a unified runtime config (~/.config/linux_post_install/
<scope>.env, chmod 600). Secret masking with show/hide, digits:/num:/url:
validation, '-' clears, blank keeps; '*plugins' expands entertainment
plugin vars from entertainment-lib.sh. pos config with no scope opens a
picker (scope list when not a TTY); completion offers scopes from the
registry at runtime.

gen-docs.sh now handles category-less tools (pos-config) instead of
emitting pos-config-config; fix set -e/pipefail abort that truncated the
header registry mid-read. install.sh ships config-ui.sh.
2026-08-09 03:57:17 -04:00
Your Name 873ae84b49 refactor: rename telegram tool to pos-communication-telegram-sender; drop --send legacy alias
The --send flag duplicated the send subcommand — completion suggested both.
Now 'pos communication telegram <TAB>' completes to just 'sender' and
'listener'. send is the single canonical action.

- git mv bin/pos-communication-telegram bin/pos-communication-telegram-sender
- remove --send branch + POS_FLAGS entry; add --markdown to completion
- lib/notify.sh: notify_sender_name() maps platform telegram -> telegram-sender
  (notify_send otherwise looks for bin/pos-communication-telegram)
- pos-system-health --send 'sent:' check + pos-entertainment-send use the new
  name and the send subcommand
- completion: keys with nested tools but no direct tool complete to the group
  suffixes (sender/listener); --type/--parse-mode value completion moved to
  the new word positions
- docs updated (POS.md, AGENT_Context, DEV.md, SCRIPTS.md, notify.env,
  HOWTO.md, postinstall.sh); removed phantom webhook/log/broadcast subcommands
  from howto/communication.md
2026-08-09 03:28:30 -04:00
Your Name 16bc6685f8 fix: honor --dry-run across install phases; repair repo conventions and doc drift
- spawn() now respects DRY_RUN, install.sh exports it to child phases, and
  postinstall.sh wraps every user-home mutation in run() — '--dry-run' no
  longer runs apt/install/clone or edits dotfiles for real
- gen-docs.sh chmods regenerated files to 644 (mktemp mv left them at 0600)
- make check now syntax-checks apps/, entertainment/, features/, templates/
- .gitignore protects config/authorized_keys + config/rclone.conf; drop the
  tracked empty authorized_keys and the stray 6 MB session file
- pos-system-health --send prints 'sent:' only when a platform sender exists,
  otherwise warns on stderr (notify_send is silent-fail)
- standardize sourced libs (no shebang); refresh AGENT_Context/DEV/APPS/SCRIPTS
  doc drift: notify.sh in lib lists, pos-health systemd units, tsui, scripts/,
  INTERACTIVE_CMDS list, entertainment scheduler (systemd timers only)
2026-08-09 03:01:58 -04:00
Your Name 7dff27206b fix: health --send is notification-only; listener @quiet prefix kills double reply 2026-08-07 14:15:33 -04:00
Your Name 81ac553590 fix: entertainment 1h timer never fired (invalid OnCalendar); drop cron backend, systemd-only 2026-08-07 13:43:45 -04:00
Your Name f99acc36a2 feat: nested pos subcommands — POS_SUBCMDS header, nested category help + completion 2026-08-06 04:01:39 -04:00
Your Name b9edd07801 feat: pos communication telegram listener — /command to bash map + owner-only daemon 2026-08-06 03:48:08 -04:00
Your Name 03e9d4c8e6 feat: add pos system nfs-server and nfs-client (systemd persistent mounts) 2026-08-06 03:19:42 -04:00
Your Name aac3c5266a docs: fix BACKUP_SERVICE_ROOTS default in system how-to (runtime $HOME, not /home/you) 2026-08-06 03:09:52 -04:00
Your Name 8bef0f8c6d docs: add pos HOW-TO guide set (index + 8 category guides) 2026-08-06 02:54:36 -04:00
Your Name 025971ca1e feat: multi-platform alerting + shared system.env config with dynamic help values
- lib/notify.sh: route notify_send to every platform in NOTIFY_PLATFORM
  (notify.env, default telegram; comma-separated = send to all). New
  platforms need only a bin/pos-communication-<p> sender implementing
  'send <value> [--markdown]' (Matrix/Synapse ready)
- pos-communication-telegram: add --markdown as alias for --parse-mode
  markdown to match the sender contract
- lib/common.sh: load_system_env() — shared ~/.config/linux_post_install/
  system.env for pos-system-* tools (env exported > file > default)
- pos-system-health/backup: load system.env and show effective dynamic
  values (NOTIFY_PLATFORM, HEALTH_BACKUP_MAX_AGE_DAYS, BACKUP_SERVICE_ROOTS)
  in --help
- config/system.env + config/notify.env templates copied by postinstall
- systemd/pos-health.service: EnvironmentFile for both configs so the
  daily digest honors them
2026-08-06 02:37:56 -04:00
Your Name 9a94329dd0 feat: add pos system health, lib/notify.sh, and daily Telegram digest timer
- bin/pos-system-health: host dashboard (disk, RAM, failed units, backup age,
  fail2ban, docker); exits 1 on any FAIL; --send/--markdown via Telegram
- lib/notify.sh: self-contained opt-in alerting helper; silent-fails, wired
  into pos-system-backup (success + ERR trap) and pos-system-firewall
- systemd/pos-health.{service,timer}: 08:00 digest as installing user;
  postinstall enables timer once telegram.env exists, now copies *.timer
- AGENT_TODO.md: worklist with Now/Next/Later/Done history; linked from AGENTS.md
2026-08-06 02:25:23 -04:00
Your Name cf36780c0f docs: add Document Map index + Entertainment section to agent context
- AGENT_Context opens with a generated Document Map (section → line ranges)
- gen-docs.sh: new gen_docmap block, self-referential (converges to a
  fixed point so line numbers stay accurate)
- new '## 8. Entertainment Module' section (CLI, lib, plugins, config,
  scheduler, pointers); renumber following sections 8-13 -> 9-14
- AGENTS.md: reference the Document Map; document the make check/gen gate
2026-08-06 01:59:35 -04:00
Your Name 7e28769ec5 add entetaiment features 2026-08-06 01:48:24 -04:00
Your Name d722842d20 add auto trig for api and send via telegram 2026-08-05 11:49:27 -04:00
Your Name bd92c7f899 feat: auto-install config/entertainment.env (default Al-Hasakah weather) on install 2026-08-05 14:59:50 +00:00
Your Name 2aaf5cff62 feat: add entertainment module — public-API plugins (weather, joke) sent via Telegram by default (pos entertainment send) 2026-08-05 14:45:51 +00:00
Your Name e3762f4074 feat: add --parse-mode (plain|markdown|html) to pos communication telegram 2026-08-05 14:45:10 +00:00
Your Name 330a3ba0b4 fix: add yt-dlp dep guard to pos-media-mp3/mp4 (clean error instead of raw command-not-found) 2026-08-05 14:23:03 +00:00
Your Name 7e2ecba219 chore: add doc/code sync gate (make gen + make check + pre-commit hook)
- bin/pos: usage() CATEGORIES now auto-derived from pos-* filenames
  (kill the stale cheat-sheet bug class); only EXAMPLES stays hand-written
- # POS: / # POS_FLAGS: headers on all 15 tools = single source of truth
  for generated docs; template updated
- scripts/gen-docs.sh: regenerates GEN-marker sections (bin tree, dispatch
  table, no-common.sh list, line-count table, completion flags)
- scripts/check-sync.sh: bash -n + exec bits + doc/code drift + smoke
- Makefile: make gen / make check; scripts/install-hooks.sh: opt-in hook
- DEV.md + AGENT_Context: add-a-tool flow is now header + make check
2026-08-05 14:11:14 +00:00
Your Name e62626b55c ai need to continue ... 2026-08-05 05:47:45 -04:00
Your Name 494eae2bdf feat: add pos usb server (USB Redirector control); fix doc/code drift
- new bin/pos-usb-server: flag-style control of usbsrv (--ls, --share,
  --unshare, --auto-share, --callback, --close-callback, --auto-connect,
  --disconnect, --nickname, --timeout, --port, --info, --version);
  interactive prompts fall back to args; command -v usbsrv guard
- wire into bin/pos: usb category, example, INTERACTIVE_CMDS
- completions: usb-server flag completion
- docs: POS.md usb section, AGENT_Context tree/dispatch/table, README
- fix: add pos-network-hotspot to no-common.sh list (was omitted)
- fix: stale pos-docker-compose line count 317 -> 363
- fix: DEV.md/AGENT_Context note non-apt deps (command -v guard, not PACKAGES)
- fix: document INTERACTIVE_CMDS all-or-nothing per-script trade-off
- fix: usage() shows docker health (was missing from cheat-sheet)
2026-08-05 04:38:03 -04:00
Your Name 6d3482939e docs: note auto-discovery of category help in new-tool checklists 2026-08-05 04:17:02 -04:00
Your Name fe751bbc0c feat: add category help to pos dispatcher (pos <category> --help) 2026-08-05 04:09:19 -04:00
Your Name d591e71363 feat: show public IP location in pos network ip 2026-08-05 03:57:21 -04:00
Your Name 49fb248454 refactor: merge vbox into docker as pos docker vbox 2026-08-05 03:30:51 -04:00
Your Name 0c9d09c331 docs: add dev templates + clarify conventions; fix pos help for multi-word commands 2026-08-05 03:03:56 -04:00
Your Name 070524bafb feat: add tsui app installer and pos communication telegram sender 2026-08-05 02:42:35 -04:00
ciya e7c8c176ed feat: add pos system backup — encrypted folder snapshots with --service picker 2026-08-03 08:58:38 -04:00
Your Name 60718b360e feat: integrate precompiled hotspot binaries from x64_bin/ via pos network hotspot 2026-08-03 03:48:33 -04:00