janito 2.7.0__py3-none-any.whl → 2.9.0__py3-none-any.whl

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 (121) hide show
  1. janito/__init__.py +0 -1
  2. janito/__main__.py +0 -1
  3. janito/_version.py +0 -3
  4. janito/agent/setup_agent.py +77 -10
  5. janito/agent/templates/profiles/{system_prompt_template_plain_software_developer.txt.j2 → system_prompt_template_Developer_with_Python_Tools.txt.j2} +5 -1
  6. janito/agent/templates/profiles/system_prompt_template_developer.txt.j2 +3 -12
  7. janito/cli/__init__.py +0 -1
  8. janito/cli/chat_mode/bindings.py +1 -1
  9. janito/cli/chat_mode/chat_entry.py +0 -2
  10. janito/cli/chat_mode/prompt_style.py +0 -3
  11. janito/cli/chat_mode/script_runner.py +9 -5
  12. janito/cli/chat_mode/session.py +100 -37
  13. janito/cli/chat_mode/session_profile_select.py +61 -52
  14. janito/cli/chat_mode/shell/commands/__init__.py +1 -5
  15. janito/cli/chat_mode/shell/commands/_priv_check.py +1 -0
  16. janito/cli/chat_mode/shell/commands/_priv_status.py +13 -0
  17. janito/cli/chat_mode/shell/commands/bang.py +10 -3
  18. janito/cli/chat_mode/shell/commands/conversation_restart.py +24 -7
  19. janito/cli/chat_mode/shell/commands/execute.py +22 -7
  20. janito/cli/chat_mode/shell/commands/help.py +4 -1
  21. janito/cli/chat_mode/shell/commands/model.py +13 -5
  22. janito/cli/chat_mode/shell/commands/privileges.py +21 -0
  23. janito/cli/chat_mode/shell/commands/prompt.py +0 -2
  24. janito/cli/chat_mode/shell/commands/read.py +22 -5
  25. janito/cli/chat_mode/shell/commands/tools.py +15 -4
  26. janito/cli/chat_mode/shell/commands/write.py +22 -5
  27. janito/cli/chat_mode/shell/input_history.py +3 -1
  28. janito/cli/chat_mode/shell/session/manager.py +0 -2
  29. janito/cli/chat_mode/toolbar.py +25 -19
  30. janito/cli/cli_commands/list_config.py +31 -0
  31. janito/cli/cli_commands/list_models.py +1 -1
  32. janito/cli/cli_commands/list_profiles.py +79 -0
  33. janito/cli/cli_commands/list_providers.py +1 -0
  34. janito/cli/cli_commands/list_tools.py +35 -7
  35. janito/cli/cli_commands/model_utils.py +5 -3
  36. janito/cli/cli_commands/show_config.py +16 -11
  37. janito/cli/cli_commands/show_system_prompt.py +23 -9
  38. janito/cli/config.py +0 -13
  39. janito/cli/core/getters.py +16 -1
  40. janito/cli/core/runner.py +25 -8
  41. janito/cli/core/setters.py +13 -76
  42. janito/cli/main_cli.py +60 -27
  43. janito/cli/prompt_core.py +19 -18
  44. janito/cli/prompt_setup.py +6 -3
  45. janito/cli/rich_terminal_reporter.py +19 -5
  46. janito/cli/single_shot_mode/handler.py +14 -5
  47. janito/cli/verbose_output.py +5 -1
  48. janito/config.py +1 -0
  49. janito/config_manager.py +15 -2
  50. janito/drivers/azure_openai/driver.py +27 -30
  51. janito/drivers/openai/driver.py +53 -36
  52. janito/formatting_token.py +12 -4
  53. janito/llm/agent.py +15 -6
  54. janito/llm/driver.py +1 -0
  55. janito/llm/provider.py +1 -1
  56. janito/provider_registry.py +31 -70
  57. janito/providers/__init__.py +1 -0
  58. janito/providers/anthropic/model_info.py +0 -1
  59. janito/providers/anthropic/provider.py +9 -14
  60. janito/providers/azure_openai/provider.py +10 -5
  61. janito/providers/deepseek/provider.py +5 -4
  62. janito/providers/google/model_info.py +4 -2
  63. janito/providers/google/provider.py +11 -5
  64. janito/providers/groq/__init__.py +1 -0
  65. janito/providers/groq/model_info.py +45 -0
  66. janito/providers/groq/provider.py +76 -0
  67. janito/providers/moonshotai/provider.py +11 -4
  68. janito/providers/openai/model_info.py +0 -1
  69. janito/providers/openai/provider.py +6 -7
  70. janito/tools/__init__.py +2 -0
  71. janito/tools/adapters/local/__init__.py +2 -1
  72. janito/tools/adapters/local/adapter.py +21 -4
  73. janito/tools/adapters/local/ask_user.py +1 -0
  74. janito/tools/adapters/local/copy_file.py +1 -0
  75. janito/tools/adapters/local/create_directory.py +1 -0
  76. janito/tools/adapters/local/create_file.py +1 -0
  77. janito/tools/adapters/local/delete_text_in_file.py +2 -1
  78. janito/tools/adapters/local/fetch_url.py +1 -0
  79. janito/tools/adapters/local/find_files.py +7 -6
  80. janito/tools/adapters/local/get_file_outline/core.py +1 -0
  81. janito/tools/adapters/local/get_file_outline/java_outline.py +22 -15
  82. janito/tools/adapters/local/get_file_outline/search_outline.py +1 -0
  83. janito/tools/adapters/local/move_file.py +1 -0
  84. janito/tools/adapters/local/open_html_in_browser.py +15 -5
  85. janito/tools/adapters/local/open_url.py +1 -0
  86. janito/tools/adapters/local/python_code_run.py +1 -0
  87. janito/tools/adapters/local/python_command_run.py +1 -0
  88. janito/tools/adapters/local/python_file_run.py +1 -0
  89. janito/tools/adapters/local/read_files.py +19 -4
  90. janito/tools/adapters/local/remove_directory.py +1 -0
  91. janito/tools/adapters/local/remove_file.py +1 -0
  92. janito/tools/adapters/local/replace_text_in_file.py +4 -3
  93. janito/tools/adapters/local/run_bash_command.py +1 -0
  94. janito/tools/adapters/local/run_powershell_command.py +1 -0
  95. janito/tools/adapters/local/search_text/core.py +18 -17
  96. janito/tools/adapters/local/search_text/match_lines.py +5 -5
  97. janito/tools/adapters/local/search_text/pattern_utils.py +1 -1
  98. janito/tools/adapters/local/search_text/traverse_directory.py +7 -7
  99. janito/tools/adapters/local/validate_file_syntax/core.py +1 -1
  100. janito/tools/adapters/local/validate_file_syntax/html_validator.py +8 -1
  101. janito/tools/disabled_tools.py +68 -0
  102. janito/tools/path_security.py +18 -11
  103. janito/tools/permissions.py +6 -0
  104. janito/tools/permissions_parse.py +4 -3
  105. janito/tools/tool_base.py +11 -5
  106. janito/tools/tool_use_tracker.py +1 -4
  107. janito/tools/tool_utils.py +1 -1
  108. janito/tools/tools_adapter.py +57 -25
  109. {janito-2.7.0.dist-info → janito-2.9.0.dist-info}/METADATA +11 -19
  110. janito-2.9.0.dist-info/RECORD +205 -0
  111. janito/cli/chat_mode/shell/commands/livelogs.py +0 -49
  112. janito/drivers/mistralai/driver.py +0 -41
  113. janito/providers/mistralai/model_info.py +0 -37
  114. janito/providers/mistralai/provider.py +0 -72
  115. janito/providers/provider_static_info.py +0 -21
  116. janito-2.7.0.dist-info/RECORD +0 -202
  117. /janito/agent/templates/profiles/{system_prompt_template_assistant.txt.j2 → system_prompt_template_model_conversation_without_tools_or_context.txt.j2} +0 -0
  118. {janito-2.7.0.dist-info → janito-2.9.0.dist-info}/WHEEL +0 -0
  119. {janito-2.7.0.dist-info → janito-2.9.0.dist-info}/entry_points.txt +0 -0
  120. {janito-2.7.0.dist-info → janito-2.9.0.dist-info}/licenses/LICENSE +0 -0
  121. {janito-2.7.0.dist-info → janito-2.9.0.dist-info}/top_level.txt +0 -0
