Token tracking y cálculo de costes por mensaje
- Config: COST_PER_1M_INPUT y COST_PER_1M_OUTPUT configurables via .env
- OpenAI adapter: stream_options include_usage para capturar tokens reales
- base.py: acumula input/output tokens de cada iteración del agente
- planner.py: devuelve usage junto con el plan
- engine.py: suma tokens de planner + steps + review, calcula coste USD
- Response incluye usage{input_tokens, output_tokens} y total_cost_usd
Formato compatible con el bridge de Claude Code CLI para integración
con el frontend y reporting a Acai webservice.
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -115,9 +115,10 @@ class OrchestratorEngine:
|
||||
|
||||
# 2. Plan
|
||||
task.status = TaskStatus.PLANNING
|
||||
planner_usage: dict[str, int] = {"input_tokens": 0, "output_tokens": 0}
|
||||
try:
|
||||
planner = self._create_agent(AgentRole.PLANNER)
|
||||
plan_steps = await planner.plan(session)
|
||||
plan_steps, planner_usage = await planner.plan(session)
|
||||
task.plan = plan_steps
|
||||
task.status = TaskStatus.EXECUTING
|
||||
except Exception as e:
|
||||
@@ -234,6 +235,21 @@ class OrchestratorEngine:
|
||||
session_id=session.session_id,
|
||||
)
|
||||
|
||||
# Accumulate token usage: planner + all steps + review
|
||||
total_input = planner_usage.get("input_tokens", 0)
|
||||
total_output = planner_usage.get("output_tokens", 0)
|
||||
for r in results:
|
||||
total_input += r.get("usage", {}).get("input_tokens", 0)
|
||||
total_output += r.get("usage", {}).get("output_tokens", 0)
|
||||
# Add review usage if any
|
||||
total_input += review_result.get("usage", {}).get("input_tokens", 0)
|
||||
total_output += review_result.get("usage", {}).get("output_tokens", 0)
|
||||
# Calculate cost
|
||||
cost_usd = (
|
||||
(total_input / 1_000_000) * settings.cost_per_1m_input
|
||||
+ (total_output / 1_000_000) * settings.cost_per_1m_output
|
||||
)
|
||||
|
||||
return {
|
||||
"session_id": session.session_id,
|
||||
"task_id": task.task_id,
|
||||
@@ -245,6 +261,11 @@ class OrchestratorEngine:
|
||||
),
|
||||
"review": review_result.get("content", ""),
|
||||
"status": status,
|
||||
"usage": {
|
||||
"input_tokens": total_input,
|
||||
"output_tokens": total_output,
|
||||
},
|
||||
"total_cost_usd": round(cost_usd, 6),
|
||||
}
|
||||
|
||||
def _error_result(self, session: SessionState, error: str) -> dict[str, Any]:
|
||||
|
||||
Reference in New Issue
Block a user