mirror of
https://github.com/NousResearch/hermes-agent.git
synced 2026-07-31 19:16:29 +00:00
fix: support Gemini billing route mapping and pricing update
This commit is contained in:
parent
ee1e789877
commit
ecebff82d2
2 changed files with 82 additions and 8 deletions
|
|
@ -511,15 +511,53 @@ _OFFICIAL_DOCS_PRICING: Dict[tuple[str, str], PricingEntry] = {
|
|||
pricing_version="deepseek-pricing-2026-07",
|
||||
),
|
||||
# Google Gemini
|
||||
(
|
||||
"google",
|
||||
"gemini-3.5-flash",
|
||||
): PricingEntry(
|
||||
input_cost_per_million=Decimal("1.50"),
|
||||
output_cost_per_million=Decimal("9.00"),
|
||||
cache_read_cost_per_million=Decimal("0.15"),
|
||||
cache_write_cost_per_million=Decimal("1.50"),
|
||||
source="official_docs_snapshot",
|
||||
source_url="https://ai.google.dev/pricing",
|
||||
pricing_version="google-pricing-2026-07-07",
|
||||
),
|
||||
(
|
||||
"google",
|
||||
"gemini-3.1-pro",
|
||||
): PricingEntry(
|
||||
input_cost_per_million=Decimal("2.00"),
|
||||
output_cost_per_million=Decimal("12.00"),
|
||||
cache_read_cost_per_million=Decimal("0.20"),
|
||||
cache_write_cost_per_million=Decimal("2.00"),
|
||||
source="official_docs_snapshot",
|
||||
source_url="https://ai.google.dev/pricing",
|
||||
pricing_version="google-pricing-2026-07-07",
|
||||
),
|
||||
(
|
||||
"google",
|
||||
"gemini-3.1-flash-lite",
|
||||
): PricingEntry(
|
||||
input_cost_per_million=Decimal("0.25"),
|
||||
output_cost_per_million=Decimal("1.50"),
|
||||
cache_read_cost_per_million=Decimal("0.025"),
|
||||
cache_write_cost_per_million=Decimal("0.25"),
|
||||
source="official_docs_snapshot",
|
||||
source_url="https://ai.google.dev/pricing",
|
||||
pricing_version="google-pricing-2026-07-07",
|
||||
),
|
||||
(
|
||||
"google",
|
||||
"gemini-2.5-pro",
|
||||
): PricingEntry(
|
||||
input_cost_per_million=Decimal("1.25"),
|
||||
output_cost_per_million=Decimal("10.00"),
|
||||
cache_read_cost_per_million=Decimal("0.125"),
|
||||
cache_write_cost_per_million=Decimal("1.25"),
|
||||
source="official_docs_snapshot",
|
||||
source_url="https://ai.google.dev/pricing",
|
||||
pricing_version="google-pricing-2026-03-16",
|
||||
pricing_version="google-pricing-2026-07-07",
|
||||
),
|
||||
(
|
||||
"google",
|
||||
|
|
@ -527,9 +565,11 @@ _OFFICIAL_DOCS_PRICING: Dict[tuple[str, str], PricingEntry] = {
|
|||
): PricingEntry(
|
||||
input_cost_per_million=Decimal("0.15"),
|
||||
output_cost_per_million=Decimal("0.60"),
|
||||
cache_read_cost_per_million=Decimal("0.015"),
|
||||
cache_write_cost_per_million=Decimal("0.15"),
|
||||
source="official_docs_snapshot",
|
||||
source_url="https://ai.google.dev/pricing",
|
||||
pricing_version="google-pricing-2026-03-16",
|
||||
pricing_version="google-pricing-2026-07-07",
|
||||
),
|
||||
(
|
||||
"google",
|
||||
|
|
@ -537,9 +577,11 @@ _OFFICIAL_DOCS_PRICING: Dict[tuple[str, str], PricingEntry] = {
|
|||
): PricingEntry(
|
||||
input_cost_per_million=Decimal("0.10"),
|
||||
output_cost_per_million=Decimal("0.40"),
|
||||
cache_read_cost_per_million=Decimal("0.01"),
|
||||
cache_write_cost_per_million=Decimal("0.10"),
|
||||
source="official_docs_snapshot",
|
||||
source_url="https://ai.google.dev/pricing",
|
||||
pricing_version="google-pricing-2026-03-16",
|
||||
pricing_version="google-pricing-2026-07-07",
|
||||
),
|
||||
# AWS Bedrock — pricing per the Bedrock pricing page.
|
||||
# Bedrock charges the same per-token rates as the model provider but
|
||||
|
|
@ -925,11 +967,17 @@ def resolve_billing_route(
|
|||
return BillingRoute(provider="openai", model=model.split("/")[-1], base_url=base_url or "", billing_mode="official_docs_snapshot")
|
||||
if provider_name in {"minimax", "minimax-cn"}:
|
||||
return BillingRoute(provider=provider_name, model=model.split("/")[-1], base_url=base_url or "", billing_mode="official_docs_snapshot")
|
||||
# Vertex AI hosts the same Gemini models as Google AI Studio; price them
|
||||
# off the gemini official-docs snapshot. Strip the "google/" vendor prefix
|
||||
# the OpenAI-compat endpoint requires so the pricing key matches.
|
||||
if provider_name == "vertex" or base_url_host_matches(base_url or "", "aiplatform.googleapis.com"):
|
||||
return BillingRoute(provider="gemini", model=model.split("/")[-1], base_url=base_url or "", billing_mode="official_docs_snapshot")
|
||||
# Google AI Studio (Gemini) and Vertex AI host the same Gemini models.
|
||||
# Price them off the official docs snapshot — the pricing keys are
|
||||
# keyed on provider='google', so normalize every Google-flavored
|
||||
# provider name/host onto it. Strip the "google/" vendor prefix the
|
||||
# Vertex OpenAI-compat endpoint requires so the pricing key matches.
|
||||
if (
|
||||
provider_name in {"google", "gemini", "vertex", "google-gemini", "google-ai-studio", "google-vertex", "vertex-ai"}
|
||||
or base_url_host_matches(base_url or "", "aiplatform.googleapis.com")
|
||||
or base_url_host_matches(base_url or "", "generativelanguage.googleapis.com")
|
||||
):
|
||||
return BillingRoute(provider="google", model=model.split("/")[-1], base_url=base_url or "", billing_mode="official_docs_snapshot")
|
||||
if provider_name == "fireworks" or base_url_host_matches(base_url or "", "api.fireworks.ai"):
|
||||
# Fireworks model ids look like accounts/fireworks/models/<name>;
|
||||
# rsplit("/", 1)[-1] yields just <name> which is what the dict keys on.
|
||||
|
|
|
|||
|
|
@ -636,3 +636,29 @@ def test_deepseek_v4_flash_estimate_usage_cost():
|
|||
assert result.amount_usd is not None
|
||||
# 1M input × $0.14/M + 500K output × $0.28/M = $0.14 + $0.14 = $0.28
|
||||
assert float(result.amount_usd) == 0.28
|
||||
|
||||
|
||||
def test_gemini_3_5_flash_pricing_resolved():
|
||||
"""Ensure gemini-3.5-flash pricing exists and resolves correctly."""
|
||||
entry = get_pricing_entry("gemini-3.5-flash", provider="google")
|
||||
assert entry is not None
|
||||
assert float(entry.input_cost_per_million) == 1.50
|
||||
assert float(entry.output_cost_per_million) == 9.00
|
||||
assert float(entry.cache_read_cost_per_million) == 0.15
|
||||
assert float(entry.cache_write_cost_per_million) == 1.50
|
||||
|
||||
|
||||
def test_gemini_provider_maps_to_google():
|
||||
"""Ensure using 'gemini' as provider resolves to 'google' pricing."""
|
||||
entry = get_pricing_entry("gemini-3.5-flash", provider="gemini")
|
||||
assert entry is not None
|
||||
assert float(entry.input_cost_per_million) == 1.50
|
||||
|
||||
# Also check base URL matching
|
||||
entry_base = get_pricing_entry(
|
||||
"gemini-3.5-flash",
|
||||
provider="custom",
|
||||
base_url="https://generativelanguage.googleapis.com/v1beta",
|
||||
)
|
||||
assert entry_base is not None
|
||||
assert float(entry_base.input_cost_per_million) == 1.50
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue