fixos 2.2.22__tar.gz → 2.2.24__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.
- {fixos-2.2.22 → fixos-2.2.24}/CHANGELOG.md +42 -0
- {fixos-2.2.22 → fixos-2.2.24}/PKG-INFO +5 -5
- {fixos-2.2.22 → fixos-2.2.24}/README.md +4 -4
- {fixos-2.2.22 → fixos-2.2.24}/fixos/__init__.py +1 -1
- {fixos-2.2.22 → fixos-2.2.24}/fixos/agent/autonomous_session.py +23 -16
- {fixos-2.2.22 → fixos-2.2.24}/fixos/agent/hitl_session.py +5 -5
- {fixos-2.2.22 → fixos-2.2.24}/fixos/agent/session_core.py +2 -1
- {fixos-2.2.22 → fixos-2.2.24}/fixos/agent/session_handlers.py +9 -6
- {fixos-2.2.22 → fixos-2.2.24}/fixos/agent/session_io.py +2 -2
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/ask_cmd.py +2 -7
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/cleanup_cmd.py +74 -83
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/config_cmd.py +2 -3
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/features_cmd.py +3 -3
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/fix_cmd.py +9 -4
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/history_cmd.py +1 -1
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/orchestrate_cmd.py +1 -1
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/profile_cmd.py +1 -1
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/provider_cmd.py +2 -2
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/report_cmd.py +2 -2
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/scan_cmd.py +3 -5
- fixos-2.2.24/fixos/constants.py +108 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/checks/_shared.py +2 -1
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/checks/audio.py +10 -9
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/checks/resources.py +17 -9
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/checks/security.py +20 -12
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/checks/system_core.py +11 -5
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/dev_project_analyzer.py +10 -4
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/disk_analyzer.py +13 -14
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/flatpak_analyzer.py +35 -38
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/service_cleanup.py +5 -4
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/service_scanner.py +2 -1
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/storage_analyzer.py +84 -79
- {fixos-2.2.22 → fixos-2.2.24}/fixos.egg-info/PKG-INFO +5 -5
- {fixos-2.2.22 → fixos-2.2.24}/pyproject.toml +1 -1
- {fixos-2.2.22 → fixos-2.2.24}/setup.py +1 -1
- fixos-2.2.22/fixos/constants.py +0 -31
- {fixos-2.2.22 → fixos-2.2.24}/.env.example +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/LICENSE +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/MANIFEST.in +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/README.md +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/TEST_RESULTS.md +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/TEST_RESULTS_V2.md +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/alpine/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/arch/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/base/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/broken-audio/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/broken-full/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/broken-network/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/broken-thumbnails/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/debian/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/docker-compose.multi-system.yml +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/docker-compose.yml +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/fedora/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/test-multi-system.sh +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docker/ubuntu/Dockerfile +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docs/examples/advanced_usage.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/docs/examples/quickstart.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/agent/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/agent/autonomous.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/agent/hitl.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/anonymizer.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/main.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/quickfix_cmd.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/rollback_cmd.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/shared.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/token_cmd.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli/watch_cmd.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/cli.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/config.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/config_interactive.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/checks/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/checks/hardware.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/checks/thumbnails.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/service_details.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/diagnostics/system_checks.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/features/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/features/auditor.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/features/catalog.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/features/installer.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/features/profiles.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/features/renderer.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/fixes/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/interactive/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/interactive/cleanup_planner.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/llm_shell.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/orchestrator/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/orchestrator/executor.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/orchestrator/graph.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/orchestrator/orchestrator.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/orchestrator/rollback.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/platform_utils.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/base.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/builtin/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/builtin/audio.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/builtin/disk.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/builtin/hardware.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/builtin/resources.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/builtin/security.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/builtin/thumbnails.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/plugins/registry.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/profiles/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/providers/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/providers/llm.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/providers/llm_analyzer.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/providers/schemas.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/system_checks.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/utils/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/utils/anonymizer.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/utils/terminal.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/utils/timeout.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/utils/web_search.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos/watch.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos.egg-info/SOURCES.txt +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos.egg-info/dependency_links.txt +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos.egg-info/entry_points.txt +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos.egg-info/requires.txt +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/fixos.egg-info/top_level.txt +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/pytest.ini +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/requirements-dev.txt +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/requirements.txt +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/scripts/pyqual-calibrate.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/setup.cfg +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/conftest.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/e2e/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/e2e/test_anonymization_layers.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/e2e/test_audio_broken.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/e2e/test_cli.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/e2e/test_executor.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/e2e/test_multi_system.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/e2e/test_network_broken.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/e2e/test_thumbnails_broken.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/test_fixos.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/unit/__init__.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/unit/test_anonymizer.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/unit/test_core.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/unit/test_executor.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/unit/test_orchestrator.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/unit/test_service_cleanup.py +0 -0
- {fixos-2.2.22 → fixos-2.2.24}/tests/unit/test_service_scanner.py +0 -0
|
@@ -150,6 +150,48 @@ fix(goal): code analysis engine
|
|
|
150
150
|
- **refactor(cli):** Usunięto zduplikowany kod ujednolicając funkcje analizy dysku do wspólnego helpera `_run_disk_analysis`.
|
|
151
151
|
- **refactor(ui):** Usunięto ikony Unicode z CLI i sformatowano wyjście `stderr` oraz standardowego logowania na czysty kod Markdown dla poprawy czytelności w oknach terminalowych.
|
|
152
152
|
|
|
153
|
+
## [2.2.24] - 2026-05-04
|
|
154
|
+
|
|
155
|
+
### Docs
|
|
156
|
+
- Update README.md
|
|
157
|
+
- Update REFACTORING_PROGRESS.md
|
|
158
|
+
|
|
159
|
+
### Other
|
|
160
|
+
- Update fixos/agent/session_handlers.py
|
|
161
|
+
- Update fixos/cli/ask_cmd.py
|
|
162
|
+
- Update fixos/cli/cleanup_cmd.py
|
|
163
|
+
- Update fixos/cli/config_cmd.py
|
|
164
|
+
- Update fixos/cli/report_cmd.py
|
|
165
|
+
- Update fixos/cli/scan_cmd.py
|
|
166
|
+
- Update fixos/constants.py
|
|
167
|
+
- Update fixos/diagnostics/checks/_shared.py
|
|
168
|
+
- Update fixos/diagnostics/checks/audio.py
|
|
169
|
+
- Update fixos/diagnostics/checks/resources.py
|
|
170
|
+
- ... and 9 more files
|
|
171
|
+
|
|
172
|
+
## [2.2.23] - 2026-05-04
|
|
173
|
+
|
|
174
|
+
### Docs
|
|
175
|
+
- Update README.md
|
|
176
|
+
- Update REFACTORING_PROGRESS.md
|
|
177
|
+
- Update SUMD.md
|
|
178
|
+
- Update SUMR.md
|
|
179
|
+
- Update project/README.md
|
|
180
|
+
- Update project/context.md
|
|
181
|
+
|
|
182
|
+
### Other
|
|
183
|
+
- Update app.doql.less
|
|
184
|
+
- Update fixos/agent/autonomous_session.py
|
|
185
|
+
- Update fixos/agent/hitl_session.py
|
|
186
|
+
- Update fixos/agent/session_core.py
|
|
187
|
+
- Update fixos/agent/session_handlers.py
|
|
188
|
+
- Update fixos/agent/session_io.py
|
|
189
|
+
- Update fixos/cli/cleanup_cmd.py
|
|
190
|
+
- Update fixos/cli/config_cmd.py
|
|
191
|
+
- Update fixos/cli/features_cmd.py
|
|
192
|
+
- Update fixos/cli/fix_cmd.py
|
|
193
|
+
- ... and 23 more files
|
|
194
|
+
|
|
153
195
|
## [2.2.22] - 2026-05-04
|
|
154
196
|
|
|
155
197
|
### Docs
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: fixos
|
|
3
|
-
Version: 2.2.
|
|
3
|
+
Version: 2.2.24
|
|
4
4
|
Summary: AI-powered Linux/Windows diagnostics and repair – audio, hardware, system issues
|
|
5
5
|
Home-page: https://github.com/wronai/fixos
|
|
6
6
|
Author: fixos contributors
|
|
@@ -63,11 +63,11 @@ AI-powered OS Diagnostics
|
|
|
63
63
|
|
|
64
64
|
## AI Cost Tracking
|
|
65
65
|
|
|
66
|
-
     
