loki-mode 7.88.0 → 7.89.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/autonomy/loki CHANGED
@@ -5315,14 +5315,17 @@ cmd_welcome_terminal() {
5315
5315
  echo -e " Quick start: ${BOLD}loki quickstart${NC} (from your idea) or ${BOLD}loki start ./prd.md${NC} (from a spec)"
5316
5316
  echo -e " Docs: ${BOLD}https://www.autonomi.dev/docs${NC}"
5317
5317
  echo ""
5318
+ # One-time honest disclosure (this welcome screen shows once, via the
5319
+ # WELCOME_MARKER). On-by-default anonymous diagnostics must be disclosed
5320
+ # somewhere so collection is never covert; this single line is that
5321
+ # disclosure. It is NOT repeated on later runs. Enterprise/CI/air-gapped
5322
+ # installs auto-disable collection, so the line only appears when it is
5323
+ # actually on. Opt out anytime: loki telemetry off.
5318
5324
  if _loki_welcome_analytics_on; then
5319
- echo -e " ${DIM}Anonymous usage analytics are ON (you opted in). We never collect${NC}"
5320
- echo -e " ${DIM}prompts, PRDs, or code. Opt out: loki telemetry off${NC}"
5321
- else
5322
- echo -e " ${DIM}Anonymous analytics are off by default. Nothing is sent unless you${NC}"
5323
- echo -e " ${DIM}opt in with: loki telemetry on${NC}"
5325
+ echo -e " ${DIM}Anonymous diagnostics on (os/arch/version/error type only -- never${NC}"
5326
+ echo -e " ${DIM}code, prompts, or paths). Off: loki telemetry off - docs/PRIVACY.md${NC}"
5327
+ echo ""
5324
5328
  fi
5325
- echo ""
5326
5329
  }
5327
5330
 
5328
5331
  cmd_welcome() {
@@ -5419,7 +5422,7 @@ cmd_web() {
5419
5422
  case "$subcommand" in
5420
5423
  start)
5421
5424
  shift || true
5422
- cmd_web_start "$@"
5425
+ cmd_web_redirect_to_dashboard "$@"
5423
5426
  ;;
5424
5427
  stop)
5425
5428
  cmd_web_stop
@@ -5449,51 +5452,87 @@ cmd_web() {
5449
5452
  *)
5450
5453
  # Treat unknown args as options to start (e.g., loki web --no-open)
5451
5454
  shift
5452
- cmd_web_start "$subcommand" "$@"
5455
+ cmd_web_redirect_to_dashboard "$subcommand" "$@"
5453
5456
  ;;
5454
5457
  esac
5455
5458
  }
5456
5459
 
