Skip to content

chore(deps): every uv package but harbor, with litellm v1.103.2 prices - #36

Merged
laithalsaadoon merged 2 commits into
mainfrom
factory/1-uv-deps
Oct 8, 2026
Merged

laithalsaadoon merged 2 commits into
mainfrom
factory/1-uv-deps

Conversation

@laithalsaadoon

Copy link
Copy Markdown
Owner

Bring every uv dependency but harbor up to date, with litellm v1.103.2 prices

Branch factory/1-uv-deps, two commits on origin/main 239e9e2:

  • d3b2c4a chore(deps): upgrade every uv package but harbor and cyclopts, litellm v1.103.2 prices
  • f896ef8 chore(deps): take cyclopts 5.1.1, a usage error exits 64

Supersedes Dependabot #33, #34 and #35, and closes Dependabot alert #1 (PyJWT, 2.14.0 -> 2.15.1). harbor stays at 0.23.0.

Why #33 was red: litellm's cost logic, not its data

litellm 1.103.0 changed _get_token_base_cost: a cache-creation or cache-read rate the price map leaves out resolves to the input rate instead of $0, and a missing 1h cache-write rate resolves to the cache-creation rate (BerriAI/litellm 22b377fe2aad "price cache writes without a creation rate", 8573241c4981 "resolve a missing 1h cache write rate after off-peak pricing", 88d1eb3b35b4 "bill cache-read tokens at the input rate when the map has no cache-read rate"). After regenerating the table, test_every_vendored_key_prices_identically and the five gpt-5.1-codex grid cells were still red, so the rule is ported into domain/pricing.py (_base_rates keeps cache rates None through the tier and threshold lookups, then resolves them). The port is sound to replicate: it is three None defaults and one fallback, and the identity grid now passes bit for bit over every shared key, shape and tier. An entry carrying off_peak_pricing is declined (litellm would price it by wall-clock time); no vendored entry carries one today. litellm was not held on 1.102.x.

Who pays more after this: any session with cache-write tokens on a model with no cache_creation_input_token_cost (107 of 258 bare keys, every OpenAI text model, plus anthropic.claude-instant-v1, anthropic.claude-v1, anthropic.claude-v2:1), and cache-read tokens on the 46 keys with no cache_read_input_token_cost (the *-pro, audio, gpt-3.5/gpt-4 and gpt-oss entries, and the three old Bedrock Claude ids). Every other Claude entry carries both cache rates and does not move (anthropic.claude-mythos-preview lacks them but prices input at 0, so it stays $0). Example: the codex synthetic golden goes from total_cost_usd 0.00198 to 0.003105 because harbor (through litellm 1.103.2) now bills its 900 cache-write tokens at gpt-5.1-codex's input rate.

CONVERTER_SCHEMA_VERSION 5 -> 6 (AGENTS.md rule: a litellm bump that can alter an artifact byte needs the decision by hand; total_cost_usd and metrics.cost_usd move), with the digest in test_converter_schema_version.py re-pinned. The next materialize re-converts the whole corpus.

Packages moved (uv.lock)

package from to
boto3 1.43.98 1.43.106
botocore 1.43.98 1.43.106
charset-normalizer 3.5.1 3.5.2
commitizen 4.18.1 4.19.0
coverage 7.16.1 7.16.2
cryptography 50.0.1 50.0.2
cyclopts 4.25.3 5.1.1
duckdb 1.5.5 1.5.6
fastapi 0.141.1 0.142.2
filelock 4.0.1 4.0.8
huggingface-hub 1.32.0 1.33.0
hypothesis 6.168.0 6.168.3
lefthook 2.1.14 2.1.15
litellm 1.102.0 1.103.2
multidict 6.9.0 6.9.1
opentelemetry-api (new, fastapi dependency) 1.45.0
platformdirs 4.11.11 4.12.2
pyjwt 2.14.0 2.15.1
python-dotenv 1.2.3 1.2.4
pytz 2026.3.post1 2026.4
regex 2026.9.10 2026.9.29
rich-rst 2.1.0 2.2.0
ruff 0.16.8 0.16.9
starlette 1.6.0 1.7.0
ty 0.0.82 0.0.84
uvicorn 0.53.0 0.54.0
wcwidth 0.8.4 0.9.1
wrapt 2.4.1 2.5.0

