janito 3.3.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/cli/cli_commands/list_plugins.py +48 -52
- janito/cli/core/getters.py +0 -3
- janito/cli/main_cli.py +12 -9
- janito/drivers/openai/driver.py +0 -1
- janito/drivers/zai/driver.py +0 -1
- janito/hello.txt +0 -0
- janito/llm/auth_utils.py +5 -14
- janito/plugins/__init__.py +7 -18
- janito/{plugins_backup_20250825_070018 → plugins}/auto_loader_fixed.py +11 -12
- janito/plugins/base.py +152 -57
- janito/plugins/builtin.py +1 -15
- janito/{plugins_backup_20250825_070018 → plugins}/core_adapter.py +9 -11
- janito/plugins/core_loader.py +34 -58
- janito/{plugin_system_backup_20250825_070018/core_loader.py → plugins/core_loader_fixed.py} +26 -45
- janito/plugins/discovery.py +3 -3
- janito/tools/__init__.py +7 -31
- janito/tools/adapters/__init__.py +1 -6
- janito/tools/adapters/local/__init__.py +70 -7
- janito/{plugins_backup_20250825_070018/tools → tools/adapters/local}/ask_user.py +3 -3
- janito/{plugins_backup_20250825_070018/tools → tools/adapters/local}/create_file.py +4 -4
- janito/{plugins/core/filemanager/tools → tools/adapters/local}/delete_text_in_file.py +0 -1
- janito/{plugins_backup_20250825_070018/tools → tools/adapters/local}/fetch_url.py +3 -3
- janito/{plugins_backup_20250825_070018/tools → tools/adapters/local}/replace_text_in_file.py +4 -4
- janito/{plugins_backup_20250825_070018/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/base.py +1 -31
- janito/tools/function_adapter.py +16 -127
- janito/tools/tool_base.py +114 -142
- janito/tools/tools_schema.py +6 -12
- {janito-3.3.0.dist-info → janito-3.4.0.dist-info}/METADATA +2 -1
- janito-3.4.0.dist-info/RECORD +264 -0
- janito/cli/cli_commands/check_tools.py +0 -212
- janito/plugin_system_backup_20250825_070018/__init__.py +0 -10
- janito/plugin_system_backup_20250825_070018/base.py +0 -155
- janito/plugin_system_backup_20250825_070018/core_loader_fixed.py +0 -149
- janito/plugins/__main__.py +0 -85
- 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/copy_file.py +0 -111
- janito/plugins/core/filemanager/tools/create_directory.py +0 -97
- janito/plugins/core/filemanager/tools/create_file.py +0 -111
- 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/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/plugins_backup_20250825_070018/__init__.py +0 -36
- janito/plugins_backup_20250825_070018/builtin.py +0 -102
- janito/plugins_backup_20250825_070018/config.py +0 -84
- janito/plugins_backup_20250825_070018/core/__init__.py +0 -7
- janito/plugins_backup_20250825_070018/core/codeanalyzer/__init__.py +0 -43
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/get_file_outline/__init__.py +0 -1
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/get_file_outline/core.py +0 -122
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/get_file_outline/java_outline.py +0 -47
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/get_file_outline/markdown_outline.py +0 -14
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/get_file_outline/python_outline.py +0 -303
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/get_file_outline/search_outline.py +0 -36
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/search_text/__init__.py +0 -1
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/search_text/core.py +0 -205
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/search_text/match_lines.py +0 -67
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/search_text/pattern_utils.py +0 -73
- janito/plugins_backup_20250825_070018/core/codeanalyzer/tools/search_text/traverse_directory.py +0 -145
- janito/plugins_backup_20250825_070018/core/filemanager/__init__.py +0 -124
- janito/plugins_backup_20250825_070018/core/filemanager/tools/create_file.py +0 -87
- janito/plugins_backup_20250825_070018/core/filemanager/tools/delete_text_in_file.py +0 -135
- janito/plugins_backup_20250825_070018/core/filemanager/tools/find_files.py +0 -143
- janito/plugins_backup_20250825_070018/core/filemanager/tools/move_file.py +0 -131
- janito/plugins_backup_20250825_070018/core/filemanager/tools/read_files.py +0 -58
- janito/plugins_backup_20250825_070018/core/filemanager/tools/remove_directory.py +0 -55
- janito/plugins_backup_20250825_070018/core/filemanager/tools/remove_file.py +0 -58
- janito/plugins_backup_20250825_070018/core/filemanager/tools/replace_text_in_file.py +0 -270
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/__init__.py +0 -1
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/core.py +0 -114
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/css_validator.py +0 -35
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/html_validator.py +0 -100
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/jinja2_validator.py +0 -50
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/js_validator.py +0 -27
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/json_validator.py +0 -6
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/markdown_validator.py +0 -109
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/ps1_validator.py +0 -32
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/python_validator.py +0 -5
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/xml_validator.py +0 -11
- janito/plugins_backup_20250825_070018/core/filemanager/tools/validate_file_syntax/yaml_validator.py +0 -6
- janito/plugins_backup_20250825_070018/core/filemanager/tools/view_file.py +0 -172
- janito/plugins_backup_20250825_070018/core/imagedisplay/__init__.py +0 -14
- janito/plugins_backup_20250825_070018/core/imagedisplay/plugin.py +0 -51
- janito/plugins_backup_20250825_070018/core/imagedisplay/tools/__init__.py +0 -1
- janito/plugins_backup_20250825_070018/core/imagedisplay/tools/show_image.py +0 -83
- janito/plugins_backup_20250825_070018/core/imagedisplay/tools/show_image_grid.py +0 -84
- janito/plugins_backup_20250825_070018/core/system/__init__.py +0 -23
- janito/plugins_backup_20250825_070018/core/system/tools/run_bash_command.py +0 -183
- janito/plugins_backup_20250825_070018/core/system/tools/run_powershell_command.py +0 -218
- janito/plugins_backup_20250825_070018/dev/__init__.py +0 -7
- janito/plugins_backup_20250825_070018/dev/pythondev/__init__.py +0 -37
- janito/plugins_backup_20250825_070018/dev/pythondev/tools/python_code_run.py +0 -172
- janito/plugins_backup_20250825_070018/dev/pythondev/tools/python_command_run.py +0 -171
- janito/plugins_backup_20250825_070018/dev/pythondev/tools/python_file_run.py +0 -172
- janito/plugins_backup_20250825_070018/dev/visualization/__init__.py +0 -23
- janito/plugins_backup_20250825_070018/dev/visualization/tools/read_chart.py +0 -259
- janito/plugins_backup_20250825_070018/discovery.py +0 -289
- janito/plugins_backup_20250825_070018/example_plugin.py +0 -108
- janito/plugins_backup_20250825_070018/manager.py +0 -243
- janito/plugins_backup_20250825_070018/tools/__init__.py +0 -10
- janito/plugins_backup_20250825_070018/tools/copy_file.py +0 -87
- janito/plugins_backup_20250825_070018/tools/core_tools_plugin.py +0 -88
- janito/plugins_backup_20250825_070018/tools/create_directory.py +0 -70
- janito/plugins_backup_20250825_070018/tools/decorators.py +0 -19
- janito/plugins_backup_20250825_070018/tools/delete_text_in_file.py +0 -135
- janito/plugins_backup_20250825_070018/tools/find_files.py +0 -143
- janito/plugins_backup_20250825_070018/tools/get_file_outline/__init__.py +0 -7
- janito/plugins_backup_20250825_070018/tools/get_file_outline/core.py +0 -122
- janito/plugins_backup_20250825_070018/tools/get_file_outline/java_outline.py +0 -47
- janito/plugins_backup_20250825_070018/tools/get_file_outline/markdown_outline.py +0 -14
- janito/plugins_backup_20250825_070018/tools/get_file_outline/python_outline.py +0 -303
- janito/plugins_backup_20250825_070018/tools/get_file_outline/search_outline.py +0 -36
- janito/plugins_backup_20250825_070018/tools/move_file.py +0 -131
- janito/plugins_backup_20250825_070018/tools/open_html_in_browser.py +0 -51
- janito/plugins_backup_20250825_070018/tools/open_url.py +0 -37
- janito/plugins_backup_20250825_070018/tools/python_code_run.py +0 -172
- janito/plugins_backup_20250825_070018/tools/python_command_run.py +0 -171
- janito/plugins_backup_20250825_070018/tools/python_file_run.py +0 -172
- janito/plugins_backup_20250825_070018/tools/read_chart.py +0 -259
- janito/plugins_backup_20250825_070018/tools/read_files.py +0 -58
- janito/plugins_backup_20250825_070018/tools/remove_directory.py +0 -55
- janito/plugins_backup_20250825_070018/tools/remove_file.py +0 -58
- janito/plugins_backup_20250825_070018/tools/run_bash_command.py +0 -183
- janito/plugins_backup_20250825_070018/tools/run_powershell_command.py +0 -218
- janito/plugins_backup_20250825_070018/tools/search_text/__init__.py +0 -7
- janito/plugins_backup_20250825_070018/tools/search_text/core.py +0 -205
- janito/plugins_backup_20250825_070018/tools/search_text/match_lines.py +0 -67
- janito/plugins_backup_20250825_070018/tools/search_text/pattern_utils.py +0 -73
- janito/plugins_backup_20250825_070018/tools/search_text/traverse_directory.py +0 -145
- janito/plugins_backup_20250825_070018/tools/show_image_grid.py +0 -85
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/__init__.py +0 -7
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/core.py +0 -114
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/css_validator.py +0 -35
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/html_validator.py +0 -100
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/jinja2_validator.py +0 -50
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/js_validator.py +0 -27
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/json_validator.py +0 -6
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/markdown_validator.py +0 -109
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/ps1_validator.py +0 -32
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/python_validator.py +0 -5
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/xml_validator.py +0 -11
- janito/plugins_backup_20250825_070018/tools/validate_file_syntax/yaml_validator.py +0 -6
- janito/plugins_backup_20250825_070018/tools/view_file.py +0 -172
- janito/plugins_backup_20250825_070018/ui/__init__.py +0 -7
- janito/plugins_backup_20250825_070018/ui/userinterface/__init__.py +0 -16
- janito/plugins_backup_20250825_070018/ui/userinterface/tools/ask_user.py +0 -110
- janito/plugins_backup_20250825_070018/web/__init__.py +0 -7
- janito/plugins_backup_20250825_070018/web/webtools/__init__.py +0 -33
- janito/plugins_backup_20250825_070018/web/webtools/tools/fetch_url.py +0 -458
- janito/plugins_backup_20250825_070018/web/webtools/tools/open_html_in_browser.py +0 -51
- janito/plugins_backup_20250825_070018/web/webtools/tools/open_url.py +0 -37
- janito/tools/cli_initializer.py +0 -88
- janito/tools/initialize.py +0 -70
- janito-3.3.0.dist-info/RECORD +0 -400
- /janito/{plugins_backup_20250825_070018 → plugins}/auto_loader.py +0 -0
- /janito/{plugins_backup_20250825_070018 → plugins}/discovery_core.py +0 -0
- /janito/{plugins_backup_20250825_070018/core/filemanager/tools → tools/adapters/local}/copy_file.py +0 -0
- /janito/{plugins_backup_20250825_070018/core/filemanager/tools → tools/adapters/local}/create_directory.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.3.0.dist-info → janito-3.4.0.dist-info}/WHEEL +0 -0
- {janito-3.3.0.dist-info → janito-3.4.0.dist-info}/entry_points.txt +0 -0
- {janito-3.3.0.dist-info → janito-3.4.0.dist-info}/licenses/LICENSE +0 -0
- {janito-3.3.0.dist-info → janito-3.4.0.dist-info}/top_level.txt +0 -0
@@ -1,12 +1,12 @@
|
|
1
1
|
from janito.tools.tool_base import ToolBase, ToolPermissions
|
2
2
|
from janito.report_events import ReportAction
|
3
|
-
from janito.
|
3
|
+
from janito.tools.adapters.local.adapter import register_local_tool
|
4
4
|
from janito.i18n import tr
|
5
5
|
from janito.tools.loop_protection_decorator import protect_against_loops
|
6
6
|
|
7
7
|
|
8
|
-
@
|
9
|
-
class
|
8
|
+
@register_local_tool
|
9
|
+
class ShowImageTool(ToolBase):
|
10
10
|
"""Display an image inline in the terminal using the rich library.
|
11
11
|
|
12
12
|
Args:
|
@@ -44,9 +44,7 @@ class ShowImage(ToolBase):
|
|
44
44
|
|
45
45
|
path = expand_path(path)
|
46
46
|
disp_path = display_path(path)
|
47
|
-
self.report_action(
|
48
|
-
tr("🖼️ Show image '{disp_path}'", disp_path=disp_path), ReportAction.READ
|
49
|
-
)
|
47
|
+
self.report_action(tr("🖼️ Show image '{disp_path}'", disp_path=disp_path), ReportAction.READ)
|
50
48
|
|
51
49
|
if not os.path.exists(path):
|
52
50
|
msg = tr("❗ not found")
|
@@ -57,14 +55,9 @@ class ShowImage(ToolBase):
|
|
57
55
|
console = Console()
|
58
56
|
from rich.console import Console
|
59
57
|
from rich.text import Text
|
60
|
-
|
61
58
|
console = Console()
|
62
59
|
img = PILImage.open(path)
|
63
|
-
console.print(
|
64
|
-
Text(
|
65
|
-
f"Image: {disp_path} ({img.width}x{img.height})", style="bold green"
|
66
|
-
)
|
67
|
-
)
|
60
|
+
console.print(Text(f"Image: {disp_path} ({img.width}x{img.height})", style="bold green"))
|
68
61
|
console.print(img)
|
69
62
|
self.report_success(tr("✅ Displayed"))
|
70
63
|
details = []
|
@@ -75,9 +68,7 @@ class ShowImage(ToolBase):
|
|
75
68
|
if not preserve_aspect:
|
76
69
|
details.append("preserve_aspect=False")
|
77
70
|
info = ("; ".join(details)) if details else "auto-fit"
|
78
|
-
return tr(
|
79
|
-
"Image displayed: {disp_path} ({info})", disp_path=disp_path, info=info
|
80
|
-
)
|
71
|
+
return tr("Image displayed: {disp_path} ({info})", disp_path=disp_path, info=info)
|
81
72
|
except Exception as e:
|
82
73
|
self.report_error(tr(" ❌ Error: {error}", error=e))
|
83
74
|
return tr("Error displaying image: {error}", error=e)
|
@@ -1,10 +1,12 @@
|
|
1
1
|
from janito.tools.tool_base import ToolBase, ToolPermissions
|
2
2
|
from janito.report_events import ReportAction
|
3
|
+
from janito.tools.adapters.local.adapter import register_local_tool
|
3
4
|
from janito.i18n import tr
|
4
5
|
from janito.tools.loop_protection_decorator import protect_against_loops
|
5
6
|
from typing import Sequence
|
6
7
|
|
7
8
|
|
9
|
+
@register_local_tool
|
8
10
|
class ShowImageGridTool(ToolBase):
|
9
11
|
"""Display multiple images in a grid inline in the terminal using rich.
|
10
12
|
|
@@ -48,9 +50,7 @@ class ShowImageGridTool(ToolBase):
|
|
48
50
|
if not paths:
|
49
51
|
return tr("No images provided")
|
50
52
|
|
51
|
-
self.report_action(
|
52
|
-
tr("🖼️ Show image grid ({n} images)", n=len(paths)), ReportAction.READ
|
53
|
-
)
|
53
|
+
self.report_action(tr("🖼️ Show image grid ({n} images)", n=len(paths)), ReportAction.READ)
|
54
54
|
|
55
55
|
console = Console()
|
56
56
|
images = []
|
@@ -63,9 +63,7 @@ class ShowImageGridTool(ToolBase):
|
|
63
63
|
try:
|
64
64
|
img = PILImage.open(fp)
|
65
65
|
title = f"{display_path(fp)} ({img.width}x{img.height})"
|
66
|
-
images.append(
|
67
|
-
Panel.fit(title, title=display_path(fp), border_style="dim")
|
68
|
-
)
|
66
|
+
images.append(Panel.fit(title, title=display_path(fp), border_style="dim"))
|
69
67
|
shown += 1
|
70
68
|
except Exception as e:
|
71
69
|
self.report_warning(tr("⚠️ Skipped {p}: {e}", p=display_path(fp), e=e))
|
@@ -73,12 +71,6 @@ class ShowImageGridTool(ToolBase):
|
|
73
71
|
if not images:
|
74
72
|
return tr("No images could be displayed")
|
75
73
|
|
76
|
-
# Render in columns (grid-like)
|
77
74
|
console.print(Columns(images, equal=True, expand=True, columns=columns))
|
78
75
|
self.report_success(tr("✅ Displayed {n} images", n=shown))
|
79
|
-
return tr(
|
80
|
-
"Displayed {shown}/{total} images in a {cols}x? grid",
|
81
|
-
shown=shown,
|
82
|
-
total=len(paths),
|
83
|
-
cols=columns,
|
84
|
-
)
|
76
|
+
return tr("Displayed {shown}/{total} images in a {cols}x? grid", shown=shown, total=len(paths), cols=columns)
|
janito/tools/base.py
CHANGED
@@ -1,35 +1,5 @@
|
|
1
1
|
class BaseTool:
|
2
|
-
"""
|
3
|
-
Base class for all tools.
|
4
|
-
|
5
|
-
Parameters:
|
6
|
-
path (str): Target file path for file operations
|
7
|
-
content (str): File content to write or process
|
8
|
-
overwrite (bool): Whether to overwrite existing files (default: False)
|
9
|
-
sources (str): Source file(s) to copy from
|
10
|
-
target (str): Destination path for copy operations
|
11
|
-
recursive (bool): Whether to process directories recursively
|
12
|
-
from_line (int): Starting line number for file reading
|
13
|
-
to_line (int): Ending line number for file reading
|
14
|
-
search_text (str): Text to search for in files
|
15
|
-
replacement_text (str): Text to replace search matches with
|
16
|
-
use_regex (bool): Whether to treat search as regex pattern
|
17
|
-
case_sensitive (bool): Whether search should be case sensitive
|
18
|
-
max_depth (int): Maximum directory depth to search
|
19
|
-
include_gitignored (bool): Whether to include .gitignored files
|
20
|
-
timeout (int): Timeout in seconds for operations
|
21
|
-
require_confirmation (bool): Whether to require user confirmation
|
22
|
-
data (dict): Chart data for visualization tools
|
23
|
-
title (str): Chart title
|
24
|
-
width (int): Chart width in pixels
|
25
|
-
height (int): Chart height in pixels
|
26
|
-
query (str): Search query for text search
|
27
|
-
paths (str): Directory or file paths to search in
|
28
|
-
src_path (str): Source path for move operations
|
29
|
-
dest_path (str): Destination path for move operations
|
30
|
-
code (str): Python code to execute
|
31
|
-
pattern (str): File pattern to match (e.g., '*.py')
|
32
|
-
"""
|
2
|
+
"""Base class for all tools."""
|
33
3
|
|
34
4
|
tool_name: str = ""
|
35
5
|
|
janito/tools/function_adapter.py
CHANGED
@@ -10,167 +10,56 @@ from janito.tools.tool_base import ToolBase, ToolPermissions
|
|
10
10
|
|
11
11
|
|
12
12
|
class FunctionToolAdapter(ToolBase):
|
13
|
-
"""
|
14
|
-
Adapter that wraps a function into a ToolBase class.
|
15
|
-
|
16
|
-
This adapter provides a unified interface for function-based tools by wrapping
|
17
|
-
individual functions with the ToolBase protocol. It handles parameter mapping
|
18
|
-
and validation automatically.
|
13
|
+
"""Adapter that wraps a function into a ToolBase class."""
|
19
14
|
|
20
|
-
Parameters:
|
21
|
-
path (str): Target file path for file operations
|
22
|
-
content (str): File content to write or process
|
23
|
-
overwrite (bool): Whether to overwrite existing files (default: False)
|
24
|
-
sources (str): Source file(s) to copy from
|
25
|
-
target (str): Destination path for copy operations
|
26
|
-
recursive (bool): Whether to process directories recursively
|
27
|
-
from_line (int): Starting line number for file reading
|
28
|
-
to_line (int): Ending line number for file reading
|
29
|
-
search_text (str): Text to search for in files
|
30
|
-
replacement_text (str): Text to replace search matches with
|
31
|
-
use_regex (bool): Whether to treat search as regex pattern
|
32
|
-
case_sensitive (bool): Whether search should be case sensitive
|
33
|
-
max_depth (int): Maximum directory depth to search
|
34
|
-
include_gitignored (bool): Whether to include .gitignored files
|
35
|
-
timeout (int): Timeout in seconds for operations
|
36
|
-
require_confirmation (bool): Whether to require user confirmation
|
37
|
-
data (dict): Chart data for visualization tools
|
38
|
-
title (str): Chart title
|
39
|
-
width (int): Chart width in pixels
|
40
|
-
height (int): Chart height in pixels
|
41
|
-
query (str): Search query for text search
|
42
|
-
paths (str): Directory or file paths to search in
|
43
|
-
src_path (str): Source path for move operations
|
44
|
-
dest_path (str): Destination path for move operations
|
45
|
-
code (str): Python code to execute
|
46
|
-
pattern (str): File pattern to match (e.g., '*.py')
|
47
|
-
"""
|
48
|
-
|
49
15
|
def __init__(self, func, tool_name: str = None, description: str = None):
|
50
16
|
super().__init__()
|
51
17
|
self._func = func
|
52
|
-
self.tool_name = tool_name or
|
18
|
+
self.tool_name = tool_name or func.__name__
|
53
19
|
self._description = description or func.__doc__ or f"Tool: {self.tool_name}"
|
54
20
|
self.permissions = ToolPermissions(read=True, write=True, execute=True)
|
55
|
-
|
56
|
-
def run(
|
57
|
-
self,
|
58
|
-
path: str = None,
|
59
|
-
content: str = None,
|
60
|
-
overwrite: bool = None,
|
61
|
-
sources: str = None,
|
62
|
-
target: str = None,
|
63
|
-
recursive: bool = None,
|
64
|
-
from_line: int = None,
|
65
|
-
to_line: int = None,
|
66
|
-
search_text: str = None,
|
67
|
-
replacement_text: str = None,
|
68
|
-
use_regex: bool = None,
|
69
|
-
case_sensitive: bool = None,
|
70
|
-
max_depth: int = None,
|
71
|
-
include_gitignored: bool = None,
|
72
|
-
timeout: int = None,
|
73
|
-
require_confirmation: bool = None,
|
74
|
-
data: dict = None,
|
75
|
-
title: str = None,
|
76
|
-
width: int = None,
|
77
|
-
height: int = None,
|
78
|
-
query: str = None,
|
79
|
-
paths: str = None,
|
80
|
-
src_path: str = None,
|
81
|
-
dest_path: str = None,
|
82
|
-
code: str = None,
|
83
|
-
pattern: str = None,
|
84
|
-
) -> str:
|
21
|
+
|
22
|
+
def run(self, **kwargs) -> Any:
|
85
23
|
"""Execute the wrapped function."""
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
sig = inspect.signature(self._func)
|
90
|
-
filtered_kwargs = {}
|
91
|
-
|
92
|
-
# Map parameter names to their actual values
|
93
|
-
param_map = {
|
94
|
-
"path": path,
|
95
|
-
"content": content,
|
96
|
-
"overwrite": overwrite,
|
97
|
-
"sources": sources,
|
98
|
-
"target": target,
|
99
|
-
"recursive": recursive,
|
100
|
-
"from_line": from_line,
|
101
|
-
"to_line": to_line,
|
102
|
-
"search_text": search_text,
|
103
|
-
"replacement_text": replacement_text,
|
104
|
-
"use_regex": use_regex,
|
105
|
-
"case_sensitive": case_sensitive,
|
106
|
-
"max_depth": max_depth,
|
107
|
-
"include_gitignored": include_gitignored,
|
108
|
-
"timeout": timeout,
|
109
|
-
"require_confirmation": require_confirmation,
|
110
|
-
"data": data,
|
111
|
-
"title": title,
|
112
|
-
"width": width,
|
113
|
-
"height": height,
|
114
|
-
"query": query,
|
115
|
-
"paths": paths,
|
116
|
-
"src_path": src_path,
|
117
|
-
"dest_path": dest_path,
|
118
|
-
"code": code,
|
119
|
-
"pattern": pattern,
|
120
|
-
}
|
121
|
-
|
122
|
-
# Only include parameters that exist in the function signature
|
123
|
-
for name, param in sig.parameters.items():
|
124
|
-
if name in param_map and param_map[name] is not None:
|
125
|
-
filtered_kwargs[name] = param_map[name]
|
126
|
-
|
127
|
-
result = self._func(**filtered_kwargs)
|
128
|
-
return str(result) if result is not None else ""
|
129
|
-
|
24
|
+
return self._func(**kwargs)
|
25
|
+
|
130
26
|
def get_signature(self) -> Dict[str, Any]:
|
131
27
|
"""Get function signature for documentation."""
|
132
28
|
sig = inspect.signature(self._func)
|
133
29
|
type_hints = get_type_hints(self._func)
|
134
|
-
|
30
|
+
|
135
31
|
params = {}
|
136
32
|
for name, param in sig.parameters.items():
|
137
33
|
param_info = {
|
138
34
|
"type": str(type_hints.get(name, Any)),
|
139
|
-
"default":
|
140
|
-
param.default if param.default != inspect.Parameter.empty else None
|
141
|
-
),
|
35
|
+
"default": param.default if param.default != inspect.Parameter.empty else None,
|
142
36
|
"required": param.default == inspect.Parameter.empty,
|
143
37
|
}
|
144
38
|
params[name] = param_info
|
145
|
-
|
39
|
+
|
146
40
|
return {
|
147
41
|
"name": self.tool_name,
|
148
42
|
"description": self._description,
|
149
43
|
"parameters": params,
|
150
|
-
"return_type": str(type_hints.get("return", Any))
|
44
|
+
"return_type": str(type_hints.get("return", Any))
|
151
45
|
}
|
152
46
|
|
153
47
|
|
154
48
|
def create_function_tool(func, tool_name: str = None, description: str = None) -> type:
|
155
49
|
"""
|
156
50
|
Create a ToolBase class from a function.
|
157
|
-
|
51
|
+
|
158
52
|
Args:
|
159
53
|
func: The function to wrap
|
160
54
|
tool_name: Optional custom tool name
|
161
55
|
description: Optional custom description
|
162
|
-
|
56
|
+
|
163
57
|
Returns:
|
164
58
|
A ToolBase subclass that wraps the function
|
165
59
|
"""
|
166
|
-
|
167
|
-
resolved_tool_name = tool_name or getattr(func, "tool_name", func.__name__)
|
168
|
-
|
60
|
+
|
169
61
|
class DynamicFunctionTool(FunctionToolAdapter):
|
170
|
-
permissions = ToolPermissions(read=True, write=True, execute=True)
|
171
|
-
tool_name = resolved_tool_name
|
172
|
-
|
173
62
|
def __init__(self):
|
174
|
-
super().__init__(func,
|
175
|
-
|
176
|
-
return DynamicFunctionTool
|
63
|
+
super().__init__(func, tool_name, description)
|
64
|
+
|
65
|
+
return DynamicFunctionTool
|
janito/tools/tool_base.py
CHANGED
@@ -1,142 +1,114 @@
|
|
1
|
-
from janito.report_events import ReportEvent, ReportSubtype, ReportAction
|
2
|
-
from janito.event_bus.bus import event_bus as default_event_bus
|
3
|
-
|
4
|
-
|
5
|
-
from collections import namedtuple
|
6
|
-
|
7
|
-
|
8
|
-
class ToolPermissions(namedtuple("ToolPermissions", ["read", "write", "execute"])):
|
9
|
-
__slots__ = ()
|
10
|
-
|
11
|
-
def __new__(cls, read=False, write=False, execute=False):
|
12
|
-
return super().__new__(cls, read, write, execute)
|
13
|
-
|
14
|
-
def __repr__(self):
|
15
|
-
return f"ToolPermissions(read={self.read}, write={self.write}, execute={self.execute})"
|
16
|
-
|
17
|
-
|
18
|
-
class ToolBase:
|
19
|
-
"""
|
20
|
-
Base class for all tools in the janito project.
|
21
|
-
Extend this class to implement specific tool functionality.
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
def
|
70
|
-
self._event_bus
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
context=context,
|
116
|
-
)
|
117
|
-
)
|
118
|
-
|
119
|
-
def report_stdout(self, message: str, context: dict = None):
|
120
|
-
self._event_bus.publish(
|
121
|
-
ReportEvent(
|
122
|
-
subtype=ReportSubtype.STDOUT,
|
123
|
-
message=message,
|
124
|
-
action=None,
|
125
|
-
tool=self.name,
|
126
|
-
context=context,
|
127
|
-
)
|
128
|
-
)
|
129
|
-
|
130
|
-
def report_stderr(self, message: str, context: dict = None):
|
131
|
-
self._event_bus.publish(
|
132
|
-
ReportEvent(
|
133
|
-
subtype=ReportSubtype.STDERR,
|
134
|
-
message=message,
|
135
|
-
action=None,
|
136
|
-
tool=self.name,
|
137
|
-
context=context,
|
138
|
-
)
|
139
|
-
)
|
140
|
-
|
141
|
-
def run(self, *args, **kwargs):
|
142
|
-
raise NotImplementedError("Subclasses must implement the run method.")
|
1
|
+
from janito.report_events import ReportEvent, ReportSubtype, ReportAction
|
2
|
+
from janito.event_bus.bus import event_bus as default_event_bus
|
3
|
+
|
4
|
+
|
5
|
+
from collections import namedtuple
|
6
|
+
|
7
|
+
|
8
|
+
class ToolPermissions(namedtuple("ToolPermissions", ["read", "write", "execute"])):
|
9
|
+
__slots__ = ()
|
10
|
+
|
11
|
+
def __new__(cls, read=False, write=False, execute=False):
|
12
|
+
return super().__new__(cls, read, write, execute)
|
13
|
+
|
14
|
+
def __repr__(self):
|
15
|
+
return f"ToolPermissions(read={self.read}, write={self.write}, execute={self.execute})"
|
16
|
+
|
17
|
+
|
18
|
+
class ToolBase:
|
19
|
+
"""
|
20
|
+
Base class for all tools in the janito project.
|
21
|
+
Extend this class to implement specific tool functionality.
|
22
|
+
"""
|
23
|
+
|
24
|
+
permissions: "ToolPermissions" = None # Required: must be set by subclasses
|
25
|
+
|
26
|
+
def __init__(self, name=None, event_bus=None):
|
27
|
+
if self.permissions is None or not isinstance(
|
28
|
+
self.permissions, ToolPermissions
|
29
|
+
):
|
30
|
+
raise ValueError(
|
31
|
+
f"Tool '{self.__class__.__name__}' must define a 'permissions' attribute of type ToolPermissions."
|
32
|
+
)
|
33
|
+
self.name = name or self.__class__.__name__
|
34
|
+
self._event_bus = event_bus or default_event_bus
|
35
|
+
|
36
|
+
@property
|
37
|
+
def event_bus(self):
|
38
|
+
return self._event_bus
|
39
|
+
|
40
|
+
@event_bus.setter
|
41
|
+
def event_bus(self, bus):
|
42
|
+
self._event_bus = bus or default_event_bus
|
43
|
+
|
44
|
+
def report_action(self, message: str, action: ReportAction, context: dict = None):
|
45
|
+
"""
|
46
|
+
Report that a tool action is starting. This should be the first reporting call for every tool action.
|
47
|
+
"""
|
48
|
+
self._event_bus.publish(
|
49
|
+
ReportEvent(
|
50
|
+
subtype=ReportSubtype.ACTION_INFO,
|
51
|
+
message=" " + message,
|
52
|
+
action=action,
|
53
|
+
tool=self.name,
|
54
|
+
context=context,
|
55
|
+
)
|
56
|
+
)
|
57
|
+
|
58
|
+
def report_error(self, message: str, context: dict = None):
|
59
|
+
self._event_bus.publish(
|
60
|
+
ReportEvent(
|
61
|
+
subtype=ReportSubtype.ERROR,
|
62
|
+
message=message,
|
63
|
+
action=None,
|
64
|
+
tool=self.name,
|
65
|
+
context=context,
|
66
|
+
)
|
67
|
+
)
|
68
|
+
|
69
|
+
def report_success(self, message: str, context: dict = None):
|
70
|
+
self._event_bus.publish(
|
71
|
+
ReportEvent(
|
72
|
+
subtype=ReportSubtype.SUCCESS,
|
73
|
+
message=message,
|
74
|
+
action=None,
|
75
|
+
tool=self.name,
|
76
|
+
context=context,
|
77
|
+
)
|
78
|
+
)
|
79
|
+
|
80
|
+
def report_warning(self, message: str, context: dict = None):
|
81
|
+
self._event_bus.publish(
|
82
|
+
ReportEvent(
|
83
|
+
subtype=ReportSubtype.WARNING,
|
84
|
+
message=message,
|
85
|
+
action=None,
|
86
|
+
tool=self.name,
|
87
|
+
context=context,
|
88
|
+
)
|
89
|
+
)
|
90
|
+
|
91
|
+
def report_stdout(self, message: str, context: dict = None):
|
92
|
+
self._event_bus.publish(
|
93
|
+
ReportEvent(
|
94
|
+
subtype=ReportSubtype.STDOUT,
|
95
|
+
message=message,
|
96
|
+
action=None,
|
97
|
+
tool=self.name,
|
98
|
+
context=context,
|
99
|
+
)
|
100
|
+
)
|
101
|
+
|
102
|
+
def report_stderr(self, message: str, context: dict = None):
|
103
|
+
self._event_bus.publish(
|
104
|
+
ReportEvent(
|
105
|
+
subtype=ReportSubtype.STDERR,
|
106
|
+
message=message,
|
107
|
+
action=None,
|
108
|
+
tool=self.name,
|
109
|
+
context=context,
|
110
|
+
)
|
111
|
+
)
|
112
|
+
|
113
|
+
def run(self, *args, **kwargs):
|
114
|
+
raise NotImplementedError("Subclasses must implement the run method.")
|
janito/tools/tools_schema.py
CHANGED
@@ -7,8 +7,6 @@ class ToolSchemaBase:
|
|
7
7
|
def parse_param_section(self, lines, param_section_headers):
|
8
8
|
param_descs = {}
|
9
9
|
in_params = False
|
10
|
-
current_param = None
|
11
|
-
|
12
10
|
for line in lines:
|
13
11
|
stripped_line = line.strip()
|
14
12
|
if any(
|
@@ -18,21 +16,17 @@ class ToolSchemaBase:
|
|
18
16
|
in_params = True
|
19
17
|
continue
|
20
18
|
if in_params:
|
21
|
-
# Check for parameter definition: "param_name (type): description"
|
22
19
|
m = re.match(
|
23
|
-
r"([a-zA-Z_][a-zA-Z0-9_]*)\s*(?:\([^)]
|
20
|
+
r"([a-zA-Z_][a-zA-Z0-9_]*)\s*(?:\(([^)]+)\))?\s*[:\-]?\s*(.+)",
|
24
21
|
stripped_line,
|
25
22
|
)
|
26
23
|
if m:
|
27
|
-
param, desc = m.groups()
|
24
|
+
param, _, desc = m.groups()
|
28
25
|
param_descs[param] = desc.strip()
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
):
|
34
|
-
# Continuation of current parameter description
|
35
|
-
param_descs[current_param] += " " + stripped_line.strip()
|
26
|
+
elif stripped_line and stripped_line[0] != "-":
|
27
|
+
if param_descs:
|
28
|
+
last = list(param_descs)[-1]
|
29
|
+
param_descs[last] += " " + stripped_line
|
36
30
|
if (
|
37
31
|
stripped_line.lower().startswith("returns:")
|
38
32
|
or stripped_line.lower() == "returns"
|
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.4
|
2
2
|
Name: janito
|
3
|
-
Version: 3.
|
3
|
+
Version: 3.4.0
|
4
4
|
Summary: A new Python package called janito.
|
5
5
|
Author-email: João Pinto <janito@ikignosis.org>
|
6
6
|
Project-URL: Homepage, https://github.com/ikignosis/janito
|
@@ -30,6 +30,7 @@ Requires-Dist: black; extra == "dev"
|
|
30
30
|
Requires-Dist: questionary>=2.0.1; extra == "dev"
|
31
31
|
Requires-Dist: setuptools_scm>=8.0; extra == "dev"
|
32
32
|
Provides-Extra: coder
|
33
|
+
Requires-Dist: janito-coder; extra == "coder"
|
33
34
|
Dynamic: license-file
|
34
35
|
|
35
36
|
# nctl
|