5460
+ # v7.x (F55): `loki web` (the command a user intuitively types) used to launch
5461
+ # the deprecated Purple Lab, whose '/' redirects to '/lab/' and whose port has
5462
+ # none of the real dashboard APIs (/api/status, /trust, etc. all 404). A user
5463
+ # typing the obvious command landed on the wrong, broken-looking surface. The
5464
+ # value-preserving fix: the START path now launches the real dashboard instead.
5465
+ # 'loki web stop|status|logs' still operate on Purple Lab so anyone who started
5466
+ # it the old way (or via scripts) is never stranded. The deprecation banner has
5467
+ # already printed in cmd_web() before we get here.
5468
+ cmd_web_redirect_to_dashboard() {
5469
+ # The dashboard start path does not accept Purple-Lab-only flags
5470
+ # (--no-open, --prd). Filter them so `loki web --no-open` (used in CI) and
5471
+ # `loki web --prd X` keep working instead of erroring on an unknown option.
5472
+ # --port is shared and passes straight through.
5473
+ local orig_args=("$@")
5474
+ local dash_args=()
5475
+ while [[ $# -gt 0 ]]; do
5476
+ case "$1" in
5477
+ --no-open)
5478
+ # Dashboard has no browser-open behavior to suppress; drop it.
5479
+ shift
5480
+ ;;
5481
+ --prd)
5482
+ # Purple-Lab-only prefill; not supported by the dashboard.
5483
+ shift 2 2>/dev/null || shift
5484
+ ;;
5485
+ --prd=*)
5486
+ shift
5487
+ ;;
5488
+ *)
5489
+ dash_args+=("$1")
5490
+ shift
5491
+ ;;
5492
+ esac
5493
+ done
5494
+
5495
+ # Safe empty-array expansion (bash 3.2 + set -u): ${arr[@]+"${arr[@]}"}
5496
+ if ! _deprecated_alias_should_suppress ${orig_args[@]+"${orig_args[@]}"}; then
5497
+ echo "Launching the dashboard (http://localhost:${DASHBOARD_DEFAULT_PORT}) instead of the deprecated Purple Lab." >&2
5498
+ fi
5499
+ cmd_dashboard_start ${dash_args[@]+"${dash_args[@]}"}
5500
+ }
5501
+
5457
5502
  cmd_web_help() {
5458
5503
  echo -e "${BOLD}Purple Lab -- Loki Mode Web UI (deprecated -- use the dashboard)${NC}"
5459
5504
  echo ""
5460
5505
  echo "Usage: loki web [command] [options]"
5461
5506
  echo ""
5462
5507
  echo "DEPRECATED as of v7.44.0: Purple Lab is consolidated into the dashboard."
5463
- echo " For local build + monitoring, use the dashboard (auto-launches at"
5464
- echo " 'loki start', http://localhost:${DASHBOARD_DEFAULT_PORT}; or 'loki dashboard')."
5465
- echo " For the hosted platform, see Autonomi Cloud."
5466
- echo " 'loki web' still works for now (it launches after a deprecation notice),"
5467
- echo " but it will be removed in a future release. Migrate to the dashboard."
5508
+ echo " 'loki web' (no subcommand) now LAUNCHES THE DASHBOARD"
5509
+ echo " (http://localhost:${DASHBOARD_DEFAULT_PORT}) instead of the deprecated Purple"
5510
+ echo " Lab, so the obvious command lands you on the working UI. Use the embedded"
5511
+ echo " 'Lab' tab there to submit a PRD. For the hosted platform, see Autonomi Cloud."
5468
5512
  echo ""
5469
- echo "Note: 'loki web' is Purple Lab (the PRD-input/build-watch UI, port ${PURPLE_LAB_DEFAULT_PORT})."
5470
- echo " It is NOT the same as 'loki dashboard' (operations UI, port ${DASHBOARD_DEFAULT_PORT})."
5471
- echo " Use 'loki dashboard' to monitor running agents, tasks, costs, council, escalations."
5513
+ echo "Note: the canonical command is 'loki dashboard' (operations UI, port ${DASHBOARD_DEFAULT_PORT})."
5514
+ echo " Use it to monitor running agents, tasks, costs, council, escalations."
5472
5515
  echo ""
5473
5516
  echo "Commands:"
5474
- echo " start Start Purple Lab (default)"
5475
- echo " stop Stop Purple Lab server"
5517
+ echo " start Launch the dashboard (default; Purple Lab is deprecated)"
5518
+ echo " stop Stop the Purple Lab server (if one was started the old way)"
5476
5519
  echo " status Show Purple Lab server status"
5477
5520
  echo " logs Show Purple Lab server logs"
5478
5521
  echo " help Show this help"
5479
5522
  echo ""
5480
5523
  echo "Options (for start):"
5481
- echo " --no-open Don't open browser automatically"
5482
- echo " --port PORT Use custom port (default: ${PURPLE_LAB_DEFAULT_PORT})"
5483
- echo ""
5484
- echo "Purple Lab is the product UI where you input PRDs and watch agents build."
5485
- echo "It runs its own backend (web-app/server.py) on port ${PURPLE_LAB_DEFAULT_PORT}."
5524
+ echo " --port PORT Use custom port (default: ${DASHBOARD_DEFAULT_PORT})"
5525
+ echo " --no-open Accepted for back-compat; ignored (no-op on the dashboard)"
5486
5526
  echo ""
5487
5527
  echo "Examples:"
5488
- echo " loki web Start Purple Lab and open in browser"
5489
- echo " loki web --no-open Start without opening browser"
5490
- echo " loki web stop Stop the Purple Lab server"
5528
+ echo " loki web Launch the dashboard"
5529
+ echo " loki web --no-open Launch the dashboard (--no-open is a no-op)"
5530
+ echo " loki web stop Stop a Purple Lab server started the old way"
5491
5531
  echo ""
5492
5532
  echo "Note (since v7.5.30):"
5493
- echo " Purple Lab is also embedded in the Dashboard as a Lab sidebar entry."
5494
- echo " Run 'loki dashboard start' and click 'Lab' to use the same UI"
5495
- echo " without spawning a second port. 'loki web' standalone remains"
5496
- echo " supported (Rule 0); both modes serve the same React bundle."
5533
+ echo " The same PRD-input UI is embedded in the dashboard as a 'Lab' sidebar entry."
5534
+ echo " 'loki web stop|status|logs' still operate on a standalone Purple Lab"
5535
+ echo " process so anyone who started one the old way is never stranded."
5497
5536
  }
