dreadnode 2.0.20__tar.gz → 2.0.21__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.
- {dreadnode-2.0.20 → dreadnode-2.0.21}/PKG-INFO +1 -1
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/drattack.py +4 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/api/models.py +6 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/airt.py +135 -18
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/client/models.py +9 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/config.py +9 -1
- dreadnode-2.0.21/dreadnode/app/env.py +291 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/app.py +33 -12
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/runtime_events.py +1 -1
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/app.py +12 -9
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/command_dispatcher.py +2 -1
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screen_router.py +34 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/capabilities.py +8 -1
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/workspaces.py +26 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/sessions_manager.py +43 -26
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/turn_reducer.py +23 -24
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/context_bar.py +13 -6
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/prompt_info.py +3 -3
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/tool.py +22 -7
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/models.py +29 -2
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/utils.py +36 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/judge.py +11 -5
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/__init__.py +4 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/pyproject.toml +1 -1
- dreadnode-2.0.20/dreadnode/app/env.py +0 -101
- {dreadnode-2.0.20 → dreadnode-2.0.21}/.gitignore +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/LICENSE +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/README.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/__main__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/agent.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/events.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/exceptions.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/format.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/hooks.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/judge.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/mcp/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/mcp/auth.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/mcp/client.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/mcp/config.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/mcp/server.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/process_judge.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/reactions.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/skills.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/stopping.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/subagent.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/tool_resolution.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/tools.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/agents/trajectory.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/adversarial_reasoning.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/advpromptier.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/alignment_faking.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/analogy_escalation.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/analytics/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/analytics/aggregator.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/analytics/classifier.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/analytics/compliance.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/analytics/engine.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/analytics/recommendations.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/analytics/types.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/aprt_progressive.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/assessment.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/attention_shifting.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/autodan_turbo.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/autoredteamer.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/beast.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/compliance/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/compliance/atlas.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/compliance/nist.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/compliance/owasp.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/compliance/owasp_agentic.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/compliance/saif.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/constants.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/cot_jailbreak.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/crescendo.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/assets/audio/adversarial_query.mp3 +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/assets/image/bomb.jpg +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/assets/image/meth.png +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/prompts/adversarial_benchmark_subset.csv +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/prompts/ai_safety.csv +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/data_exfiltration.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/goal_hijacking.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/memory_poisoning.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/privilege_escalation.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/rce.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/scope_creep.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/tool_chaining.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/tool_selection_safety.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/unbounded_agency.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/rubrics/web_chatbot_security.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/templates/crescendo/variant_1.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/templates/crescendo/variant_2.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/templates/crescendo/variant_3.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/templates/crescendo/variant_4.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/data/templates/crescendo/variant_5.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/deep_inception.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/echo_chamber.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/events.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/genetic_persona.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/goat.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/goat_v2.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/gptfuzzer.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/humor_bypass.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/image.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/j2_meta.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/jbdistill.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/jbfuzz.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/lrm_autonomous.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/mapf.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/multimodal.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/nexus.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/pair.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/persona_hijack.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/prompt.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/quantization_safety.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/rainbow.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/refusal_aware.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/renellm.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/reporting/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/reporting/json_report.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/reporting/llm_summary.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/reporting/markdown.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/reward_hacking.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/salami_slicing.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/self_persuasion.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/siren.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/tap.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/templatefuzz.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/tmap_trajectory.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/trojail.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/airt/watermark_removal.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/api/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/api/client.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/args.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/capability.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/dataset.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/environment.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/evaluation.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/inference_model.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/main.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/model.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/optimize.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/runtime.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/sandbox.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/secret.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/session.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/shared.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/task.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/init/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/init/challenge/Dockerfile +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/init/docker-compose.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/init/provision.sh +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/init/solution.sh +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/init/task-remote.yaml.tmpl +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/init/task.yaml.tmpl +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/init/teardown.sh +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/templates/init/verify.sh +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/train.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/cli/worlds.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/client/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/client/interactive.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/client/managed_client.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/client/runtime_client.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/client/transports.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/main.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/model_catalog.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/paths.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/print_mode.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/auth.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/capability_manager.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/model_resolution.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/prompt.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/prompt_registry.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/session_hydrator.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/session_persistence.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/turn_coordinator.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/utils.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/websocket.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/server/worker_manager.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/auth_flow.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/capabilities_manager.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/commands.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/connection.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/dreadnode.tcss +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/error_handler.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/model_manager.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/model_variants.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/profile_manager.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/runtime_cache.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/auth.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/base.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/capability_docs.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/connection_error.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/console.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/environments.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/evaluations.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/model_picker.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/models.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/raw_spans.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/runtimes.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/sandboxes.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/secrets.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/services.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/sessions.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/theme_showcase.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/screens/traces.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/spans_reader.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/status_messages.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/theme.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/tool_format.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/turn_coordinator.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/turn_lifecycle.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/turn_state_phase.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/update_check.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/agent_dialog.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/agent_suggester.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/composer.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/confirm_modal.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/conversation.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/flash.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/header_bar.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/help_panel.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/human_prompt.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/mention_overlay.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/message_queue.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/new_messages_pill.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/overlay_mixin.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/permission_prompt.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/profile_dialog.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/session_sidebar.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/skills_dialog.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/slash_overlay.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/status_bar.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/throbber.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/tool_progress.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/tools_dialog.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/welcome.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/widgets/whoami.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/app/tui/wire_events.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/MAINTAINING.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/agents/dreadnode.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/capability.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/SKILL.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/capability-improvement.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/promoting-capabilities.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/INDEX.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/agents.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/dependencies-and-checks.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/env-vars.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/events.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/flags.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/hooks.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/installing.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/manifest.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/mcp-servers.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/overview.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/policies.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/publishing.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/quickstart.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/skills.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/tools.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/workers-reference.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/workers.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/capabilities/writing-skills.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/guides/capability-optimization-loop.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/sdk/agents.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/sdk/capabilities.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/references/tui/default-tools.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/creating-capabilities/runtime-default-capability.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/SKILL.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/INDEX.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/airt.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/capability.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/dataset.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/env.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/evaluation.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/inference-model.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/main.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/model.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/optimize.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/overview.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/runtime.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/sandbox.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/secret.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/task.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/train.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/cli/worlds.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-cli/references/getting-started/authentication.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/SKILL.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/INDEX.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/capabilities/installing.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/capabilities/overview.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/getting-started/authentication.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/getting-started/overview.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/getting-started/quickstart.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/platform/chat-models.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/platform/credits.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/platform/organizations.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/platform/overview.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/platform/projects.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/platform/secrets.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/platform/settings.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/platform/users.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/platform/workspaces.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/runtimes/configuration.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/runtimes/managing.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/runtimes/manifest-reference.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/runtimes/overview.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/runtimes/quickstart.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/runtimes/serve.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/sandboxes/environment-lifecycle.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/sandboxes/inspecting.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/dreadnode-concepts/references/sandboxes/overview.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/getting-started/SKILL.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/dreadnode/skills/research-capabilities/SKILL.md +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/.gitignore +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/capability.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/hooks/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/hooks/observer.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/self_improvement_lib/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/self_improvement_lib/classifier.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/self_improvement_lib/reflector_goal.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/self_improvement_lib/skill_io.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/skills-promoted/.gitkeep +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/skills-proposed/.gitkeep +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/tools/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/tools/reflector.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/builtin_capabilities/self-improvement/tools/skill_stats.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/capabilities/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/capabilities/capability.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/capabilities/flags.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/capabilities/loader.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/capabilities/sync.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/capabilities/tool_rules.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/capabilities/types.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/capabilities/worker.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/capabilities/worker_runner.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/conditions.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/discovery.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/environment.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/exceptions.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/execution.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/hook.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/judge.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/load.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/log.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/meta/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/meta/config.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/meta/context.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/meta/hydrate.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/meta/introspect.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/metric.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/object.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/scorer.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/serialization.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/stopping.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/task.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/templating.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/transforms.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/types/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/types/audio.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/types/base.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/types/common.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/types/image.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/types/object_3d.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/types/table.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/types/text.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/types/video.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/core/util.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/datasets/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/datasets/dataset.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/datasets/hf.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/datasets/local.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/evaluations/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/evaluations/console.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/evaluations/evaluation.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/evaluations/events.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/evaluations/format.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/evaluations/result.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/evaluations/sample.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/caching.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/chat.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/data.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/exceptions.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/generator/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/generator/base.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/generator/http.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/generator/litellm_.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/generator/transformers_.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/generator/vllm_.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/message.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/parsing.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/tokenizer/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/tokenizer/base.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/generators/tokenizer/transformers_.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/models/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/models/hf.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/models/local.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/models/model.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/adapters/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/adapters/_env_eval.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/adapters/agent.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/adapters/env.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/adapters/runtime.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/adapters/stack.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/api.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/backends/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/backends/base.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/backends/gepa.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/collectors.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/config.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/console.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/events.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/format.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/jobs.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/result.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/sampler.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/sampling.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/search.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/stopping.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/study.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/optimization/trial.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/packaging/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/packaging/loader.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/packaging/manifest.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/packaging/oci.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/packaging/package.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/packaging/task_validation.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/policies/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/policies/guard.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/policies/rubrics/process/default.yaml +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/py.typed +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/boundary.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/fuzzing.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/graph.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/grid.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/image.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/mapelites.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/optuna.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/random.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/registry.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/samplers/strategy.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/advanced_jailbreak_detection.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/agent_security.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/agentic.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/agentic_workflow.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/attack_outcome.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/classification.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/consistency.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/contains.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/cosine_sim.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/credentials.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/crucible.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/documentation_security.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/exfiltration_detection.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/format.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/harm.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/ide_security.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/image.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/json.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/judge_ensemble.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/length.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/lexical.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/mcp_security.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/memorization.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/multi_agent_security.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/pii.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/prompt_leak.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/readability.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/reasoning_security.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/sentiment.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/similarity.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/structural_detection.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/scorers/supply_chain_detection.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/storage/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/storage/providers.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/storage/session_store.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/storage/storage.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/_ripgrep.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/apply_patch.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/dreadnode_cli.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/editing.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/execute.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/fetch.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/glob.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/grep.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/interaction.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/ls.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/memory.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/read.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/report.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/task.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/think.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/todo.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/trajectory_search.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/web_extract.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/web_search.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tools/write.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tracing/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tracing/constants.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tracing/convert.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tracing/exporter.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tracing/exporters.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tracing/span.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tracing/spans.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/tracing/trace_converter.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/_progress.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/base.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/dpo.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/env_rollouts.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/etl/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/etl/_common.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/etl/rl.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/etl/sft.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/etl/worlds.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/events.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/grpo.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/jobs.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/models.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ppo.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/prime.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/async_trainer.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/config.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/coordinator.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/distributed.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/dpo.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/experience.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/fsdp2_learner.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/inference.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/learner.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/multi_turn.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/ppo.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/reward_model.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/rollout_env.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/rollout_worker.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/sft.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/ray/trainer.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/recipes.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rewards/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rewards/aggregator.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rewards/functions.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rewards/scorer_bridge.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rewards/shaping.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rewards/types.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rollouts/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rollouts/adapters.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rollouts/agent_rollout.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rollouts/orchestrator.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rollouts/types.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/rollouts/worlds.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/serving/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/serving/vllm_client.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/sft.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/tinker/__init__.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/tinker/config.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/tinker/data.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/tinker/renderer.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/tinker/rl.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/tinker/trainer.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/tinker_sft.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/training/utils.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/advanced_jailbreak.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/adversarial_suffix.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/agent_skill.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/agentic_workflow.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/audio.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/backdoor_finetune.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/browser_agent_attacks.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/cipher.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/competitive_parity.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/constitutional.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/document.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/documentation_poison.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/encoding.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/exfiltration.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/flip_attack.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/guardrail_bypass.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/ide_injection.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/image.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/injection.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/json_tools.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/language.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/logic_bomb.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/mcp_attacks.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/multi_agent_attacks.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/multimodal_attacks.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/persuasion.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/perturbation.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/pii_extraction.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/pythonic_tools.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/rag_poisoning.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/reasoning_attacks.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/refine.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/response_steering.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/structural_exploits.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/stylistic.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/substitution.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/supply_chain.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/swap.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/system_prompt_extraction.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/text.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/video.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/transforms/xml_tools.py +0 -0
- {dreadnode-2.0.20 → dreadnode-2.0.21}/dreadnode/version.py +0 -0
|
@@ -926,6 +926,11 @@ class SessionInfo(BaseModel):
|
|
|
926
926
|
total_tokens: int = 0
|
|
927
927
|
total_tool_call_count: int = 0
|
|
928
928
|
total_cost_usd: float | None = None
|
|
929
|
+
# ``input_tokens`` from the most recent ``GenerationStep`` — represents
|
|
930
|
+
# "context the model last saw", the right denominator for a context-window
|
|
931
|
+
# gauge. ``None`` when no generation has run yet. Mirrors the platform's
|
|
932
|
+
# ``SessionUsageResponse.last_generation_input_tokens``.
|
|
933
|
+
last_generation_input_tokens: int | None = None
|
|
929
934
|
|
|
930
935
|
|
|
931
936
|
class SessionMessage(BaseModel):
|
|
@@ -1869,6 +1874,7 @@ class OptimizationJob(BaseModel):
|
|
|
1869
1874
|
error: str | None = None
|
|
1870
1875
|
created_at: datetime
|
|
1871
1876
|
created_by: str | None = None
|
|
1877
|
+
created_by_email: str | None = None
|
|
1872
1878
|
started_at: datetime | None = None
|
|
1873
1879
|
completed_at: datetime | None = None
|
|
1874
1880
|
cancel_requested_at: datetime | None = None
|
|
@@ -23,7 +23,6 @@ from dreadnode.app.cli.shared import (
|
|
|
23
23
|
_status_color,
|
|
24
24
|
_status_dot,
|
|
25
25
|
_summarize_sandbox,
|
|
26
|
-
configured_dreadnode,
|
|
27
26
|
confirm_destructive,
|
|
28
27
|
console,
|
|
29
28
|
print_error,
|
|
@@ -781,24 +780,119 @@ def generate_project_report(
|
|
|
781
780
|
# Attack execution commands
|
|
782
781
|
# ===========================================================================
|
|
783
782
|
|
|
784
|
-
#
|
|
785
|
-
|
|
783
|
+
# Auto-discovered attack registry will be created after function definition
|
|
784
|
+
|
|
785
|
+
# Legacy manual registry for compatibility (will be removed)
|
|
786
|
+
_LEGACY_ATTACK_REGISTRY: dict[str, str] = {
|
|
786
787
|
"tap": "dreadnode.airt.tap:tap_attack",
|
|
787
788
|
"goat": "dreadnode.airt.goat:goat_attack",
|
|
788
789
|
"pair": "dreadnode.airt.pair:pair_attack",
|
|
789
790
|
"crescendo": "dreadnode.airt.crescendo:crescendo_attack",
|
|
790
|
-
"prompt": "dreadnode.airt.
|
|
791
|
+
"prompt": "dreadnode.airt.tap:prompt_attack", # Fixed: prompt is in tap module
|
|
791
792
|
"rainbow": "dreadnode.airt.rainbow:rainbow_attack",
|
|
792
793
|
"gptfuzzer": "dreadnode.airt.gptfuzzer:gptfuzzer_attack",
|
|
793
794
|
"autodan_turbo": "dreadnode.airt.autodan_turbo:autodan_turbo_attack",
|
|
794
795
|
"renellm": "dreadnode.airt.renellm:renellm_attack",
|
|
795
796
|
"beast": "dreadnode.airt.beast:beast_attack",
|
|
796
|
-
"drattack": "dreadnode.airt.drattack:
|
|
797
|
+
"drattack": "dreadnode.airt.drattack:drattack_attack",
|
|
797
798
|
"deep_inception": "dreadnode.airt.deep_inception:deep_inception_attack",
|
|
798
799
|
}
|
|
799
800
|
|
|
800
|
-
|
|
801
|
-
|
|
801
|
+
|
|
802
|
+
def _discover_attacks() -> dict[str, str]:
|
|
803
|
+
"""Automatically discover all available attack functions from all airt modules."""
|
|
804
|
+
import inspect
|
|
805
|
+
|
|
806
|
+
import dreadnode.airt
|
|
807
|
+
|
|
808
|
+
registry = {}
|
|
809
|
+
|
|
810
|
+
# Get all airt module members
|
|
811
|
+
members = inspect.getmembers(dreadnode.airt, inspect.ismodule)
|
|
812
|
+
|
|
813
|
+
for module_name, module in members:
|
|
814
|
+
try:
|
|
815
|
+
# Look for functions ending in '_attack'
|
|
816
|
+
module_members = inspect.getmembers(module, inspect.isfunction)
|
|
817
|
+
for func_name, _func_obj in module_members:
|
|
818
|
+
if func_name.endswith("_attack") and not func_name.startswith("_"):
|
|
819
|
+
attack_name = func_name.replace("_attack", "")
|
|
820
|
+
registry[attack_name] = f"dreadnode.airt.{module_name}:{func_name}"
|
|
821
|
+
except (ImportError, AttributeError, TypeError):
|
|
822
|
+
# Skip modules that can't be introspected
|
|
823
|
+
continue
|
|
824
|
+
|
|
825
|
+
return registry
|
|
826
|
+
|
|
827
|
+
|
|
828
|
+
# Create auto-discovered attack registry
|
|
829
|
+
_ATTACK_REGISTRY: dict[str, str] = _discover_attacks()
|
|
830
|
+
|
|
831
|
+
# Merge auto-discovered attacks with legacy ones for backward compatibility
|
|
832
|
+
_ATTACK_REGISTRY.update(_LEGACY_ATTACK_REGISTRY)
|
|
833
|
+
|
|
834
|
+
|
|
835
|
+
def _discover_transforms() -> dict[str, str]:
|
|
836
|
+
"""Automatically discover all available transform functions from all modules."""
|
|
837
|
+
import importlib
|
|
838
|
+
import inspect
|
|
839
|
+
|
|
840
|
+
from dreadnode.transforms import __lazy_submodules__
|
|
841
|
+
|
|
842
|
+
registry = {}
|
|
843
|
+
|
|
844
|
+
# Iterate through all transform modules
|
|
845
|
+
for module_name in __lazy_submodules__:
|
|
846
|
+
try:
|
|
847
|
+
# Import the module
|
|
848
|
+
module = importlib.import_module(f"dreadnode.transforms.{module_name}")
|
|
849
|
+
|
|
850
|
+
# Find all callable transform functions
|
|
851
|
+
for name, _obj in inspect.getmembers(module, inspect.isfunction):
|
|
852
|
+
# Skip private/internal functions, test helpers, and utility functions
|
|
853
|
+
if name.startswith("_") or name in ["Config", "dedent", "print_chars"]:
|
|
854
|
+
continue
|
|
855
|
+
|
|
856
|
+
try:
|
|
857
|
+
# More inclusive discovery - include all transform functions
|
|
858
|
+
|
|
859
|
+
# Include all transform functions unless they're clearly utility/helper functions
|
|
860
|
+
# This gives users maximum choice in available transforms
|
|
861
|
+
if not (
|
|
862
|
+
name
|
|
863
|
+
in [
|
|
864
|
+
"Transform",
|
|
865
|
+
"Generator",
|
|
866
|
+
"t",
|
|
867
|
+
"typing",
|
|
868
|
+
"inspect",
|
|
869
|
+
"importlib",
|
|
870
|
+
"functools",
|
|
871
|
+
] # Common imports
|
|
872
|
+
or (
|
|
873
|
+
name[0].isupper() and len(name) > 3
|
|
874
|
+
) # Skip classes (Transform, GenerateParams, etc.)
|
|
875
|
+
or name.endswith(("_test", "_helper")) # Skip test helpers
|
|
876
|
+
or name
|
|
877
|
+
in ["dedent", "print_chars", "Config"] # Skip known utility functions
|
|
878
|
+
):
|
|
879
|
+
registry[name] = f"dreadnode.transforms.{module_name}:{name}"
|
|
880
|
+
except (AttributeError, TypeError, ImportError):
|
|
881
|
+
# Skip functions that can't be inspected or have missing dependencies
|
|
882
|
+
continue
|
|
883
|
+
|
|
884
|
+
except (ImportError, AttributeError):
|
|
885
|
+
# Skip modules that can't be imported (optional dependencies like confusables, etc.)
|
|
886
|
+
continue
|
|
887
|
+
|
|
888
|
+
return registry
|
|
889
|
+
|
|
890
|
+
|
|
891
|
+
# Auto-discovered transform registry (replaces manual curation)
|
|
892
|
+
_TRANSFORM_REGISTRY: dict[str, str] = _discover_transforms()
|
|
893
|
+
|
|
894
|
+
# Legacy manual registry for compatibility (will be removed)
|
|
895
|
+
_LEGACY_TRANSFORM_REGISTRY: dict[str, str] = {
|
|
802
896
|
# Encoding transforms
|
|
803
897
|
"base64": "dreadnode.transforms.encoding:base64_encode",
|
|
804
898
|
"base32": "dreadnode.transforms.encoding:base32_encode",
|
|
@@ -855,6 +949,9 @@ _TRANSFORM_REGISTRY: dict[str, str] = {
|
|
|
855
949
|
"reasoning_hijack": "dreadnode.transforms.reasoning_attacks:reasoning_hijack",
|
|
856
950
|
}
|
|
857
951
|
|
|
952
|
+
# Merge auto-discovered transforms with legacy ones for backward compatibility
|
|
953
|
+
_TRANSFORM_REGISTRY.update(_LEGACY_TRANSFORM_REGISTRY)
|
|
954
|
+
|
|
858
955
|
# Goal categories matching the SDK's GoalCategory enum
|
|
859
956
|
_GOAL_CATEGORIES = [
|
|
860
957
|
"harmful_content",
|
|
@@ -1056,8 +1153,16 @@ def run(
|
|
|
1056
1153
|
async def _run() -> None:
|
|
1057
1154
|
from dreadnode.airt import Assessment
|
|
1058
1155
|
|
|
1059
|
-
# Configure the SDK
|
|
1060
|
-
|
|
1156
|
+
# Configure the SDK using the validated profile
|
|
1157
|
+
from dreadnode.app.main import Dreadnode
|
|
1158
|
+
|
|
1159
|
+
Dreadnode().configure(
|
|
1160
|
+
server=profile.url,
|
|
1161
|
+
api_key=profile.api_key,
|
|
1162
|
+
organization=profile.organization,
|
|
1163
|
+
workspace=profile.workspace,
|
|
1164
|
+
project=profile.project,
|
|
1165
|
+
)
|
|
1061
1166
|
|
|
1062
1167
|
async with Assessment(
|
|
1063
1168
|
name=name,
|
|
@@ -1423,15 +1528,27 @@ _TRANSFORM_LIST_ROW_FIELDS: tuple[str, ...] = (
|
|
|
1423
1528
|
|
|
1424
1529
|
|
|
1425
1530
|
def _transform_rows() -> list[dict[str, t.Any]]:
|
|
1426
|
-
rows: list[dict[str, t.Any]] = [
|
|
1427
|
-
|
|
1428
|
-
|
|
1429
|
-
|
|
1430
|
-
|
|
1431
|
-
|
|
1432
|
-
|
|
1433
|
-
|
|
1434
|
-
|
|
1531
|
+
rows: list[dict[str, t.Any]] = []
|
|
1532
|
+
for name in sorted(_TRANSFORM_REGISTRY):
|
|
1533
|
+
# Get description from manual registry or generate one from the module/function name
|
|
1534
|
+
description = _TRANSFORM_DESCRIPTIONS.get(name, "")
|
|
1535
|
+
if not description:
|
|
1536
|
+
# Generate description from function name and module
|
|
1537
|
+
factory_path = _TRANSFORM_REGISTRY[name]
|
|
1538
|
+
if ":" in factory_path:
|
|
1539
|
+
module_path, func_name = factory_path.split(":", 1)
|
|
1540
|
+
module_name = module_path.split(".")[-1]
|
|
1541
|
+
# Create a readable description from the function/module names
|
|
1542
|
+
description = f"{func_name.replace('_', ' ').title()} from {module_name}"
|
|
1543
|
+
|
|
1544
|
+
rows.append(
|
|
1545
|
+
{
|
|
1546
|
+
"name": name,
|
|
1547
|
+
"description": description,
|
|
1548
|
+
"factory": _TRANSFORM_REGISTRY[name],
|
|
1549
|
+
"requires_attacker_model": False,
|
|
1550
|
+
}
|
|
1551
|
+
)
|
|
1435
1552
|
rows.append(
|
|
1436
1553
|
{
|
|
1437
1554
|
"name": "language_XX",
|
|
@@ -237,6 +237,10 @@ class SessionInfo:
|
|
|
237
237
|
total_tokens: int = 0
|
|
238
238
|
total_tool_call_count: int = 0
|
|
239
239
|
total_cost_usd: float | None = None
|
|
240
|
+
# ``input_tokens`` from the most recent generation — "context the model
|
|
241
|
+
# last saw", used by the TUI's context-window gauge. Mirrors the
|
|
242
|
+
# platform's ``SessionUsageResponse.last_generation_input_tokens``.
|
|
243
|
+
last_generation_input_tokens: int | None = None
|
|
240
244
|
|
|
241
245
|
@classmethod
|
|
242
246
|
def from_dict(cls, data: dict[str, t.Any]) -> "SessionInfo":
|
|
@@ -277,6 +281,11 @@ class SessionInfo:
|
|
|
277
281
|
total_cost_usd=(
|
|
278
282
|
float(data["total_cost_usd"]) if data.get("total_cost_usd") is not None else None
|
|
279
283
|
),
|
|
284
|
+
last_generation_input_tokens=(
|
|
285
|
+
int(data["last_generation_input_tokens"])
|
|
286
|
+
if data.get("last_generation_input_tokens") is not None
|
|
287
|
+
else None
|
|
288
|
+
),
|
|
280
289
|
)
|
|
281
290
|
|
|
282
291
|
|
|
@@ -253,6 +253,12 @@ class Profile(BaseModel):
|
|
|
253
253
|
else:
|
|
254
254
|
return
|
|
255
255
|
|
|
256
|
+
def _raise_project_not_found(self, proj_key: str) -> t.NoReturn:
|
|
257
|
+
"""Raise a project not found error."""
|
|
258
|
+
raise RuntimeError(
|
|
259
|
+
f"Project '{proj_key}' not found in workspace '{self.workspace_key}' of organization '{self.org_key}'."
|
|
260
|
+
) from None
|
|
261
|
+
|
|
256
262
|
def _validate_scope_inner(self, api: "ApiClient") -> None:
|
|
257
263
|
"""Core validation logic, separated for retry wrapping."""
|
|
258
264
|
from dreadnode.core.util import valid_key
|
|
@@ -304,10 +310,12 @@ class Profile(BaseModel):
|
|
|
304
310
|
proj = api.get_project(org_key, self.workspace_key, proj_key)
|
|
305
311
|
if proj:
|
|
306
312
|
self._project_id = str(proj.id)
|
|
313
|
+
else:
|
|
314
|
+
self._raise_project_not_found(proj_key)
|
|
307
315
|
except RuntimeError as e:
|
|
308
316
|
if "404" not in str(e):
|
|
309
317
|
raise
|
|
310
|
-
# Project doesn't exist — clear it
|
|
318
|
+
# Project doesn't exist — clear it (404 → None behavior)
|
|
311
319
|
self._project = None
|
|
312
320
|
self._project_id = None
|
|
313
321
|
|
|
@@ -0,0 +1,291 @@
|
|
|
1
|
+
"""Runtime env var resolution with deprecation warnings for legacy names.
|
|
2
|
+
|
|
3
|
+
Centralizes reads of the ``DREADNODE_RUNTIME_*`` family so legacy aliases (which
|
|
4
|
+
collided with the platform ``DREADNODE_SERVER`` var or lived under the narrow
|
|
5
|
+
``SANDBOX_`` prefix) can be honored during the deprecation window without
|
|
6
|
+
duplicating warning bookkeeping at every call site.
|
|
7
|
+
"""
|
|
8
|
+
|
|
9
|
+
import os
|
|
10
|
+
import platform
|
|
11
|
+
import shutil
|
|
12
|
+
import subprocess
|
|
13
|
+
import sys
|
|
14
|
+
import threading
|
|
15
|
+
import typing as t
|
|
16
|
+
import warnings
|
|
17
|
+
from pathlib import Path
|
|
18
|
+
|
|
19
|
+
from loguru import logger
|
|
20
|
+
|
|
21
|
+
__all__ = [
|
|
22
|
+
"read_env_with_deprecation",
|
|
23
|
+
"resolve_python_executable",
|
|
24
|
+
]
|
|
25
|
+
|
|
26
|
+
_ALREADY_WARNED: set[str] = set()
|
|
27
|
+
# Guard the check-then-add on ``_ALREADY_WARNED`` so concurrent threads
|
|
28
|
+
# racing on startup (SDK + TUI + worker manager) still produce exactly one
|
|
29
|
+
# warning per legacy name.
|
|
30
|
+
_WARN_LOCK = threading.Lock()
|
|
31
|
+
|
|
32
|
+
|
|
33
|
+
def resolve_python_executable() -> str:
|
|
34
|
+
"""Resolve the Python executable for dreadnode, never using sys.executable.
|
|
35
|
+
|
|
36
|
+
Finds the correct Python that has dreadnode SDK installed by checking:
|
|
37
|
+
1. Dreadnode installation paths
|
|
38
|
+
2. UV tool environments
|
|
39
|
+
3. Virtual environments
|
|
40
|
+
4. PATH with validation
|
|
41
|
+
|
|
42
|
+
Returns:
|
|
43
|
+
Path to the Python executable that should be used for subprocess execution.
|
|
44
|
+
|
|
45
|
+
Raises:
|
|
46
|
+
ValueError: If no Python with dreadnode SDK is found.
|
|
47
|
+
"""
|
|
48
|
+
# 1. Try dreadnode installation detection
|
|
49
|
+
installation_python = _get_dreadnode_installation_python()
|
|
50
|
+
if installation_python and _validate_python_has_dreadnode(installation_python):
|
|
51
|
+
logger.debug(f"Using dreadnode installation Python: {installation_python}")
|
|
52
|
+
return installation_python
|
|
53
|
+
|
|
54
|
+
# 2. Try UV tool environment
|
|
55
|
+
uv_python = _get_uv_tool_python()
|
|
56
|
+
if uv_python and _validate_python_has_dreadnode(uv_python):
|
|
57
|
+
logger.debug(f"Using UV tool Python: {uv_python}")
|
|
58
|
+
return uv_python
|
|
59
|
+
|
|
60
|
+
# 3. Try virtual environment
|
|
61
|
+
venv_python = _get_venv_python()
|
|
62
|
+
if venv_python and _validate_python_has_dreadnode(venv_python):
|
|
63
|
+
logger.debug(f"Using virtual environment Python: {venv_python}")
|
|
64
|
+
return venv_python
|
|
65
|
+
|
|
66
|
+
# 4. Try PATH with validation
|
|
67
|
+
for python_name in ["python3", "python"]:
|
|
68
|
+
python_from_path = shutil.which(python_name)
|
|
69
|
+
if python_from_path and _validate_python_has_dreadnode(python_from_path):
|
|
70
|
+
logger.debug(f"Using PATH Python: {python_from_path}")
|
|
71
|
+
return python_from_path
|
|
72
|
+
|
|
73
|
+
# 5. FAIL FAST - no sys.executable fallback
|
|
74
|
+
raise ValueError(
|
|
75
|
+
"Dreadnode installation not found. No Python executable found with dreadnode SDK installed. "
|
|
76
|
+
"Please install following the documentation: https://docs.dreadnode.io/getting-started/quickstart/"
|
|
77
|
+
)
|
|
78
|
+
|
|
79
|
+
|
|
80
|
+
def _get_platform_uv_tool_paths() -> list[Path]:
|
|
81
|
+
"""Get platform-specific UV tool installation paths for dreadnode."""
|
|
82
|
+
paths = []
|
|
83
|
+
|
|
84
|
+
if platform.system() == "Windows":
|
|
85
|
+
# Windows UV tool paths
|
|
86
|
+
if os.environ.get("LOCALAPPDATA"):
|
|
87
|
+
paths.append(
|
|
88
|
+
Path(os.environ["LOCALAPPDATA"])
|
|
89
|
+
/ "uv"
|
|
90
|
+
/ "tools"
|
|
91
|
+
/ "dreadnode"
|
|
92
|
+
/ "Scripts"
|
|
93
|
+
/ "python.exe"
|
|
94
|
+
)
|
|
95
|
+
if os.environ.get("APPDATA"):
|
|
96
|
+
paths.append(
|
|
97
|
+
Path(os.environ["APPDATA"])
|
|
98
|
+
/ "uv"
|
|
99
|
+
/ "tools"
|
|
100
|
+
/ "dreadnode"
|
|
101
|
+
/ "Scripts"
|
|
102
|
+
/ "python.exe"
|
|
103
|
+
)
|
|
104
|
+
# Fallback for Windows with Unix-style paths (WSL, Git Bash, etc.)
|
|
105
|
+
paths.append(
|
|
106
|
+
Path.home()
|
|
107
|
+
/ ".local"
|
|
108
|
+
/ "share"
|
|
109
|
+
/ "uv"
|
|
110
|
+
/ "tools"
|
|
111
|
+
/ "dreadnode"
|
|
112
|
+
/ "Scripts"
|
|
113
|
+
/ "python.exe"
|
|
114
|
+
)
|
|
115
|
+
else:
|
|
116
|
+
# Unix-like systems (Linux, macOS)
|
|
117
|
+
paths.extend(
|
|
118
|
+
[
|
|
119
|
+
Path.home() / ".local" / "share" / "uv" / "tools" / "dreadnode" / "bin" / "python3",
|
|
120
|
+
Path.home() / ".local" / "share" / "uv" / "tools" / "dreadnode" / "bin" / "python",
|
|
121
|
+
]
|
|
122
|
+
)
|
|
123
|
+
|
|
124
|
+
return paths
|
|
125
|
+
|
|
126
|
+
|
|
127
|
+
def _get_dreadnode_installation_python() -> str | None:
|
|
128
|
+
"""Find Python from dreadnode installation directory."""
|
|
129
|
+
# Method 1: Derive from current executable location
|
|
130
|
+
current_executable = sys.argv[0]
|
|
131
|
+
if current_executable:
|
|
132
|
+
executable_path = Path(current_executable).resolve()
|
|
133
|
+
|
|
134
|
+
# UV tool pattern: ~/.local/share/uv/tools/dreadnode/bin/dreadnode
|
|
135
|
+
if "uv/tools/dreadnode" in str(executable_path):
|
|
136
|
+
# UV tool installation - Python is in same directory
|
|
137
|
+
if platform.system() == "Windows":
|
|
138
|
+
potential_python = executable_path.parent / "python.exe"
|
|
139
|
+
else:
|
|
140
|
+
potential_python = executable_path.parent / "python3"
|
|
141
|
+
if potential_python.exists():
|
|
142
|
+
return str(potential_python)
|
|
143
|
+
if platform.system() != "Windows":
|
|
144
|
+
potential_python = executable_path.parent / "python"
|
|
145
|
+
if potential_python.exists():
|
|
146
|
+
return str(potential_python)
|
|
147
|
+
|
|
148
|
+
# Check for other common installation patterns:
|
|
149
|
+
# ~/.local/bin/dn -> ~/.local/bin/python3
|
|
150
|
+
# ~/.dreadnode/bin/dn -> ~/.dreadnode/bin/python3
|
|
151
|
+
# /usr/local/bin/dn -> /usr/local/bin/python3
|
|
152
|
+
if platform.system() == "Windows":
|
|
153
|
+
potential_python = executable_path.parent / "python.exe"
|
|
154
|
+
else:
|
|
155
|
+
potential_python = executable_path.parent / "python3"
|
|
156
|
+
if potential_python.exists():
|
|
157
|
+
return str(potential_python)
|
|
158
|
+
|
|
159
|
+
# Method 2: Check standard installation locations
|
|
160
|
+
installation_paths = []
|
|
161
|
+
|
|
162
|
+
# UV tool installation (highest priority) - platform-aware
|
|
163
|
+
installation_paths.extend(_get_platform_uv_tool_paths())
|
|
164
|
+
|
|
165
|
+
# Other standard locations
|
|
166
|
+
if platform.system() == "Windows":
|
|
167
|
+
installation_paths.extend(
|
|
168
|
+
[
|
|
169
|
+
Path.home() / ".dreadnode" / "Scripts" / "python.exe",
|
|
170
|
+
Path.home() / "AppData" / "Local" / "Programs" / "Python" / "python.exe",
|
|
171
|
+
]
|
|
172
|
+
)
|
|
173
|
+
else:
|
|
174
|
+
installation_paths.extend(
|
|
175
|
+
[
|
|
176
|
+
Path.home() / ".dreadnode" / "bin" / "python3",
|
|
177
|
+
Path.home() / ".local" / "bin" / "python3",
|
|
178
|
+
Path("/usr/local/bin/python3"),
|
|
179
|
+
]
|
|
180
|
+
)
|
|
181
|
+
|
|
182
|
+
for python_path in installation_paths:
|
|
183
|
+
if python_path.exists():
|
|
184
|
+
return str(python_path)
|
|
185
|
+
|
|
186
|
+
return None
|
|
187
|
+
|
|
188
|
+
|
|
189
|
+
def _get_uv_tool_python() -> str | None:
|
|
190
|
+
"""Find Python from UV tool installation."""
|
|
191
|
+
# Check if current executable is in a UV tool path
|
|
192
|
+
current_executable = sys.argv[0]
|
|
193
|
+
if current_executable:
|
|
194
|
+
executable_path = Path(current_executable).resolve()
|
|
195
|
+
|
|
196
|
+
# UV tool pattern: ~/.local/share/uv/tools/dreadnode/bin/dreadnode
|
|
197
|
+
if "uv/tools" in str(executable_path):
|
|
198
|
+
# Extract the tool directory and find Python
|
|
199
|
+
tool_parts = str(executable_path).split("uv/tools/")
|
|
200
|
+
if len(tool_parts) == 2:
|
|
201
|
+
tool_base = tool_parts[0] + "uv/tools/" + tool_parts[1].split("/")[0]
|
|
202
|
+
if platform.system() == "Windows":
|
|
203
|
+
uv_python = Path(tool_base) / "Scripts" / "python.exe"
|
|
204
|
+
if uv_python.exists():
|
|
205
|
+
return str(uv_python)
|
|
206
|
+
else:
|
|
207
|
+
uv_python = Path(tool_base) / "bin" / "python3"
|
|
208
|
+
if uv_python.exists():
|
|
209
|
+
return str(uv_python)
|
|
210
|
+
# Try without the '3' suffix
|
|
211
|
+
uv_python = Path(tool_base) / "bin" / "python"
|
|
212
|
+
if uv_python.exists():
|
|
213
|
+
return str(uv_python)
|
|
214
|
+
|
|
215
|
+
# Fallback: check platform-specific standard UV tool locations for dreadnode
|
|
216
|
+
platform_paths = _get_platform_uv_tool_paths()
|
|
217
|
+
for python_path in platform_paths:
|
|
218
|
+
if python_path.exists():
|
|
219
|
+
return str(python_path)
|
|
220
|
+
|
|
221
|
+
return None
|
|
222
|
+
|
|
223
|
+
|
|
224
|
+
def _get_venv_python() -> str | None:
|
|
225
|
+
"""Find Python from virtual environment."""
|
|
226
|
+
virtual_env = os.environ.get("VIRTUAL_ENV")
|
|
227
|
+
if virtual_env:
|
|
228
|
+
venv_python = Path(virtual_env) / "bin" / "python3"
|
|
229
|
+
if venv_python.exists():
|
|
230
|
+
return str(venv_python)
|
|
231
|
+
|
|
232
|
+
return None
|
|
233
|
+
|
|
234
|
+
|
|
235
|
+
def _validate_python_has_dreadnode(python_path: str) -> bool:
|
|
236
|
+
"""Verify this Python can import dreadnode SDK."""
|
|
237
|
+
try:
|
|
238
|
+
result = subprocess.run( # noqa: S603
|
|
239
|
+
[python_path, "-c", "import dreadnode.sdk; import dreadnode.app; print('OK')"],
|
|
240
|
+
capture_output=True,
|
|
241
|
+
text=True,
|
|
242
|
+
timeout=5,
|
|
243
|
+
check=False, # We handle returncode ourselves
|
|
244
|
+
)
|
|
245
|
+
if result.returncode == 0 and "OK" in result.stdout:
|
|
246
|
+
return True
|
|
247
|
+
except Exception as e:
|
|
248
|
+
logger.debug(f"Python validation failed for {python_path}: {e}")
|
|
249
|
+
return False
|
|
250
|
+
|
|
251
|
+
|
|
252
|
+
@t.overload
|
|
253
|
+
def read_env_with_deprecation(canonical: str, legacy: str) -> str | None: ...
|
|
254
|
+
|
|
255
|
+
|
|
256
|
+
@t.overload
|
|
257
|
+
def read_env_with_deprecation(canonical: str, legacy: str, default: str) -> str: ...
|
|
258
|
+
|
|
259
|
+
|
|
260
|
+
def read_env_with_deprecation(
|
|
261
|
+
canonical: str,
|
|
262
|
+
legacy: str,
|
|
263
|
+
default: str | None = None,
|
|
264
|
+
) -> str | None:
|
|
265
|
+
"""Return the value of ``canonical`` if set, else ``legacy`` (warning once), else ``default``.
|
|
266
|
+
|
|
267
|
+
The ``DeprecationWarning`` fires at most once per legacy name per process,
|
|
268
|
+
so repeated reads during startup don't flood logs. The mirrored
|
|
269
|
+
``logger.warning`` ensures the message is visible even when warnings are
|
|
270
|
+
filtered out of the user's environment.
|
|
271
|
+
"""
|
|
272
|
+
canonical_value = os.environ.get(canonical)
|
|
273
|
+
if canonical_value is not None:
|
|
274
|
+
return canonical_value
|
|
275
|
+
|
|
276
|
+
legacy_value = os.environ.get(legacy)
|
|
277
|
+
if legacy_value is not None:
|
|
278
|
+
with _WARN_LOCK:
|
|
279
|
+
should_warn = legacy not in _ALREADY_WARNED
|
|
280
|
+
if should_warn:
|
|
281
|
+
_ALREADY_WARNED.add(legacy)
|
|
282
|
+
if should_warn:
|
|
283
|
+
msg = (
|
|
284
|
+
f"{legacy} is deprecated and will be removed in a future release. "
|
|
285
|
+
f"Use {canonical} instead."
|
|
286
|
+
)
|
|
287
|
+
warnings.warn(msg, DeprecationWarning, stacklevel=2)
|
|
288
|
+
logger.warning(msg)
|
|
289
|
+
return legacy_value
|
|
290
|
+
|
|
291
|
+
return default
|