harbor 0.23.0 is unchanged. pyproject.toml and packages/atif-cli/pyproject.toml raise cyclopts>=4.10.2 to cyclopts>=5.1.1.

Held by cooldown (newer than the 7-day exclude-newer, upload time on PyPI)

  • polars 2.0.0 (2026-10-06), stays 1.44.2
  • pydantic 2.14.0 (2026-10-08), stays 2.13.5
  • tenacity 9.2.1 (2026-10-07), stays 9.1.4
  • lancedb 0.40.0 (2026-10-07), stays 0.39.0; also capped <0.40 in pyproject.toml
  • litellm 1.103.3 and 1.103.4 (1.103.4 on 2026-10-07), so litellm lands on 1.103.2
  • cyclopts 5.2.0 (2026-10-06, PowerShell completion only), so cyclopts lands on 5.1.1

Vendored price table: v1.102.0 -> v1.103.2

Regenerated with uv run scripts/update_prices.py --ref v1.103.2, never by hand. 257 -> 259 entries: added gpt-5.5-cyber and gpt-rosalind-research, none removed. 24 entries changed a rate field; the rest of the diff is metadata (source on 108 Bedrock entries, supports_tool_search, supports_thinking_cache_preservation, deprecation_date, max_input_tokens for claude-sonnet-4-5 200000 -> 1000000). The converter reads no *_batches key, so of the rate changes only the flex rows can move a cost, and only for a flex service tier. Every rate change, per token:

model field old new
gpt-3.5-turbo-0125 input_cost_per_token_batches (absent) 2.5e-07
gpt-3.5-turbo-0125 output_cost_per_token_batches (absent) 7.5e-07
gpt-3.5-turbo-1106 input_cost_per_token_batches (absent) 1e-06
gpt-3.5-turbo-1106 output_cost_per_token_batches (absent) 2e-06
gpt-4-0613 input_cost_per_token_batches (absent) 1.5e-05
gpt-4-0613 output_cost_per_token_batches (absent) 3e-05
gpt-4-turbo-2024-04-09 input_cost_per_token_batches (absent) 5e-06
gpt-4-turbo-2024-04-09 output_cost_per_token_batches (absent) 1.5e-05
gpt-5 input_cost_per_token_batches (absent) 6.25e-07
gpt-5 output_cost_per_token_batches (absent) 5e-06
gpt-5-2025-08-07 input_cost_per_token_batches (absent) 6.25e-07
gpt-5-2025-08-07 output_cost_per_token_batches (absent) 5e-06
gpt-5-mini input_cost_per_token_batches (absent) 1.25e-07
gpt-5-mini output_cost_per_token_batches (absent) 1e-06
gpt-5-mini-2025-08-07 input_cost_per_token_batches (absent) 1.25e-07
gpt-5-mini-2025-08-07 output_cost_per_token_batches (absent) 1e-06
gpt-5-nano input_cost_per_token_batches (absent) 2.5e-08
gpt-5-nano output_cost_per_token_batches (absent) 2e-07
gpt-5-nano-2025-08-07 input_cost_per_token_batches (absent) 2.5e-08
gpt-5-nano-2025-08-07 output_cost_per_token_batches (absent) 2e-07
gpt-5.1 cache_read_input_token_cost_flex (absent) 6.25e-08
gpt-5.1 input_cost_per_token_batches (absent) 6.25e-07
gpt-5.1 input_cost_per_token_flex (absent) 6.25e-07
gpt-5.1 output_cost_per_token_batches (absent) 5e-06
gpt-5.1 output_cost_per_token_flex (absent) 5e-06
gpt-5.1-2025-11-13 cache_read_input_token_cost_flex (absent) 6.25e-08
gpt-5.1-2025-11-13 input_cost_per_token_batches (absent) 6.25e-07
gpt-5.1-2025-11-13 input_cost_per_token_flex (absent) 6.25e-07
gpt-5.1-2025-11-13 output_cost_per_token_batches (absent) 5e-06
gpt-5.1-2025-11-13 output_cost_per_token_flex (absent) 5e-06
gpt-5.2 cache_read_input_token_cost_flex (absent) 8.75e-08
gpt-5.2 input_cost_per_token_batches (absent) 8.75e-07
gpt-5.2 input_cost_per_token_flex (absent) 8.75e-07
gpt-5.2 output_cost_per_token_batches (absent) 7e-06
gpt-5.2 output_cost_per_token_flex (absent) 7e-06
gpt-5.2-2025-12-11 cache_read_input_token_cost_flex (absent) 8.75e-08
gpt-5.2-2025-12-11 input_cost_per_token_batches (absent) 8.75e-07
gpt-5.2-2025-12-11 input_cost_per_token_flex (absent) 8.75e-07
gpt-5.2-2025-12-11 output_cost_per_token_batches (absent) 7e-06
gpt-5.2-2025-12-11 output_cost_per_token_flex (absent) 7e-06
gpt-5.2-pro input_cost_per_token_batches (absent) 1.05e-05
gpt-5.2-pro output_cost_per_token_batches (absent) 8.4e-05
gpt-5.2-pro-2025-12-11 input_cost_per_token_batches (absent) 1.05e-05
gpt-5.2-pro-2025-12-11 output_cost_per_token_batches (absent) 8.4e-05
o1 input_cost_per_token_batches (absent) 7.5e-06
o1 output_cost_per_token_batches (absent) 3e-05
o1-2024-12-17 input_cost_per_token_batches (absent) 7.5e-06
o1-2024-12-17 output_cost_per_token_batches (absent) 3e-05
o3 input_cost_per_token_batches (absent) 1e-06
o3 output_cost_per_token_batches (absent) 4e-06
o3-2025-04-16 input_cost_per_token_batches (absent) 1e-06
o3-2025-04-16 output_cost_per_token_batches (absent) 4e-06
o3-mini input_cost_per_token_batches (absent) 5.5e-07
o3-mini output_cost_per_token_batches (absent) 2.2e-06
o3-mini-2025-01-31 input_cost_per_token_batches (absent) 5.5e-07
o3-mini-2025-01-31 output_cost_per_token_batches (absent) 2.2e-06
o4-mini cache_read_input_token_cost_flex 1.375e-07 1.38e-07
o4-mini input_cost_per_token_batches (absent) 5.5e-07
o4-mini output_cost_per_token_batches (absent) 2.2e-06
o4-mini-2025-04-16 cache_read_input_token_cost_flex 1.375e-07 1.38e-07
o4-mini-2025-04-16 input_cost_per_token_batches (absent) 5.5e-07
o4-mini-2025-04-16 output_cost_per_token_batches (absent) 2.2e-06

cyclopts 5

Read the 5.0.0, 5.1.0 and 5.1.1 release notes (GitHub releases of BrianPugh/cyclopts, 2026-10-08). atif-sql has no meta app, no *args subcommand and no parameter named help or version, so fuzzy-match removal, child-wins fallthrough, greedy *args and flag shadowing do not reach it. One change does: parse errors exit 2 instead of 1, and 2 is a wire code in EXIT_CODES (empty_session, no_embeddings). main() runs app(sys.argv[1:], exit_on_error=False) and maps cyclopts.CycloptsError to EXIT_CODES["invalid_input"] (64) after cyclopts prints its panel. TestUsageErrorExitCode covers --bogus, convert --bogus and search q -k many; with the mapping removed it fails 3 of 3. docs/reference/cli.md and errors.py say so. Help pages gain cyclopts 5 metavars (--format CHOICE); no committed doc holds help output.

Goldens

ATIF_FREEZE_GOLDENS=1 uv run pytest packages/atif-converter/tests/test_harbor_oracle.py -k freeze rewrote only codex.synthetic.trajectory.json, and only $.final_metrics.total_cost_usd (0.00198 -> 0.003105) and $.steps[2].metrics.cost_usd (0.000525 -> 0.00165). claude_code.synthetic did not change. The eight gpt-5.1-codex and gpt-5.5 rows of FROZEN_PRICES in test_pricing_policy.py are re-captured from litellm 1.103.2 for the same reason.

Gates (2026-10-08, in a fresh clone)

  • mise run check on commit 1: 2351 passed, 1 skipped in 256.77 s; ruff, ty, pyright (0 errors), import-linter, actionlint, lefthook validate, vex check all green.
  • mise run check on commit 2 (head): 2354 passed, 1 skipped in 242.68 s, all legs green.
  • The four chore(deps): bump the python-minor-patch group with 7 updates #33 files (test_pricing_identity, test_harbor_oracle, test_parity_codex, test_codex_conversion_port) pass inside both runs.
  • mise run lock:check: uv lock --check resolved 137 packages, clean.
  • mise run security:vex:check: osv-scanner.toml matches security/atif-sql.openvex.json; the ledger has no statements, so it needed no edit.
  • mise run docs:install && mise run docs:gate: 0 errors, 0 warnings; vitest 64 passed.