5498
5537
 
5499
5538
  cmd_web_start() {
@@ -16110,6 +16149,18 @@ worktree wt projects cp rc trust-metrics serve agent code self_update test help
16110
16149
 
16111
16150
  # Main command dispatcher
16112
16151
  main() {
16152
+ # v7.89.0 telemetry TTY fix (council cH_r1 AC1): resolve interactivity EXACTLY
16153
+ # ONCE here, while autonomy/loki main still owns the user's real TTY, and
16154
+ # export the explicit signal that the telemetry/crash gates trust instead of a
16155
+ # late `-t` re-probe. When invoked via the bin/loki shim the var is already
16156
+ # exported (and re-exporting the same value is a no-op); this covers the path
16157
+ # where autonomy/loki is invoked directly (LOKI_LEGACY_BASH, no-Bun, or a
16158
+ # direct call). Only set when a terminal is actually present; leave UNSET
16159
+ # otherwise so isolated gate unit tests fall back to their own `-t` probe.
16160
+ if [ -z "${LOKI_TTY_INTERACTIVE:-}" ] && { [ -t 1 ] || [ -t 0 ]; }; then
16161
+ export LOKI_TTY_INTERACTIVE=1
16162
+ fi
16163
+
16113
16164
  # v7.5.18: early guard -- LOKI_PROVIDER=gemini is no longer supported.
16114
16165
  if [ "${LOKI_PROVIDER:-}" = "gemini" ]; then
16115
16166
  echo -e "${RED}Error: Provider 'gemini' is deprecated as of v7.5.18 and has been removed.${NC}" >&2
@@ -16131,6 +16182,19 @@ main() {
16131
16182
  # v7.4.13: first-run telemetry moved to bin/loki shim so it fires for
16132
16183
  # both Bun-routed and bash-routed commands (autonomy/loki main() never
16133
16184
  # runs for the 8 ported commands). Marker file: ~/.loki-first-run.
16185
+ #
16186
+ # v7.89.0 (council cH_r1 AC4): this is a FOREGROUND egress on the bash route.
16187
+ # Before it can phone home, the user must have seen the disclosure once -- a
16188
+ # bash-routed first command must never be covert. Evaluate the SAME gate the
16189
+ # egress uses, and if collection is genuinely enabled, disclose once (shared
16190
+ # impl from telemetry.sh, keyed on its own marker, so it never double-prints
16191
+ # with the Bun route or repeats). loki_telemetry itself re-checks the gate, so
16192
+ # this only adds the disclosure; it never changes whether we send.
16193
+ if declare -f _loki_telemetry_enabled >/dev/null 2>&1 \
16194
+ && declare -f _loki_disclose_telemetry_once >/dev/null 2>&1 \
16195
+ && _loki_telemetry_enabled; then
16196
+ _loki_disclose_telemetry_once
16197
+ fi
16134
16198
  loki_telemetry "cli_command" "command=$command" 2>/dev/null || true
16135
16199
 
16136
16200
  # Unified config-file pre-pass (#691). For session commands ONLY, honor
@@ -21947,13 +22011,32 @@ try {
21947
22011
 
21948
22012
  # Unified collection state (PostHog usage telemetry + crash reporting).
21949
22013
  # loki_collection_enabled is the single source of truth (crash.sh).
21950
- # Collection is OPT-IN: OFF by default, enabled only after opt-in.
22014
+ # Collection is ON BY DEFAULT for individual interactive installs and
22015
+ # auto-off in enterprise/CI/air-gapped/non-interactive contexts; an
22016
+ # explicit opt-out always wins. AC8 (council cH_r1): the status copy
22017
+ # must distinguish "on by default" from an explicit "you opted in".
21951
22018
  echo ""
21952
22019
  if type loki_collection_enabled &>/dev/null; then
21953
22020
  if loki_collection_enabled; then
21954
- echo -e " Collection: ${GREEN}enabled${NC} (you opted in; anonymous diagnostics; opt out with: loki telemetry off)"
22021
+ # Detect an EXPLICIT opt-in (env LOKI_TELEMETRY=on, or the
22022
+ # persistent ~/.loki/config TELEMETRY_ENABLED=true written by
22023
+ # `loki telemetry on`). Anything else that is enabled is the
22024
+ # individual on-by-default path.
22025
+ local _telem_lower_status
22026
+ _telem_lower_status="$(printf '%s' "${LOKI_TELEMETRY:-}" | tr '[:upper:]' '[:lower:]')"
22027
+ local _explicit_optin=false
22028
+ if [ "$_telem_lower_status" = "on" ]; then
22029
+ _explicit_optin=true
22030
+ elif [ -f "$global_config" ] && grep -q "^TELEMETRY_ENABLED=true" "$global_config" 2>/dev/null; then
22031
+ _explicit_optin=true
22032
+ fi
22033
+ if [ "$_explicit_optin" = true ]; then
22034
+ echo -e " Collection: ${GREEN}enabled${NC} (you opted in; anonymous diagnostics; opt out with: loki telemetry off)"
22035
+ else
22036
+ echo -e " Collection: ${GREEN}on by default${NC} (anonymous diagnostics; opt out with: loki telemetry off)"
22037
+ fi
21955
22038
  else
21956
- echo -e " Collection: ${YELLOW}off by default${NC} (nothing sent; opt in with: loki telemetry on)"
22039
+ echo -e " Collection: ${YELLOW}off${NC} (nothing sent; enterprise/CI/air-gapped or opted out; opt in with: loki telemetry on)"
21957
22040
  fi
21958
22041
  fi
21959
22042
 
@@ -30649,7 +30732,7 @@ cmd_proof() {
30649
30732
  # "No proofs found" line -- matching the Bun route (proof.ts
30650
30733
  # listProofs, which returns before the header when rows is empty).
30651
30734
  if [ "$found" -eq 0 ]; then
30652
- printf "%-26s %-20s %-10s %-9s %s\n" "RUN_ID" "GENERATED_AT" "VERDICT" "COST_USD" "FILES"
30735
+ printf "%-26s %-20s %-18s %-9s %s\n" "RUN_ID" "GENERATED_AT" "VERDICT" "COST_USD" "FILES"
30653
30736
  fi
30654
30737
  found=1
30655
30738
  LOKI_PROOF_JSON="$pj" python3 - <<'PYEOF'
@@ -30667,10 +30750,14 @@ def s(v):
30667
30750
  return "-" if v is None else str(v)
30668
30751
  run_id = d.get("run_id")
30669
30752
  gen = d.get("generated_at")
30670
- verdict = (d.get("council") or {}).get("final_verdict")
30753
+ # The honest verdict lives in honesty.headline (VERIFIED / VERIFIED WITH GAPS /
30754
+ # NOT VERIFIED); fall back to legacy council.final_verdict for older proofs.
30755
+ verdict = (d.get("honesty") or {}).get("headline")
30756
+ if verdict is None:
30757
+ verdict = (d.get("council") or {}).get("final_verdict")
30671
30758
  cost = (d.get("cost") or {}).get("usd")
30672
30759
  files = (d.get("files_changed") or {}).get("count")
30673
- print("{:<26} {:<20} {:<10} {:<9} {}".format(
30760
+ print("{:<26} {:<20} {:<18} {:<9} {}".format(
30674
30761
  s(run_id), s(gen), s(verdict), s(cost), s(files)))
30675
30762
  PYEOF
30676
30763
  done