fix: make cap unwrap text imply text output
This commit is contained in:
+3
-3
@@ -182,12 +182,12 @@ MCP content-block envelopes:
|
||||
wf cap call wf.std.constant --input '{"value": "hello"}' --format compact
|
||||
```
|
||||
|
||||
Use `--format text --unwrap-text` to extract exactly one MCP text content block.
|
||||
This mode refuses images, resources, blobs, multiple content blocks, and
|
||||
Use `--unwrap-text` to extract exactly one MCP text content block. This implies
|
||||
text output and refuses images, resources, blobs, multiple content blocks, and
|
||||
non-MCP output:
|
||||
|
||||
```bash
|
||||
wf cap call everything.default.echo --input '{"message": "hello"}' --format text --unwrap-text
|
||||
wf cap call everything.default.echo --input '{"message": "hello"}' --unwrap-text
|
||||
```
|
||||
|
||||
Use `--max-output-chars N` to bound compact/text terminal output. JSON output
|
||||
|
||||
@@ -12,6 +12,18 @@ from wf_cli.formats import ListOutputFormat, emit_list_payload
|
||||
from wf_cli.io import CliInputError, emit_json, parse_json_input
|
||||
from wf_cli.remote_errors import run_cli_operation
|
||||
|
||||
CAP_CALL_HELP = """Call one workflow capability once for authoring/runtime smoke tests.
|
||||
|
||||
Output modes:
|
||||
|
||||
- json: Full lossless payload. Default. Never truncated.
|
||||
- compact: One bounded summary line.
|
||||
- text: Requires --unwrap-text and prints exactly one MCP text content block.
|
||||
|
||||
Text unwrap refuses images, resources, blobs, multiple blocks, and non-MCP
|
||||
output. Use --max-output-chars to bound compact/text terminal output.
|
||||
"""
|
||||
|
||||
|
||||
class CapCallOutputFormat(StrEnum):
|
||||
JSON = "json"
|
||||
@@ -80,7 +92,7 @@ def inspect_capability(
|
||||
emit_json(payload)
|
||||
|
||||
|
||||
@app.command("call")
|
||||
@app.command("call", help=CAP_CALL_HELP)
|
||||
def call_capability(
|
||||
ctx: typer.Context,
|
||||
qualified_name: Annotated[str, typer.Argument(help="Workflow capability name.")],
|
||||
@@ -121,11 +133,10 @@ def call_capability(
|
||||
bool,
|
||||
typer.Option(
|
||||
"--unwrap-text",
|
||||
help="Only with --format text: unwrap one MCP text block.",
|
||||
help="Unwrap one safe MCP text block; implies --format text.",
|
||||
),
|
||||
] = False,
|
||||
) -> None:
|
||||
"""Call one workflow capability once for authoring/runtime smoke tests."""
|
||||
try:
|
||||
payload = parse_json_input(input_json=input_json, input_file=input_file)
|
||||
except CliInputError as exc:
|
||||
@@ -143,7 +154,10 @@ def call_capability(
|
||||
try:
|
||||
rendered = render_cap_call_output(
|
||||
result,
|
||||
output_format=output_format,
|
||||
output_format=_resolve_cap_call_output_format(
|
||||
output_format=output_format,
|
||||
unwrap_text=unwrap_text,
|
||||
),
|
||||
unwrap_text=unwrap_text,
|
||||
max_output_chars=max_output_chars,
|
||||
)
|
||||
@@ -173,6 +187,17 @@ def render_cap_call_output(
|
||||
return _truncate_text(summary, max_output_chars=max_output_chars)
|
||||
|
||||
|
||||
def _resolve_cap_call_output_format(
|
||||
*,
|
||||
output_format: CapCallOutputFormat,
|
||||
unwrap_text: bool,
|
||||
) -> CapCallOutputFormat:
|
||||
"""Treat --unwrap-text as the explicit request for safe text extraction."""
|
||||
if unwrap_text and output_format is CapCallOutputFormat.JSON:
|
||||
return CapCallOutputFormat.TEXT
|
||||
return output_format
|
||||
|
||||
|
||||
def _compact_cap_call_summary(result: dict[str, Any]) -> str:
|
||||
output = result.get("output")
|
||||
output_summary = _summarize_output(output)
|
||||
|
||||
@@ -157,8 +157,6 @@ def test_cap_call_cli_unwraps_single_mcp_text_block(monkeypatch) -> None:
|
||||
"everything.default.echo",
|
||||
"--input",
|
||||
'{"message": "hello"}',
|
||||
"--format",
|
||||
"text",
|
||||
"--unwrap-text",
|
||||
],
|
||||
)
|
||||
@@ -191,6 +189,29 @@ def test_cap_call_cli_refuses_to_unwrap_blob_content(monkeypatch) -> None:
|
||||
assert "exactly one MCP text content block" in result.output
|
||||
|
||||
|
||||
def test_cap_call_cli_format_text_requires_unwrap_text(monkeypatch) -> None:
|
||||
_patch_context(
|
||||
monkeypatch,
|
||||
_base_result({"content": [{"type": "text", "text": "hello text"}]}),
|
||||
)
|
||||
|
||||
result = CliRunner().invoke(
|
||||
app,
|
||||
[
|
||||
"cap",
|
||||
"call",
|
||||
"everything.default.echo",
|
||||
"--input",
|
||||
"{}",
|
||||
"--format",
|
||||
"text",
|
||||
],
|
||||
)
|
||||
|
||||
assert result.exit_code != 0
|
||||
assert "--format text requires --unwrap-text" in result.output
|
||||
|
||||
|
||||
def test_cap_call_cli_refuses_to_unwrap_multiple_text_blocks(monkeypatch) -> None:
|
||||
_patch_context(
|
||||
monkeypatch,
|
||||
|
||||
@@ -381,8 +381,11 @@ def test_wf_cap_commands_use_rpc_url_override(monkeypatch, tmp_path) -> None:
|
||||
|
||||
help_result = runner.invoke(app, ["cap", "call", "--help"])
|
||||
assert help_result.exit_code == 0
|
||||
help_text = " ".join(help_result.output.split())
|
||||
assert "--unwrap-text" in help_result.output
|
||||
assert "MCP text block" in help_result.output
|
||||
assert "MCP text content block" in help_text
|
||||
assert "multiple blocks" in help_text
|
||||
assert "non-MCP" in help_text
|
||||
|
||||
|
||||
def test_wf_source_commands_use_rpc_url_override(monkeypatch, tmp_path) -> None:
|
||||
|
||||
Reference in New Issue
Block a user