Metadata-Version: 2.4
Name: superred-target-dtap-claudecode
Version: 0.1.0
Summary: Claude Code (claude_agent_sdk) DTAP agent target for superred: subclasses dtap_scaffold.DtapAgentTarget and runs the Claude Agent SDK in an isolated Docker container against the DTAP env MCP proxy, normalizing the in-container transcript into the shared TrajectoryArtifact.
Project-URL: Homepage, https://superred.simonsure.com
Project-URL: Documentation, https://superred.simonsure.com
Project-URL: Repository, https://github.com/RoldSI/superred-modules
Project-URL: Issues, https://github.com/RoldSI/superred-modules/issues
Author-email: Simon Sure <info@simonsure.com>
License-Expression: MIT
License-File: LICENSE
License-File: LICENSES/DecodingTrust-Agent-Apache-2.0.txt
License-File: LICENSES/NOTICE.md
Keywords: agent,ai-safety,claude-code,decodingtrust,dtap,llm,red-teaming,security,superred,target
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Science/Research
Classifier: Programming Language :: Python :: 3
Classifier: Programming Language :: Python :: 3.11
Classifier: Programming Language :: Python :: 3.12
Classifier: Programming Language :: Python :: 3.13
Classifier: Topic :: Scientific/Engineering :: Artificial Intelligence
Classifier: Topic :: Security
Requires-Python: <3.14,>=3.11
Requires-Dist: superred-target-dtap-scaffold>=0.1.0
Requires-Dist: superred>=0.1.0
Provides-Extra: dev
Requires-Dist: pytest-asyncio>=0.23; extra == 'dev'
Requires-Dist: pytest-cov>=6.0; extra == 'dev'
Requires-Dist: pytest>=8.0; extra == 'dev'
Description-Content-Type: text/markdown

# dtap-claudecode-target

A superred `Target` that runs the **Claude Code** agent (the `claude_agent_sdk`
Python SDK, which drives the `@anthropic-ai/claude-code` CLI) as one victim of the
[DecodingTrust-Agent (DTAP)](https://github.com/AI-secure/DecodingTrust-Agent)
benchmark, wired into superred.

It is one of two concrete agents over the shared
[`dtap-scaffold`](../dtap_scaffold/) base; the other is
[`dtap-openclaw-target`](../dtap_openclaw/). The base
(`dtap_scaffold.agent_base.DtapAgentTarget`) owns the entire superred lifecycle:
environment activation by config, the security-domain forest, the five DTAP
attack controllables, the emit-once observables, the Docker/MCP-proxy/injection
collaborators, and the post-run query surface the DTAP claim's judge reads. This
package adds **only** the Claude-Code-specific pieces.

In the project's target taxonomy (chatbot < agent < assistant) this is an
**assistant**: a container-isolated agent with full native tools (bash, file
edit, web) plus the DTAP environment tools exposed over MCP.

## What it adds

`DtapClaudeCodeTarget` implements the four abstract hooks of the base:

1. **`_agent_kind()`** -> `"claude_code"`.
2. **`_native_tool_deny(policy)`** maps the `native_tools_policy` config slot to
   Claude Code's native deny list: `"enabled"` -> none; `"disabled"` -> the
   upstream os-filesystem deny list (`Bash`, `Read`, `Write`, `Edit`,
   `MultiEdit`, `Glob`, `Grep`, `NotebookEdit`, `AskUserQuestion`); any other
   value is parsed as a JSON list of explicit tool names.
3. **`_run_episode(spec)`** launches the agent in an isolated Docker container via
   the single overridable `_docker_run` helper, then reads back `result.json`.
   The container runs `driver.py`, which drives `ClaudeSDKClient` turn-by-turn
   against the host MCP proxy and writes a transcript.
4. **`_extract_trajectory(episode)`** parses that transcript with
   `trajectory.convert`, **skipping the proxied env tools** (the proxy already
   emitted them) so only the agent's native tool calls and non-tool messages
   surface for the base to emit once.

## How a run flows

```
Controller → base.run()                       (host)
  ├─ fires the 5 DTAP controllables, applies env injections, binds the proxy
  ├─ _run_episode(spec) → _docker_run(spec):
  │     docker run  (env: ANTHROPIC_BASE_URL/AUTH_TOKEN/MODEL, --add-host …)
  │       └─ driver.py  (in container)
  │            ClaudeSDKClient ⇄ mcp__dtap_proxy__*  ⇄ host MCP proxy ⇄ env
  │            writes transcript.jsonl + result.json to the mounted dir
  ├─ _extract_trajectory → trajectory.convert(dir)  → TrajectoryArtifact
  └─ emits native_tool_call / agent_trace_message observables; stores the query
     surface (final_response, agent_responses, trajectory_json, env_ports)
```

The env MCP tools are all fronted by one proxy server, `dtap_proxy`, so the agent
calls them as `mcp__dtap_proxy__<tool>`; the host proxy observes each call and
fires the per-server env-tool PostCall controllable. The converter therefore
drops every `mcp__`-prefixed call (proxy-owned), keeping the artifact free of
double-counted env traffic.

## Usage

```python
from dtap_claudecode_target import DtapClaudeCodeTarget

target = DtapClaudeCodeTarget(
    model="claude-opus-4-8",
    api_base="https://my-litellm-proxy/",   # → ANTHROPIC_BASE_URL in the container
    api_key="sk-...",                        # → ANTHROPIC_AUTH_TOKEN
    image="dtap-claudecode:latest",          # the agent image (built below)
    state_root="/var/tmp/dtap",              # optional per-instance dir root
    max_turns=200,
)
```

The DTAP claim configures it per task via the base's config slots
(`active_mcp_servers`, `env_injection_config`, `system_prompt`, `user_prompt`,
`task_dir`, `available_injections`, `threat_model`, `max_turns`,
`native_tools_policy`). The model is fixed at construction (not a config slot).

## Build the agent image

```bash
# build context is the package dir (which contains driver.py)
docker build -f docker/Dockerfile -t dtap-claudecode:latest \
    src/dtap_claudecode_target
```

## Install / test

```bash
pip install -e targets/dtap_claudecode

# offline unit tests (no Docker, no network, no LLM):
pytest targets/dtap_claudecode/tests -m "not docker and not live"

# full container + live-model e2e (needs Docker + LITELLM_API_KEY/BASE):
LITELLM_API_KEY=... LITELLM_API_BASE=... \
    pytest targets/dtap_claudecode/tests -m "docker and live"
```

See `ASSUMPTIONS.md` for the fidelity ledger (transcript schema, the env-tool
skip, the native-tool list, and the Docker/proxy wiring).

## Credits / upstream

This target is a faithful reimplementation of the Claude Agent SDK backend of
the [DecodingTrust-Agent (DTAP)](https://github.com/AI-secure/DecodingTrust-Agent)
red-teaming platform (Apache-2.0; arXiv:2605.04808). No upstream source is
vendored; the code independently reproduces upstream's run loop, transcript
schema, and trajectory-conversion structure, with superred-specific deviations
documented in `ASSUMPTIONS.md`. The only near-verbatim fragment is the
os-filesystem tool deny list. See `LICENSES/NOTICE.md` for full attribution.

At Docker-image build time the agent image pulls Anthropic's
[`claude-agent-sdk`](https://github.com/anthropics/claude-agent-sdk-python)
(MIT) and the `@anthropic-ai/claude-code` CLI (Anthropic commercial terms)
directly from PyPI/npm; neither is redistributed inside this package.

This module's own code is released under the MIT License,
Copyright (c) 2026 Simon Sure.
