feat: add estimate-tokens command for offline LLM token & cost estimation - #12
Open
malteos wants to merge 2 commits into
Open
feat: add estimate-tokens command for offline LLM token & cost estimation#12malteos wants to merge 2 commits into
malteos wants to merge 2 commits into
Conversation
…tion Reconstructs the exact DSPy prompt per dataset sample and counts tokens with the model's own tokenizer (tiktoken for OpenAI/Azure, HF AutoTokenizer for huggingface/* models) via LiteLLM's token_counter; prices the result via LiteLLM's model map. Makes no API calls. - New src/commonlid/evaluation/token_cost.py: estimate() + TokenCostEstimate. Accounts for the system prompt (per-request overhead) and an optional per-sample reasoning-token assumption (billed as completion tokens). Handles unknown-model pricing (reports tokens, no cost) and unresolved tokenizers (heuristic fallback + note). --limit projects a measured subset onto the full dataset. - New `commonlid estimate-tokens` CLI command mirroring `run`'s options, accepting the same dspy:<name> spec; text and --json output. - Tests, README + adding-a-model guide.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Adds
commonlid estimate-tokens— offline token & cost estimation for LLMevaluation runs, so we can budget a full-benchmark run (e.g. gpt-5 on the
full
commonliddataset) before spending anything. Makes no API calls.The command reconstructs the exact DSPy prompt the evaluator would send per
sample (system instruction + per-sample text, via
ChatAdapter.formaton thesame signature
runuses), counts tokens with the model's own tokenizer, andprices the result via LiteLLM.
What it does
token_counterusestiktokenfor OpenAI/Azure models and a Hugging Face
AutoTokenizerforhuggingface/*models (installtransformersfor the latter).--reasoning-tokensper-sampleassumption (default
0, billed as completion tokens) — true usage can't beknown before a run, so the output labels the assumption used.
cost
n/arather than a misleading$0.pip install transformersnote; never crashes an estimate.--limit Nmeasures a subset and projects to the full dataset;--jsonfor machine-readable output. Accepts the same
dspy:<name>spec asrun.Example
gpt-5 on the full
commonliddataset (373,230 samples)Measured by this command (offline, full dataset):
Implied gpt-5 pricing from LiteLLM: ~$1.25/M input, ~$10/M output.
Cost is dominated by the reasoning-token assumption — input tokens (111M,
~$139) are fixed, while the output side scales with
--reasoning-tokens:--reasoning-tokensFor a task as short as a one-word language ID, real reasoning usage is likely
toward the low end; dial it in with
reasoning_efforton the actual run.Files
src/commonlid/evaluation/token_cost.py— new:estimate()+TokenCostEstimate.src/commonlid/cli.py— new@app.command("estimate-tokens").tests/unit/test_token_cost.py— new: 9 unit tests (arithmetic, reasoningroll-up,
dspy:stripping, unknown-model & zero-price handling, missingtokenizer fallback,
--limitextrapolation, and a realChatAdaptershapeguard).
README.md,docs/contributing/adding_a_model.md— usage docs.Test plan
make lint— cleanmake typecheck— cleanmake test— 258 passed, coverage 94.7%commonlid_nano(offline): text output,--reasoning-tokens,--limitextrapolation,--json, and HFn/a-pricing paths.commonlid(table above).Notes / out of scope
reasoning_effortintoDSPyLLMModelfor the real run is a separatechange; this estimator only assumes a reasoning-token budget.
tiktoken, already present via LiteLLM. HF-model tokenization is best-effortpending
transformers.