tunacode-cli 0.1.21__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.
Potentially problematic release.
This version of tunacode-cli might be problematic. Click here for more details.
- tunacode/__init__.py +0 -0
- tunacode/cli/textual_repl.tcss +283 -0
- tunacode/configuration/__init__.py +1 -0
- tunacode/configuration/defaults.py +45 -0
- tunacode/configuration/models.py +147 -0
- tunacode/configuration/models_registry.json +1 -0
- tunacode/configuration/pricing.py +74 -0
- tunacode/configuration/settings.py +35 -0
- tunacode/constants.py +227 -0
- tunacode/core/__init__.py +6 -0
- tunacode/core/agents/__init__.py +39 -0
- tunacode/core/agents/agent_components/__init__.py +48 -0
- tunacode/core/agents/agent_components/agent_config.py +441 -0
- tunacode/core/agents/agent_components/agent_helpers.py +290 -0
- tunacode/core/agents/agent_components/message_handler.py +99 -0
- tunacode/core/agents/agent_components/node_processor.py +477 -0
- tunacode/core/agents/agent_components/response_state.py +129 -0
- tunacode/core/agents/agent_components/result_wrapper.py +51 -0
- tunacode/core/agents/agent_components/state_transition.py +112 -0
- tunacode/core/agents/agent_components/streaming.py +271 -0
- tunacode/core/agents/agent_components/task_completion.py +40 -0
- tunacode/core/agents/agent_components/tool_buffer.py +44 -0
- tunacode/core/agents/agent_components/tool_executor.py +101 -0
- tunacode/core/agents/agent_components/truncation_checker.py +37 -0
- tunacode/core/agents/delegation_tools.py +109 -0
- tunacode/core/agents/main.py +545 -0
- tunacode/core/agents/prompts.py +66 -0
- tunacode/core/agents/research_agent.py +231 -0
- tunacode/core/compaction.py +218 -0
- tunacode/core/prompting/__init__.py +27 -0
- tunacode/core/prompting/loader.py +66 -0
- tunacode/core/prompting/prompting_engine.py +98 -0
- tunacode/core/prompting/sections.py +50 -0
- tunacode/core/prompting/templates.py +69 -0
- tunacode/core/state.py +409 -0
- tunacode/exceptions.py +313 -0
- tunacode/indexing/__init__.py +5 -0
- tunacode/indexing/code_index.py +432 -0
- tunacode/indexing/constants.py +86 -0
- tunacode/lsp/__init__.py +112 -0
- tunacode/lsp/client.py +351 -0
- tunacode/lsp/diagnostics.py +19 -0
- tunacode/lsp/servers.py +101 -0
- tunacode/prompts/default_prompt.md +952 -0
- tunacode/prompts/research/sections/agent_role.xml +5 -0
- tunacode/prompts/research/sections/constraints.xml +14 -0
- tunacode/prompts/research/sections/output_format.xml +57 -0
- tunacode/prompts/research/sections/tool_use.xml +23 -0
- tunacode/prompts/sections/advanced_patterns.xml +255 -0
- tunacode/prompts/sections/agent_role.xml +8 -0
- tunacode/prompts/sections/completion.xml +10 -0
- tunacode/prompts/sections/critical_rules.xml +37 -0
- tunacode/prompts/sections/examples.xml +220 -0
- tunacode/prompts/sections/output_style.xml +94 -0
- tunacode/prompts/sections/parallel_exec.xml +105 -0
- tunacode/prompts/sections/search_pattern.xml +100 -0
- tunacode/prompts/sections/system_info.xml +6 -0
- tunacode/prompts/sections/tool_use.xml +84 -0
- tunacode/prompts/sections/user_instructions.xml +3 -0
- tunacode/py.typed +0 -0
- tunacode/templates/__init__.py +5 -0
- tunacode/templates/loader.py +15 -0
- tunacode/tools/__init__.py +10 -0
- tunacode/tools/authorization/__init__.py +29 -0
- tunacode/tools/authorization/context.py +32 -0
- tunacode/tools/authorization/factory.py +20 -0
- tunacode/tools/authorization/handler.py +58 -0
- tunacode/tools/authorization/notifier.py +35 -0
- tunacode/tools/authorization/policy.py +19 -0
- tunacode/tools/authorization/requests.py +119 -0
- tunacode/tools/authorization/rules.py +72 -0
- tunacode/tools/bash.py +222 -0
- tunacode/tools/decorators.py +213 -0
- tunacode/tools/glob.py +353 -0
- tunacode/tools/grep.py +468 -0
- tunacode/tools/grep_components/__init__.py +9 -0
- tunacode/tools/grep_components/file_filter.py +93 -0
- tunacode/tools/grep_components/pattern_matcher.py +158 -0
- tunacode/tools/grep_components/result_formatter.py +87 -0
- tunacode/tools/grep_components/search_result.py +34 -0
- tunacode/tools/list_dir.py +205 -0
- tunacode/tools/prompts/bash_prompt.xml +10 -0
- tunacode/tools/prompts/glob_prompt.xml +7 -0
- tunacode/tools/prompts/grep_prompt.xml +10 -0
- tunacode/tools/prompts/list_dir_prompt.xml +7 -0
- tunacode/tools/prompts/read_file_prompt.xml +9 -0
- tunacode/tools/prompts/todoclear_prompt.xml +12 -0
- tunacode/tools/prompts/todoread_prompt.xml +16 -0
- tunacode/tools/prompts/todowrite_prompt.xml +28 -0
- tunacode/tools/prompts/update_file_prompt.xml +9 -0
- tunacode/tools/prompts/web_fetch_prompt.xml +11 -0
- tunacode/tools/prompts/write_file_prompt.xml +7 -0
- tunacode/tools/react.py +111 -0
- tunacode/tools/read_file.py +68 -0
- tunacode/tools/todo.py +222 -0
- tunacode/tools/update_file.py +62 -0
- tunacode/tools/utils/__init__.py +1 -0
- tunacode/tools/utils/ripgrep.py +311 -0
- tunacode/tools/utils/text_match.py +352 -0
- tunacode/tools/web_fetch.py +245 -0
- tunacode/tools/write_file.py +34 -0
- tunacode/tools/xml_helper.py +34 -0
- tunacode/types/__init__.py +166 -0
- tunacode/types/base.py +94 -0
- tunacode/types/callbacks.py +53 -0
- tunacode/types/dataclasses.py +121 -0
- tunacode/types/pydantic_ai.py +31 -0
- tunacode/types/state.py +122 -0
- tunacode/ui/__init__.py +6 -0
- tunacode/ui/app.py +542 -0
- tunacode/ui/commands/__init__.py +430 -0
- tunacode/ui/components/__init__.py +1 -0
- tunacode/ui/headless/__init__.py +5 -0
- tunacode/ui/headless/output.py +72 -0
- tunacode/ui/main.py +252 -0
- tunacode/ui/renderers/__init__.py +41 -0
- tunacode/ui/renderers/errors.py +197 -0
- tunacode/ui/renderers/panels.py +550 -0
- tunacode/ui/renderers/search.py +314 -0
- tunacode/ui/renderers/tools/__init__.py +21 -0
- tunacode/ui/renderers/tools/bash.py +247 -0
- tunacode/ui/renderers/tools/diagnostics.py +186 -0
- tunacode/ui/renderers/tools/glob.py +226 -0
- tunacode/ui/renderers/tools/grep.py +228 -0
- tunacode/ui/renderers/tools/list_dir.py +198 -0
- tunacode/ui/renderers/tools/read_file.py +226 -0
- tunacode/ui/renderers/tools/research.py +294 -0
- tunacode/ui/renderers/tools/update_file.py +237 -0
- tunacode/ui/renderers/tools/web_fetch.py +182 -0
- tunacode/ui/repl_support.py +226 -0
- tunacode/ui/screens/__init__.py +16 -0
- tunacode/ui/screens/model_picker.py +303 -0
- tunacode/ui/screens/session_picker.py +181 -0
- tunacode/ui/screens/setup.py +218 -0
- tunacode/ui/screens/theme_picker.py +90 -0
- tunacode/ui/screens/update_confirm.py +69 -0
- tunacode/ui/shell_runner.py +129 -0
- tunacode/ui/styles/layout.tcss +98 -0
- tunacode/ui/styles/modals.tcss +38 -0
- tunacode/ui/styles/panels.tcss +81 -0
- tunacode/ui/styles/theme-nextstep.tcss +303 -0
- tunacode/ui/styles/widgets.tcss +33 -0
- tunacode/ui/styles.py +18 -0
- tunacode/ui/widgets/__init__.py +23 -0
- tunacode/ui/widgets/command_autocomplete.py +62 -0
- tunacode/ui/widgets/editor.py +402 -0
- tunacode/ui/widgets/file_autocomplete.py +47 -0
- tunacode/ui/widgets/messages.py +46 -0
- tunacode/ui/widgets/resource_bar.py +182 -0
- tunacode/ui/widgets/status_bar.py +98 -0
- tunacode/utils/__init__.py +0 -0
- tunacode/utils/config/__init__.py +13 -0
- tunacode/utils/config/user_configuration.py +91 -0
- tunacode/utils/messaging/__init__.py +10 -0
- tunacode/utils/messaging/message_utils.py +34 -0
- tunacode/utils/messaging/token_counter.py +77 -0
- tunacode/utils/parsing/__init__.py +13 -0
- tunacode/utils/parsing/command_parser.py +55 -0
- tunacode/utils/parsing/json_utils.py +188 -0
- tunacode/utils/parsing/retry.py +146 -0
- tunacode/utils/parsing/tool_parser.py +267 -0
- tunacode/utils/security/__init__.py +15 -0
- tunacode/utils/security/command.py +106 -0
- tunacode/utils/system/__init__.py +25 -0
- tunacode/utils/system/gitignore.py +155 -0
- tunacode/utils/system/paths.py +190 -0
- tunacode/utils/ui/__init__.py +9 -0
- tunacode/utils/ui/file_filter.py +135 -0
- tunacode/utils/ui/helpers.py +24 -0
- tunacode_cli-0.1.21.dist-info/METADATA +170 -0
- tunacode_cli-0.1.21.dist-info/RECORD +174 -0
- tunacode_cli-0.1.21.dist-info/WHEEL +4 -0
- tunacode_cli-0.1.21.dist-info/entry_points.txt +2 -0
- tunacode_cli-0.1.21.dist-info/licenses/LICENSE +21 -0
|
@@ -0,0 +1,121 @@
|
|
|
1
|
+
"""Dataclass definitions for TunaCode CLI.
|
|
2
|
+
|
|
3
|
+
Contains structured data types used throughout the application.
|
|
4
|
+
"""
|
|
5
|
+
|
|
6
|
+
from dataclasses import dataclass, field
|
|
7
|
+
from enum import Enum
|
|
8
|
+
from typing import TYPE_CHECKING, Any
|
|
9
|
+
|
|
10
|
+
if TYPE_CHECKING:
|
|
11
|
+
from tunacode.types.state import StateManagerProtocol
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
@dataclass
|
|
15
|
+
class ModelPricing:
|
|
16
|
+
"""Pricing information for a model."""
|
|
17
|
+
|
|
18
|
+
input: float
|
|
19
|
+
cached_input: float
|
|
20
|
+
output: float
|
|
21
|
+
|
|
22
|
+
|
|
23
|
+
@dataclass
|
|
24
|
+
class ModelConfig:
|
|
25
|
+
"""Configuration for a model including pricing."""
|
|
26
|
+
|
|
27
|
+
pricing: ModelPricing
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
ModelRegistry = dict[str, ModelConfig]
|
|
31
|
+
|
|
32
|
+
|
|
33
|
+
@dataclass
|
|
34
|
+
class ToolConfirmationRequest:
|
|
35
|
+
"""Request for tool execution confirmation."""
|
|
36
|
+
|
|
37
|
+
tool_name: str
|
|
38
|
+
args: dict[str, Any]
|
|
39
|
+
filepath: str | None = None
|
|
40
|
+
diff_content: str | None = None
|
|
41
|
+
|
|
42
|
+
|
|
43
|
+
@dataclass
|
|
44
|
+
class ToolConfirmationResponse:
|
|
45
|
+
"""Response from tool confirmation dialog."""
|
|
46
|
+
|
|
47
|
+
approved: bool
|
|
48
|
+
skip_future: bool = False
|
|
49
|
+
abort: bool = False
|
|
50
|
+
instructions: str = ""
|
|
51
|
+
|
|
52
|
+
|
|
53
|
+
@dataclass
|
|
54
|
+
class ResponseState:
|
|
55
|
+
"""Track whether a user visible response was produced."""
|
|
56
|
+
|
|
57
|
+
has_user_response: bool = False
|
|
58
|
+
has_final_synthesis: bool = False
|
|
59
|
+
task_completed: bool = False
|
|
60
|
+
awaiting_user_guidance: bool = False
|
|
61
|
+
|
|
62
|
+
|
|
63
|
+
@dataclass
|
|
64
|
+
class FallbackResponse:
|
|
65
|
+
"""Structure for synthesized fallback responses."""
|
|
66
|
+
|
|
67
|
+
summary: str
|
|
68
|
+
progress: str = ""
|
|
69
|
+
issues: list[str] = field(default_factory=list)
|
|
70
|
+
next_steps: list[str] = field(default_factory=list)
|
|
71
|
+
|
|
72
|
+
|
|
73
|
+
class AgentState(Enum):
|
|
74
|
+
"""Agent loop states for enhanced completion detection."""
|
|
75
|
+
|
|
76
|
+
USER_INPUT = "user_input"
|
|
77
|
+
ASSISTANT = "assistant"
|
|
78
|
+
TOOL_EXECUTION = "tool_execution"
|
|
79
|
+
RESPONSE = "response"
|
|
80
|
+
|
|
81
|
+
|
|
82
|
+
@dataclass
|
|
83
|
+
class CommandContext:
|
|
84
|
+
"""Context passed to command handlers."""
|
|
85
|
+
|
|
86
|
+
state_manager: "StateManagerProtocol"
|
|
87
|
+
process_request: Any | None = None
|
|
88
|
+
|
|
89
|
+
|
|
90
|
+
@dataclass
|
|
91
|
+
class TokenUsage:
|
|
92
|
+
"""Token usage for a request."""
|
|
93
|
+
|
|
94
|
+
input_tokens: int
|
|
95
|
+
cached_tokens: int
|
|
96
|
+
output_tokens: int
|
|
97
|
+
|
|
98
|
+
|
|
99
|
+
@dataclass
|
|
100
|
+
class CostBreakdown:
|
|
101
|
+
"""Breakdown of costs for a request."""
|
|
102
|
+
|
|
103
|
+
input_cost: float
|
|
104
|
+
cached_cost: float
|
|
105
|
+
output_cost: float
|
|
106
|
+
total_cost: float
|
|
107
|
+
|
|
108
|
+
|
|
109
|
+
__all__ = [
|
|
110
|
+
"AgentState",
|
|
111
|
+
"CommandContext",
|
|
112
|
+
"CostBreakdown",
|
|
113
|
+
"FallbackResponse",
|
|
114
|
+
"ModelConfig",
|
|
115
|
+
"ModelPricing",
|
|
116
|
+
"ModelRegistry",
|
|
117
|
+
"ResponseState",
|
|
118
|
+
"TokenUsage",
|
|
119
|
+
"ToolConfirmationRequest",
|
|
120
|
+
"ToolConfirmationResponse",
|
|
121
|
+
]
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
"""Pydantic-AI type wrappers for TunaCode CLI.
|
|
2
|
+
|
|
3
|
+
Isolates pydantic-ai dependencies to a single module for easier
|
|
4
|
+
migration if the underlying library changes.
|
|
5
|
+
"""
|
|
6
|
+
|
|
7
|
+
from typing import Any
|
|
8
|
+
|
|
9
|
+
from pydantic_ai import Agent
|
|
10
|
+
from pydantic_ai.messages import ModelRequest as _ModelRequest
|
|
11
|
+
from pydantic_ai.messages import ToolReturnPart
|
|
12
|
+
|
|
13
|
+
# Re-export with stable names ugly but better thab what we had before
|
|
14
|
+
PydanticAgent = Agent
|
|
15
|
+
MessagePart = ToolReturnPart | Any
|
|
16
|
+
ModelRequest = _ModelRequest
|
|
17
|
+
ModelResponse = Any
|
|
18
|
+
|
|
19
|
+
AgentResponse = Any
|
|
20
|
+
MessageHistory = list[Any]
|
|
21
|
+
AgentRun = Any
|
|
22
|
+
|
|
23
|
+
__all__ = [
|
|
24
|
+
"AgentResponse",
|
|
25
|
+
"AgentRun",
|
|
26
|
+
"MessageHistory",
|
|
27
|
+
"MessagePart",
|
|
28
|
+
"ModelRequest",
|
|
29
|
+
"ModelResponse",
|
|
30
|
+
"PydanticAgent",
|
|
31
|
+
]
|
tunacode/types/state.py
ADDED
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
"""State management protocol for TunaCode CLI.
|
|
2
|
+
|
|
3
|
+
Defines the StateManager protocol to enable type-safe usage without
|
|
4
|
+
creating circular imports with the concrete implementation.
|
|
5
|
+
"""
|
|
6
|
+
|
|
7
|
+
from typing import TYPE_CHECKING, Any, Protocol
|
|
8
|
+
|
|
9
|
+
if TYPE_CHECKING:
|
|
10
|
+
from tunacode.types.callbacks import ToolProgressCallback
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
class SessionStateProtocol(Protocol):
|
|
14
|
+
"""Protocol for session state access."""
|
|
15
|
+
|
|
16
|
+
user_config: dict[str, Any]
|
|
17
|
+
current_model: str
|
|
18
|
+
tool_progress_callback: "ToolProgressCallback | None"
|
|
19
|
+
messages: list[Any]
|
|
20
|
+
tool_calls: list[dict[str, Any]]
|
|
21
|
+
tool_ignore: list[str]
|
|
22
|
+
yolo: bool
|
|
23
|
+
show_thoughts: bool
|
|
24
|
+
operation_cancelled: bool
|
|
25
|
+
total_tokens: int
|
|
26
|
+
max_tokens: int
|
|
27
|
+
# Persistence fields
|
|
28
|
+
project_id: str
|
|
29
|
+
created_at: str
|
|
30
|
+
working_directory: str
|
|
31
|
+
|
|
32
|
+
def update_token_count(self) -> None:
|
|
33
|
+
"""Calculate total token count from conversation messages."""
|
|
34
|
+
...
|
|
35
|
+
|
|
36
|
+
|
|
37
|
+
class StateManagerProtocol(Protocol):
|
|
38
|
+
"""Protocol defining the StateManager interface.
|
|
39
|
+
|
|
40
|
+
This protocol enables type-safe references to StateManager without
|
|
41
|
+
importing the concrete implementation, avoiding circular imports.
|
|
42
|
+
"""
|
|
43
|
+
|
|
44
|
+
@property
|
|
45
|
+
def session(self) -> SessionStateProtocol:
|
|
46
|
+
"""Access the current session state."""
|
|
47
|
+
...
|
|
48
|
+
|
|
49
|
+
@property
|
|
50
|
+
def tool_handler(self) -> Any:
|
|
51
|
+
"""Get the current tool handler."""
|
|
52
|
+
...
|
|
53
|
+
|
|
54
|
+
def set_tool_handler(self, handler: Any) -> None:
|
|
55
|
+
"""Set the tool handler instance."""
|
|
56
|
+
...
|
|
57
|
+
|
|
58
|
+
# ReAct scratchpad methods
|
|
59
|
+
def get_react_scratchpad(self) -> dict[str, Any]:
|
|
60
|
+
"""Get the ReAct scratchpad dictionary."""
|
|
61
|
+
...
|
|
62
|
+
|
|
63
|
+
def append_react_entry(self, entry: dict[str, Any]) -> None:
|
|
64
|
+
"""Append an entry to the ReAct timeline."""
|
|
65
|
+
...
|
|
66
|
+
|
|
67
|
+
def clear_react_scratchpad(self) -> None:
|
|
68
|
+
"""Clear the ReAct scratchpad."""
|
|
69
|
+
...
|
|
70
|
+
|
|
71
|
+
# Todo list methods
|
|
72
|
+
def get_todos(self) -> list[dict[str, Any]]:
|
|
73
|
+
"""Get the current todo list."""
|
|
74
|
+
...
|
|
75
|
+
|
|
76
|
+
def set_todos(self, todos: list[dict[str, Any]]) -> None:
|
|
77
|
+
"""Replace the entire todo list."""
|
|
78
|
+
...
|
|
79
|
+
|
|
80
|
+
def clear_todos(self) -> None:
|
|
81
|
+
"""Clear the todo list."""
|
|
82
|
+
...
|
|
83
|
+
|
|
84
|
+
# Recursive execution methods
|
|
85
|
+
def push_recursive_context(self, context: dict[str, Any]) -> None:
|
|
86
|
+
"""Push a context onto the recursive stack."""
|
|
87
|
+
...
|
|
88
|
+
|
|
89
|
+
def pop_recursive_context(self) -> dict[str, Any] | None:
|
|
90
|
+
"""Pop and return the top context."""
|
|
91
|
+
...
|
|
92
|
+
|
|
93
|
+
def can_recurse_deeper(self) -> bool:
|
|
94
|
+
"""Check if recursion limit allows deeper nesting."""
|
|
95
|
+
...
|
|
96
|
+
|
|
97
|
+
def reset_recursive_state(self) -> None:
|
|
98
|
+
"""Reset all recursive execution state."""
|
|
99
|
+
...
|
|
100
|
+
|
|
101
|
+
# Session persistence methods
|
|
102
|
+
def save_session(self) -> bool:
|
|
103
|
+
"""Save current session to disk."""
|
|
104
|
+
...
|
|
105
|
+
|
|
106
|
+
def load_session(self, session_id: str) -> bool:
|
|
107
|
+
"""Load a session from disk by ID."""
|
|
108
|
+
...
|
|
109
|
+
|
|
110
|
+
def list_sessions(self) -> list[dict[str, Any]]:
|
|
111
|
+
"""List available saved sessions."""
|
|
112
|
+
...
|
|
113
|
+
|
|
114
|
+
|
|
115
|
+
# Backward compatibility alias
|
|
116
|
+
StateManager = StateManagerProtocol
|
|
117
|
+
|
|
118
|
+
__all__ = [
|
|
119
|
+
"SessionStateProtocol",
|
|
120
|
+
"StateManager",
|
|
121
|
+
"StateManagerProtocol",
|
|
122
|
+
]
|