hellochusquis 0.6.0__tar.gz

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.
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Arnau Moyano
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,151 @@
1
+ Metadata-Version: 2.4
2
+ Name: hellochusquis
3
+ Version: 0.6.0
4
+ Summary: A powerful terminal AI agent with multi-provider fallback, plugin system, and web interface
5
+ Author: aminoy77
6
+ License: MIT
7
+ Project-URL: Homepage, https://github.com/aminoy77/HelloChusquis
8
+ Keywords: ai,agent,cli,llm,automation
9
+ Requires-Python: >=3.10
10
+ Description-Content-Type: text/markdown
11
+ License-File: LICENSE
12
+ Requires-Dist: rich>=13.0.0
13
+ Requires-Dist: pyyaml>=6.0
14
+ Requires-Dist: httpx>=0.24.0
15
+ Requires-Dist: fastapi>=0.100.0
16
+ Requires-Dist: uvicorn>=0.23.0
17
+ Dynamic: license-file
18
+
19
+ # HelloChusquis
20
+
21
+ A powerful terminal AI agent built in Python with web interface, multi-provider fallback, plugin system, persistent memory, and auto-learning.
22
+
23
+ ## Features
24
+
25
+ - πŸ€– **AI Agent** β€” chat in terminal or browser with full tool access
26
+ - πŸ”„ **Multi-provider fallback** β€” automatically switches between providers when one fails
27
+ - 🧩 **Plugin system** β€” install plugins with one command, build your own
28
+ - 🧠 **Persistent memory** β€” remembers past conversations and learns from them
29
+ - πŸ“‹ **Task planner** β€” detects complex tasks and executes them step by step
30
+ - 🌐 **Web interface** β€” chat from your browser with sidebar showing status
31
+ - πŸ“„ **Real file creation** β€” generates real PDF and Word documents
32
+ - πŸ” **Browser control** β€” search the web and extract content from pages
33
+
34
+ ## Supported Providers
35
+
36
+ OpenRouter, Ollama Cloud, Anthropic Claude, OpenAI, Google Gemini, Groq, xAI (Grok), Perplexity, Qwen, MiniMax, Mistral, DeepSeek, Cohere, Together AI, Fireworks AI, Novita AI, and more.
37
+
38
+ ## Installation
39
+
40
+ ### Option 1 β€” Download ZIP
41
+
42
+ 1. Go to [github.com/aminoy77/HelloChusquis](https://github.com/aminoy77/HelloChusquis)
43
+ 2. Click **Code β†’ Download ZIP**
44
+ 3. Unzip the file
45
+ 4. Open terminal in the unzipped folder
46
+ 5. Run:
47
+ ```bash
48
+ pip install -e .
49
+ ```
50
+
51
+ ### Option 2 β€” Clone repo
52
+
53
+ ```bash
54
+ git clone https://github.com/aminoy77/HelloChusquis.git
55
+ cd HelloChusquis
56
+ pip install -e .
57
+ ```
58
+
59
+ ## First Run
60
+
61
+ ```bash
62
+ hellochusquis
63
+ ```
64
+
65
+ First run will launch the setup wizard to configure your providers. It is recommended to add at least 2 providers for automatic fallback.
66
+
67
+ Get free API keys at:
68
+ - [openrouter.ai](https://openrouter.ai) β€” access 300+ models, many free
69
+ - [console.groq.com](https://console.groq.com) β€” fastest free tier
70
+ - [ollama.com](https://ollama.com) β€” cloud models
71
+
72
+ ## Usage
73
+
74
+ ### Terminal
75
+
76
+ ```bash
77
+ hellochusquis # Start chat in terminal
78
+ hellochusquis web # Start web interface (opens browser)
79
+ ```
80
+
81
+ ### Chat Commands
82
+
83
+ | Command | Description |
84
+ |---|---|
85
+ | `/help` | Show available commands |
86
+ | `/status` | Show provider status |
87
+ | `/clear` | Clear conversation history |
88
+ | `/plan <task>` | Force planning mode for a task |
89
+ | `πŸ‘` or `+` | Positive feedback on last response |
90
+ | `πŸ‘Ž` or `-` | Negative feedback on last response |
91
+ | `exit` | Exit and save memory |
92
+
93
+ ### Terminal Commands
94
+
95
+ ```bash
96
+ hellochusquis install # Install a plugin
97
+ hellochusquis uninstall # Remove a plugin
98
+ hellochusquis plugins # List installed plugins
99
+ hellochusquis build # Build a new plugin with AI
100
+ hellochusquis learn # Show learned patterns and rules
101
+ hellochusquis web # Start web interface
102
+ ```
103
+
104
+ ## Plugins
105
+
106
+ Install plugins from the public registry:
107
+
108
+ ```bash
109
+ hellochusquis install weather
110
+ hellochusquis install stocks
111
+ hellochusquis install browser
112
+ hellochusquis install pdf
113
+ hellochusquis install docx
114
+ hellochusquis install crypto
115
+ hellochusquis install calculator
116
+ hellochusquis install worldclock
117
+ ```
118
+
119
+ Browse all available plugins at [github.com/aminoy77/Hellochusquis-plugins](https://github.com/aminoy77/HelloChusquis-plugins.git)
120
+
121
+ ### Build your own plugin
122
+
123
+ ```bash
124
+ hellochusquis build
125
+ ```
126
+
127
+ The AI will research the API, write the plugin code, test it, and ask if you want to submit it to the public registry.
128
+
129
+ ## Web Interface
130
+
131
+ ```bash
132
+ hellochusquis web
133
+ ```
134
+
135
+ Opens a web chat at `http://localhost:8000` with:
136
+ - Chat interface with tool call visualization
137
+ - Sidebar with provider status, installed plugins, memory stats, and learned patterns
138
+
139
+ ## How it works
140
+
141
+ **Provider fallback** β€” if a provider hits rate limits or times out, HelloChusquis automatically switches to the next one. Providers that support tool calling are prioritized for tasks that need tools.
142
+
143
+ **Task planner** β€” for complex tasks, HelloChusquis generates a step-by-step plan, shows it to you for confirmation, then executes each step automatically.
144
+
145
+ **Memory** β€” at the end of each session, HelloChusquis summarizes the conversation and stores it. Next session it remembers what you discussed.
146
+
147
+ **Auto-learning** β€” after each session, the agent analyzes what worked and what didn't, and improves its behavior over time.
148
+
149
+ ## License
150
+
151
+ MIT
@@ -0,0 +1,133 @@
1
+ # HelloChusquis
2
+
3
+ A powerful terminal AI agent built in Python with web interface, multi-provider fallback, plugin system, persistent memory, and auto-learning.
4
+
5
+ ## Features
6
+
7
+ - πŸ€– **AI Agent** β€” chat in terminal or browser with full tool access
8
+ - πŸ”„ **Multi-provider fallback** β€” automatically switches between providers when one fails
9
+ - 🧩 **Plugin system** β€” install plugins with one command, build your own
10
+ - 🧠 **Persistent memory** β€” remembers past conversations and learns from them
11
+ - πŸ“‹ **Task planner** β€” detects complex tasks and executes them step by step
12
+ - 🌐 **Web interface** β€” chat from your browser with sidebar showing status
13
+ - πŸ“„ **Real file creation** β€” generates real PDF and Word documents
14
+ - πŸ” **Browser control** β€” search the web and extract content from pages
15
+
16
+ ## Supported Providers
17
+
18
+ OpenRouter, Ollama Cloud, Anthropic Claude, OpenAI, Google Gemini, Groq, xAI (Grok), Perplexity, Qwen, MiniMax, Mistral, DeepSeek, Cohere, Together AI, Fireworks AI, Novita AI, and more.
19
+
20
+ ## Installation
21
+
22
+ ### Option 1 β€” Download ZIP
23
+
24
+ 1. Go to [github.com/aminoy77/HelloChusquis](https://github.com/aminoy77/HelloChusquis)
25
+ 2. Click **Code β†’ Download ZIP**
26
+ 3. Unzip the file
27
+ 4. Open terminal in the unzipped folder
28
+ 5. Run:
29
+ ```bash
30
+ pip install -e .
31
+ ```
32
+
33
+ ### Option 2 β€” Clone repo
34
+
35
+ ```bash
36
+ git clone https://github.com/aminoy77/HelloChusquis.git
37
+ cd HelloChusquis
38
+ pip install -e .
39
+ ```
40
+
41
+ ## First Run
42
+
43
+ ```bash
44
+ hellochusquis
45
+ ```
46
+
47
+ First run will launch the setup wizard to configure your providers. It is recommended to add at least 2 providers for automatic fallback.
48
+
49
+ Get free API keys at:
50
+ - [openrouter.ai](https://openrouter.ai) β€” access 300+ models, many free
51
+ - [console.groq.com](https://console.groq.com) β€” fastest free tier
52
+ - [ollama.com](https://ollama.com) β€” cloud models
53
+
54
+ ## Usage
55
+
56
+ ### Terminal
57
+
58
+ ```bash
59
+ hellochusquis # Start chat in terminal
60
+ hellochusquis web # Start web interface (opens browser)
61
+ ```
62
+
63
+ ### Chat Commands
64
+
65
+ | Command | Description |
66
+ |---|---|
67
+ | `/help` | Show available commands |
68
+ | `/status` | Show provider status |
69
+ | `/clear` | Clear conversation history |
70
+ | `/plan <task>` | Force planning mode for a task |
71
+ | `πŸ‘` or `+` | Positive feedback on last response |
72
+ | `πŸ‘Ž` or `-` | Negative feedback on last response |
73
+ | `exit` | Exit and save memory |
74
+
75
+ ### Terminal Commands
76
+
77
+ ```bash
78
+ hellochusquis install # Install a plugin
79
+ hellochusquis uninstall # Remove a plugin
80
+ hellochusquis plugins # List installed plugins
81
+ hellochusquis build # Build a new plugin with AI
82
+ hellochusquis learn # Show learned patterns and rules
83
+ hellochusquis web # Start web interface
84
+ ```
85
+
86
+ ## Plugins
87
+
88
+ Install plugins from the public registry:
89
+
90
+ ```bash
91
+ hellochusquis install weather
92
+ hellochusquis install stocks
93
+ hellochusquis install browser
94
+ hellochusquis install pdf
95
+ hellochusquis install docx
96
+ hellochusquis install crypto
97
+ hellochusquis install calculator
98
+ hellochusquis install worldclock
99
+ ```
100
+
101
+ Browse all available plugins at [github.com/aminoy77/Hellochusquis-plugins](https://github.com/aminoy77/HelloChusquis-plugins.git)
102
+
103
+ ### Build your own plugin
104
+
105
+ ```bash
106
+ hellochusquis build
107
+ ```
108
+
109
+ The AI will research the API, write the plugin code, test it, and ask if you want to submit it to the public registry.
110
+
111
+ ## Web Interface
112
+
113
+ ```bash
114
+ hellochusquis web
115
+ ```
116
+
117
+ Opens a web chat at `http://localhost:8000` with:
118
+ - Chat interface with tool call visualization
119
+ - Sidebar with provider status, installed plugins, memory stats, and learned patterns
120
+
121
+ ## How it works
122
+
123
+ **Provider fallback** β€” if a provider hits rate limits or times out, HelloChusquis automatically switches to the next one. Providers that support tool calling are prioritized for tasks that need tools.
124
+
125
+ **Task planner** β€” for complex tasks, HelloChusquis generates a step-by-step plan, shows it to you for confirmation, then executes each step automatically.
126
+
127
+ **Memory** β€” at the end of each session, HelloChusquis summarizes the conversation and stores it. Next session it remembers what you discussed.
128
+
129
+ **Auto-learning** β€” after each session, the agent analyzes what worked and what didn't, and improves its behavior over time.
130
+
131
+ ## License
132
+
133
+ MIT
@@ -0,0 +1,61 @@
1
+ import sys
2
+ import os
3
+ sys.path.insert(0, os.path.dirname(__file__))
4
+
5
+
6
+ def main():
7
+ args = sys.argv[1:]
8
+
9
+ if args and args[0] == "install" and len(args) > 1:
10
+ from core.plugins import install_plugin
11
+ install_plugin(args[1])
12
+ return
13
+
14
+ if args and args[0] == "uninstall" and len(args) > 1:
15
+ from core.plugins import uninstall_plugin
16
+ uninstall_plugin(args[1])
17
+ return
18
+
19
+ if args and args[0] == "plugins":
20
+ from core.plugins import list_plugins
21
+ list_plugins()
22
+ return
23
+
24
+ if args and args[0] == "build":
25
+ from core.setup import ensure_config
26
+ from core.provider import ProviderPool
27
+ ensure_config()
28
+ pool = ProviderPool()
29
+ from core.builder import build_plugin
30
+ build_plugin(pool)
31
+ return
32
+
33
+ if args and args[0] == "learn":
34
+ from core.setup import ensure_config
35
+ from core.learning import load_learnings
36
+ from rich.console import Console
37
+ import json
38
+ ensure_config()
39
+ console = Console()
40
+ learnings = load_learnings()
41
+ console.print("\n[bold]Current learnings:[/bold]")
42
+ console.print_json(json.dumps(learnings, indent=2, ensure_ascii=False))
43
+ return
44
+
45
+ if args and args[0] == "web":
46
+ import webbrowser
47
+ from rich.console import Console
48
+ console = Console()
49
+ console.print("[cyan]Starting HelloChusquis web interface...[/cyan]")
50
+ console.print("[dim]Open: http://localhost:8000[/dim]")
51
+ webbrowser.open("http://localhost:8000")
52
+ from web.server import start
53
+ start()
54
+ return
55
+
56
+ from main import main as run
57
+ run()
58
+
59
+
60
+ if __name__ == "__main__":
61
+ main()
@@ -0,0 +1,189 @@
1
+ import json
2
+ import core.memory as memory
3
+ import core.learning as learning
4
+ from core.provider import ProviderPool
5
+ from core.history import History
6
+ from tools.shell import ShellTool
7
+ from tools.files import FilesTool
8
+ from tools.code import CodeTool
9
+ from workspace.manager import WorkspaceManager
10
+ from core.plugins import load_plugins
11
+
12
+
13
+ TOOLS_SCHEMA = [
14
+ {
15
+ "type": "function",
16
+ "function": {
17
+ "name": "shell",
18
+ "description": "Execute a terminal command",
19
+ "parameters": {
20
+ "type": "object",
21
+ "properties": {
22
+ "command": {"type": "string", "description": "The command to run"}
23
+ },
24
+ "required": ["command"]
25
+ }
26
+ }
27
+ },
28
+ {
29
+ "type": "function",
30
+ "function": {
31
+ "name": "code",
32
+ "description": "Execute Python code",
33
+ "parameters": {
34
+ "type": "object",
35
+ "properties": {
36
+ "code": {"type": "string", "description": "Python code to execute"}
37
+ },
38
+ "required": ["code"]
39
+ }
40
+ }
41
+ },
42
+ {
43
+ "type": "function",
44
+ "function": {
45
+ "name": "files",
46
+ "description": "Read, write, delete, list files in the workspace",
47
+ "parameters": {
48
+ "type": "object",
49
+ "properties": {
50
+ "action": {
51
+ "type": "string",
52
+ "enum": ["read", "write", "delete", "list", "create_dir"]
53
+ },
54
+ "path": {"type": "string"},
55
+ "content": {"type": "string", "description": "Required for write"}
56
+ },
57
+ "required": ["action", "path"]
58
+ }
59
+ }
60
+ }
61
+ ]
62
+
63
+
64
+ class Agent:
65
+ def __init__(self, config: dict):
66
+ self.pool = ProviderPool()
67
+ self.history = History()
68
+ self.workspace = WorkspaceManager(config["settings"]["workspace_dirs"])
69
+ self.shell = ShellTool()
70
+ self.files = FilesTool(config["settings"]["workspace_dirs"])
71
+ self.code = CodeTool()
72
+ self.system_prompt = config["agent"]["system_prompt"]
73
+ self.workspace_dirs = config["settings"]["workspace_dirs"]
74
+
75
+ # Cargar memoria de sesiones anteriores
76
+ summary = memory.load_summary()
77
+ if summary:
78
+ self.system_prompt += f"\n\nWhat you remember from past sessions:\n{summary}"
79
+
80
+ # Cargar learnings
81
+ learnings = learning.load_learnings()
82
+ learning_prompt = learning.build_learning_prompt(learnings)
83
+ if learning_prompt:
84
+ self.system_prompt += f"\n\n{learning_prompt}"
85
+
86
+ # Cargar plugins
87
+ self.plugins = load_plugins()
88
+ for plugin in self.plugins:
89
+ TOOLS_SCHEMA.append(plugin["schema"])
90
+
91
+ # Informar al agente quΓ© plugins tiene disponibles
92
+ if self.plugins:
93
+ plugin_names = ", ".join(p["name"] for p in self.plugins)
94
+ self.system_prompt += f"\n\nInstalled plugins available as tools: {plugin_names}. Use them directly without asking the user to install anything."
95
+
96
+ def _dispatch_tool(self, name: str, args: dict):
97
+ if name == "shell":
98
+ return self.shell.run(**args)
99
+ elif name == "code":
100
+ return self.code.run(**args)
101
+ elif name == "files":
102
+ path = args.get("path", "")
103
+ if not self.workspace.is_allowed(path):
104
+ granted = self.workspace.request_access(path)
105
+ if not granted:
106
+ from tools.base import ToolResult
107
+ return ToolResult(success=False, output="", error="Access denied by user")
108
+ self.files.allow_dir(path)
109
+ return self.files.run(**args)
110
+
111
+ for plugin in self.plugins:
112
+ if plugin["name"] == name:
113
+ try:
114
+ result_text = plugin["run"](**args)
115
+ from tools.base import ToolResult
116
+ return ToolResult(success=True, output=str(result_text))
117
+ except Exception as e:
118
+ from tools.base import ToolResult
119
+ return ToolResult(success=False, output="", error=str(e))
120
+
121
+ from tools.base import ToolResult
122
+ return ToolResult(success=False, output="", error=f"Unknown tool: {name}")
123
+
124
+ def run(self, user_input: str) -> str:
125
+ self.history.add("user", user_input)
126
+
127
+ messages = [
128
+ {"role": "system", "content": (
129
+ self.system_prompt +
130
+ f"\n\nWorkspace directories: {', '.join(self.workspace_dirs)}. "
131
+ "Always use absolute paths when calling file tools. "
132
+ "Only use tools when strictly necessary. Never use shell or code tools just to print or display text."
133
+ )},
134
+ *self.history.get()
135
+ ]
136
+
137
+ while True:
138
+ response = self.pool.chat_with_retry(messages, tools=TOOLS_SCHEMA)
139
+ message = response["choices"][0]["message"]
140
+
141
+ if not message.get("tool_calls"):
142
+ content = message.get("content", "")
143
+ self.history.add("assistant", content)
144
+ return content
145
+
146
+ messages.append(message)
147
+
148
+ for tc in message["tool_calls"]:
149
+ tool_name = tc["function"]["name"]
150
+ tool_args = json.loads(tc["function"]["arguments"])
151
+
152
+ from ui.terminal import print_tool_call, print_tool_result
153
+ print_tool_call(tool_name, tool_args)
154
+ result = self._dispatch_tool(tool_name, tool_args)
155
+ print_tool_result(result.success, result.output)
156
+
157
+ messages.append({
158
+ "role": "tool",
159
+ "tool_call_id": tc["id"],
160
+ "content": result.output if result.success else f"ERROR: {result.error}"
161
+ })
162
+
163
+ def summarize_and_save(self, retention_days: int = 30):
164
+ messages = self.history.get()
165
+ if not messages:
166
+ return
167
+
168
+ memory.save_session(messages)
169
+
170
+ summary_prompt = (
171
+ "Summarize the key facts, tasks completed, and important context "
172
+ "from this conversation in 3-5 bullet points. Be very concise. "
173
+ "This will be injected into future sessions as memory.\n\n"
174
+ + "\n".join(f"{m['role']}: {m['content'][:200]}" for m in messages)
175
+ )
176
+
177
+ try:
178
+ response = self.pool.chat_with_retry([
179
+ {"role": "user", "content": summary_prompt}
180
+ ])
181
+ summary = response["choices"][0]["message"]["content"]
182
+ memory.save_summary(summary)
183
+ except Exception:
184
+ pass
185
+
186
+ # Analizar y aprender de la sesiΓ³n
187
+ learning.analyze_and_learn(messages, self.pool)
188
+
189
+ memory.cleanup_old_sessions(retention_days)