Risks

  • Every corpus re-converts on the next materialize (schema 6), and Codex sessions with cache writes report higher total_cost_usd. This follows litellm, which harbor uses, so parity holds; whether OpenAI actually bills cache writes at the input rate is litellm's claim, not ours.
  • A usage error exits 64 instead of 1. A script that branched on 1 for a typo changes; scripts/atif-sql-refresh.sh branches only on 0 and 78.

What to look at

  • packages/atif-converter/src/atif_converter/domain/pricing.py _base_rates and _tiered_rates against litellm v1.103.2 litellm/litellm_core_utils/llm_cost_calc/utils.py _get_token_base_cost.
  • packages/atif-cli/src/atif_cli/app.py main.
  • The golden diff is two numbers.

Lead review (2026-10-08)

Re-ran on f896ef8 in a fresh worktree: mise run check 2354 passed, 1 skipped (pyright 0 errors), lock:check clean at 137 packages, and test_pricing_identity, test_harbor_oracle, test_parity_codex and test_codex_conversion_port 243 passed, 1 skipped. harbor is 0.23.0 in uv.lock. The three cited litellm commits exist and are inside v1.103.0 (compare v1.103.0...88d1eb3b35b4 is behind).

🤖 Generated with Claude Code

laithalsaadoon and others added 2 commits October 8, 2026 15:45
…m v1.103.2 prices

`uv lock --upgrade` past the 7-day cooldown, with cyclopts held at 4.25.3 for
its own commit and harbor still at 0.23.0. Moves boto3 1.43.106, pytz 2026.4,
commitizen 4.19.0, litellm 1.103.2, hypothesis 6.168.3, ruff 0.16.9, ty
0.0.84, duckdb 1.5.6, lefthook 2.1.15 and pyjwt 2.15.1 (Dependabot alert #1),
plus their transitives. Supersedes Dependabot #33 and #35.

litellm 1.103.0 changed its cost arithmetic: a cache-creation or cache-read
rate the price map leaves out resolves to the input rate instead of $0, and a
missing 1h write rate to the cache-creation rate (BerriAI/litellm 22b377fe2aad,
8573241c4981, 88d1eb3b35b4). That, not the data, is what turned #33 red, so
the vendored table is regenerated with `scripts/update_prices.py --ref
v1.103.2` and `domain/pricing.py` ports the rule; an entry carrying
off_peak_pricing is declined rather than priced by wall-clock time.

The codex synthetic golden is re-frozen by `ATIF_FREEZE_GOLDENS=1` because
harbor prices its 900 cache-write tokens at gpt-5.1-codex's input rate under
litellm 1.103.2: only `total_cost_usd` and one step's `cost_usd` move. The
eight gpt-5.1-codex / gpt-5.5 frozen prices in test_pricing_policy.py are
re-captured from litellm 1.103.2 for the same reason.

CONVERTER_SCHEMA_VERSION 5 -> 6: total_cost_usd and metrics.cost_usd change
for sessions with cache tokens on a model without cache rates, so the corpus
re-converts on the next materialize.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
cyclopts 5 is a major: the 5.0.0 notes list dropped fuzzy command matching,
child-wins fallthrough parsing, greedy *args subcommands, user parameters
shadowing --help/--version, and parse errors exiting 2 instead of 1. atif-sql
has no meta app, no *args command and no help/version parameter, so only the
exit code reaches it, and 2 is a wire code in EXIT_CODES (empty_session,
no_embeddings): an agent would read a typo as an empty session. main() runs
the app with exit_on_error=False and maps cyclopts' parse error to
invalid_input (64) after cyclopts prints its panel. The new test fails with
the mapping removed (3 red) and passes with it.

Both floors (root and atif-cli) rise to >=5.1.1 so test_distribution's union
holds. Supersedes Dependabot #34.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@laithalsaadoon
laithalsaadoon marked this pull request as ready for review October 8, 2026 18:01
@laithalsaadoon
laithalsaadoon merged commit a995f9e into main Oct 8, 2026
17 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant