utim-cli 1.46.30__tar.gz → 1.46.32__tar.gz

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.
Files changed (74) hide show
  1. {utim_cli-1.46.30 → utim_cli-1.46.32}/CHANGELOG.md +5 -1
  2. {utim_cli-1.46.30/utim_cli.egg-info → utim_cli-1.46.32}/PKG-INFO +1 -1
  3. {utim_cli-1.46.30 → utim_cli-1.46.32}/pyproject.toml +1 -1
  4. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/__init__.py +1 -1
  5. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/_version.py +1 -1
  6. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/config.py +50 -10
  7. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/orchestrator.py +14 -1
  8. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/utim.py +13 -5
  9. {utim_cli-1.46.30 → utim_cli-1.46.32/utim_cli.egg-info}/PKG-INFO +1 -1
  10. {utim_cli-1.46.30 → utim_cli-1.46.32}/LICENSE +0 -0
  11. {utim_cli-1.46.30 → utim_cli-1.46.32}/MANIFEST.in +0 -0
  12. {utim_cli-1.46.30 → utim_cli-1.46.32}/README.md +0 -0
  13. {utim_cli-1.46.30 → utim_cli-1.46.32}/setup.cfg +0 -0
  14. {utim_cli-1.46.30 → utim_cli-1.46.32}/setup.py +0 -0
  15. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/agent.py +0 -0
  16. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/auth.py +0 -0
  17. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/backup.py +0 -0
  18. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/blender_agent.py +0 -0
  19. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/bootstrap.py +0 -0
  20. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/client_utils.py +0 -0
  21. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/constants.py +0 -0
  22. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/context_pruner.py +0 -0
  23. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/doctor.py +0 -0
  24. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/knowledge_graph.py +0 -0
  25. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/local_db.py +0 -0
  26. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/logger.py +0 -0
  27. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/mcp_clean_wrapper.py +0 -0
  28. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/mcp_client.py +0 -0
  29. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/mcp_registry.json +0 -0
  30. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/reflection.py +0 -0
  31. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/report.py +0 -0
  32. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/scrapy_search.py +0 -0
  33. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/__init__.py +0 -0
  34. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/auth.py +0 -0
  35. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/db.py +0 -0
  36. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/email_utils.py +0 -0
  37. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/exchange_rate.py +0 -0
  38. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/firebase.py +0 -0
  39. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/history.py +0 -0
  40. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/logging_config.py +0 -0
  41. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/models.py +0 -0
  42. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/pricing_updater.py +0 -0
  43. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/rate_limit.py +0 -0
  44. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/router.py +0 -0
  45. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/routes/__init__.py +0 -0
  46. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/routes/auth_routes.py +0 -0
  47. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/routes/completion_routes.py +0 -0
  48. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/routes/credit_routes.py +0 -0
  49. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/routes/feedback_routes.py +0 -0
  50. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/routes/quota_routes.py +0 -0
  51. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/routes/session_routes.py +0 -0
  52. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/routes/share_routes.py +0 -0
  53. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/server/server.py +0 -0
  54. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/share.py +0 -0
  55. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/share_tui.py +0 -0
  56. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/situational_scoring.py +0 -0
  57. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/state.py +0 -0
  58. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/tools.py +0 -0
  59. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/tui/__init__.py +0 -0
  60. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/tui/feedback_dialog.py +0 -0
  61. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/tui/history_dialog.py +0 -0
  62. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/tui/mcp_dialog.py +0 -0
  63. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/tui/model_dialog.py +0 -0
  64. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/tui/resume_dialog.py +0 -0
  65. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/tui/tools_dialog.py +0 -0
  66. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/tui/update_dialog.py +0 -0
  67. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/utilities.py +0 -0
  68. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/vector_memory.py +0 -0
  69. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli/workspace.py +0 -0
  70. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli.egg-info/SOURCES.txt +0 -0
  71. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli.egg-info/dependency_links.txt +0 -0
  72. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli.egg-info/entry_points.txt +0 -0
  73. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli.egg-info/requires.txt +0 -0
  74. {utim_cli-1.46.30 → utim_cli-1.46.32}/utim_cli.egg-info/top_level.txt +0 -0
@@ -2,7 +2,7 @@
2
2
 
3
3
  All notable changes to the UTIM CLI Agent will be documented in this file.
4
4
 
5
- ## [1.46.30] - 2026-07-11
5
+ ## [1.46.32] - 2026-07-11
6
6
 
7
7
  ### Added
8
8
  - **Dynamic Console Glyph Fallbacks**: Detected legacy Windows terminals (where `WT_SESSION` is not set) and automatically fell back to standard ASCII symbols (`>` and `->`) instead of unicode characters (`❯`, `▶`, and `➔`) to prevent `⍰` or empty box rendering issues.
@@ -12,6 +12,10 @@ All notable changes to the UTIM CLI Agent will be documented in this file.
12
12
  - **Model Selection Dialog Crash**: Fixed an `AttributeError` crash on the model list dialog screen (main agent or subagent picker) when the user's local `user_plan` config value is missing or explicitly `null`.
13
13
  - **Global Config Null-Safety Improvements**: Fixed multiple potential crashes across the tools dialog, share manager, and usage dashboard when keys like `disabled_tools`, `mcpServers`, `role`, or `user_plan` are missing or set to `null` in config files.
14
14
  - **Server Upload Limit & Connection Resets**: Increased the `/shares/upload` workspace file sharing size limit from 4MB to 25MB on the server. Added stream consumption middleware handlers to prevent connection termination resets and `SSLEOFError` crashes on the client during larger uploads.
15
+ - **Modern prompt_toolkit Style Crash**: Fixed a crash (`ValueError: Wrong color format 'dim'`) on lists with scrolling indicators (like the model dialog or history dialog) when run on newer versions of `prompt_toolkit` (3.0.40+) by correcting the shorthand styling `'dim fg:#f9e2af'` to `'class:dim fg:#f9e2af'`.
16
+ - **User-Agent Shielding & HTTP 429 Proxy Blocks**: Patched the global requests Session initializer to spoof a standard browser User-Agent, preventing corporate firewalls/proxies from blocking or rate-limiting requests. Added HTML-stripping parser helpers to the orchestrator to extract and display readable error details directly inside the offline connection panels if a proxy returns an HTTP 429.
17
+ - **Added /sslverify command**: Integrated a local slash command `/sslverify` to toggle SSL verification directly from the CLI input prompt without needing to edit config files manually.
18
+ - **Automated SSL Verification Fallback**: Implemented an automated, silent self-healing retry mechanism inside the requests wrapper. If UTIM encounters an SSL validation failure (commonly caused by decrypting proxies/firewalls in corporate or local networks), it automatically suppresses warnings, updates the config file to persist `"verify_ssl": false`, and retries the connection silently in the background with SSL verification disabled, preventing any service interruption without displaying warning messages to the user.
15
19
 
16
20
  ## [1.46.29] - 2026-07-11
17
21
 
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: utim-cli
3
- Version: 1.46.30
3
+ Version: 1.46.32
4
4
  Summary: UTIM – Universal Terminal Intelligence Manager. A powerful agentic AI coding assistant for your terminal.
5
5
  License: MIT
6
6
  Project-URL: Homepage, https://utim.dev
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "utim-cli"
7
- version = "1.46.30"
7
+ version = "1.46.32"
8
8
  description = "UTIM – Universal Terminal Intelligence Manager. A powerful agentic AI coding assistant for your terminal."
9
9
  readme = "README.md"
10
10
  requires-python = ">=3.9"
@@ -5,7 +5,7 @@ try:
5
5
  from utim_cli._version import VERSION as __version__
6
6
  except ImportError:
7
7
  # Fallback during first-install / editable-install edge cases
8
- __version__ = "1.46.30"
8
+ __version__ = "1.46.32"
9
9
 
10
10
  import builtins, os, pathlib, urllib.parse, re
11
11
 
@@ -11,4 +11,4 @@
11
11
  # from here so every surface stays in sync automatically.
12
12
  # ─────────────────────────────────────────────────────────────────────────────
13
13
 
14
- VERSION = "1.46.30"
14
+ VERSION = "1.46.32"
@@ -22,22 +22,62 @@ class Config:
22
22
  self._global_data: Dict[str, Any] = {}
23
23
  self._local_data: Dict[str, Any] = {}
24
24
  self._load()
25
- # Suppress warnings and patch requests if SSL verification is disabled
25
+ # Always inject a browser User-Agent to prevent firewalls/proxies blocking default python-requests
26
+ try:
27
+ import requests
28
+ original_init = requests.Session.__init__
29
+ def patched_init(self_session, *args, **kwargs):
30
+ original_init(self_session, *args, **kwargs)
31
+ self_session.headers.update({
32
+ "User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36"
33
+ })
34
+ requests.Session.__init__ = patched_init
35
+ except Exception:
36
+ pass
37
+
38
+ # Patch requests Session to support automatic SSL verification bypass and fallback
39
+ try:
40
+ import requests
41
+ original_request = requests.Session.request
42
+ def new_request(self_session, method, url, *args, **kwargs):
43
+ # If verify_ssl is explicitly False, always disable verification
44
+ if not self.verify_ssl:
45
+ kwargs['verify'] = False
46
+ return original_request(self_session, method, url, *args, **kwargs)
47
+
48
+ try:
49
+ return original_request(self_session, method, url, *args, **kwargs)
50
+ except Exception as exc:
51
+ is_ssl_err = False
52
+ err_str = str(exc).lower()
53
+ if "ssl" in err_str and ("cert" in err_str or "verify" in err_str or "untrusted" in err_str or "authority" in err_str):
54
+ is_ssl_err = True
55
+
56
+ if is_ssl_err:
57
+ try:
58
+ import urllib3
59
+ urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
60
+ except Exception:
61
+ pass
62
+ try:
63
+ self.set("verify_ssl", False)
64
+ except Exception:
65
+ pass
66
+ kwargs['verify'] = False
67
+ return original_request(self_session, method, url, *args, **kwargs)
68
+ raise exc
69
+
70
+ requests.Session.request = new_request
71
+ except Exception:
72
+ pass
73
+
74
+ # Suppress warnings if SSL verification is disabled
26
75
  if not self.verify_ssl:
27
76
  try:
28
77
  import urllib3
29
78
  urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
30
79
  except Exception:
31
80
  pass
32
- try:
33
- import requests
34
- original_request = requests.Session.request
35
- def new_request(self, method, url, *args, **kwargs):
36
- kwargs['verify'] = False
37
- return original_request(self, method, url, *args, **kwargs)
38
- requests.Session.request = new_request
39
- except Exception:
40
- pass
41
81
 
42
82
  def _load(self):
43
83
  # Load global config
@@ -1607,7 +1607,20 @@ class Orchestrator:
1607
1607
  # If we exit the loop, all models failed
1608
1608
  if isinstance(last_exc, requests.exceptions.HTTPError):
1609
1609
  code = last_exc.response.status_code if last_exc.response is not None else "?"
1610
- raise _ServerUnavailableError(f"Model API returned an error after trying all fallbacks (HTTP {code}).") from last_exc
1610
+ err_msg = f"Model API returned an error after trying all fallbacks (HTTP {code})."
1611
+ if code == 429 and last_exc.response is not None:
1612
+ try:
1613
+ text_detail = last_exc.response.text.strip()
1614
+ if text_detail:
1615
+ import re
1616
+ text_detail = re.sub('<[^<]+?>', '', text_detail)
1617
+ text_detail = " ".join(text_detail.split())
1618
+ if len(text_detail) > 150:
1619
+ text_detail = text_detail[:147] + "..."
1620
+ err_msg += f"\nDetails: {text_detail}"
1621
+ except Exception:
1622
+ pass
1623
+ raise _ServerUnavailableError(err_msg) from last_exc
1611
1624
  elif last_exc:
1612
1625
  raise _ServerUnavailableError(f"Cannot reach model API after trying all fallback models. Last error: {last_exc}") from last_exc
1613
1626
  else:
