janito 3.2.0__py3-none-any.whl → 3.4.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.
- janito/README.md +0 -3
- janito/cli/chat_mode/bindings.py +0 -26
- janito/cli/chat_mode/session.py +1 -12
- janito/cli/chat_mode/shell/commands/security/allowed_sites.py +33 -47
- janito/cli/cli_commands/list_plugins.py +43 -52
- janito/cli/core/getters.py +0 -3
- janito/cli/core/model_guesser.py +24 -40
- janito/cli/main_cli.py +12 -9
- janito/cli/prompt_core.py +9 -20
- janito/drivers/openai/driver.py +0 -1
- janito/drivers/zai/driver.py +0 -1
- janito/hello.txt +0 -0
- janito/i18n/it.py +46 -46
- janito/llm/agent.py +16 -32
- janito/llm/auth_utils.py +5 -14
- janito/llm/driver.py +0 -8
- janito/plugins/__init__.py +12 -31
- janito/plugins/auto_loader.py +11 -12
- janito/plugins/auto_loader_fixed.py +11 -12
- janito/{plugin_system → plugins}/base.py +2 -5
- janito/plugins/builtin.py +1 -15
- janito/plugins/core_adapter.py +11 -89
- janito/plugins/core_loader.py +120 -0
- janito/plugins/core_loader_fixed.py +125 -0
- janito/plugins/discovery.py +5 -5
- janito/plugins/discovery_core.py +9 -14
- janito/plugins/manager.py +1 -1
- janito/providers/__init__.py +0 -1
- janito/tools/__init__.py +7 -31
- janito/tools/adapters/__init__.py +1 -6
- janito/tools/adapters/local/__init__.py +70 -7
- janito/{plugins/tools → tools/adapters/local}/ask_user.py +3 -3
- janito/{plugins/tools → tools/adapters/local}/create_file.py +6 -6
- janito/{plugins/tools → tools/adapters/local}/fetch_url.py +3 -3
- janito/{plugins/tools → tools/adapters/local}/replace_text_in_file.py +4 -4
- janito/{plugins/tools → tools/adapters/local}/show_image.py +6 -15
- janito/{plugins/core/imagedisplay/tools → tools/adapters/local}/show_image_grid.py +5 -13
- janito/tools/function_adapter.py +65 -0
- janito/tools/loop_protection_decorator.py +117 -114
- {janito-3.2.0.dist-info → janito-3.4.0.dist-info}/METADATA +2 -1
- {janito-3.2.0.dist-info → janito-3.4.0.dist-info}/RECORD +85 -156
- janito/cli/cli_commands/check_tools.py +0 -212
- janito/llm/cancellation_manager.py +0 -63
- janito/llm/enter_cancellation.py +0 -107
- janito/plugin_system/__init__.py +0 -10
- janito/plugin_system/core_loader.py +0 -217
- janito/plugin_system/core_loader_fixed.py +0 -225
- janito/plugins/core/__init__.py +0 -7
- janito/plugins/core/codeanalyzer/__init__.py +0 -43
- janito/plugins/core/filemanager/__init__.py +0 -124
- janito/plugins/core/filemanager/tools/create_file.py +0 -87
- janito/plugins/core/filemanager/tools/replace_text_in_file.py +0 -270
- janito/plugins/core/imagedisplay/__init__.py +0 -14
- janito/plugins/core/imagedisplay/plugin.py +0 -51
- janito/plugins/core/imagedisplay/tools/__init__.py +0 -1
- janito/plugins/core/imagedisplay/tools/show_image.py +0 -83
- janito/plugins/core/system/__init__.py +0 -23
- janito/plugins/dev/__init__.py +0 -7
- janito/plugins/dev/pythondev/__init__.py +0 -37
- janito/plugins/dev/visualization/__init__.py +0 -23
- janito/plugins/example_plugin.py +0 -108
- janito/plugins/tools/__init__.py +0 -10
- janito/plugins/tools/copy_file.py +0 -87
- janito/plugins/tools/core_tools_plugin.py +0 -87
- janito/plugins/tools/create_directory.py +0 -70
- janito/plugins/tools/decorators.py +0 -19
- janito/plugins/tools/delete_text_in_file.py +0 -134
- janito/plugins/tools/find_files.py +0 -143
- janito/plugins/tools/get_file_outline/__init__.py +0 -7
- janito/plugins/tools/get_file_outline/core.py +0 -122
- janito/plugins/tools/get_file_outline/java_outline.py +0 -47
- janito/plugins/tools/get_file_outline/markdown_outline.py +0 -14
- janito/plugins/tools/get_file_outline/python_outline.py +0 -303
- janito/plugins/tools/get_file_outline/search_outline.py +0 -36
- janito/plugins/tools/move_file.py +0 -131
- janito/plugins/tools/open_html_in_browser.py +0 -51
- janito/plugins/tools/open_url.py +0 -37
- janito/plugins/tools/python_code_run.py +0 -172
- janito/plugins/tools/python_command_run.py +0 -171
- janito/plugins/tools/python_file_run.py +0 -172
- janito/plugins/tools/read_chart.py +0 -259
- janito/plugins/tools/read_files.py +0 -58
- janito/plugins/tools/remove_directory.py +0 -55
- janito/plugins/tools/remove_file.py +0 -58
- janito/plugins/tools/run_bash_command.py +0 -183
- janito/plugins/tools/run_powershell_command.py +0 -218
- janito/plugins/tools/search_text/__init__.py +0 -7
- janito/plugins/tools/search_text/core.py +0 -205
- janito/plugins/tools/search_text/match_lines.py +0 -67
- janito/plugins/tools/search_text/pattern_utils.py +0 -73
- janito/plugins/tools/search_text/traverse_directory.py +0 -145
- janito/plugins/tools/show_image_grid.py +0 -85
- janito/plugins/tools/validate_file_syntax/__init__.py +0 -7
- janito/plugins/tools/validate_file_syntax/core.py +0 -114
- janito/plugins/tools/validate_file_syntax/css_validator.py +0 -35
- janito/plugins/tools/validate_file_syntax/html_validator.py +0 -100
- janito/plugins/tools/validate_file_syntax/jinja2_validator.py +0 -50
- janito/plugins/tools/validate_file_syntax/js_validator.py +0 -27
- janito/plugins/tools/validate_file_syntax/json_validator.py +0 -6
- janito/plugins/tools/validate_file_syntax/markdown_validator.py +0 -109
- janito/plugins/tools/validate_file_syntax/ps1_validator.py +0 -32
- janito/plugins/tools/validate_file_syntax/python_validator.py +0 -5
- janito/plugins/tools/validate_file_syntax/xml_validator.py +0 -11
- janito/plugins/tools/validate_file_syntax/yaml_validator.py +0 -6
- janito/plugins/tools/view_file.py +0 -172
- janito/plugins/ui/__init__.py +0 -7
- janito/plugins/ui/userinterface/__init__.py +0 -16
- janito/plugins/ui/userinterface/tools/ask_user.py +0 -110
- janito/plugins/web/__init__.py +0 -7
- janito/plugins/web/webtools/__init__.py +0 -33
- janito/plugins/web/webtools/tools/fetch_url.py +0 -458
- janito/providers/together/__init__.py +0 -1
- janito/providers/together/model_info.py +0 -69
- janito/providers/together/provider.py +0 -108
- janito/tools/cli_initializer.py +0 -88
- janito/tools/initialize.py +0 -70
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/copy_file.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/create_directory.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/delete_text_in_file.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/find_files.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/get_file_outline/__init__.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/get_file_outline/core.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/get_file_outline/java_outline.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/get_file_outline/markdown_outline.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/get_file_outline/python_outline.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/get_file_outline/search_outline.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/move_file.py +0 -0
- /janito/{plugins/web/webtools/tools → tools/adapters/local}/open_html_in_browser.py +0 -0
- /janito/{plugins/web/webtools/tools → tools/adapters/local}/open_url.py +0 -0
- /janito/{plugins/dev/pythondev/tools → tools/adapters/local}/python_code_run.py +0 -0
- /janito/{plugins/dev/pythondev/tools → tools/adapters/local}/python_command_run.py +0 -0
- /janito/{plugins/dev/pythondev/tools → tools/adapters/local}/python_file_run.py +0 -0
- /janito/{plugins/dev/visualization/tools → tools/adapters/local}/read_chart.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/read_files.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/remove_directory.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/remove_file.py +0 -0
- /janito/{plugins/core/system/tools → tools/adapters/local}/run_bash_command.py +0 -0
- /janito/{plugins/core/system/tools → tools/adapters/local}/run_powershell_command.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/search_text/__init__.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/search_text/core.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/search_text/match_lines.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/search_text/pattern_utils.py +0 -0
- /janito/{plugins/core/codeanalyzer/tools → tools/adapters/local}/search_text/traverse_directory.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/__init__.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/core.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/css_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/html_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/jinja2_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/js_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/json_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/markdown_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/ps1_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/python_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/xml_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/validate_file_syntax/yaml_validator.py +0 -0
- /janito/{plugins/core/filemanager/tools → tools/adapters/local}/view_file.py +0 -0
- {janito-3.2.0.dist-info → janito-3.4.0.dist-info}/WHEEL +0 -0
- {janito-3.2.0.dist-info → janito-3.4.0.dist-info}/entry_points.txt +0 -0
- {janito-3.2.0.dist-info → janito-3.4.0.dist-info}/licenses/LICENSE +0 -0
- {janito-3.2.0.dist-info → janito-3.4.0.dist-info}/top_level.txt +0 -0
janito/llm/agent.py
CHANGED
@@ -318,39 +318,23 @@ class LLMAgent:
|
|
318
318
|
loop_count = 1
|
319
319
|
import threading
|
320
320
|
|
321
|
-
|
322
|
-
|
323
|
-
|
324
|
-
|
325
|
-
|
326
|
-
|
327
|
-
|
328
|
-
|
329
|
-
|
330
|
-
|
331
|
-
|
332
|
-
|
333
|
-
|
334
|
-
config, cancel_event=driver_cancel_event
|
321
|
+
cancel_event = threading.Event()
|
322
|
+
while True:
|
323
|
+
self._print_verbose_chat_loop(loop_count)
|
324
|
+
driver_input = self._prepare_driver_input(config, cancel_event=cancel_event)
|
325
|
+
self.input_queue.put(driver_input)
|
326
|
+
try:
|
327
|
+
result, added_tool_results = self._process_next_response()
|
328
|
+
except KeyboardInterrupt:
|
329
|
+
cancel_event.set()
|
330
|
+
raise
|
331
|
+
if getattr(self, "verbose_agent", False):
|
332
|
+
print(
|
333
|
+
f"[agent] [DEBUG] Returned from _process_next_response: result={result}, added_tool_results={added_tool_results}"
|
335
334
|
)
|
336
|
-
|
337
|
-
|
338
|
-
|
339
|
-
except KeyboardInterrupt:
|
340
|
-
cancel_manager.cancel_current_request()
|
341
|
-
raise
|
342
|
-
if getattr(self, "verbose_agent", False):
|
343
|
-
print(
|
344
|
-
f"[agent] [DEBUG] Returned from _process_next_response: result={result}, added_tool_results={added_tool_results}"
|
345
|
-
)
|
346
|
-
if self._should_exit_chat_loop(result, added_tool_results):
|
347
|
-
return result
|
348
|
-
loop_count += 1
|
349
|
-
finally:
|
350
|
-
cancel_manager.clear_current_request()
|
351
|
-
# Clean up cancellation event
|
352
|
-
if hasattr(self, "cancel_event"):
|
353
|
-
delattr(self, "cancel_event")
|
335
|
+
if self._should_exit_chat_loop(result, added_tool_results):
|
336
|
+
return result
|
337
|
+
loop_count += 1
|
354
338
|
|
355
339
|
def _clear_driver_queues(self):
|
356
340
|
if hasattr(self, "driver") and self.driver:
|
janito/llm/auth_utils.py
CHANGED
@@ -13,18 +13,9 @@ def handle_missing_api_key(provider_name: str, env_var_name: str) -> None:
|
|
13
13
|
provider_name: Name of the provider (e.g., 'alibaba', 'openai')
|
14
14
|
env_var_name: Environment variable name (e.g., 'ALIBABA_API_KEY')
|
15
15
|
"""
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
print()
|
22
|
-
print(f"To set a new API key, use:")
|
23
|
-
print(f" janito --set-api-key YOUR_NEW_API_KEY -p moonshot")
|
24
|
-
else:
|
25
|
-
print(
|
26
|
-
f"[ERROR] No API key found for provider '{provider_name}'. Please set the API key using:"
|
27
|
-
)
|
28
|
-
print(f" janito --set-api-key YOUR_API_KEY -p {provider_name}")
|
29
|
-
print(f"Or set the {env_var_name} environment variable.")
|
16
|
+
print(
|
17
|
+
f"[ERROR] No API key found for provider '{provider_name}'. Please set the API key using:"
|
18
|
+
)
|
19
|
+
print(f" janito --set-api-key YOUR_API_KEY -p {provider_name}")
|
20
|
+
print(f"Or set the {env_var_name} environment variable.")
|
30
21
|
sys.exit(1)
|
janito/llm/driver.py
CHANGED
@@ -252,11 +252,3 @@ class LLMDriver(ABC):
|
|
252
252
|
def _get_message_from_result(self, result):
|
253
253
|
"""Extract the message object from the provider result. Subclasses must implement this."""
|
254
254
|
raise NotImplementedError("Subclasses must implement _get_message_from_result.")
|
255
|
-
|
256
|
-
def cancel_current_request(self):
|
257
|
-
"""Cancel the current request being processed."""
|
258
|
-
# Use global cancellation manager to cancel the current request
|
259
|
-
from janito.llm.cancellation_manager import get_cancellation_manager
|
260
|
-
|
261
|
-
cancel_manager = get_cancellation_manager()
|
262
|
-
cancel_manager.cancel_current_request()
|
janito/plugins/__init__.py
CHANGED
@@ -1,36 +1,17 @@
|
|
1
1
|
"""
|
2
|
-
Plugin
|
2
|
+
Plugin system for janito.
|
3
3
|
|
4
|
-
This package
|
5
|
-
|
4
|
+
This package provides a flexible plugin system that allows extending
|
5
|
+
janito's functionality with custom tools, commands, and features.
|
6
6
|
"""
|
7
7
|
|
8
|
-
|
9
|
-
|
8
|
+
from .manager import PluginManager
|
9
|
+
from .base import Plugin, PluginMetadata
|
10
|
+
from .discovery import discover_plugins
|
10
11
|
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
PLUGINS = {
|
18
|
-
"core.filemanager": filemanager,
|
19
|
-
"core.codeanalyzer": codeanalyzer,
|
20
|
-
"core.system": system,
|
21
|
-
"core.imagedisplay": imagedisplay,
|
22
|
-
"web.webtools": webtools,
|
23
|
-
"dev.pythondev": pythondev,
|
24
|
-
"dev.visualization": visualization,
|
25
|
-
"ui.userinterface": userinterface,
|
26
|
-
}
|
27
|
-
|
28
|
-
|
29
|
-
def list_plugins():
|
30
|
-
"""Return all available plugins"""
|
31
|
-
return list(PLUGINS.keys())
|
32
|
-
|
33
|
-
|
34
|
-
def get_plugin(name):
|
35
|
-
"""Get a specific plugin by name"""
|
36
|
-
return PLUGINS.get(name)
|
12
|
+
__all__ = [
|
13
|
+
"PluginManager",
|
14
|
+
"Plugin",
|
15
|
+
"PluginMetadata",
|
16
|
+
"discover_plugins",
|
17
|
+
]
|
janito/plugins/auto_loader.py
CHANGED
@@ -13,7 +13,7 @@ from janito.plugins.discovery import list_available_plugins
|
|
13
13
|
# List of core plugins that should be enabled by default
|
14
14
|
CORE_PLUGINS = [
|
15
15
|
"core.filemanager",
|
16
|
-
"core.codeanalyzer",
|
16
|
+
"core.codeanalyzer",
|
17
17
|
"core.system",
|
18
18
|
"core.imagedisplay",
|
19
19
|
"dev.pythondev",
|
@@ -26,23 +26,23 @@ CORE_PLUGINS = [
|
|
26
26
|
def load_core_plugins(pm: PluginManager = None) -> List[str]:
|
27
27
|
"""
|
28
28
|
Load all core plugins.
|
29
|
-
|
29
|
+
|
30
30
|
Args:
|
31
31
|
pm: PluginManager instance. If None, creates a new one.
|
32
|
-
|
32
|
+
|
33
33
|
Returns:
|
34
34
|
List of successfully loaded plugin names
|
35
35
|
"""
|
36
36
|
if pm is None:
|
37
37
|
pm = PluginManager()
|
38
|
-
|
38
|
+
|
39
39
|
# Ensure plugins directory is in search path
|
40
40
|
plugins_dir = Path.cwd() / "plugins"
|
41
41
|
if plugins_dir.exists():
|
42
42
|
pm.add_plugin_path(str(plugins_dir))
|
43
|
-
|
43
|
+
|
44
44
|
loaded = []
|
45
|
-
|
45
|
+
|
46
46
|
# Load core plugins
|
47
47
|
for plugin_name in CORE_PLUGINS:
|
48
48
|
try:
|
@@ -50,14 +50,14 @@ def load_core_plugins(pm: PluginManager = None) -> List[str]:
|
|
50
50
|
loaded.append(plugin_name)
|
51
51
|
except Exception as e:
|
52
52
|
print(f"Warning: Failed to load core plugin {plugin_name}: {e}")
|
53
|
-
|
53
|
+
|
54
54
|
return loaded
|
55
55
|
|
56
56
|
|
57
57
|
def get_loaded_core_plugins() -> List[str]:
|
58
58
|
"""
|
59
59
|
Get list of currently loaded core plugins.
|
60
|
-
|
60
|
+
|
61
61
|
Returns:
|
62
62
|
List of loaded core plugin names
|
63
63
|
"""
|
@@ -69,10 +69,10 @@ def get_loaded_core_plugins() -> List[str]:
|
|
69
69
|
def is_core_plugin(plugin_name: str) -> bool:
|
70
70
|
"""
|
71
71
|
Check if a plugin is a core plugin.
|
72
|
-
|
72
|
+
|
73
73
|
Args:
|
74
74
|
plugin_name: Name of the plugin to check
|
75
|
-
|
75
|
+
|
76
76
|
Returns:
|
77
77
|
True if it's a core plugin
|
78
78
|
"""
|
@@ -82,11 +82,10 @@ def is_core_plugin(plugin_name: str) -> bool:
|
|
82
82
|
# Auto-load core plugins when module is imported
|
83
83
|
_plugin_manager = None
|
84
84
|
|
85
|
-
|
86
85
|
def get_plugin_manager() -> PluginManager:
|
87
86
|
"""Get the global plugin manager with core plugins loaded."""
|
88
87
|
global _plugin_manager
|
89
88
|
if _plugin_manager is None:
|
90
89
|
_plugin_manager = PluginManager()
|
91
90
|
load_core_plugins(_plugin_manager)
|
92
|
-
return _plugin_manager
|
91
|
+
return _plugin_manager
|
@@ -9,12 +9,12 @@ import os
|
|
9
9
|
from pathlib import Path
|
10
10
|
from typing import List
|
11
11
|
from janito.plugins.manager import PluginManager
|
12
|
-
from janito.
|
12
|
+
from janito.plugins.core_loader_fixed import load_core_plugin, get_core_plugins
|
13
13
|
|
14
14
|
# List of core plugins that should be enabled by default
|
15
15
|
CORE_PLUGINS = [
|
16
16
|
"core.filemanager",
|
17
|
-
"core.codeanalyzer",
|
17
|
+
"core.codeanalyzer",
|
18
18
|
"core.system",
|
19
19
|
"core.imagedisplay",
|
20
20
|
"dev.pythondev",
|
@@ -27,18 +27,18 @@ CORE_PLUGINS = [
|
|
27
27
|
def load_core_plugins(pm: PluginManager = None) -> List[str]:
|
28
28
|
"""
|
29
29
|
Load all core plugins.
|
30
|
-
|
30
|
+
|
31
31
|
Args:
|
32
32
|
pm: PluginManager instance. If None, creates a new one.
|
33
|
-
|
33
|
+
|
34
34
|
Returns:
|
35
35
|
List of successfully loaded plugin names
|
36
36
|
"""
|
37
37
|
if pm is None:
|
38
38
|
pm = PluginManager()
|
39
|
-
|
39
|
+
|
40
40
|
loaded = []
|
41
|
-
|
41
|
+
|
42
42
|
# Load core plugins
|
43
43
|
for plugin_name in CORE_PLUGINS:
|
44
44
|
try:
|
@@ -49,14 +49,14 @@ def load_core_plugins(pm: PluginManager = None) -> List[str]:
|
|
49
49
|
loaded.append(plugin_name)
|
50
50
|
except Exception as e:
|
51
51
|
print(f"Warning: Failed to load core plugin {plugin_name}: {e}")
|
52
|
-
|
52
|
+
|
53
53
|
return loaded
|
54
54
|
|
55
55
|
|
56
56
|
def get_loaded_core_plugins() -> List[str]:
|
57
57
|
"""
|
58
58
|
Get list of currently loaded core plugins.
|
59
|
-
|
59
|
+
|
60
60
|
Returns:
|
61
61
|
List of loaded core plugin names
|
62
62
|
"""
|
@@ -68,10 +68,10 @@ def get_loaded_core_plugins() -> List[str]:
|
|
68
68
|
def is_core_plugin(plugin_name: str) -> bool:
|
69
69
|
"""
|
70
70
|
Check if a plugin is a core plugin.
|
71
|
-
|
71
|
+
|
72
72
|
Args:
|
73
73
|
plugin_name: Name of the plugin to check
|
74
|
-
|
74
|
+
|
75
75
|
Returns:
|
76
76
|
True if it's a core plugin
|
77
77
|
"""
|
@@ -81,11 +81,10 @@ def is_core_plugin(plugin_name: str) -> bool:
|
|
81
81
|
# Auto-load core plugins when module is imported
|
82
82
|
_plugin_manager = None
|
83
83
|
|
84
|
-
|
85
84
|
def get_plugin_manager() -> PluginManager:
|
86
85
|
"""Get the global plugin manager with core plugins loaded."""
|
87
86
|
global _plugin_manager
|
88
87
|
if _plugin_manager is None:
|
89
88
|
_plugin_manager = PluginManager()
|
90
89
|
load_core_plugins(_plugin_manager)
|
91
|
-
return _plugin_manager
|
90
|
+
return _plugin_manager
|
@@ -5,10 +5,7 @@ Base classes for janito plugins.
|
|
5
5
|
from abc import ABC, abstractmethod
|
6
6
|
from dataclasses import dataclass
|
7
7
|
from typing import Dict, Any, List, Optional, Type, Union
|
8
|
-
from
|
9
|
-
|
10
|
-
if TYPE_CHECKING:
|
11
|
-
from janito.tools.tool_base import ToolBase
|
8
|
+
from janito.tools.tool_base import ToolBase
|
12
9
|
|
13
10
|
|
14
11
|
@dataclass
|
@@ -53,7 +50,7 @@ class Plugin(ABC):
|
|
53
50
|
"""Return metadata describing this plugin."""
|
54
51
|
pass
|
55
52
|
|
56
|
-
def get_tools(self) -> List[Type[
|
53
|
+
def get_tools(self) -> List[Type[ToolBase]]:
|
57
54
|
"""
|
58
55
|
Return a list of tool classes provided by this plugin.
|
59
56
|
|
janito/plugins/builtin.py
CHANGED
@@ -7,7 +7,7 @@ with janito and available by default without requiring external installation.
|
|
7
7
|
|
8
8
|
import importlib
|
9
9
|
from typing import Dict, List, Optional, Type
|
10
|
-
from janito.
|
10
|
+
from janito.plugins.base import Plugin
|
11
11
|
|
12
12
|
|
13
13
|
class BuiltinPluginRegistry:
|
@@ -83,20 +83,6 @@ try:
|
|
83
83
|
"documentation_generator", DocumentationGeneratorPlugin
|
84
84
|
)
|
85
85
|
|
86
|
-
# Register core tools plugin
|
87
|
-
from janito.plugins.tools import CoreToolsPlugin
|
88
|
-
|
89
|
-
BuiltinPluginRegistry.register("core_tools", CoreToolsPlugin)
|
90
|
-
|
91
86
|
except ImportError:
|
92
87
|
# janito-coder not available, skip registration
|
93
88
|
pass
|
94
|
-
|
95
|
-
# Register core tools plugin (always available)
|
96
|
-
try:
|
97
|
-
from janito.plugins.tools import CoreToolsPlugin
|
98
|
-
|
99
|
-
BuiltinPluginRegistry.register("core_tools", CoreToolsPlugin)
|
100
|
-
except ImportError:
|
101
|
-
# Should not happen, but handle gracefully
|
102
|
-
pass
|
janito/plugins/core_adapter.py
CHANGED
@@ -5,24 +5,25 @@ This module provides proper Plugin class implementations for core plugins
|
|
5
5
|
that use the function-based approach instead of class-based.
|
6
6
|
"""
|
7
7
|
|
8
|
-
from janito.
|
8
|
+
from janito.plugins.base import Plugin, PluginMetadata
|
9
9
|
from typing import List, Type
|
10
|
-
from janito.tools.tool_base import ToolBase
|
10
|
+
from janito.tools.tool_base import ToolBase
|
11
|
+
from janito.tools.function_adapter import create_function_tool
|
11
12
|
|
12
13
|
|
13
14
|
class CorePluginAdapter(Plugin):
|
14
15
|
"""Adapter for core plugins using function-based tools."""
|
15
|
-
|
16
|
+
|
16
17
|
def __init__(self, plugin_name: str, description: str, tools_module):
|
17
18
|
super().__init__()
|
18
19
|
self._plugin_name = plugin_name
|
19
20
|
self._description = description
|
20
21
|
self._tools_module = tools_module
|
21
22
|
self._tool_classes = []
|
22
|
-
|
23
|
+
|
23
24
|
# Set the metadata attribute that Plugin expects
|
24
25
|
self.metadata = self.get_metadata()
|
25
|
-
|
26
|
+
|
26
27
|
def get_metadata(self) -> PluginMetadata:
|
27
28
|
return PluginMetadata(
|
28
29
|
name=self._plugin_name,
|
@@ -31,101 +32,22 @@ class CorePluginAdapter(Plugin):
|
|
31
32
|
author="Janito",
|
32
33
|
license="MIT",
|
33
34
|
)
|
34
|
-
|
35
|
+
|
35
36
|
def get_tools(self) -> List[Type[ToolBase]]:
|
36
37
|
return self._tool_classes
|
37
|
-
|
38
|
-
def _create_tool_class(self, func):
|
39
|
-
"""Create a ToolBase class from a function."""
|
40
|
-
resolved_tool_name = getattr(func, "tool_name", func.__name__)
|
41
|
-
|
42
|
-
# Create a proper tool class with explicit parameters and documentation
|
43
|
-
import inspect
|
44
|
-
from typing import get_type_hints
|
45
|
-
|
46
|
-
func_sig = inspect.signature(func)
|
47
|
-
type_hints = get_type_hints(func)
|
48
|
-
|
49
|
-
# Build parameter definitions for the run method
|
50
|
-
param_defs = []
|
51
|
-
param_docs = []
|
52
|
-
for name, param in func_sig.parameters.items():
|
53
|
-
type_hint = type_hints.get(name, str)
|
54
|
-
if param.default == inspect.Parameter.empty:
|
55
|
-
param_defs.append(f"{name}: {type_hint.__name__}")
|
56
|
-
else:
|
57
|
-
param_defs.append(f"{name}: {type_hint.__name__} = {repr(param.default)}")
|
58
|
-
|
59
|
-
# Add parameter documentation
|
60
|
-
param_docs.append(f" {name}: {type_hint.__name__} - Parameter {name}")
|
61
|
-
|
62
|
-
# Get function docstring or create one
|
63
|
-
func_doc = func.__doc__ or f"Execute {resolved_tool_name} tool"
|
64
|
-
|
65
|
-
# Create the tool class with proper signature and documentation
|
66
|
-
exec_globals = {
|
67
|
-
'ToolBase': ToolBase,
|
68
|
-
'ToolPermissions': ToolPermissions,
|
69
|
-
'func': func,
|
70
|
-
'inspect': inspect,
|
71
|
-
'str': str,
|
72
|
-
'List': list,
|
73
|
-
'Dict': dict,
|
74
|
-
'Optional': type(None),
|
75
|
-
}
|
76
|
-
|
77
|
-
param_docs_str = '\n'.join(param_docs)
|
78
|
-
|
79
|
-
class_def = f'''
|
80
|
-
class DynamicTool(ToolBase):
|
81
|
-
"""
|
82
|
-
{func_doc}
|
83
|
-
|
84
|
-
Parameters:
|
85
|
-
{param_docs_str}
|
86
|
-
|
87
|
-
Returns:
|
88
|
-
str: Execution result
|
89
|
-
"""
|
90
|
-
tool_name = "{resolved_tool_name}"
|
91
|
-
permissions = ToolPermissions(read=True, write=True, execute=True)
|
92
38
|
|
93
|
-
def __init__(self):
|
94
|
-
super().__init__()
|
95
|
-
|
96
|
-
def run(self, {', '.join(param_defs)}) -> str:
|
97
|
-
kwargs = locals()
|
98
|
-
sig = inspect.signature(func)
|
99
|
-
|
100
|
-
# Filter kwargs to only include parameters the function accepts
|
101
|
-
filtered_kwargs = {{}}
|
102
|
-
for name, param in sig.parameters.items():
|
103
|
-
if name in kwargs and kwargs[name] is not None:
|
104
|
-
filtered_kwargs[name] = kwargs[name]
|
105
|
-
|
106
|
-
result = func(**filtered_kwargs)
|
107
|
-
return str(result) if result is not None else ""
|
108
|
-
'''
|
109
|
-
|
110
|
-
exec(class_def, exec_globals)
|
111
|
-
return exec_globals['DynamicTool']
|
112
|
-
|
113
|
-
return DynamicTool
|
114
|
-
|
115
39
|
def initialize(self):
|
116
40
|
"""Initialize the plugin by creating tool classes."""
|
117
41
|
# Get tools from the module
|
118
42
|
tools = getattr(self._tools_module, "__plugin_tools__", [])
|
119
|
-
|
43
|
+
|
120
44
|
self._tool_classes = []
|
121
45
|
for tool_func in tools:
|
122
46
|
if callable(tool_func):
|
123
|
-
tool_class =
|
47
|
+
tool_class = create_function_tool(tool_func)
|
124
48
|
self._tool_classes.append(tool_class)
|
125
49
|
|
126
50
|
|
127
|
-
def create_core_plugin(
|
128
|
-
plugin_name: str, description: str, tools_module
|
129
|
-
) -> CorePluginAdapter:
|
51
|
+
def create_core_plugin(plugin_name: str, description: str, tools_module) -> CorePluginAdapter:
|
130
52
|
"""Create a core plugin adapter."""
|
131
|
-
return CorePluginAdapter(plugin_name, description, tools_module)
|
53
|
+
return CorePluginAdapter(plugin_name, description, tools_module)
|
@@ -0,0 +1,120 @@
|
|
1
|
+
"""
|
2
|
+
Core plugin loader that properly handles function-based plugins.
|
3
|
+
|
4
|
+
This module provides a simplified approach to load core plugins
|
5
|
+
without the complex discovery mechanism.
|
6
|
+
"""
|
7
|
+
|
8
|
+
import importlib.util
|
9
|
+
import sys
|
10
|
+
from pathlib import Path
|
11
|
+
from typing import Optional
|
12
|
+
|
13
|
+
from janito.plugins.base import Plugin, PluginMetadata
|
14
|
+
from janito.tools.function_adapter import create_function_tool
|
15
|
+
from janito.tools.tool_base import ToolBase
|
16
|
+
|
17
|
+
|
18
|
+
class CorePlugin(Plugin):
|
19
|
+
"""Simple core plugin implementation."""
|
20
|
+
|
21
|
+
def __init__(self, name: str, description: str, tools: list):
|
22
|
+
super().__init__()
|
23
|
+
self._plugin_name = name
|
24
|
+
self._description = description
|
25
|
+
self._tools = tools
|
26
|
+
self._tool_classes = []
|
27
|
+
|
28
|
+
def get_metadata(self) -> PluginMetadata:
|
29
|
+
return PluginMetadata(
|
30
|
+
name=self._plugin_name,
|
31
|
+
version="1.0.0",
|
32
|
+
description=self._description,
|
33
|
+
author="Janito",
|
34
|
+
license="MIT",
|
35
|
+
)
|
36
|
+
|
37
|
+
def get_tools(self) -> list:
|
38
|
+
return self._tool_classes
|
39
|
+
|
40
|
+
def initialize(self):
|
41
|
+
"""Initialize by creating tool classes."""
|
42
|
+
self._tool_classes = []
|
43
|
+
for tool_func in self._tools:
|
44
|
+
if callable(tool_func):
|
45
|
+
tool_class = create_function_tool(tool_func)
|
46
|
+
self._tool_classes.append(tool_class)
|
47
|
+
|
48
|
+
|
49
|
+
def load_core_plugin(plugin_name: str) -> Optional[Plugin]:
|
50
|
+
"""
|
51
|
+
Load a core plugin by name.
|
52
|
+
|
53
|
+
Args:
|
54
|
+
plugin_name: Name of the plugin (e.g., 'core.filemanager')
|
55
|
+
|
56
|
+
Returns:
|
57
|
+
Plugin instance if loaded successfully
|
58
|
+
"""
|
59
|
+
try:
|
60
|
+
# Parse plugin name
|
61
|
+
if "." not in plugin_name:
|
62
|
+
return None
|
63
|
+
|
64
|
+
parts = plugin_name.split(".")
|
65
|
+
if len(parts) != 2:
|
66
|
+
return None
|
67
|
+
|
68
|
+
package_name, submodule_name = parts
|
69
|
+
|
70
|
+
# Build path to plugin
|
71
|
+
plugin_path = Path("plugins") / package_name / submodule_name / "__init__.py"
|
72
|
+
if not plugin_path.exists():
|
73
|
+
return None
|
74
|
+
|
75
|
+
# Load the module
|
76
|
+
spec = importlib.util.spec_from_file_location(plugin_name, plugin_path)
|
77
|
+
if spec is None or spec.loader is None:
|
78
|
+
return None
|
79
|
+
|
80
|
+
module = importlib.util.module_from_spec(spec)
|
81
|
+
spec.loader.exec_module(module)
|
82
|
+
|
83
|
+
# Get plugin info
|
84
|
+
name = getattr(module, "__plugin_name__", plugin_name)
|
85
|
+
description = getattr(module, "__plugin_description__", f"Core plugin: {plugin_name}")
|
86
|
+
tools = getattr(module, "__plugin_tools__", [])
|
87
|
+
|
88
|
+
if not tools:
|
89
|
+
return None
|
90
|
+
|
91
|
+
# Create plugin
|
92
|
+
plugin = CorePlugin(name, description, tools)
|
93
|
+
plugin.initialize()
|
94
|
+
return plugin
|
95
|
+
|
96
|
+
except Exception as e:
|
97
|
+
print(f"Error loading core plugin {plugin_name}: {e}")
|
98
|
+
return None
|
99
|
+
|
100
|
+
|
101
|
+
def get_core_plugins() -> list:
|
102
|
+
"""Get list of all available core plugins."""
|
103
|
+
core_plugins = [
|
104
|
+
"core.filemanager",
|
105
|
+
"core.codeanalyzer",
|
106
|
+
"core.system",
|
107
|
+
"core.imagedisplay",
|
108
|
+
"dev.pythondev",
|
109
|
+
"dev.visualization",
|
110
|
+
"ui.userinterface",
|
111
|
+
"web.webtools",
|
112
|
+
]
|
113
|
+
|
114
|
+
available = []
|
115
|
+
for plugin_name in core_plugins:
|
116
|
+
plugin = load_core_plugin(plugin_name)
|
117
|
+
if plugin:
|
118
|
+
available.append(plugin_name)
|
119
|
+
|
120
|
+
return available
|