power-loop 6.1.0__tar.gz → 6.2.0__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.
- {power_loop-6.1.0 → power_loop-6.2.0}/PKG-INFO +1 -1
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/__init__.py +1 -1
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/event_payloads.py +9 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/core/pipeline.py +2 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/representation.py +7 -5
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop.egg-info/PKG-INFO +1 -1
- {power_loop-6.1.0 → power_loop-6.2.0}/LICENSE +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/README.md +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/_vendor/__init__.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/_vendor/llm_client/__init__.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/_vendor/llm_client/anthropic_factory.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/_vendor/llm_client/capabilities.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/_vendor/llm_client/interface.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/_vendor/llm_client/llm_factory.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/_vendor/llm_client/llm_tooling.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/_vendor/llm_client/llm_utils.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/_vendor/llm_client/multimodal.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/agent/__init__.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/agent/follow_up.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/agent/sink.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/agent/stateful_loop.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/agent/system_prompt.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/agent/types.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/__init__.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/errors.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/events.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/handlers.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/hook_contexts.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/hooks.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/messages.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/protocols.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contracts/tools.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contrib/__init__.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contrib/_redact.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contrib/jsonl_sink.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contrib/logging_sink.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contrib/mcp.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contrib/metrics_sink.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/contrib/otel_sink.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/core/agent_context.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/core/events.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/core/hooks.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/core/phase.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/core/runner.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/core/state.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/py.typed +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/blackboard.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/budget.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/cancellation.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/compact.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/env.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/exec_backend.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/fold.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/fold_adapter.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/history_projector.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/history_sanitize.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/human_input.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/image_recall.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/memory.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/notes.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/provider.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/retry.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/runtime_state.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/session_store.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/skills.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/spec.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/__init__.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/backends/__init__.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/backends/mysql.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/backends/postgres.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/backends/sqlite.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/capabilities.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/db.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/dialect.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/factory.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/schema.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/store.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/store/types.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/structured.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/stub_provider.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/runtime/timers.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/tools/__init__.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/tools/blackboard.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/tools/command_policy.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/tools/default_manifest.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/tools/default_tools.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/tools/registry.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/tools/spawn_agent.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/__init__.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/api.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/engine.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/introspect.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/journal.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/result.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/resume.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/runner.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/spec.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/subprocess_executor.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/tool.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop/workflow/worker.py +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop.egg-info/SOURCES.txt +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop.egg-info/dependency_links.txt +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop.egg-info/requires.txt +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/power_loop.egg-info/top_level.txt +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/pyproject.toml +0 -0
- {power_loop-6.1.0 → power_loop-6.2.0}/setup.cfg +0 -0
|
@@ -15,7 +15,7 @@ Stability tiers
|
|
|
15
15
|
无版本承诺,可随时变更或删除。
|
|
16
16
|
"""
|
|
17
17
|
|
|
18
|
-
__version__ = "6.
|
|
18
|
+
__version__ = "6.2.0"
|
|
19
19
|
|
|
20
20
|
# Public LLM contract (SDK-free) re-exported so callers (e.g. writing llm.* hooks or
|
|
21
21
|
# a custom LLMService) don't reach into the internal vendored transport package (H3.4).
|
|
@@ -63,6 +63,15 @@ class LlmCallCompletedPayload(BaseEventPayload):
|
|
|
63
63
|
prompt_tokens: int | None = None
|
|
64
64
|
completion_tokens: int | None = None
|
|
65
65
|
total_tokens: int | None = None
|
|
66
|
+
#: Prompt-cache split, when the provider reports it (DeepSeek, OpenAI, …). The transport has
|
|
67
|
+
#: parsed these into ``LLMTokenUsage`` since forever, but the event dropped them — so a host
|
|
68
|
+
#: could see "this round cost 44k prompt tokens" and had **no way to tell** whether that was
|
|
69
|
+
#: 44k billed at full price or 99% served from cache at a tenth of it. Without the split, any
|
|
70
|
+
#: judgement about context cost is guesswork: it is the difference between "trim the history"
|
|
71
|
+
#: being a big win and being a 20× loss (editing history mid-prefix invalidates the cache).
|
|
72
|
+
#: ``None`` = the provider did not report it (not "zero").
|
|
73
|
+
prompt_cached_tokens: int | None = None
|
|
74
|
+
prompt_cache_miss_tokens: int | None = None
|
|
66
75
|
|
|
67
76
|
|
|
68
77
|
@dataclass
|
|
@@ -778,6 +778,8 @@ class AgentPipeline:
|
|
|
778
778
|
prompt_tokens=getattr(usage, "prompt_tokens", None),
|
|
779
779
|
completion_tokens=getattr(usage, "completion_tokens", None),
|
|
780
780
|
total_tokens=getattr(usage, "total_tokens", None),
|
|
781
|
+
prompt_cached_tokens=getattr(usage, "prompt_cached_tokens", None),
|
|
782
|
+
prompt_cache_miss_tokens=getattr(usage, "prompt_cache_miss_tokens", None),
|
|
781
783
|
),
|
|
782
784
|
round_index=round_index, stream_id="main",
|
|
783
785
|
)
|
|
@@ -125,7 +125,7 @@ def _row_to_loop_dict(row: MessageRow) -> LoopMessage:
|
|
|
125
125
|
not mirror."""
|
|
126
126
|
msg: LoopMessage = {"role": row.role}
|
|
127
127
|
if row.content is not None:
|
|
128
|
-
msg["content"] = decode_row_content(row.content, row
|
|
128
|
+
msg["content"] = decode_row_content(row.content, getattr(row, "meta", None))
|
|
129
129
|
if row.tool_calls:
|
|
130
130
|
msg["tool_calls"] = list(row.tool_calls)
|
|
131
131
|
if row.tool_call_id:
|
|
@@ -365,11 +365,13 @@ class ProjectedRepresentation:
|
|
|
365
365
|
if r.role == "user":
|
|
366
366
|
if seen_assistant:
|
|
367
367
|
# Verbatim like the input (conversation content, not tool output).
|
|
368
|
-
tools.append({
|
|
369
|
-
|
|
370
|
-
|
|
368
|
+
tools.append({
|
|
369
|
+
"name": "__user__",
|
|
370
|
+
"text": distill_multimodal_text(r.content, getattr(r, "meta", None)),
|
|
371
|
+
"seq": r.seq,
|
|
372
|
+
})
|
|
371
373
|
else:
|
|
372
|
-
inputs.append(distill_multimodal_text(r.content, r
|
|
374
|
+
inputs.append(distill_multimodal_text(r.content, getattr(r, "meta", None)))
|
|
373
375
|
continue
|
|
374
376
|
if r.role != "assistant":
|
|
375
377
|
continue
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|