mirror of
https://github.com/aljazceru/goose.git
synced 2025-12-26 18:44:36 +01:00
Enable cli options for plugin (#22)
* added the entry point for plugin with cli group option
This commit is contained in:
@@ -1,7 +1,7 @@
|
||||
[project]
|
||||
name = "goose-ai"
|
||||
description = "a programming agent that runs on your machine"
|
||||
version = "0.8.0"
|
||||
version = "0.8.1"
|
||||
readme = "README.md"
|
||||
requires-python = ">=3.10"
|
||||
dependencies = [
|
||||
@@ -30,9 +30,11 @@ default = "goose.profile:default_profile"
|
||||
[project.entry-points."goose.command"]
|
||||
file = "goose.command.file:FileCommand"
|
||||
|
||||
[project.entry-points."goose.cli"]
|
||||
[project.entry-points."goose.cli.group"]
|
||||
goose = "goose.cli.main:goose_cli"
|
||||
|
||||
[project.entry-points."goose.cli.group_option"]
|
||||
|
||||
[project.scripts]
|
||||
goose = "goose.cli.main:cli"
|
||||
|
||||
|
||||
@@ -12,12 +12,10 @@ from goose.cli.session import Session
|
||||
from goose.utils import load_plugins
|
||||
from goose.utils.session_file import list_sorted_session_files
|
||||
|
||||
|
||||
@click.group()
|
||||
def goose_cli() -> None:
|
||||
pass
|
||||
|
||||
|
||||
@goose_cli.command()
|
||||
def version() -> None:
|
||||
"""Lists the version of goose and any plugins"""
|
||||
@@ -81,7 +79,7 @@ def session_start(profile: str, plan: Optional[str] = None) -> None:
|
||||
@session.command(name="resume")
|
||||
@click.argument("name", required=False)
|
||||
@click.option("--profile")
|
||||
def session_resume(name: str, profile: str) -> None:
|
||||
def session_resume(name: Optional[str], profile: str) -> None:
|
||||
"""Resume an existing goose session"""
|
||||
if name is None:
|
||||
session_files = get_session_files()
|
||||
@@ -97,6 +95,7 @@ def session_resume(name: str, profile: str) -> None:
|
||||
|
||||
@session.command(name="list")
|
||||
def session_list() -> None:
|
||||
"""List goose sessions"""
|
||||
session_files = get_session_files().items()
|
||||
for session_name, session_file in session_files:
|
||||
print(f"{datetime.fromtimestamp(session_file.stat().st_mtime).strftime('%Y-%m-%d %H:%M:%S')} {session_name}")
|
||||
@@ -105,6 +104,7 @@ def session_list() -> None:
|
||||
@session.command(name="clear")
|
||||
@click.option("--keep", default=3, help="Keep this many entries, default 3")
|
||||
def session_clear(keep: int) -> None:
|
||||
"""Delete old goose sessions, keeping the most recent sessions up to the specified number"""
|
||||
for i, (_, session_file) in enumerate(get_session_files().items()):
|
||||
if i >= keep:
|
||||
session_file.unlink()
|
||||
@@ -113,13 +113,22 @@ def session_clear(keep: int) -> None:
|
||||
def get_session_files() -> Dict[str, Path]:
|
||||
return list_sorted_session_files(SESSIONS_PATH)
|
||||
|
||||
@click.group(
|
||||
invoke_without_command=True,
|
||||
name="goose",
|
||||
help="AI-powered tool to assist in solving programming and operational tasks",)
|
||||
@click.pass_context
|
||||
def cli(_: click.Context, **kwargs: Dict) -> None:
|
||||
pass
|
||||
|
||||
# merging goose cli with additional cli plugins.
|
||||
def cli() -> None:
|
||||
clis = load_plugins("goose.cli")
|
||||
cli_list = list(clis.values()) or []
|
||||
click.CommandCollection(sources=cli_list)()
|
||||
all_cli_group_options = load_plugins("goose.cli.group_option")
|
||||
for option in all_cli_group_options.values():
|
||||
cli = option()(cli)
|
||||
|
||||
all_cli_groups = load_plugins("goose.cli.group")
|
||||
for group in all_cli_groups.values():
|
||||
for command in group.commands.values():
|
||||
cli.add_command(command)
|
||||
|
||||
if __name__ == "__main__":
|
||||
cli()
|
||||
|
||||
@@ -1,11 +1,13 @@
|
||||
from datetime import datetime
|
||||
import importlib
|
||||
from time import time
|
||||
from unittest.mock import MagicMock, patch
|
||||
|
||||
import click
|
||||
import pytest
|
||||
from click.testing import CliRunner
|
||||
from exchange import Message
|
||||
from goose.cli.main import goose_cli
|
||||
from goose.cli.main import cli, goose_cli
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
@@ -78,3 +80,41 @@ def test_session_clear_command(mock_session_files_path, create_session_file):
|
||||
session_files = list(mock_session_files_path.glob("*.jsonl"))
|
||||
assert len(session_files) == 1
|
||||
assert session_files[0].stem == "second"
|
||||
|
||||
|
||||
def test_combined_group_option():
|
||||
with patch("goose.utils.load_plugins") as mock_load_plugin:
|
||||
group_option_name = "--describe-commands"
|
||||
def option_callback(ctx, *_):
|
||||
click.echo("Option callback")
|
||||
ctx.exit()
|
||||
mock_group_options = {
|
||||
'option1': lambda: click.option(
|
||||
group_option_name,
|
||||
is_flag=True,
|
||||
callback=option_callback,
|
||||
),
|
||||
}
|
||||
def side_effect_func(param):
|
||||
if param == "goose.cli.group_option":
|
||||
return mock_group_options
|
||||
elif param == "goose.cli.group":
|
||||
return { }
|
||||
mock_load_plugin.side_effect = side_effect_func
|
||||
|
||||
# reload cli after mocking
|
||||
importlib.reload(importlib.import_module('goose.cli.main'))
|
||||
import goose.cli.main
|
||||
cli = goose.cli.main.cli
|
||||
|
||||
runner = CliRunner()
|
||||
result = runner.invoke(cli, [group_option_name])
|
||||
assert result.exit_code == 0
|
||||
|
||||
def test_combined_group_commands(mock_session):
|
||||
mock_session_class, mock_session_instance = mock_session
|
||||
runner = CliRunner()
|
||||
runner.invoke(cli, ["session", "resume", "session1", "--profile", "default"])
|
||||
mock_session_class.assert_called_once_with(name="session1", profile="default")
|
||||
mock_session_instance.run.assert_called_once()
|
||||
|
||||
|
||||
Reference in New Issue
Block a user