|
|
67
|
+
  
|
|
68
68
|
|
|
69
|
-
- 🤖 **LLM usage:** $7.5000 (
|
|
70
|
-
- 👤 **Human dev:** ~$
|
|
69
|
+
- 🤖 **LLM usage:** $7.5000 (123 commits)
|
|
70
|
+
- 👤 **Human dev:** ~$2539 (25.4h @ $100/h, 30min dedup)
|
|
71
71
|
|
|
72
72
|
Generated on 2026-05-04 using [openrouter/qwen/qwen3-coder-next](https://openrouter.ai/qwen/qwen3-coder-next)
|
|
73
73
|
|
|
@@ -19,11 +19,11 @@ AI-powered OS Diagnostics
|
|
|
19
19
|
|
|
20
20
|
## AI Cost Tracking
|
|
21
21
|
|
|
22
|
-
     
|
|
23
|
+
  
|
|
24
24
|
|
|
25
|
-
- 🤖 **LLM usage:** $7.5000 (
|
|
26
|
-
- 👤 **Human dev:** ~$
|
|
25
|
+
- 🤖 **LLM usage:** $7.5000 (123 commits)
|
|
26
|
+
- 👤 **Human dev:** ~$2539 (25.4h @ $100/h, 30min dedup)
|
|
27
27
|
|
|
28
28
|
Generated on 2026-05-04 using [openrouter/qwen/qwen3-coder-next](https://openrouter.ai/qwen/qwen3-coder-next)
|
|
29
29
|
|
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
"""fixos – AI-powered Linux/Windows diagnostics and repair."""
|
|
2
|
-
__version__ = "2.2.
|
|
2
|
+
__version__ = "2.2.24"
|
|
@@ -15,9 +15,16 @@ from ..utils.anonymizer import anonymize, display_anonymized_preview
|
|
|
15
15
|
from ..utils.web_search import search_all, format_results_for_llm
|
|
16
16
|
from ..config import FixOsConfig
|
|
17
17
|
from ..utils.timeout import SessionTimeout
|
|
18
|
+
from ..constants import (
|
|
19
|
+
UI_BORDER_WIDTH,
|
|
20
|
+
MAX_OUTPUT_PREVIEW_LENGTH,
|
|
21
|
+
MAX_ANON_PREVIEW_LENGTH,
|
|
22
|
+
DEFAULT_COMMAND_TIMEOUT,
|
|
23
|
+
DEFAULT_TOKEN_LIMIT,
|
|
24
|
+
MAX_COMMAND_LENGTH,
|
|
25
|
+
MAX_SEARCH_QUERY_LENGTH,
|
|
26
|
+
)
|
|
18
27
|
|
|
19
|
-
# UI formatting constants
|
|
20
|
-
UI_BORDER_WIDTH = 65
|
|
21
28
|
|
|
22
29
|
|
|
23
30
|
# Commands NEVER executed automatically
|
|
@@ -121,14 +128,14 @@ class AutonomousSession:
|
|
|
121
128
|
self.start_time = time.time()
|
|
122
129
|
self._setup_timeout()
|
|
123
130
|
|
|
124
|
-
def _setup_timeout(self):
|
|
131
|
+
def _setup_timeout(self) -> None:
|
|
125
132
|
"""Setup session timeout handler."""
|
|
126
|
-
def _timeout_handler(signum, frame):
|
|
133
|
+
def _timeout_handler(signum, frame) -> None:
|
|
127
134
|
raise SessionTimeout()
|
|
128
135
|
signal.signal(signal.SIGALRM, _timeout_handler)
|
|
129
136
|
signal.alarm(self.config.session_timeout)
|
|
130
137
|
|
|
131
|
-
def _clear_timeout(self):
|
|
138
|
+
def _clear_timeout(self) -> None:
|
|
132
139
|
"""Clear the timeout alarm."""
|
|
133
140
|
signal.alarm(0)
|
|
134
141
|
|
|
@@ -148,7 +155,7 @@ class AutonomousSession:
|
|
|
148
155
|
return False
|
|
149
156
|
return True
|
|
150
157
|
|
|
151
|
-
def _initialize_messages(self):
|
|
158
|
+
def _initialize_messages(self) -> None:
|
|
152
159
|
"""Initialize LLM message history with system prompt and diagnostics."""
|
|
153
160
|
anon_str, anon_report = anonymize(str(self.diagnostics))
|
|
154
161
|
if self.show_data:
|
|
@@ -170,7 +177,7 @@ class AutonomousSession:
|
|
|
170
177
|
from . import get_remaining_time
|
|
171
178
|
return get_remaining_time(self)
|
|
172
179
|
|
|
173
|
-
def _check_timeout(self):
|
|
180
|
+
def _check_timeout(self) -> None:
|
|
174
181
|
"""Check if session has timed out."""
|
|
175
182
|
if self._get_remaining_time() <= 0:
|
|
176
183
|
raise SessionTimeout()
|
|
@@ -178,7 +185,7 @@ class AutonomousSession:
|
|
|
178
185
|
def _query_llm(self) -> Optional[str]:
|
|
179
186
|
"""Query LLM and return reply."""
|
|
180
187
|
try:
|
|
181
|
-
return self.llm.chat(self.messages, max_tokens=
|
|
188
|
+
return self.llm.chat(self.messages, max_tokens=DEFAULT_TOKEN_LIMIT, temperature=0.1)
|
|
182
189
|
except LLMError as e:
|
|
183
190
|
print(f" ❌ LLM błąd: {e}")
|
|
184
191
|
return None
|
|
@@ -235,12 +242,12 @@ class AutonomousSession:
|
|
|
235
242
|
"""Execute command and return (success, output)."""
|
|
236
243
|
try:
|
|
237
244
|
proc = subprocess.run(
|
|
238
|
-
cmd, shell=True, capture_output=True, text=True, timeout=
|
|
245
|
+
cmd, shell=True, capture_output=True, text=True, timeout=DEFAULT_COMMAND_TIMEOUT
|
|
239
246
|
)
|
|
240
247
|
out = proc.stdout.strip() or proc.stderr.strip() or "(brak outputu)"
|
|
241
|
-
return proc.returncode == 0, out[:
|
|
248
|
+
return proc.returncode == 0, out[:MAX_OUTPUT_PREVIEW_LENGTH]
|
|
242
249
|
except subprocess.TimeoutExpired:
|
|
243
|
-
return False, "[TIMEOUT
|
|
250
|
+
return False, f"[TIMEOUT {DEFAULT_COMMAND_TIMEOUT}s]"
|
|
244
251
|
except Exception as e:
|
|
245
252
|
return False, f"[WYJĄTEK: {e}]"
|
|
246
253
|
|
|
@@ -299,7 +306,7 @@ class AutonomousSession:
|
|
|
299
306
|
self.fix_count += 1
|
|
300
307
|
|
|
301
308
|
icon = "✅" if ok else "❌"
|
|
302
|
-
print(f" {icon} Wynik: {out[:
|
|
309
|
+
print(f" {icon} Wynik: {out[:MAX_COMMAND_LENGTH]}")
|
|
303
310
|
|
|
304
311
|
# Anonymize before sending to LLM
|
|
305
312
|
anon_out, _ = anonymize(out)
|
|
@@ -310,13 +317,13 @@ class AutonomousSession:
|
|
|
310
317
|
"content": (
|
|
311
318
|
f"Wykonano: `{anon_cmd}`\n"
|
|
312
319
|
f"Sukces: {ok}\n"
|
|
313
|
-
f"Output: {anon_out[:
|
|
320
|
+
f"Output: {anon_out[:MAX_SEARCH_QUERY_LENGTH]}\n"
|
|
314
321
|
f"Zweryfikuj wynik i zaproponuj następną akcję."
|
|
315
322
|
),
|
|
316
323
|
})
|
|
317
324
|
return True
|
|
318
325
|
|
|
319
|
-
def _handle_skip(self, action_data: Dict[str, Any]):
|
|
326
|
+
def _handle_skip(self, action_data: Dict[str, Any]) -> None:
|
|
320
327
|
"""Handle SKIP action."""
|
|
321
328
|
reason = action_data.get("reason", "")
|
|
322
329
|
print(f" ⏭️ Pomijam: {reason}")
|
|
@@ -326,7 +333,7 @@ class AutonomousSession:
|
|
|
326
333
|
})
|
|
327
334
|
self.fix_count += 1
|
|
328
335
|
|
|
329
|
-
def _handle_done(self):
|
|
336
|
+
def _handle_done(self) -> None:
|
|
330
337
|
"""Handle DONE action - session complete."""
|
|
331
338
|
print("\n ✅ Agent zakończył – wszystkie problemy naprawione!")
|
|
332
339
|
|
|
@@ -408,7 +415,7 @@ class AutonomousSession:
|
|
|
408
415
|
self._print_report()
|
|
409
416
|
return self.report
|
|
410
417
|
|
|
411
|
-
def _print_report(self):
|
|
418
|
+
def _print_report(self) -> None:
|
|
412
419
|
"""Print session report."""
|
|
413
420
|
print(f"\n{'═' * UI_BORDER_WIDTH}")
|
|
414
421
|
print(" 📊 RAPORT SESJI AUTONOMICZNEJ")
|
|
@@ -51,16 +51,16 @@ class HITLSession:
|
|
|
51
51
|
self.start_ts = time.time()
|
|
52
52
|
self._setup_timeout()
|
|
53
53
|
|
|
54
|
-
def _setup_timeout(self):
|
|
54
|
+
def _setup_timeout(self) -> None:
|
|
55
55
|
"""Setup session timeout handler."""
|
|
56
56
|
from . import session_io
|
|
57
|
-
def _timeout(signum, frame):
|
|
57
|
+
def _timeout(signum, frame) -> None:
|
|
58
58
|
raise SessionTimeout()
|
|
59
59
|
# Store reference in session_io for reinstatement during user input
|
|
60
60
|
session_io._setup_timeout_ref(self, self.config.session_timeout, _timeout)
|
|
61
61
|
setup_signal_timeout(self.config.session_timeout, _timeout)
|
|
62
62
|
|
|
63
|
-
def _clear_timeout(self):
|
|
63
|
+
def _clear_timeout(self) -> None:
|
|
64
64
|
"""Clear the timeout alarm."""
|
|
65
65
|
cancel_signal_timeout()
|
|
66
66
|
|
|
@@ -93,7 +93,7 @@ class HITLSession:
|
|
|
93
93
|
]
|
|
94
94
|
return True
|
|
95
95
|
|
|
96
|
-
def _print_header(self):
|
|
96
|
+
def _print_header(self) -> None:
|
|
97
97
|
"""Print session header with system info."""
|
|
98
98
|
io.print_session_header(
|
|
99
99
|
self.os_info, self.pkg_manager,
|
|
@@ -191,7 +191,7 @@ class HITLSession:
|
|
|
191
191
|
|
|
192
192
|
self._print_summary()
|
|
193
193
|
|
|
194
|
-
def _print_summary(self):
|
|
194
|
+
def _print_summary(self) -> None:
|
|
195
195
|
"""Print session summary."""
|
|
196
196
|
elapsed = int(time.time() - self.start_ts)
|
|
197
197
|
io.print_session_summary(len(self.messages)-2, elapsed, self.llm.total_tokens, self.executed)
|
|
@@ -9,6 +9,7 @@ from typing import List, Tuple
|
|
|
9
9
|
|
|
10
10
|
from ..constants import (
|
|
11
11
|
MAX_SUMMARY_LENGTH,
|
|
12
|
+
MAX_TECH_TERMS,
|
|
12
13
|
)
|
|
13
14
|
|
|
14
15
|
|
|
@@ -144,6 +145,6 @@ def extract_search_topic(llm_reply: str) -> str:
|
|
|
144
145
|
llm_reply, re.IGNORECASE
|
|
145
146
|
)
|
|
146
147
|
if tech_terms:
|
|
147
|
-
return " ".join(dict.fromkeys(tech_terms[:
|
|
148
|
+
return " ".join(dict.fromkeys(tech_terms[:MAX_TECH_TERMS]))
|
|
148
149
|
first_sentence = llm_reply.split(".")[0][:MAX_SUMMARY_LENGTH]
|
|
149
150
|
return first_sentence or "linux system diagnostics"
|
|
@@ -11,6 +11,9 @@ from ..constants import (
|
|
|
11
11
|
DEFAULT_COMMAND_TIMEOUT,
|
|
12
12
|
FAST_COMMAND_TIMEOUT,
|
|
13
13
|
LONG_COMMAND_TIMEOUT,
|
|
14
|
+
MAX_ANON_PREVIEW_LENGTH,
|
|
15
|
+
MAX_STDERR_PREVIEW_LENGTH,
|
|
16
|
+
MAX_DIRECT_CMD_PREVIEW_LENGTH,
|
|
14
17
|
)
|
|
15
18
|
from ..platform_utils import (
|
|
16
19
|
is_dangerous, is_interactive_blocker, elevate_cmd, run_command,
|
|
@@ -101,7 +104,7 @@ def _sort_fixes_by_priority(fixes: list) -> list:
|
|
|
101
104
|
r"\bflatpak\s+(update|install)\b",
|
|
102
105
|
)
|
|
103
106
|
|
|
104
|
-
def score(item):
|
|
107
|
+
def score(item) -> int:
|
|
105
108
|
cmd = item[0].lower()
|
|
106
109
|
if any(re.search(p, cmd) for p in cleanup_patterns):
|
|
107
110
|
return 0
|
|
@@ -164,8 +167,8 @@ def handle_fix_by_number(
|
|
|
164
167
|
"content": (
|
|
165
168
|
f"Executed: `{cmd}`\n"
|
|
166
169
|
f"Success: {result.ok}\n"
|
|
167
|
-
f"Stdout:\n```\n{anon_out[:
|
|
168
|
-
f"Stderr:\n```\n{anon_err[:
|
|
170
|
+
f"Stdout:\n```\n{anon_out[:MAX_ANON_PREVIEW_LENGTH]}\n```\n"
|
|
171
|
+
f"Stderr:\n```\n{anon_err[:MAX_STDERR_PREVIEW_LENGTH]}\n```\n"
|
|
169
172
|
f"What next?"
|
|
170
173
|
),
|
|
171
174
|
})
|
|
@@ -184,10 +187,10 @@ def handle_direct_command(
|
|
|
184
187
|
cmd = user_in[1:].strip()
|
|
185
188
|
result = run_cmd_fn(cmd, "Komenda użytkownika")
|
|
186
189
|
executed.append(result)
|
|
187
|
-
anon_out, _ = anonymize(result.stdout
|
|
190
|
+
anon_out, _ = anonymize(f"{result.stdout}\n{result.stderr}")
|
|
188
191
|
messages.append({
|
|
189
192
|
"role": "user",
|
|
190
|
-
"content": f"User ran: `{cmd}`\nResult: {anon_out[:
|
|
193
|
+
"content": f"User ran: `{cmd}`\nResult: {anon_out[:MAX_DIRECT_CMD_PREVIEW_LENGTH]}\nWhat next?"
|
|
191
194
|
})
|
|
192
195
|
return True
|
|
193
196
|
|
|
@@ -252,7 +255,7 @@ def run_single_command(cmd: str, comment: str) -> CmdResult:
|
|
|
252
255
|
with io.suspend_timeout():
|
|
253
256
|
ok, stdout, stderr, rc = run_command(cmd, timeout=timeout)
|
|
254
257
|
|
|
255
|
-
io.console.print("\r
|
|
258
|
+
io.console.print(f"\r{' ' * 30}\r", end="")
|
|
256
259
|
result = CmdResult(cmd=cmd, comment=comment, ok=ok,
|
|
257
260
|
stdout=stdout, stderr=stderr, returncode=rc)
|
|
258
261
|
io.print_cmd_result(result)
|
|
@@ -30,7 +30,7 @@ _session_ref = None
|
|
|
30
30
|
|
|
31
31
|
|
|
32
32
|
@contextmanager
|
|
33
|
-
def suspend_timeout():
|
|
33
|
+
def suspend_timeout() -> object:
|
|
34
34
|
"""Context manager to temporarily suspend session timeout during user input."""
|
|
35
35
|
global _timeout_handler, _timeout_seconds, _session_ref
|
|
36
36
|
try:
|
|
@@ -167,7 +167,7 @@ def print_thinking() -> None:
|
|
|
167
167
|
|
|
168
168
|
def clear_thinking() -> None:
|
|
169
169
|
"""Clear the 'Analyzing...' indicator."""
|
|
170
|
-
console.print("\r
|
|
170
|
+
console.print(f"\r{' ' * 30}\r", end="")
|
|
171
171
|
|
|
172
172
|
|
|
173
173
|
def print_llm_reply(reply: str) -> None:
|
|
@@ -2,6 +2,8 @@
|
|
|
2
2
|
Natural language command (ask) for fixOS CLI
|
|
3
3
|
"""
|
|
4
4
|
import click
|
|
5
|
+
import yaml
|
|
6
|
+
import subprocess
|
|
5
7
|
|
|
6
8
|
|
|
7
9
|
@click.command("ask")
|
|
@@ -111,8 +113,6 @@ def _build_output_dict(
|
|
|
111
113
|
|
|
112
114
|
def _execute_heuristic_command(cmd_str: str, prompt: str, dry_run: bool, cfg) -> None:
|
|
113
115
|
"""Execute a heuristic-matched command and output result."""
|
|
114
|
-
import subprocess
|
|
115
|
-
import yaml
|
|
116
116
|
|
|
117
117
|
if dry_run:
|
|
118
118
|
output = _build_output_dict(
|
|
@@ -161,8 +161,6 @@ def _execute_heuristic_command(cmd_str: str, prompt: str, dry_run: bool, cfg) ->
|
|
|
161
161
|
|
|
162
162
|
def _execute_with_llm(prompt: str, dry_run: bool, cfg) -> None:
|
|
163
163
|
"""Generate and execute command using LLM when no heuristic match found."""
|
|
164
|
-
import subprocess
|
|
165
|
-
import yaml
|
|
166
164
|
from fixos.providers.llm import LLMClient
|
|
167
165
|
|
|
168
166
|
llm_provider = f"{cfg.provider}/{cfg.model}"
|
|
@@ -236,7 +234,6 @@ def _handle_natural_command(prompt: str, dry_run: bool = False) -> None:
|
|
|
236
234
|
"""
|
|
237
235
|
Handle natural language commands with heuristic matching and LLM fallback.
|
|
238
236
|
"""
|
|
239
|
-
import yaml
|
|
240
237
|
from fixos.config import FixOsConfig
|
|
241
238
|
|
|
242
239
|
prompt_lower = prompt.lower()
|
|
@@ -268,8 +265,6 @@ def _handle_natural_command(prompt: str, dry_run: bool = False) -> None:
|
|
|
268
265
|
|
|
269
266
|
def _validate_result_with_llm(prompt: str, cmd_str: str, result, cfg) -> None:
|
|
270
267
|
"""Validate command result using LLM - generates check command and assesses outcome."""
|
|
271
|
-
import yaml
|
|
272
|
-
import subprocess
|
|
273
268
|
from fixos.providers.llm import LLMClient
|
|
274
269
|
|
|
275
270
|
try:
|