kolega-code 0.8.2__tar.gz → 0.8.3__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.
- {kolega_code-0.8.2 → kolega_code-0.8.3}/.github/workflows/ci.yml +1 -1
- {kolega_code-0.8.2 → kolega_code-0.8.3}/CONTRIBUTING.md +1 -1
- {kolega_code-0.8.2 → kolega_code-0.8.3}/PKG-INFO +1 -1
- {kolega_code-0.8.2 → kolega_code-0.8.3}/RELEASING.md +1 -1
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/__init__.py +1 -1
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/__init__.py +1 -1
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/app.py +3 -3
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/main.py +36 -7
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/settings.py +18 -0
- kolega_code-0.8.3/kolega_code/cli/tui/styles.tcss +335 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/pyproject.toml +2 -1
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_anthropic_token_counting.py +4 -6
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_chatgpt_live.py +1 -1
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_client.py +8 -17
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_instrumented_client_integration.py +5 -6
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_live_providers.py +1 -1
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_openai_token_counting.py +5 -6
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_commands.py +1 -1
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_prompt_provider.py +1 -1
- {kolega_code-0.8.2/kolega_code/auth/tests → kolega_code-0.8.3/tests/auth}/test_chatgpt_oauth.py +1 -1
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_app.py +8 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_clipboard_image.py +1 -1
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_main.py +59 -2
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_settings.py +29 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_slash_commands.py +2 -2
- kolega_code-0.8.3/tests/cli/test_tui_stylesheet.py +87 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3/tests}/conftest.py +1 -1
- kolega_code-0.8.3/tests/utils/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/uv.lock +5 -5
- kolega_code-0.8.2/kolega_code/cli/tui/styles.py +0 -339
- {kolega_code-0.8.2 → kolega_code-0.8.3}/.env.example +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/.github/workflows/docs.yml +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/.github/workflows/release.yml +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/.gitignore +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/LICENSE +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/README.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/SECURITY.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/.gitignore +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/README.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/astro.config.mjs +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/package-lock.json +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/package.json +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/public/favicon.svg +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/assets/demo.gif +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/assets/kolega-dark.svg +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/assets/kolega-light.svg +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/cli/ask.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/cli/doctor.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/cli/overview.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/cli/sessions.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/concepts/agents.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/concepts/how-it-works.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/concepts/tools.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/configuration/environment-variables.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/configuration/providers-and-models.mdx +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/configuration/settings-and-api-keys.mdx +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/configuration/sign-in-with-chatgpt.mdx +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/getting-started/installation.mdx +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/getting-started/quick-start.mdx +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/gigacode.mdx +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/hooks.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/index.mdx +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/skills.mdx +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/tui/composer.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/tui/interface.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/tui/modes.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/tui/sessions-and-resume.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content/docs/tui/slash-commands.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/content.config.ts +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/src/styles/brand.css +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/docs/tsconfig.json +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/baseagent.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/browseragent.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/coder.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/common.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/compression.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/context.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/conversation.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/errors.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/generalagent.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/investigationagent.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/orchestration/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/orchestration/budget.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/orchestration/errors.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/orchestration/executor.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/orchestration/guide.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/orchestration/journal.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/orchestration/runtime.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/orchestration/types.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/planningagent.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_provider.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/auxiliary/compression/summary.system.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/auxiliary/compression/summary.user.md.j2 +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/auxiliary/terminal/output_summary.system.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/auxiliary/terminal/safety.system.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/auxiliary/tools/think_hard.system.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/extensions/cli/planning_questions.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/extensions/cli/shared_task_list.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/extensions/skills/catalog.md.j2 +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/agents/browser.md.j2 +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/agents/coder_cli.md.j2 +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/agents/general.md.j2 +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/agents/investigation.md.j2 +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/agents/planning.md.j2 +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/includes/agents_md_instructions.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/includes/environment_variables/workspace_env_vars.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/includes/frontend_guidance.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/includes/starter_templates/expo.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/includes/starter_templates/html_website.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/includes/starter_templates/mern_stack.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/system/includes/starter_templates/react_vite_shadcdn.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/user_tasks/cli/implement_plan.md.j2 +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompt_templates/user_tasks/cli/init_agents.md.j2 +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/prompts.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/agent_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/base_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/browser_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/build_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/create_file_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/edit_preview.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/glob_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/list_directory_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/memory_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/read_file_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/read_image_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/replace_entire_file_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/replace_lines_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_and_replace_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_backends/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_backends/base.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_backends/duckduckgo.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_backends/errors.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_backends/firecrawl.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_backends/models.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_backends/searxng.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_backends/tavily.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/search_codebase_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/streaming_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/terminal_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/think_hard_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/web_fetch_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/web_search_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tool_backend/workflow_tool.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/tools.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/agent/utils/commands.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/auth/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/auth/_jwt.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/auth/chatgpt_oauth.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/auth/constants.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/auth/tokens.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/clipboard_image.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/config.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/connection.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/file_index.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/mentions.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/messages.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/provider_registry.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/session_store.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/skills.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/slash_commands.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/theme.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/agent_runtime.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/command_handlers.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/constants.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/prompt_flows.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/settings_panel.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/state.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/status_dashboard.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/sub_agent_screen.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/transcript.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/tui/widgets.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/cli/updater.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/config.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/events.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/hooks/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/hooks/backends.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/hooks/config.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/hooks/dispatcher.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/hooks/events.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/hooks/matcher.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/hooks/outcome.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/client.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/exceptions.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/instrumented_client.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/models.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/orchestration/tests → kolega_code-0.8.3/kolega_code/llm/providers}/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/providers/anthropic.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/providers/base.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/providers/chatgpt_oauth.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/providers/google.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/providers/models.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/providers/openai.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/providers/openai_responses.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/providers/responses_common.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/ratelimit.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/specs.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/llm/tool_execution_ids.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/models/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/models/sandbox_terminal_state.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/permissions.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/runtime.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/README.md +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/async_filesystem.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/base.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/browser.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/event_loop.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/filesystem.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/local.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/serializer.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/terminal.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/sandbox/utils.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/services/base.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/services/browser.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/services/file_system.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/services/html.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/services/terminal.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/services/terminal_buffer.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/tools/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/tools/core.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/tools/definitions.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/tools/registry.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/utils/__init__.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/kolega_code/utils/images.py +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/run_tests.sh +0 -0
- {kolega_code-0.8.2 → kolega_code-0.8.3}/scripts/install-kolega-code.sh +0 -0
- {kolega_code-0.8.2/kolega_code/agent → kolega_code-0.8.3}/tests/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests/llm → kolega_code-0.8.3/tests/agent}/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/compaction_helpers.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests/tool_backend → kolega_code-0.8.3/tests/agent/llm}/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_billing_openai_cache.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_chatgpt_oauth_provider.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_dashscope_mapping.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_error_boundary.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_exceptions.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_google_thought_signature.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_google_tool_signature_live.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_instrumented_client.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_langfuse_normalization.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_model_specs.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_openai_cached_tokens.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_openai_cached_tokens_stream.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_openai_message_conversion.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_openai_responses_provider.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_supports_vision.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_thinking_effort.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_tool_execution_ids.py +0 -0
- {kolega_code-0.8.2/kolega_code/auth/tests → kolega_code-0.8.3/tests/agent/orchestration}/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/orchestration/tests → kolega_code-0.8.3/tests/agent/orchestration}/test_orchestration.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/services/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/services/test_browser.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/services/test_browser_parity.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/services/test_file_system.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/services/test_sandbox_terminal_input.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/services/test_terminal.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/services/test_terminal_buffer.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/services/test_terminal_state_serializer.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_agent_tools_inventory.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_base_agent.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_coder_attachments.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_coder_prompt_extensions.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_compaction_integration.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_compaction_persistence.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_compaction_subagent.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_compaction_tui_events.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_compress_command.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_compression.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_conversation_compaction.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_duplicate_tool_results.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_empty_message_handling.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_event_emitter.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_general_agent.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_gigacode_gating.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_hooks_integration.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_html.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_image_compat.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_parallel_tool_calls.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_permissions.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_planning_agent.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_prompts.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_read_image_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_tool_registry.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/test_tools.py +0 -0
- {kolega_code-0.8.2/kolega_code/hooks/tests → kolega_code-0.8.3/tests/agent/tool_backend}/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_agent_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_base_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_browser_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_build_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_create_file_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_edit_preview.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_glob_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_glob_tool_sandbox_parity.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_list_directory_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_read_file_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_replace_entire_file_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_replace_lines_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_search_and_replace_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_search_codebase_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_terminal_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_think_hard_integration.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_think_hard_streaming.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_web_fetch_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_web_search_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/tool_backend/test_workflow_tool.py +0 -0
- {kolega_code-0.8.2/kolega_code/llm/providers → kolega_code-0.8.3/tests/auth}/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/auth/tests → kolega_code-0.8.3/tests/auth}/test_tokens.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_app_compaction_restore.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_app_image_vision_warning.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_app_model_switch_vision.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_cli_config.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_connection.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_file_index.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_mentions.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_provider_registry.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_session_store.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_skills.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_themes.py +0 -0
- {kolega_code-0.8.2/kolega_code/cli/tests → kolega_code-0.8.3/tests/cli}/test_updater.py +0 -0
- {kolega_code-0.8.2/kolega_code/tools/tests → kolega_code-0.8.3/tests/hooks}/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/hooks/tests → kolega_code-0.8.3/tests/hooks}/test_hooks.py +0 -0
- {kolega_code-0.8.2/kolega_code/utils/tests → kolega_code-0.8.3/tests/tools}/__init__.py +0 -0
- {kolega_code-0.8.2/kolega_code/tools/tests → kolega_code-0.8.3/tests/tools}/test_definitions.py +0 -0
- {kolega_code-0.8.2/kolega_code/utils/tests → kolega_code-0.8.3/tests/utils}/test_images.py +0 -0
- {kolega_code-0.8.2/kolega_code/utils/tests → kolega_code-0.8.3/tests/utils}/test_images_ascii.py +0 -0
|
@@ -46,7 +46,7 @@ Run slow and integration tests only when you have the required credentials:
|
|
|
46
46
|
You can pass additional pytest arguments through the wrapper:
|
|
47
47
|
|
|
48
48
|
```bash
|
|
49
|
-
./run_tests.sh
|
|
49
|
+
./run_tests.sh tests/agent/llm/test_client.py -ra
|
|
50
50
|
```
|
|
51
51
|
|
|
52
52
|
## Documentation
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: kolega-code
|
|
3
|
-
Version: 0.8.
|
|
3
|
+
Version: 0.8.3
|
|
4
4
|
Summary: Local-first AI coding agent for the terminal
|
|
5
5
|
Project-URL: Homepage, https://kolega-ai.github.io/kolega-code/
|
|
6
6
|
Project-URL: Documentation, https://kolega-ai.github.io/kolega-code/
|
|
@@ -86,7 +86,6 @@ from .tui import state as tui_state
|
|
|
86
86
|
from .tui import sub_agent_screen as tui_sub_agents
|
|
87
87
|
from .tui import transcript as tui_transcript
|
|
88
88
|
from .tui import widgets as tui_widgets
|
|
89
|
-
from .tui.styles import APP_CSS
|
|
90
89
|
|
|
91
90
|
CLI_AGENT_MODE = AgentMode.CLI.value
|
|
92
91
|
LOG_MAX_LINES = 10_000
|
|
@@ -106,8 +105,7 @@ class KolegaCodeApp(
|
|
|
106
105
|
):
|
|
107
106
|
"""Interactive terminal UI for Kolega Code."""
|
|
108
107
|
|
|
109
|
-
|
|
110
|
-
|
|
108
|
+
CSS_PATH = "tui/styles.tcss"
|
|
111
109
|
|
|
112
110
|
BINDINGS = [
|
|
113
111
|
Binding(
|
|
@@ -978,7 +976,9 @@ class KolegaCodeApp(
|
|
|
978
976
|
|
|
979
977
|
self.permission_mode = mode
|
|
980
978
|
self.session.permission_mode = mode.value
|
|
979
|
+
self.settings.permission_mode = mode.value
|
|
981
980
|
await self._save_session_async()
|
|
981
|
+
await asyncio.to_thread(self.settings_store.save, self.settings)
|
|
982
982
|
if self.agent is not None:
|
|
983
983
|
self.agent.set_permission_mode(mode)
|
|
984
984
|
self.agent.set_permission_callback(self._permission_callback)
|
|
@@ -36,7 +36,7 @@ from .config import (
|
|
|
36
36
|
from .connection import CliConnectionManager
|
|
37
37
|
from .mentions import build_file_attachments
|
|
38
38
|
from .session_store import SessionRecord, SessionStore, SessionStoreError
|
|
39
|
-
from .settings import SettingsStore, SettingsStoreError
|
|
39
|
+
from .settings import CliSettings, SettingsStore, SettingsStoreError
|
|
40
40
|
from .slash_commands import SKILLS_LIST_COMMAND, agent_command_names
|
|
41
41
|
from .skills import (
|
|
42
42
|
SkillCatalog,
|
|
@@ -327,6 +327,32 @@ def _resolve_tui_session(
|
|
|
327
327
|
return store.create(project_path, CLI_AGENT_MODE, summary)
|
|
328
328
|
|
|
329
329
|
|
|
330
|
+
def _safe_permission_mode_value(value: Optional[str]) -> str:
|
|
331
|
+
try:
|
|
332
|
+
return normalize_permission_mode(value, default=PermissionMode.ASK).value
|
|
333
|
+
except ValueError:
|
|
334
|
+
return PermissionMode.ASK.value
|
|
335
|
+
|
|
336
|
+
|
|
337
|
+
def _resolve_tui_permission_mode(
|
|
338
|
+
session: SessionRecord,
|
|
339
|
+
settings: CliSettings,
|
|
340
|
+
requested_permission_mode: Optional[str],
|
|
341
|
+
*,
|
|
342
|
+
resumed: bool,
|
|
343
|
+
) -> str:
|
|
344
|
+
"""Resolve the TUI permission mode for this launch.
|
|
345
|
+
|
|
346
|
+
Precedence: explicit CLI flag, resumed session value, then global setting for
|
|
347
|
+
new sessions. Invalid legacy values fall back to ask.
|
|
348
|
+
"""
|
|
349
|
+
if requested_permission_mode:
|
|
350
|
+
return normalize_permission_mode(requested_permission_mode, default=PermissionMode.ASK).value
|
|
351
|
+
if resumed:
|
|
352
|
+
return _safe_permission_mode_value(session.permission_mode)
|
|
353
|
+
return _safe_permission_mode_value(settings.permission_mode)
|
|
354
|
+
|
|
355
|
+
|
|
330
356
|
def _run_version() -> int:
|
|
331
357
|
result = check_for_update()
|
|
332
358
|
print(f"kolega-code {result.current_version}")
|
|
@@ -374,11 +400,14 @@ def _run_tui(args: argparse.Namespace) -> int:
|
|
|
374
400
|
args.resume,
|
|
375
401
|
args.session,
|
|
376
402
|
)
|
|
377
|
-
|
|
378
|
-
session
|
|
379
|
-
|
|
380
|
-
|
|
381
|
-
)
|
|
403
|
+
effective_permission_mode = _resolve_tui_permission_mode(
|
|
404
|
+
session,
|
|
405
|
+
settings,
|
|
406
|
+
args.permission_mode,
|
|
407
|
+
resumed=args.resume is not None or bool(args.session),
|
|
408
|
+
)
|
|
409
|
+
if session.permission_mode != effective_permission_mode:
|
|
410
|
+
session.permission_mode = effective_permission_mode
|
|
382
411
|
store.save(session)
|
|
383
412
|
|
|
384
413
|
from .app import KolegaCodeApp
|
|
@@ -391,7 +420,7 @@ def _run_tui(args: argparse.Namespace) -> int:
|
|
|
391
420
|
settings_store=settings_store,
|
|
392
421
|
overrides=_overrides_from_args(args),
|
|
393
422
|
session=session,
|
|
394
|
-
permission_mode=
|
|
423
|
+
permission_mode=effective_permission_mode,
|
|
395
424
|
browser_visible=args.browser_visible,
|
|
396
425
|
check_for_updates=True,
|
|
397
426
|
show_logs=args.show_logs,
|
|
@@ -8,6 +8,8 @@ from dataclasses import dataclass, field
|
|
|
8
8
|
from pathlib import Path
|
|
9
9
|
from typing import Optional
|
|
10
10
|
|
|
11
|
+
from kolega_code.permissions import PermissionMode
|
|
12
|
+
|
|
11
13
|
from .session_store import default_state_dir
|
|
12
14
|
|
|
13
15
|
SETTINGS_SCHEMA_VERSION = 3
|
|
@@ -59,6 +61,16 @@ def _coerce_oauth_tokens(raw: object) -> dict[str, dict]:
|
|
|
59
61
|
return result
|
|
60
62
|
|
|
61
63
|
|
|
64
|
+
def _coerce_permission_mode(raw: object) -> str:
|
|
65
|
+
"""Normalize a stored permission mode, falling back safely for old/bad files."""
|
|
66
|
+
if raw is None:
|
|
67
|
+
return PermissionMode.ASK.value
|
|
68
|
+
try:
|
|
69
|
+
return PermissionMode(str(raw).lower()).value
|
|
70
|
+
except ValueError:
|
|
71
|
+
return PermissionMode.ASK.value
|
|
72
|
+
|
|
73
|
+
|
|
62
74
|
@dataclass
|
|
63
75
|
class CliSettings:
|
|
64
76
|
active_provider: Optional[str] = None
|
|
@@ -83,6 +95,9 @@ class CliSettings:
|
|
|
83
95
|
# field — absent in older files -> empty mapping, no schema bump (same
|
|
84
96
|
# convention as web_search_backend / active_theme).
|
|
85
97
|
oauth_tokens: dict[str, dict] = field(default_factory=dict)
|
|
98
|
+
# Global default for new TUI sessions. Resumed sessions keep their own
|
|
99
|
+
# SessionRecord.permission_mode unless a CLI override is supplied.
|
|
100
|
+
permission_mode: str = PermissionMode.ASK.value
|
|
86
101
|
schema_version: int = SETTINGS_SCHEMA_VERSION
|
|
87
102
|
|
|
88
103
|
@classmethod
|
|
@@ -109,6 +124,8 @@ class CliSettings:
|
|
|
109
124
|
web_search_base_url=data.get("web_search_base_url"),
|
|
110
125
|
# Additive optional field; absent in older files -> empty mapping.
|
|
111
126
|
oauth_tokens=_coerce_oauth_tokens(data.get("oauth_tokens")),
|
|
127
|
+
# Additive optional field; absent in older files -> ask.
|
|
128
|
+
permission_mode=_coerce_permission_mode(data.get("permission_mode")),
|
|
112
129
|
)
|
|
113
130
|
|
|
114
131
|
def to_dict(self) -> dict:
|
|
@@ -124,6 +141,7 @@ class CliSettings:
|
|
|
124
141
|
"web_search_backend": self.web_search_backend,
|
|
125
142
|
"web_search_base_url": self.web_search_base_url,
|
|
126
143
|
"oauth_tokens": self.oauth_tokens,
|
|
144
|
+
"permission_mode": _coerce_permission_mode(self.permission_mode),
|
|
127
145
|
}
|
|
128
146
|
|
|
129
147
|
def get_api_key(self, provider: str) -> Optional[str]:
|
|
@@ -0,0 +1,335 @@
|
|
|
1
|
+
Screen {
|
|
2
|
+
layout: vertical;
|
|
3
|
+
}
|
|
4
|
+
|
|
5
|
+
#body {
|
|
6
|
+
height: 1fr;
|
|
7
|
+
}
|
|
8
|
+
|
|
9
|
+
#conversation_panel {
|
|
10
|
+
width: 2fr;
|
|
11
|
+
height: 100%;
|
|
12
|
+
}
|
|
13
|
+
|
|
14
|
+
#side_panel {
|
|
15
|
+
width: 1fr;
|
|
16
|
+
min-width: 34;
|
|
17
|
+
height: 100%;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
#conversation, #logs, #terminal {
|
|
21
|
+
height: 1fr;
|
|
22
|
+
border: round $surface;
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
ConversationEntryWidget {
|
|
26
|
+
height: auto;
|
|
27
|
+
padding-bottom: 1;
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
ToolEntryWidget {
|
|
31
|
+
height: auto;
|
|
32
|
+
padding-bottom: 1;
|
|
33
|
+
}
|
|
34
|
+
|
|
35
|
+
ToolEntryWidget Collapsible {
|
|
36
|
+
background: transparent;
|
|
37
|
+
border-top: none;
|
|
38
|
+
padding-bottom: 0;
|
|
39
|
+
padding-left: 0;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
ToolEntryWidget Collapsible Contents {
|
|
43
|
+
padding-left: 3;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
ToolEntryWidget .tool-body {
|
|
47
|
+
color: $text-muted;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
#jump_to_bottom {
|
|
51
|
+
display: none;
|
|
52
|
+
height: 1;
|
|
53
|
+
padding: 0 1;
|
|
54
|
+
background: $surface;
|
|
55
|
+
color: $text-muted;
|
|
56
|
+
text-align: center;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
#status_container {
|
|
60
|
+
height: 1fr;
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
#status_dashboard {
|
|
64
|
+
height: 1fr;
|
|
65
|
+
min-height: 15;
|
|
66
|
+
border: round $surface;
|
|
67
|
+
padding: 1;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
#settings_form, #planning_form {
|
|
71
|
+
height: 1fr;
|
|
72
|
+
padding: 1;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
.settings-section {
|
|
76
|
+
height: auto;
|
|
77
|
+
border: round $surface;
|
|
78
|
+
border-title-color: $text;
|
|
79
|
+
border-title-style: bold;
|
|
80
|
+
padding: 0 1;
|
|
81
|
+
margin-bottom: 1;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
#settings_status {
|
|
85
|
+
margin-top: 1;
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
#settings_form Label {
|
|
89
|
+
margin-top: 1;
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
#settings_form Button {
|
|
93
|
+
margin-top: 1;
|
|
94
|
+
}
|
|
95
|
+
|
|
96
|
+
.settings-hint {
|
|
97
|
+
color: $text-muted;
|
|
98
|
+
margin-top: 0;
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
.agent-model-group {
|
|
102
|
+
height: auto;
|
|
103
|
+
margin-top: 1;
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
.agent-model-role {
|
|
107
|
+
text-style: bold;
|
|
108
|
+
color: $text;
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
.agent-model-field {
|
|
112
|
+
height: auto;
|
|
113
|
+
margin-top: 1;
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
.agent-model-field-label {
|
|
117
|
+
width: 10;
|
|
118
|
+
margin-top: 1;
|
|
119
|
+
color: $text-muted;
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
.agent-model-field Select {
|
|
123
|
+
width: 1fr;
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
#settings_actions {
|
|
127
|
+
height: auto;
|
|
128
|
+
padding: 0 1;
|
|
129
|
+
margin-top: 1;
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
#planning_form Markdown.empty-state {
|
|
133
|
+
color: $text-muted;
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
#composer {
|
|
137
|
+
dock: bottom;
|
|
138
|
+
height: 5;
|
|
139
|
+
border: round $surface;
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
#turn_status {
|
|
143
|
+
display: none;
|
|
144
|
+
height: 1;
|
|
145
|
+
padding: 0 1;
|
|
146
|
+
color: $text-muted;
|
|
147
|
+
background: $surface;
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
#composer_hint_row {
|
|
151
|
+
display: none;
|
|
152
|
+
height: auto;
|
|
153
|
+
max-height: 4;
|
|
154
|
+
background: $surface;
|
|
155
|
+
}
|
|
156
|
+
|
|
157
|
+
#composer_hint_row #composer_hint {
|
|
158
|
+
width: 1fr;
|
|
159
|
+
height: auto;
|
|
160
|
+
padding: 0 1;
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
#composer_hint_row #detach_btn {
|
|
164
|
+
width: 3;
|
|
165
|
+
height: 1;
|
|
166
|
+
min-height: 1;
|
|
167
|
+
border: none;
|
|
168
|
+
background: transparent;
|
|
169
|
+
color: $text-muted;
|
|
170
|
+
padding: 0 1;
|
|
171
|
+
}
|
|
172
|
+
|
|
173
|
+
#composer_hint_row #detach_btn:hover {
|
|
174
|
+
color: $warning;
|
|
175
|
+
}
|
|
176
|
+
|
|
177
|
+
#composer_hint_row #detach_btn:focus {
|
|
178
|
+
color: $warning;
|
|
179
|
+
text-style: bold;
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
#completion_dropdown {
|
|
183
|
+
display: none;
|
|
184
|
+
height: auto;
|
|
185
|
+
max-height: 10;
|
|
186
|
+
border: round $surface;
|
|
187
|
+
background: $surface;
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
#composer_hint.hint-warning {
|
|
191
|
+
color: $warning;
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
#composer_hint.hint-info {
|
|
195
|
+
color: $text-muted;
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
#composer:disabled {
|
|
199
|
+
opacity: 0.6;
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
#plan_actions, #model_actions, #effort_actions, #theme_actions {
|
|
203
|
+
display: none;
|
|
204
|
+
height: auto;
|
|
205
|
+
max-height: 12;
|
|
206
|
+
border: round $surface;
|
|
207
|
+
background: $surface;
|
|
208
|
+
}
|
|
209
|
+
|
|
210
|
+
/* Question / approval prompts: the question is folded into the panel header
|
|
211
|
+
(the border title) above its options, so the whole prompt reads as one
|
|
212
|
+
bordered unit. The inner ActionList drops its own border. */
|
|
213
|
+
#question_prompt, #approval_prompt {
|
|
214
|
+
display: none;
|
|
215
|
+
height: auto;
|
|
216
|
+
max-height: 14;
|
|
217
|
+
border: round $surface;
|
|
218
|
+
background: $surface;
|
|
219
|
+
border-title-color: $text;
|
|
220
|
+
border-title-style: bold;
|
|
221
|
+
padding: 0 1;
|
|
222
|
+
}
|
|
223
|
+
|
|
224
|
+
#question_prompt > .prompt-header-scroll, #approval_prompt > .prompt-header-scroll {
|
|
225
|
+
height: auto;
|
|
226
|
+
max-height: 6;
|
|
227
|
+
overflow-y: auto;
|
|
228
|
+
background: $surface;
|
|
229
|
+
}
|
|
230
|
+
|
|
231
|
+
#question_prompt > ActionList, #approval_prompt > ActionList {
|
|
232
|
+
border: none;
|
|
233
|
+
background: $surface;
|
|
234
|
+
height: auto;
|
|
235
|
+
max-height: 6;
|
|
236
|
+
padding: 0;
|
|
237
|
+
}
|
|
238
|
+
|
|
239
|
+
.prompt-header {
|
|
240
|
+
height: auto;
|
|
241
|
+
padding: 0 0 1 0;
|
|
242
|
+
background: $surface;
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
/* Neutralize the selected-row highlight on every choice list. Textual paints
|
|
246
|
+
it with $block-cursor-background (= $primary, a saturated brand color),
|
|
247
|
+
which clashes with the otherwise-neutral chrome and looks wrong in 256-color
|
|
248
|
+
Terminal.app. Each theme pins $surface-lighten-2 to a near-neutral gray
|
|
249
|
+
(see theme.build_textual_theme) so the highlight stays subtle across all
|
|
250
|
+
themes — incl. Solarized, whose auto-derived $surface-lighten-2 would
|
|
251
|
+
otherwise quantize to a saturated teal. The OptionList type selector also
|
|
252
|
+
covers its subclasses: ActionList, CompletionDropdown, and the Select's
|
|
253
|
+
SelectOverlay dropdown. */
|
|
254
|
+
OptionList > .option-list--option-highlighted {
|
|
255
|
+
background: $surface-lighten-2;
|
|
256
|
+
color: $text;
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
.meta {
|
|
260
|
+
color: $text-muted;
|
|
261
|
+
}
|
|
262
|
+
|
|
263
|
+
Footer {
|
|
264
|
+
background: $surface;
|
|
265
|
+
}
|
|
266
|
+
|
|
267
|
+
Input {
|
|
268
|
+
border: round $surface;
|
|
269
|
+
}
|
|
270
|
+
|
|
271
|
+
Input:focus {
|
|
272
|
+
border: round $surface-lighten-2;
|
|
273
|
+
}
|
|
274
|
+
|
|
275
|
+
Select > SelectCurrent {
|
|
276
|
+
border: round $surface;
|
|
277
|
+
}
|
|
278
|
+
|
|
279
|
+
Select:focus > SelectCurrent {
|
|
280
|
+
border: round $surface-lighten-2;
|
|
281
|
+
}
|
|
282
|
+
|
|
283
|
+
Select > SelectOverlay {
|
|
284
|
+
border: round $surface;
|
|
285
|
+
}
|
|
286
|
+
|
|
287
|
+
SubAgentInspectorScreen {
|
|
288
|
+
align: center middle;
|
|
289
|
+
}
|
|
290
|
+
|
|
291
|
+
SubAgentInspectorScreen #inspector_body {
|
|
292
|
+
width: 100%;
|
|
293
|
+
height: 1fr;
|
|
294
|
+
}
|
|
295
|
+
|
|
296
|
+
SubAgentInspectorScreen #inspector_roster {
|
|
297
|
+
width: 40;
|
|
298
|
+
height: 100%;
|
|
299
|
+
border: round $surface;
|
|
300
|
+
padding: 0 1;
|
|
301
|
+
}
|
|
302
|
+
|
|
303
|
+
SubAgentInspectorScreen #inspector_main {
|
|
304
|
+
width: 1fr;
|
|
305
|
+
height: 100%;
|
|
306
|
+
}
|
|
307
|
+
|
|
308
|
+
SubAgentInspectorScreen #inspector_header {
|
|
309
|
+
height: auto;
|
|
310
|
+
border: round $surface;
|
|
311
|
+
padding: 0 1;
|
|
312
|
+
}
|
|
313
|
+
|
|
314
|
+
SubAgentInspectorScreen #inspector_trajectory {
|
|
315
|
+
height: 1fr;
|
|
316
|
+
border: round $surface;
|
|
317
|
+
padding: 0 1;
|
|
318
|
+
}
|
|
319
|
+
|
|
320
|
+
SubAgentRosterRow {
|
|
321
|
+
height: auto;
|
|
322
|
+
padding: 0 0 1 0;
|
|
323
|
+
}
|
|
324
|
+
|
|
325
|
+
SubAgentInspectorScreen .inspector-empty {
|
|
326
|
+
color: $text-muted;
|
|
327
|
+
padding: 1;
|
|
328
|
+
}
|
|
329
|
+
|
|
330
|
+
SubAgentInspectorScreen #inspector_footer {
|
|
331
|
+
height: 1;
|
|
332
|
+
padding: 0 1;
|
|
333
|
+
background: $surface;
|
|
334
|
+
color: $text-muted;
|
|
335
|
+
}
|
|
@@ -4,7 +4,7 @@ build-backend = "hatchling.build"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "kolega-code"
|
|
7
|
-
version = "0.8.
|
|
7
|
+
version = "0.8.3"
|
|
8
8
|
description = "Local-first AI coding agent for the terminal"
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
license = {file = "LICENSE"}
|
|
@@ -73,6 +73,7 @@ kolega-code = "kolega_code.cli.main:main"
|
|
|
73
73
|
packages = ["kolega_code"]
|
|
74
74
|
|
|
75
75
|
[tool.pytest.ini_options]
|
|
76
|
+
testpaths = ["tests"]
|
|
76
77
|
asyncio_mode = "strict"
|
|
77
78
|
asyncio_default_fixture_loop_scope = "function"
|
|
78
79
|
markers = [
|
|
@@ -21,12 +21,10 @@ from kolega_code.llm.providers.anthropic import AnthropicProvider
|
|
|
21
21
|
from kolega_code.agent.prompt_provider import AgentMode, AgentType, PromptContext, PromptProvider
|
|
22
22
|
from kolega_code.agent.tools import ToolCollection, ToolCollectionConfig
|
|
23
23
|
|
|
24
|
-
# Load environment variables
|
|
25
|
-
|
|
26
|
-
dotenv_path =
|
|
27
|
-
|
|
28
|
-
)
|
|
29
|
-
if os.path.exists(dotenv_path):
|
|
24
|
+
# Load environment variables from the repository root.
|
|
25
|
+
REPO_ROOT = Path(__file__).resolve().parents[3]
|
|
26
|
+
dotenv_path = REPO_ROOT / ".env"
|
|
27
|
+
if dotenv_path.exists():
|
|
30
28
|
load_dotenv(dotenv_path)
|
|
31
29
|
|
|
32
30
|
|
{kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_chatgpt_live.py
RENAMED
|
@@ -4,7 +4,7 @@ Unlike the key-based providers, this one needs OAuth tokens from an interactive
|
|
|
4
4
|
``/login``. It is skipped unless real tokens are available, so it never runs in
|
|
5
5
|
CI. To run it locally after signing in via the TUI::
|
|
6
6
|
|
|
7
|
-
pytest -m integration
|
|
7
|
+
pytest -m integration tests/agent/llm/test_chatgpt_live.py -v
|
|
8
8
|
|
|
9
9
|
Token source (first match wins):
|
|
10
10
|
- KOLEGA_CODE_CHATGPT_TOKENS env var holding the JSON of an OAuthTokens dump, or
|
{kolega_code-0.8.2/kolega_code/agent/tests → kolega_code-0.8.3/tests/agent}/llm/test_client.py
RENAMED
|
@@ -1,13 +1,16 @@
|
|
|
1
1
|
import asyncio
|
|
2
2
|
import os
|
|
3
|
+
from pathlib import Path
|
|
3
4
|
from unittest.mock import AsyncMock, patch
|
|
4
5
|
|
|
5
6
|
import pytest
|
|
6
7
|
from dotenv import load_dotenv
|
|
7
8
|
|
|
8
|
-
# Load environment variables directly at module level
|
|
9
|
-
|
|
10
|
-
|
|
9
|
+
# Load repository-local environment variables directly at module level.
|
|
10
|
+
REPO_ROOT = Path(__file__).resolve().parents[3]
|
|
11
|
+
|
|
12
|
+
dotenv_path = REPO_ROOT / ".env"
|
|
13
|
+
if dotenv_path.exists():
|
|
11
14
|
print(f"Loading environment variables from: {dotenv_path}")
|
|
12
15
|
load_dotenv(dotenv_path)
|
|
13
16
|
print(f"ANTHROPIC_API_KEY present: {bool(os.getenv('ANTHROPIC_API_KEY'))}")
|
|
@@ -18,24 +21,12 @@ else:
|
|
|
18
21
|
print(f"Warning: .env file not found at {dotenv_path}")
|
|
19
22
|
print("Tests requiring API keys may be skipped.")
|
|
20
23
|
|
|
21
|
-
backend_env_local_path =
|
|
22
|
-
|
|
23
|
-
".env.local",
|
|
24
|
-
)
|
|
25
|
-
if os.path.exists(backend_env_local_path):
|
|
24
|
+
backend_env_local_path = REPO_ROOT / ".env.local"
|
|
25
|
+
if backend_env_local_path.exists():
|
|
26
26
|
print(f"Loading environment variables from: {backend_env_local_path}")
|
|
27
27
|
load_dotenv(backend_env_local_path)
|
|
28
28
|
print(f"MOONSHOT_API_KEY present: {bool(os.getenv('MOONSHOT_API_KEY'))}")
|
|
29
29
|
|
|
30
|
-
backend_env_path = os.path.join(
|
|
31
|
-
os.path.dirname(os.path.dirname(os.path.dirname(os.path.dirname(os.path.dirname(__file__))))),
|
|
32
|
-
".env",
|
|
33
|
-
)
|
|
34
|
-
if os.path.exists(backend_env_path):
|
|
35
|
-
print(f"Loading environment variables from: {backend_env_path}")
|
|
36
|
-
load_dotenv(backend_env_path)
|
|
37
|
-
print(f"MOONSHOT_API_KEY present: {bool(os.getenv('MOONSHOT_API_KEY'))}")
|
|
38
|
-
|
|
39
30
|
from kolega_code.llm.client import (
|
|
40
31
|
GenerationParams,
|
|
41
32
|
LLMClient,
|
|
@@ -8,6 +8,7 @@ and Langfuse tracing.
|
|
|
8
8
|
|
|
9
9
|
import asyncio
|
|
10
10
|
import os
|
|
11
|
+
from pathlib import Path
|
|
11
12
|
from unittest.mock import Mock
|
|
12
13
|
|
|
13
14
|
import pytest
|
|
@@ -18,12 +19,10 @@ from opentelemetry.sdk.trace import TracerProvider as _OtelTracerProvider
|
|
|
18
19
|
from kolega_code.llm.instrumented_client import InstrumentedLLMClient
|
|
19
20
|
from kolega_code.llm.models import Message, MessageHistory, TextBlock, ToolCall
|
|
20
21
|
|
|
21
|
-
# Load environment variables
|
|
22
|
-
|
|
23
|
-
dotenv_path =
|
|
24
|
-
|
|
25
|
-
)
|
|
26
|
-
if os.path.exists(dotenv_path):
|
|
22
|
+
# Load environment variables from the repository root.
|
|
23
|
+
REPO_ROOT = Path(__file__).resolve().parents[3]
|
|
24
|
+
dotenv_path = REPO_ROOT / ".env"
|
|
25
|
+
if dotenv_path.exists():
|
|
27
26
|
print(f"Loading environment variables from: {dotenv_path}")
|
|
28
27
|
load_dotenv(dotenv_path)
|
|
29
28
|
print(f"ANTHROPIC_API_KEY present: {bool(os.getenv('ANTHROPIC_API_KEY'))}")
|
|
@@ -8,7 +8,7 @@ retired ID surfaces here as a 4xx instead of silently shipping.
|
|
|
8
8
|
|
|
9
9
|
Run them explicitly with the relevant keys set, e.g.::
|
|
10
10
|
|
|
11
|
-
pytest -m integration
|
|
11
|
+
pytest -m integration tests/agent/llm/test_live_providers.py -v
|
|
12
12
|
|
|
13
13
|
The provider/model matrix is derived from the catalog itself, so new models are
|
|
14
14
|
covered automatically.
|
|
@@ -6,6 +6,7 @@ of OpenAI's official API token counting, using real system prompts and tool defi
|
|
|
6
6
|
"""
|
|
7
7
|
|
|
8
8
|
import os
|
|
9
|
+
from pathlib import Path
|
|
9
10
|
from unittest.mock import Mock
|
|
10
11
|
|
|
11
12
|
import pytest
|
|
@@ -25,12 +26,10 @@ from kolega_code.llm.providers.openai import OpenAIProvider
|
|
|
25
26
|
from kolega_code.agent.prompt_provider import AgentMode, AgentType, PromptContext, PromptProvider
|
|
26
27
|
from kolega_code.agent.tools import ToolCollection, ToolCollectionConfig
|
|
27
28
|
|
|
28
|
-
# Load environment variables
|
|
29
|
-
|
|
30
|
-
dotenv_path =
|
|
31
|
-
|
|
32
|
-
)
|
|
33
|
-
if os.path.exists(dotenv_path):
|
|
29
|
+
# Load environment variables from the repository root.
|
|
30
|
+
REPO_ROOT = Path(__file__).resolve().parents[3]
|
|
31
|
+
dotenv_path = REPO_ROOT / ".env"
|
|
32
|
+
if dotenv_path.exists():
|
|
34
33
|
load_dotenv(dotenv_path)
|
|
35
34
|
|
|
36
35
|
|