@@ -660,6 +660,7 @@ COMMANDS = {
660
660
  "redo": "Redo the last undone action",
661
661
  "report": "Generate a redacted support zip bundle under .utim_tmp/",
662
662
  "chatrestore": "Toggle active session state auto-restoration on startup",
663
+ "sslverify": "Toggle SSL certificate validation (useful behind decrypting proxies)",
663
664
  "resume": "Manage/Load previous conversations",
664
665
  "rewind": "Undo last action and revert code",
665
666
  "share": "Share chat and zip package of the workspace",
@@ -859,7 +860,7 @@ def _print_animated_banner(animated: bool = True):
859
860
  else:
860
861
  console.print(f"[bold {color}]{BANNER_BIG}[/bold {color}]")
861
862
 
862
- console.print(f" [bold white]U Think I Make[/bold white] [dim]v1.46.30[/dim]")
863
+ console.print(f" [bold white]U Think I Make[/bold white] [dim]v1.46.32[/dim]")
863
864
  user_email = config.email
864
865
  user_type = "UTIM Community"
865
866
  api_key = config.get("api_key")
@@ -1014,7 +1015,7 @@ def _run_list_dialog(rows, render_row_fn, title="", legend="", extra_keys=None):
1014
1015
  # Show indicator for items below the viewport
1015
1016
  remaining = N - end_idx
1016
1017
  if remaining > 0:
1017
- out.append(('dim fg:#f9e2af', f' ▼ ... ({remaining} more item{"s" if remaining > 1 else ""} below) ... ▼\n'))
1018
+ out.append(('class:dim fg:#f9e2af', f' ▼ ... ({remaining} more item{"s" if remaining > 1 else ""} below) ... ▼\n'))
1018
1019
 
1019
1020
  out.append(('', '\n'))
1020
1021
  return out
@@ -1197,7 +1198,7 @@ def _run_mcp_search_list_dialog(rows, render_row_fn, title="", legend="", search
1197
1198
 
1198
1199
  remaining = N_filtered[0] - end_idx
1199
1200
  if remaining > 0:
1200
- out.append(('dim fg:#f9e2af', f'\n ▼ ... ({remaining} more below) ... ▼\n'))
1201
+ out.append(('class:dim fg:#f9e2af', f'\n ▼ ... ({remaining} more below) ... ▼\n'))
1201
1202
 
1202
1203
  return out
1203
1204
 
@@ -1637,6 +1638,13 @@ def _handle_command(cmd: str, orchestrator: Orchestrator, app_ref) -> None:
1637
1638
  if not new_val:
1638
1639
  console.print("[dim]Next time you boot UTIM, it will start with a fresh new chat session.[/dim]\n")
1639
1640
 
1641
+ elif c == "sslverify":
1642
+ current = config.get("verify_ssl", True)
1643
+ new_val = not current
1644
+ config.set("verify_ssl", new_val)
1645
+ console.print(f"\n[bold green]✓ SSL certificate verification has been {'enabled' if new_val else 'disabled'}.[/bold green]\n")
1646
+ console.print("[dim]Restart UTIM for changes to take full effect across all components.[/dim]\n")
1647
+
1640
1648
  elif c == "rate":
1641
1649
  from utim_cli.tui.feedback_dialog import _dialog_submit_feedback
1642
1650
  _dialog_submit_feedback(orchestrator)
@@ -2820,7 +2828,7 @@ def _build_pt_app(orchestrator, last_sigint):
2820
2828
  words[0] = cmd_word
2821
2829
  text = " ".join(words)
2822
2830
  cmd_name = cmd_word.lstrip('/')
2823
- CONCURRENT_COMMANDS = {"usage", "hint", "tools", "help", "about", "doctor", "report", "chatrestore", "rate", "feedback", "feedbacks"}
2831
+ CONCURRENT_COMMANDS = {"usage", "hint", "tools", "help", "about", "doctor", "report", "chatrestore", "sslverify", "rate", "feedback", "feedbacks"}
2824
2832
  if STATE["busy"] and cmd_name not in CONCURRENT_COMMANDS:
2825
2833
  console.print(f"\n[dim yellow]⚠ Cannot execute command {text} while agent is busy.[/dim yellow]")
2826
2834
  return
@@ -3109,7 +3117,7 @@ def check_and_update_background():
3109
3117
  return
3110
3118
 
3111
3119
  latest_ver = resp.json().get("version", "")
3112
- current_ver = "1.46.30"
3120
+ current_ver = "1.46.32"
3113
3121
 
3114
3122
  def parse_ver(v):
3115
3123
  return [int(x) for x in v.split(".") if x.isdigit()]
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: utim-cli
3
- Version: 1.46.30
3
+ Version: 1.46.32
4
4
  Summary: UTIM – Universal Terminal Intelligence Manager. A powerful agentic AI coding assistant for your terminal.
5
5
  License: MIT
6
6
  Project-URL: Homepage, https://utim.dev
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes