feat(ultraplan-local): v1.6.0 — /ultraresearch-local deep research command
Add /ultraresearch-local for structured research combining local codebase analysis with external knowledge via parallel agent swarms. Produces research briefs with triangulation, confidence ratings, and source quality assessment. New command: /ultraresearch-local with modes --quick, --local, --external, --fg. New agents: research-orchestrator (opus), docs-researcher, community-researcher, security-researcher, contrarian-researcher, gemini-bridge (all sonnet). New template: research-brief-template.md. Integration: --research flag in /ultraplan-local accepts pre-built research briefs (up to 3), enriches the interview and exploration phases. Planning orchestrator cross-references brief findings during synthesis. Design principle: Context Engineering — right information to right agent at right time. Research briefs are structured artifacts in the pipeline: ultraresearch → brief → ultraplan --research → plan → ultraexecute. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
commit
baa2d0220b
488 changed files with 213221 additions and 0 deletions
|
|
@ -0,0 +1,385 @@
|
|||
# Agent Cost Optimization and Resource Management
|
||||
|
||||
**Last updated:** 2026-02
|
||||
**Status:** GA
|
||||
**Category:** Agent Orchestration & Automation
|
||||
|
||||
---
|
||||
|
||||
## Introduksjon
|
||||
|
||||
Kostnadsoptimalisering for agentsystemer er en strategisk nødvendighet ettersom organisasjoner skalerer fra pilot til produksjon. Agenter som involverer flere LLM-kall, RAG-retrievals og verktøyinvokasjoner kan generere betydelige kostnader -- en enkelt kompleks agentforespørsel kan involvere 3-5 modellkall med totalt 5000-20000 tokens. Uten bevisst kostnadsstyring eskalerer utgiftene raskt når brukervolum øker.
|
||||
|
||||
Microsoft tilbyr et komplett verktøysett for agentkostnadsoptimalisering: Azure AI Foundry Control Plane med Ask AI-agenten for kostnadsanalyse, Model Router for automatisk modellvalg basert på kvalitet/kostnad, APIM som AI Gateway for token rate limiting og kostnadsallokering, og tiered deployment-modeller (Standard, Provisioned, Global). Foundry-portalen gir direkte sammenligning av modeller med hensyn til både ytelse og kostnad.
|
||||
|
||||
For norsk offentlig sektor er kostnadsbevissthet spesielt viktig gitt budsjettrammene i offentlige virksomheter. FinOps-prinsipper tilpasset AI -- med tagging, kostnadsallokering per enhet og budsjettvarslinger -- sikrer at AI-investeringer er sporbare og forsvarlge.
|
||||
|
||||
## Kjernekomponenter
|
||||
|
||||
| Komponent | Formål | Teknologi |
|
||||
|-----------|--------|-----------|
|
||||
| Model Selection | Velg kostnadseffektiv modell per oppgave | Model Router, Model Catalog |
|
||||
| Token Optimization | Reduser token-forbruk | Prompt engineering, max_tokens |
|
||||
| Request Deduplication | Unngå dupliserte forespørsler | Semantic caching, APIM policies |
|
||||
| Resource Pooling | Del ressurser effektivt | Shared deployments, PTU |
|
||||
| Cost Attribution | Spor kostnader per agent/bruker/avdeling | Azure Cost Management, tagging |
|
||||
| Foundry Control Plane | Unified kostnadsovervåking | Ask AI agent, dashboards |
|
||||
|
||||
## Model Selection per Task
|
||||
|
||||
### Tiered modellstrategi
|
||||
|
||||
| Oppgavetype | Anbefalt modell | Kostnad/1M tokens (input) | Rasjonale |
|
||||
|-------------|-----------------|---------------------------|-----------|
|
||||
| Intent routing | gpt-4.1-nano | ~$0.10 | Minimal resonnering nødvendig |
|
||||
| Enkel klassifisering | gpt-4o-mini | ~$0.15 | Rask, kostnadseffektiv |
|
||||
| Standard agent-svar | gpt-4.1-mini | ~$0.40 | Balanse kvalitet/kostnad |
|
||||
| RAG-syntetisering | gpt-4o | ~$2.50 | Krever god resonnering |
|
||||
| Kompleks analyse | gpt-4.1 | ~$2.00 | Dyp resonnering |
|
||||
| Evaluering (batch) | gpt-4o-mini (batch) | ~$0.075 | 50% rabatt via Batch API |
|
||||
|
||||
### Model Router
|
||||
|
||||
```python
|
||||
# Azure AI Foundry Model Router for automatisk modellvalg
|
||||
# Model Router velger dynamisk mellom modeller basert på oppgavekompleksitet
|
||||
|
||||
from openai import AzureOpenAI
|
||||
|
||||
client = AzureOpenAI(
|
||||
azure_endpoint=os.environ["AZURE_OPENAI_ENDPOINT"],
|
||||
api_key=os.environ["AZURE_OPENAI_KEY"],
|
||||
api_version="2024-12-01-preview"
|
||||
)
|
||||
|
||||
# Model Router deployment ruter automatisk til gpt-4o-mini
|
||||
# eller gpt-4o basert på oppgavens kompleksitet
|
||||
response = client.chat.completions.create(
|
||||
model="model-router", # Spesialdeployment for routing
|
||||
messages=[
|
||||
{"role": "system", "content": "Du er en hjelpsom assistent."},
|
||||
{"role": "user", "content": query}
|
||||
]
|
||||
)
|
||||
|
||||
# Model Router sparer 30-50% på typiske workloads ved å
|
||||
# rute enkle forespørsler til billigere modeller
|
||||
```
|
||||
|
||||
### Manuell modellvalg basert på oppgave
|
||||
|
||||
```python
|
||||
class CostAwareModelSelector:
|
||||
"""Velg modell basert på oppgavens krav og budsjett"""
|
||||
|
||||
MODEL_COSTS = {
|
||||
"gpt-4.1-nano": {"input": 0.10, "output": 0.40},
|
||||
"gpt-4o-mini": {"input": 0.15, "output": 0.60},
|
||||
"gpt-4.1-mini": {"input": 0.40, "output": 1.60},
|
||||
"gpt-4o": {"input": 2.50, "output": 10.00},
|
||||
"gpt-4.1": {"input": 2.00, "output": 8.00},
|
||||
}
|
||||
|
||||
def select_model(self, task: dict) -> str:
|
||||
complexity = task.get("complexity", "medium")
|
||||
budget_sensitive = task.get("budget_sensitive", True)
|
||||
requires_reasoning = task.get("requires_reasoning", False)
|
||||
|
||||
if complexity == "low" or not requires_reasoning:
|
||||
return "gpt-4o-mini"
|
||||
if complexity == "medium" and budget_sensitive:
|
||||
return "gpt-4.1-mini"
|
||||
if complexity == "high" or requires_reasoning:
|
||||
return "gpt-4o" if not budget_sensitive else "gpt-4.1-mini"
|
||||
return "gpt-4o-mini" # Default til billigste
|
||||
|
||||
def estimate_cost(self, model: str,
|
||||
input_tokens: int, output_tokens: int) -> float:
|
||||
costs = self.MODEL_COSTS[model]
|
||||
return (
|
||||
(input_tokens / 1_000_000) * costs["input"] +
|
||||
(output_tokens / 1_000_000) * costs["output"]
|
||||
)
|
||||
```
|
||||
|
||||
## Token Optimization for Agents
|
||||
|
||||
### Prompt-komprimering
|
||||
|
||||
```python
|
||||
# Reduser system prompt størrelse uten å miste kvalitet
|
||||
class PromptOptimizer:
|
||||
def optimize_system_prompt(self, full_prompt: str,
|
||||
max_tokens: int = 500) -> str:
|
||||
"""Komprimer system prompt til essensielt innhold"""
|
||||
sections = self._parse_sections(full_prompt)
|
||||
prioritized = sorted(sections,
|
||||
key=lambda s: s.priority, reverse=True)
|
||||
|
||||
optimized = []
|
||||
current_tokens = 0
|
||||
for section in prioritized:
|
||||
section_tokens = self._count_tokens(section.text)
|
||||
if current_tokens + section_tokens <= max_tokens:
|
||||
optimized.append(section.text)
|
||||
current_tokens += section_tokens
|
||||
else:
|
||||
# Komprimer seksjonen
|
||||
compressed = self._compress_section(
|
||||
section.text,
|
||||
max_tokens - current_tokens
|
||||
)
|
||||
optimized.append(compressed)
|
||||
break
|
||||
|
||||
return "\n".join(optimized)
|
||||
|
||||
def optimize_context_window(self, messages: list,
|
||||
max_context_tokens: int) -> list:
|
||||
"""Trim samtalehistorikk for å holde seg under token-grensen"""
|
||||
total_tokens = sum(
|
||||
self._count_tokens(m["content"]) for m in messages
|
||||
)
|
||||
|
||||
if total_tokens <= max_context_tokens:
|
||||
return messages
|
||||
|
||||
# Behold system message og siste N meldinger
|
||||
system_msg = messages[0]
|
||||
recent = messages[-4:] # Siste 2 turnarounds
|
||||
|
||||
# Komprimer mellomliggende meldinger til sammendrag
|
||||
middle = messages[1:-4]
|
||||
if middle:
|
||||
summary = self._summarize_messages(middle)
|
||||
return [system_msg,
|
||||
{"role": "system", "content": f"Samtalesammendrag: {summary}"},
|
||||
*recent]
|
||||
|
||||
return [system_msg, *recent]
|
||||
```
|
||||
|
||||
### Max tokens-optimalisering
|
||||
|
||||
```python
|
||||
# Sett max_tokens tilpasset oppgaven
|
||||
TASK_TOKEN_LIMITS = {
|
||||
"classification": 50, # Én label
|
||||
"yes_no": 10, # Ja/nei
|
||||
"short_answer": 200, # Kort svar
|
||||
"detailed_answer": 500, # Detaljert svar
|
||||
"analysis": 1000, # Dybdeanalyse
|
||||
"code_generation": 2000, # Kode
|
||||
}
|
||||
|
||||
def get_optimal_max_tokens(task_type: str) -> int:
|
||||
return TASK_TOKEN_LIMITS.get(task_type, 500)
|
||||
```
|
||||
|
||||
## Request Deduplication
|
||||
|
||||
### APIM-basert deduplication
|
||||
|
||||
```xml
|
||||
<!-- Azure API Management policy for request deduplication -->
|
||||
<policies>
|
||||
<inbound>
|
||||
<!-- Generer cache-nøkkel basert på request body -->
|
||||
<set-variable name="cacheKey"
|
||||
value="@{
|
||||
var body = context.Request.Body.As<string>(true);
|
||||
var hash = System.Security.Cryptography.SHA256.Create()
|
||||
.ComputeHash(System.Text.Encoding.UTF8.GetBytes(body));
|
||||
return Convert.ToBase64String(hash);
|
||||
}" />
|
||||
|
||||
<!-- Sjekk om identisk forespørsel nylig ble prosessert -->
|
||||
<cache-lookup-value
|
||||
key="@((string)context.Variables["cacheKey"])"
|
||||
variable-name="cachedResponse" />
|
||||
|
||||
<choose>
|
||||
<when condition="@(context.Variables.ContainsKey("cachedResponse"))">
|
||||
<return-response>
|
||||
<set-status code="200" />
|
||||
<set-body>@((string)context.Variables["cachedResponse"])</set-body>
|
||||
</return-response>
|
||||
</when>
|
||||
</choose>
|
||||
</inbound>
|
||||
<outbound>
|
||||
<!-- Cache responsen for 5 minutter -->
|
||||
<cache-store-value
|
||||
key="@((string)context.Variables["cacheKey"])"
|
||||
value="@(context.Response.Body.As<string>(true))"
|
||||
duration="300" />
|
||||
</outbound>
|
||||
</policies>
|
||||
```
|
||||
|
||||
## Resource Pooling
|
||||
|
||||
### Provisioned Throughput Units (PTU)
|
||||
|
||||
```python
|
||||
# PTU vs. Standard deployment kostnadssammenligning
|
||||
class DeploymentCostCalculator:
|
||||
def compare_deployment_types(
|
||||
self,
|
||||
daily_requests: int,
|
||||
avg_input_tokens: int,
|
||||
avg_output_tokens: int,
|
||||
model: str = "gpt-4o"
|
||||
) -> dict:
|
||||
# Standard (pay-per-token)
|
||||
daily_input_cost = (daily_requests * avg_input_tokens / 1_000_000) * 2.50
|
||||
daily_output_cost = (daily_requests * avg_output_tokens / 1_000_000) * 10.00
|
||||
standard_monthly = (daily_input_cost + daily_output_cost) * 30
|
||||
|
||||
# PTU (fast pris per enhet)
|
||||
# 1 PTU ~= 6 RPM for gpt-4o (avhenger av workload)
|
||||
required_ptu = max(1, daily_requests / (6 * 60 * 24))
|
||||
ptu_monthly = required_ptu * 2.00 * 24 * 30 # $2/PTU/time
|
||||
|
||||
return {
|
||||
"standard_monthly_usd": round(standard_monthly, 2),
|
||||
"ptu_monthly_usd": round(ptu_monthly, 2),
|
||||
"recommendation": "PTU" if ptu_monthly < standard_monthly
|
||||
else "Standard",
|
||||
"savings_percent": round(
|
||||
abs(standard_monthly - ptu_monthly) /
|
||||
max(standard_monthly, 1) * 100, 1
|
||||
)
|
||||
}
|
||||
```
|
||||
|
||||
## Cost Attribution per Agent
|
||||
|
||||
### Tagging-strategi
|
||||
|
||||
```python
|
||||
# Kostnadsattribusjon med Azure resource tags og custom telemetry
|
||||
class AgentCostTracker:
|
||||
def __init__(self, app_insights_client):
|
||||
self.client = app_insights_client
|
||||
|
||||
def track_agent_cost(
|
||||
self,
|
||||
agent_name: str,
|
||||
department: str,
|
||||
model: str,
|
||||
input_tokens: int,
|
||||
output_tokens: int,
|
||||
cost_usd: float
|
||||
):
|
||||
self.client.track_event(
|
||||
"agent_cost",
|
||||
properties={
|
||||
"agent_name": agent_name,
|
||||
"department": department,
|
||||
"model": model,
|
||||
"cost_center": f"AI-{department}",
|
||||
},
|
||||
measurements={
|
||||
"input_tokens": input_tokens,
|
||||
"output_tokens": output_tokens,
|
||||
"cost_usd": cost_usd,
|
||||
"cost_nok": cost_usd * 11.0 # Omtrentlig kurs
|
||||
}
|
||||
)
|
||||
```
|
||||
|
||||
### KQL for kostnadsrapportering
|
||||
|
||||
```kql
|
||||
// Månedlig kostnad per agent og avdeling
|
||||
customEvents
|
||||
| where timestamp > ago(30d)
|
||||
| where name == "agent_cost"
|
||||
| extend
|
||||
agent = tostring(customDimensions.agent_name),
|
||||
department = tostring(customDimensions.department),
|
||||
model = tostring(customDimensions.model),
|
||||
cost_nok = todouble(customMeasurements.cost_nok),
|
||||
tokens = todouble(customMeasurements.input_tokens)
|
||||
+ todouble(customMeasurements.output_tokens)
|
||||
| summarize
|
||||
total_cost_nok = sum(cost_nok),
|
||||
total_tokens = sum(tokens),
|
||||
request_count = count(),
|
||||
cost_per_request_nok = sum(cost_nok) / count()
|
||||
by agent, department, model
|
||||
| order by total_cost_nok desc
|
||||
```
|
||||
|
||||
## Foundry Control Plane Kostnadsoptimalisering
|
||||
|
||||
Azure AI Foundry Control Plane tilbyr innebygd kostnadsanalyse:
|
||||
|
||||
```
|
||||
Ask AI agent dialog-eksempler:
|
||||
|
||||
1. "Oppsummer min nylige kostnadstrend"
|
||||
→ Identifiserer kostnadsdrivere og trender
|
||||
|
||||
2. "Hvilke agenter bidrar mest til kostnadsøkningen?"
|
||||
→ Breakdown per agent med token-bruk
|
||||
|
||||
3. "Anbefal en billigere modell med lignende ytelse"
|
||||
→ Sammenligner modeller i katalogen
|
||||
|
||||
4. "Evaluer ytelsesforskjellen mellom gpt-4o og gpt-4o-mini"
|
||||
→ Kjører sammenlignende evaluering
|
||||
|
||||
5. "Vis meg oppsummering av siste data for kostnad"
|
||||
→ Kontinuerlig forbedring etter modellbytte
|
||||
```
|
||||
|
||||
## Norsk offentlig sektor
|
||||
|
||||
| Aspekt | Krav | Implementering |
|
||||
|--------|------|----------------|
|
||||
| Budsjettkontroll | Statsbudsjettet, rammefinansiering | Månedlige budsjettvarslinger per avdeling |
|
||||
| Gevinstrealisering | DFDs gevinstmetodikk | Spor kostnad vs. tidsbesparelse per agent |
|
||||
| Anskaffelse | Anskaffelsesloven | Rammeavtale for Azure-tjenester |
|
||||
| Rapportering | Årsmelding, tildelingsbrev | Kvartalsvis AI-kostnadsrapport |
|
||||
| Rettferdighet | Likebehandling | Lik tilgang til AI-verktøy på tvers av enheter |
|
||||
|
||||
### Budsjettvarslinger
|
||||
|
||||
```python
|
||||
# Azure Monitor budget alerts for AI-kostnader
|
||||
budget_alert_config = {
|
||||
"name": "ai-agent-monthly-budget",
|
||||
"amount": 50000, # NOK
|
||||
"time_grain": "Monthly",
|
||||
"notifications": [
|
||||
{"threshold": 50, "contact_emails": ["ai-ops@virksomhet.no"]},
|
||||
{"threshold": 80, "contact_emails": [
|
||||
"ai-ops@virksomhet.no", "leder@virksomhet.no"
|
||||
]},
|
||||
{"threshold": 100, "contact_emails": [
|
||||
"ai-ops@virksomhet.no", "leder@virksomhet.no",
|
||||
"okonomi@virksomhet.no"
|
||||
]}
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
## Beslutningsrammeverk
|
||||
|
||||
| Scenario | Anbefaling | Begrunnelse |
|
||||
|----------|------------|-------------|
|
||||
| Ny agent, usikker bruk | Standard deployment + gpt-4o-mini | Lav risiko, betal per bruk |
|
||||
| Stabil workload > 100K req/dag | PTU deployment | Forutsigbar kostnad, bedre ytelse |
|
||||
| Mange lignende forespørsler | Semantic caching + APIM | Eliminer dupliserte LLM-kall |
|
||||
| Budsjettsensitiv organisasjon | Model Router + strenge token-grenser | Automatisk kostnadsoptimalisering |
|
||||
| Multi-avdelings deployment | Cost attribution med tagging | Sporbar kostnadsfordeling |
|
||||
|
||||
## For Cosmo
|
||||
|
||||
- **Model tiering er den viktigste optimaliseringen** -- bruk gpt-4.1-nano/mini for routing og klassifisering, og reserver gpt-4o for kompleks resonnering. Typisk 30-50% kostnadsreduksjon.
|
||||
- **Model Router** i Azure AI Foundry er det enkleste tiltaket -- det ruter automatisk enkle forespørsler til billigere modeller uten kodeendringer.
|
||||
- **Token-optimalisering** gjennom komprimerte system prompts og riktige max_tokens-verdier har kumulativ effekt -- 20% tokenreduksjon over millioner av kall er betydelig.
|
||||
- **Cost attribution med Azure tags** er obligatorisk for offentlig sektor -- spor kostnad per agent, per avdeling, per bruksområde for budsjettering og gevinstrealisering.
|
||||
- **PTU-deployment** lønner seg typisk ved > 50K forespørsler/dag med stabil trafikk -- under dette er Standard med pay-per-token mer kostnadseffektivt.
|
||||
Loading…
Add table
Add a link
Reference in a new issue