@@ -16,20 +16,35 @@ from .prompt_style import chat_shell_style
16
16
  Profile selection logic for Janito Chat CLI using questionary.
17
17
  """
18
18
 
19
- def _handle_helpful_assistant():
20
- return {"profile": "assistant", "profile_system_prompt": None}
19
+
20
+ def _handle_raw_model_session_no_tools():
21
+ return {
22
+ "profile": "model_conversation_without_tools_or_context",
23
+ "profile_system_prompt": None,
24
+ "no_tools_mode": True,
25
+ } # Raw Model Session (no tools, no context)
26
+
21
27
 
22
28
  def _handle_using_role():
23
29
  role_name = questionary.text("Enter the role name:").ask()
24
30
  return f"role:{role_name}"
25
31
 
32
+
26
33
  def _get_toolbar(mode):
27
34
  if mode["multiline"]:
28
- return HTML("<b>Multiline mode (Esc+Enter to submit). Type /single to switch.</b>")
35
+ return HTML(
36
+ "<b>Multiline mode (Esc+Enter to submit). Type /single to switch.</b>"
37
+ )
29
38
  else:
30
- return HTML("<b>Single-line mode (Enter to submit). Type /multi for multiline.</b>")
39
+ return HTML(
40
+ "<b>Single-line mode (Enter to submit). Type /multi for multiline.</b>"
41
+ )
42
+
31
43
 
32
44
  def _handle_custom_system_prompt():
45
+ print(
46
+ "\n[Custom System Prompt]\nPlease enter the message that will be used as the model system prompt. This will define how the AI behaves for this session.\nYou can use /multi for multiline mode, and /single to return to single-line mode.\n"
47
+ )
33
48
  mode = {"multiline": False}
34
49
  bindings = KeyBindings()
35
50
 
@@ -52,7 +67,13 @@ def _handle_custom_system_prompt():
52
67
  )
53
68
  prompt_icon = HTML("<inputline>📝 </inputline>")
54
69
  while True:
55
- response = session.prompt(prompt_icon)
70
+ try:
71
+ response = session.prompt(prompt_icon)
72
+ except KeyboardInterrupt:
73
+ print("[Custom System Prompt] Exited by the user.")
74
+ import sys
75
+
76
+ sys.exit(0)
56
77
  if not mode["multiline"] and response.strip() == "/multi":
57
78
  mode["multiline"] = True
58
79
  session.multiline = True
@@ -88,63 +109,51 @@ def _load_user_profiles():
88
109
  def select_profile():
89
110
  user_profiles = _load_user_profiles()
90
111
  choices = [
91
- "helpful assistant",
92
- "developer",
93
- "plain_software_developer",
94
- "using role...",
95
- "full custom system prompt..."
112
+ "Developer with Python Tools",
113
+ "Developer",
114
+ "Custom system prompt...",
115
+ "Raw Model Session (no tools, no context)",
96
116
  ]
97
117
  # Add user profiles to choices
98
118
  if user_profiles:
99
119
  choices.extend(user_profiles.keys())
100
120
 
101
- custom_style = Style([
102
- ("highlighted", "bg:#00aaff #ffffff"), # background for item under cursor
103
- ("question", "fg:#00aaff bold"),
104
- ])
121
+ custom_style = Style(
122
+ [
123
+ ("highlighted", "bg:#00aaff #ffffff"), # background for item under cursor
124
+ ("question", "fg:#00aaff bold"),
125
+ ]
126
+ )
105
127
  answer = questionary.select(
106
- "Select a profile to use:",
107
- choices=choices,
108
- default=None,
109
- style=custom_style
128
+ "Select a profile to use:", choices=choices, default=None, style=custom_style
110
129
  ).ask()
111
130
 
112
- if answer == "helpful assistant":
113
- return _handle_helpful_assistant()
114
- if answer == "using role...":
115
- return _handle_using_role()
116
- elif answer == "full custom system prompt...":
131
+ if not answer:
132
+ import sys
133
+
134
+ sys.exit(0)
135
+
136
+ if answer == "Raw Model Session (no tools, no context)":
137
+ return _handle_raw_model_session_no_tools()
138
+ elif answer == "Custom system prompt...":
117
139
  return _handle_custom_system_prompt()
118
140
  elif answer in user_profiles:
119
141
  # Return the content of the user profile as a custom system prompt
120
142
  return {"profile": None, "profile_system_prompt": user_profiles[answer]}
121
- elif answer == "plain_software_developer":
122
- # Return the content of the built-in plain_software_developer profile prompt
123
- with open("./janito/agent/templates/profiles/system_prompt_template_plain_software_developer.txt.j2", "r", encoding="utf-8") as f:
124
- prompt = f.read().strip()
125
- return {"profile": "plain_software_developer", "profile_system_prompt": prompt}
126
- return answer
127
-
128
- choices = [
129
- "helpful assistant",
130
- "developer",
131
- "using role...",
132
- "full custom system prompt..."
133
- ]
134
- custom_style = Style([
135
- ("highlighted", "bg:#00aaff #ffffff"), # background for item under cursor
136
- ("question", "fg:#00aaff bold"),
137
- ])
138
- answer = questionary.select(
139
- "Select a profile to use:",
140
- choices=choices,
141
- default=None,
142
- style=custom_style
143
- ).ask()
144
- if answer == "helpful assistant":
145
- return _handle_helpful_assistant()
146
- if answer == "using role...":
147
- return _handle_using_role()
148
- elif answer == "full custom system prompt...":
149
- return _handle_custom_system_prompt()
143
+ elif answer == "Developer":
144
+ # Return the content of the built-in Developer profile prompt
145
+ from pathlib import Path
146
+ from jinja2 import Template
147
+ from janito.agent.setup_agent import _prepare_template_context
148
+
149
+ template_path = Path(
150
+ "./janito/agent/templates/profiles/system_prompt_template_Developer.txt.j2"
151
+ )
152
+ with open(template_path, "r", encoding="utf-8") as f:
153
+ template_content = f.read()
154
+
155
+ template = Template(template_content)
156
+ context = _prepare_template_context("developer", "Developer", None)
157
+ prompt = template.render(**context)
158
+ return {"profile": "Developer", "profile_system_prompt": prompt}
150
159
  return answer
@@ -1,7 +1,7 @@
1
1
  from .base import ShellCmdHandler
2
2
  from .history_view import ViewShellHandler
3
3
  from .lang import LangShellHandler
4
- from .livelogs import LivelogsShellHandler
4
+
5
5
  from .prompt import PromptShellHandler, RoleShellHandler
6
6
  from .multi import MultiShellHandler
7
7
  from .model import ModelShellHandler
@@ -32,15 +32,11 @@ COMMAND_HANDLERS = {
32
32
  "janito.cli.chat_mode.shell.commands.conversation_restart",
33
33
  fromlist=["RestartShellHandler"],
34
34
  ).RestartShellHandler,
35
-
36
35
  "/view": ViewShellHandler,
37
36
  "/lang": LangShellHandler,
38
- "/livelogs": LivelogsShellHandler,
39
37
  "/prompt": PromptShellHandler,
40
38
  "/role": RoleShellHandler,
41
-
42
39
  "/history": HistoryShellHandler,
43
-
44
40
  "/tools": ToolsShellHandler,
45
41
  "/model": ModelShellHandler,
46
42
  "/multi": MultiShellHandler,
@@ -1,5 +1,6 @@
1
1
  from janito.tools.permissions import get_global_allowed_permissions
2
2
 
3
+
3
4
  def user_has_any_privileges():
4
5
  perms = get_global_allowed_permissions()
5
6
  return perms.read or perms.write or perms.execute
@@ -0,0 +1,13 @@
1
+ from janito.tools.permissions import get_global_allowed_permissions
2
+
3
+
4
+ def get_privilege_status_message():
5
+ perms = get_global_allowed_permissions()
6
+ if perms.read and perms.write:
7
+ return "[cyan]Read-Write tools enabled[/cyan]"
8
+ elif perms.read:
9
+ return "[cyan]Read-Only tools enabled[/cyan]"
10
+ elif perms.write:
11
+ return "[cyan]Write-Only tools enabled[/cyan]"
12
+ else:
13
+ return "[yellow]No tool permissions enabled[/yellow]"
@@ -4,6 +4,7 @@ from janito.platform_discovery import PlatformDiscovery
4
4
  import subprocess
5
5
  import sys
6
6
 
7
+
7
8
  class BangShellHandler(ShellCmdHandler):
8
9
  help_text = "!<cmd>: Run a shell command in the underlying shell (PowerShell or Bash). Usage: !ls -al or !Get-Process. Use ! with no command to launch an interactive shell."
9
10
 
@@ -15,16 +16,22 @@ class BangShellHandler(ShellCmdHandler):
15
16
  if not cmd:
16
17
  pd = PlatformDiscovery()
17
18
  if pd.is_windows():
18
- shared_console.print("[yellow]Launching interactive PowerShell. Type 'exit' to return.[/yellow]")
19
+ shared_console.print(
20
+ "[yellow]Launching interactive PowerShell. Type 'exit' to return.[/yellow]"
21
+ )
19
22
  subprocess.run(["powershell.exe"], check=False)
20
23
  else:
21
- shared_console.print("[yellow]Launching interactive Bash shell. Type 'exit' to return.[/yellow]")
24
+ shared_console.print(
25
+ "[yellow]Launching interactive Bash shell. Type 'exit' to return.[/yellow]"
26
+ )
22
27
  subprocess.run(["bash"], check=False)
23
28
  return
24
29
  pd = PlatformDiscovery()
25
30
  if pd.is_windows():
26
31
  shared_console.print(f"[cyan]Running in PowerShell:[/cyan] {cmd}")
27
- completed = subprocess.run(["powershell.exe", "-Command", cmd], capture_output=True, text=True)
32
+ completed = subprocess.run(
33
+ ["powershell.exe", "-Command", cmd], capture_output=True, text=True
34
+ )
28
35
  else:
29
36
  shared_console.print(f"[cyan]Running in Bash:[/cyan] {cmd}")
30
37
  completed = subprocess.run(cmd, shell=True, capture_output=True, text=True)
@@ -16,7 +16,9 @@ def handle_restart(shell_state=None):
16
16
  shell_state.agent.reset_conversation_history()
17
17
  # Reset system prompt to original template context if available
18
18
  if hasattr(shell_state.agent, "_original_template_vars"):
19
- shell_state.agent._template_vars = shell_state.agent._original_template_vars.copy()
19
+ shell_state.agent._template_vars = (
20
+ shell_state.agent._original_template_vars.copy()
21
+ )
20
22
  shell_state.agent.refresh_system_prompt_from_template()
21
23
  # No need to print the system prompt after restart
22
24
 
@@ -47,27 +49,42 @@ def handle_restart(shell_state=None):
47
49
 
48
50
  # Restore tool permissions to the CLI default on restart
49
51
  try:
50
- from janito.tools.permissions import set_global_allowed_permissions, get_default_allowed_permissions
52
+ from janito.tools.permissions import (
53
+ set_global_allowed_permissions,
54
+ get_default_allowed_permissions,
55
+ )
51
56
  import janito.tools
57
+
52
58
  default_perms = get_default_allowed_permissions()
53
59
  if default_perms is not None:
54
60
  set_global_allowed_permissions(default_perms)
55
61
  janito.tools.local_tools_adapter.set_allowed_permissions(default_perms)
56
62
  msg = None
57
-
63
+
58
64
  else:
59
65
  from janito.tools.tool_base import ToolPermissions
60
- set_global_allowed_permissions(ToolPermissions(read=False, write=False, execute=False))
61
- janito.tools.local_tools_adapter.set_allowed_permissions(ToolPermissions(read=False, write=False, execute=False))
66
+
67
+ set_global_allowed_permissions(
68
+ ToolPermissions(read=False, write=False, execute=False)
69
+ )
70
+ janito.tools.local_tools_adapter.set_allowed_permissions(
71
+ ToolPermissions(read=False, write=False, execute=False)
72
+ )
62
73
  msg = "[green]All tool permissions have been set to OFF (read, write, execute = False).[/green]"
63
74
  # Refresh system prompt to reflect new permissions
64
- if hasattr(shell_state, "agent") and shell_state.agent and hasattr(shell_state.agent, "refresh_system_prompt_from_template"):
75
+ if (
76
+ hasattr(shell_state, "agent")
77
+ and shell_state.agent
78
+ and hasattr(shell_state.agent, "refresh_system_prompt_from_template")
79
+ ):
65
80
  shell_state.agent.refresh_system_prompt_from_template()
66
81
  if msg:
67
82
  shared_console.print(msg)
68
83
 
69
84
  except Exception as e:
70
- shared_console.print(f"[yellow]Warning: Failed to restore tool permissions: {e}[/yellow]")
85
+ shared_console.print(
86
+ f"[yellow]Warning: Failed to restore tool permissions: {e}[/yellow]"
87
+ )
71
88
 
72
89
  shared_console.print(
73
90
  "[bold green]Conversation history has been started (context reset).[/bold green]"
@@ -1,10 +1,14 @@
1
1
  from janito.cli.console import shared_console
2
2
  from janito.cli.chat_mode.shell.commands.base import ShellCmdHandler
3
3
 
4
+
4
5
  class ExecuteShellHandler(ShellCmdHandler):
5
6
  help_text = "/execute on|off: Enable or disable code and command execution tools. Usage: /execute on or /execute off."
6
7
 
7
8
  def run(self):
9
+ if self.shell_state and getattr(self.shell_state, 'no_tools_mode', False):
10
+ shared_console.print("[yellow]No tools are available in this mode (no tools, no context).[/yellow]")
11
+ return
8
12
  if not self.shell_state:
9
13
  shared_console.print("[red]Shell state unavailable.[/red]")
10
14
  return
@@ -15,27 +19,38 @@ class ExecuteShellHandler(ShellCmdHandler):
15
19
  enable = arg == "on"
16
20
  # Dynamically enable/disable execution tools in the registry
17
21
  try:
18
- from janito.tools.permissions import set_global_allowed_permissions, get_global_allowed_permissions
22
+ from janito.tools.permissions import (
23
+ set_global_allowed_permissions,
24
+ get_global_allowed_permissions,
25
+ )
19
26
  from janito.tools.tool_base import ToolPermissions
27
+
20
28
  current_perms = get_global_allowed_permissions()
21
29
  new_perms = ToolPermissions(
22
- read=getattr(current_perms, 'read', False),
23
- write=getattr(current_perms, 'write', False),
24
- execute=enable
30
+ read=getattr(current_perms, "read", False),
31
+ write=getattr(current_perms, "write", False),
32
+ execute=enable,
25
33
  )
26
34
  set_global_allowed_permissions(new_perms)
27
35
  # Also update the singleton tools registry permissions
28
36
  import janito.tools
37
+
29
38
  janito.tools.local_tools_adapter.set_allowed_permissions(new_perms)
30
39
 
31
40
  except Exception as e:
32
- shared_console.print(f"[yellow]Warning: Could not update execution tools dynamically: {e}[/yellow]")
41
+ shared_console.print(
42
+ f"[yellow]Warning: Could not update execution tools dynamically: {e}[/yellow]"
43
+ )
33
44
  # Refresh system prompt if agent is available
34
45
  agent = getattr(self.shell_state, "agent", None)
35
46
  if agent:
36
47
  agent.refresh_system_prompt_from_template()
37
48
  # No need to print the system prompt after permission change
38
49
  if enable:
39
- shared_console.print("[green]Execution tools ENABLED. Tools can now execute code and commands.[/green]")
50
+ shared_console.print(
51
+ "[green]Execution tools ENABLED. Tools can now execute code and commands.[/green]"
52
+ )
40
53
  else:
41
- shared_console.print("[yellow]Execution tools DISABLED. Tools cannot run code or commands.[/yellow]")
54
+ shared_console.print(
55
+ "[yellow]Execution tools DISABLED. Tools cannot run code or commands.[/yellow]"
56
+ )
@@ -2,6 +2,7 @@ from janito.cli.chat_mode.shell.commands.base import ShellCmdHandler
2
2
  from janito.cli.console import shared_console
3
3
  import os
4
4
 
5
+
5
6
  class HelpShellHandler(ShellCmdHandler):
6
7
  help_text = "Show this help message"
7
8
 
@@ -16,4 +17,6 @@ class HelpShellHandler(ShellCmdHandler):
16
17
 
17
18
  # After help, print privilege info if user has no privileges
18
19
  if not user_has_any_privileges():
19
- shared_console.print("[yellow]Note: You currently have no privileges enabled. If you need to interact with files or the system, enable permissions using /read on, /write on, or /execute on.[/yellow]")
20
+ shared_console.print(
21
+ "[yellow]Note: You currently have no privileges enabled. If you need to interact with files or the system, enable permissions using /read on, /write on, or /execute on.[/yellow]"
22
+ )
@@ -4,6 +4,7 @@ from janito.cli.config import config
4
4
 
5
5
  from janito.cli.cli_commands.show_config import resolve_effective_model
6
6
 
7
+
7
8
  class ModelShellHandler(ShellCmdHandler):
8
9
  help_text = "Change or show the current LLM model (usage: /model [MODEL_NAME])"
9
10
 
@@ -14,15 +15,22 @@ class ModelShellHandler(ShellCmdHandler):
14
15
  provider = config.get("provider")
15
16
  effective_model = resolve_effective_model(provider) if provider else None
16
17
  if effective_model:
17
- shared_console.print(f"[bold green]Current effective model:[/bold green] {effective_model}")
18
+ shared_console.print(
19
+ f"[bold green]Current effective model:[/bold green] {effective_model}"
20
+ )
18
21
  else:
19
- shared_console.print("[bold yellow]No model is currently set.[/bold yellow]")
22
+ shared_console.print(
23
+ "[bold yellow]No model is currently set.[/bold yellow]"
24
+ )
20
25
  return
21
26
  # Set new model (global override)
22
27
  config.runtime_set("model", model_name)
23
28
  # Update agent's model in shell_state if possible
24
29
  agent = getattr(self.shell_state, "agent", None)
25
- if agent is not None and hasattr(agent, "reset_driver_config_to_model_defaults"):
30
+ if agent is not None and hasattr(
31
+ agent, "reset_driver_config_to_model_defaults"
32
+ ):
26
33
  agent.reset_driver_config_to_model_defaults(model_name)
27
- shared_console.print(f"[bold green]Model and config reset to defaults for:[/bold green] {model_name}")
28
-
34
+ shared_console.print(
35
+ f"[bold green]Model and config reset to defaults for:[/bold green] {model_name}"
36
+ )
@@ -0,0 +1,21 @@
1
+ from janito.cli.console import shared_console
2
+ from janito.cli.chat_mode.shell.commands.base import ShellCmdHandler
3
+
4
+ class PrivilegesShellHandler(ShellCmdHandler):
5
+ help_text = "Show current tool privileges or availability."
6
+
7
+ def run(self):
8
+ # Check for no_tools_mode in shell_state
9
+ if self.shell_state and getattr(self.shell_state, 'no_tools_mode', False):
10
+ shared_console.print("[yellow]No tools are available in this mode (no tools, no context).[/yellow]")
11
+ return
12
+ try:
13
+ from janito.tools.permissions import get_global_allowed_permissions
14
+ perms = get_global_allowed_permissions()
15
+ lines = ["[bold]Current tool privileges:[/bold]"]
16
+ lines.append(f"Read: {'✅' if perms.read else '❌'}")
17
+ lines.append(f"Write: {'✅' if perms.write else '❌'}")
18
+ lines.append(f"Execute: {'✅' if perms.execute else '❌'}")
19
+ shared_console.print("\n".join(lines))
20
+ except Exception as e:
21
+ shared_console.print(f"[red]Error fetching privileges: {e}[/red]")
@@ -45,5 +45,3 @@ class RoleShellHandler(ShellCmdHandler):
45
45
  shared_console.print(
46
46
  f"[bold green]System role updated to:[/bold green] {new_role}"
47
47
  )
48
-
49
-
@@ -1,10 +1,14 @@
1
1
  from janito.cli.console import shared_console
2
2
  from janito.cli.chat_mode.shell.commands.base import ShellCmdHandler
3
3
 
4
+
4
5
  class ReadShellHandler(ShellCmdHandler):
5
6
  help_text = "/read on|off: Enable or disable read permissions for tools. Usage: /read on or /read off."
6
7
 
7
8
  def run(self):
9
+ if self.shell_state and getattr(self.shell_state, 'no_tools_mode', False):
10
+ shared_console.print("[yellow]No tools are available in this mode (no tools, no context).[/yellow]")
11
+ return
8
12
  if not self.shell_state:
9
13
  shared_console.print("[red]Shell state unavailable.[/red]")
10
14
  return
@@ -14,23 +18,36 @@ class ReadShellHandler(ShellCmdHandler):
14
18
  return
15
19
  enable = arg == "on"
16
20
  try:
17
- from janito.tools.permissions import set_global_allowed_permissions, get_global_allowed_permissions
21
+ from janito.tools.permissions import (
22
+ set_global_allowed_permissions,
23
+ get_global_allowed_permissions,
24
+ )
18
25
  from janito.tools.tool_base import ToolPermissions
26
+
19
27
  current = get_global_allowed_permissions()
20
- new_perms = ToolPermissions(read=enable, write=current.write, execute=current.execute)
28
+ new_perms = ToolPermissions(
29
+ read=enable, write=current.write, execute=current.execute
30
+ )
21
31
  set_global_allowed_permissions(new_perms)
22
32
  # Also update the singleton tools registry permissions
23
33
  import janito.tools
34
+
24
35
  janito.tools.local_tools_adapter.set_allowed_permissions(new_perms)
25
36
 
26
37
  except Exception as e:
27
- shared_console.print(f"[yellow]Warning: Could not update read permissions dynamically: {e}[/yellow]")
38
+ shared_console.print(
39
+ f"[yellow]Warning: Could not update read permissions dynamically: {e}[/yellow]"
40
+ )
28
41
  # Refresh system prompt if agent is available
29
42
  agent = getattr(self.shell_state, "agent", None)
30
43
  if agent:
31
44
  agent.refresh_system_prompt_from_template()
32
45
  # No need to print the system prompt after permission change
33
46
  if enable:
34
- shared_console.print("[green]Read permissions ENABLED. Tools can now read files and data.[/green]")
47
+ shared_console.print(
48
+ "[green]Read permissions ENABLED. Tools can now read files and data.[/green]"
49
+ )
35
50
  else:
36
- shared_console.print("[yellow]Read permissions DISABLED. Tools cannot read files/data.[/yellow]")
51
+ shared_console.print(
52
+ "[yellow]Read permissions DISABLED. Tools cannot read files/data.[/yellow]"
53
+ )
@@ -1,6 +1,7 @@
1
1
  from janito.cli.console import shared_console
2
2
  from janito.cli.chat_mode.shell.commands.base import ShellCmdHandler
3
3
 
4
+
4
5
  class ToolsShellHandler(ShellCmdHandler):
5
6
  help_text = "List available tools"
6
7
 
@@ -27,7 +28,7 @@ class ToolsShellHandler(ShellCmdHandler):
27
28
  perm_groups = {}
28
29
  for tool in tools:
29
30
  inst = tool_instances.get(tool, None)
30
- perms = getattr(inst, 'permissions', None)
31
+ perms = getattr(inst, "permissions", None)
31
32
  if not perms:
32
33
  group = "unknown"
33
34
  else:
@@ -37,6 +38,7 @@ class ToolsShellHandler(ShellCmdHandler):
37
38
 
38
39
  def _print_tools_table(self, perm_groups):
39
40
  from rich.table import Table
41
+
40
42
  table = Table(title="Tools by Permission Class")
41
43
  table.add_column("Permission Type", style="cyan", no_wrap=True)
42
44
  table.add_column("Tools", style="magenta")
@@ -47,27 +49,36 @@ class ToolsShellHandler(ShellCmdHandler):
47
49
  def _find_exec_tools(self, registry):
48
50
  exec_tools = []
49
51
  for tool_instance in registry.get_tools():
50
- perms = getattr(tool_instance, 'permissions', None)
52
+ perms = getattr(tool_instance, "permissions", None)
51
53
  if perms and perms.execute:
52
54
  exec_tools.append(tool_instance.tool_name)
53
55
  return exec_tools
54
56
 
55
57
  def run(self):
58
+ # Check for no_tools_mode in shell_state
59
+ if self.shell_state and getattr(self.shell_state, 'no_tools_mode', False):
60
+ shared_console.print("[yellow]No tools are available in this mode (no tools, no context).[/yellow]")
61
+ return
56
62
  try:
57
63
  import janito.tools # Ensure all tools are registered
58
64
  from janito.tools.permissions import get_global_allowed_permissions
65
+
59
66
  registry = janito.tools.get_local_tools_adapter()
60
67
  tools = registry.list_tools()
61
68
  shared_console.print("Registered tools:")
62
69
  tool_instances = {t.tool_name: t for t in registry.get_tools()}
63
70
  if not tools:
64
- shared_console.print("No tools are enabled under the current permission settings.")
71
+ shared_console.print(
72
+ "No tools are enabled under the current permission settings."
73
+ )
65
74
  return
66
75
  perm_groups = self._group_tools_by_permission(tools, tool_instances)
67
76
  self._print_tools_table(perm_groups)
68
77
  exec_tools = self._find_exec_tools(registry)
69
78
  perms = get_global_allowed_permissions()
70
79
  if not perms.execute and exec_tools:
71
- shared_console.print("[yellow]⚠️ Warning: Execution tools (e.g., commands, code execution) are disabled. Use -x to enable them.[/yellow]")
80
+ shared_console.print(
81
+ "[yellow]⚠️ Warning: Execution tools (e.g., commands, code execution) are disabled. Use -x to enable them.[/yellow]"
82
+ )
72
83
  except Exception as e:
73
84
  shared_console.print(f"[red]Error loading tools: {e}[/red]")
@@ -1,10 +1,14 @@
1
1
  from janito.cli.console import shared_console
2
2
  from janito.cli.chat_mode.shell.commands.base import ShellCmdHandler
3
3
 
4
+
4
5
  class WriteShellHandler(ShellCmdHandler):
5
6
  help_text = "/write on|off: Enable or disable write permissions for tools. Usage: /write on or /write off."
6
7
 
7
8
  def run(self):
9
+ if self.shell_state and getattr(self.shell_state, 'no_tools_mode', False):
10
+ shared_console.print("[yellow]No tools are available in this mode (no tools, no context).[/yellow]")
11
+ return
8
12
  if not self.shell_state:
9
13
  shared_console.print("[red]Shell state unavailable.[/red]")
10
14
  return
@@ -14,23 +18,36 @@ class WriteShellHandler(ShellCmdHandler):
14
18
  return
15
19
  enable = arg == "on"
16
20
  try:
17
- from janito.tools.permissions import set_global_allowed_permissions, get_global_allowed_permissions
21
+ from janito.tools.permissions import (
22
+ set_global_allowed_permissions,
23
+ get_global_allowed_permissions,
24
+ )
18
25
  from janito.tools.tool_base import ToolPermissions
26
+
19
27
  current = get_global_allowed_permissions()
20
- new_perms = ToolPermissions(read=current.read, write=enable, execute=current.execute)
28
+ new_perms = ToolPermissions(
29
+ read=current.read, write=enable, execute=current.execute
30
+ )
21
31
  set_global_allowed_permissions(new_perms)
22
32
  # Also update the singleton tools registry permissions
23
33
  import janito.tools
34
+
24
35
  janito.tools.local_tools_adapter.set_allowed_permissions(new_perms)
25
36
 
26
37
  except Exception as e:
27
- shared_console.print(f"[yellow]Warning: Could not update write permissions dynamically: {e}[/yellow]")
38
+ shared_console.print(
39
+ f"[yellow]Warning: Could not update write permissions dynamically: {e}[/yellow]"
40
+ )
28
41
  # Refresh system prompt if agent is available
29
42
  agent = getattr(self.shell_state, "agent", None)
30
43
  if agent:
31
44
  agent.refresh_system_prompt_from_template()
32
45
  # No need to print the system prompt after permission change
33
46
  if enable:
34
- shared_console.print("[green]Write permissions ENABLED. Tools can now write files and data.[/green]")
47
+ shared_console.print(
48
+ "[green]Write permissions ENABLED. Tools can now write files and data.[/green]"
49
+ )
35
50
  else:
36
- shared_console.print("[yellow]Write permissions DISABLED. Tools cannot write files/data.[/yellow]")
51
+ shared_console.print(
52
+ "[yellow]Write permissions DISABLED. Tools cannot write files/data.[/yellow]"
53
+ )
@@ -12,7 +12,9 @@ class UserInputHistory:
12
12
  """
13
13
 
14
14
  def __init__(self, history_dir=None):
15
- self.history_dir = history_dir or os.path.join(os.path.expanduser("~"), ".janito", "input_history")
15
+ self.history_dir = history_dir or os.path.join(
16
+ os.path.expanduser("~"), ".janito", "input_history"
17
+ )
16
18
  os.makedirs(self.history_dir, exist_ok=True)
17
19
 
18
20
  def _get_today_file(self):
@@ -38,5 +38,3 @@ def set_role(role):
38
38
  rc = RuntimeConfig()
39
39
  rc.role = role
40
40
  rc.save()
41
-
42
-