Skip to content

refactor(types): remove forced tokenlens and cache casts#517

Merged
izadoesdev merged 1 commit into
stagingfrom
codex/desloppify-cleanup
Jun 30, 2026
Merged

refactor(types): remove forced tokenlens and cache casts#517
izadoesdev merged 1 commit into
stagingfrom
codex/desloppify-cleanup

Conversation

@izadoesdev

@izadoesdev izadoesdev commented Jun 30, 2026

Copy link
Copy Markdown
Member

Summary

  • remove forced as unknown as SourceModel casts from AI usage telemetry and dashboard token cost lookup
  • replace the links cache null object cast with an in-memory Symbol sentinel and honest cache union type
  • inline the small configured-model lookup wrapper while preserving fallback cost behavior

Verification

  • bun run check-types
  • bun run lint
  • bun run test
  • cd packages/ai && bun test src/lib/usage-telemetry.test.ts
  • cd apps/links && bun test src
  • bunx ultracite check packages/ai/src/lib/usage-telemetry.ts apps/dashboard/components/ai-elements/context.tsx apps/links/src/routes/redirect.ts

AI Disclosure

  • Prepared with AI assistance and human-reviewed before submission.

Summary by cubic

Remove unsafe casts in model cost lookups and caches to improve type safety, with no behavior changes. This makes tokenlens integrations and link caching clearer and safer.

  • Refactors
    • AI usage telemetry: construct SourceModel with satisfies, resolve costs via configured lookupAgentModelCost first, then fall back to tokenlens models.
    • Dashboard model lookup: remove forced casts; use satisfies for SourceModel.
    • Links redirect cache: replace null-object cast with a Symbol("null") sentinel and a precise union type in LRUCache.

Written for commit 0f9ac32. Summary will update on new commits.

Review in cubic

@vercel

vercel Bot commented Jun 30, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated (UTC)
dashboard Ready Ready Preview, Comment Jun 30, 2026 4:47pm
databuddy-status Ready Ready Preview, Comment Jun 30, 2026 4:47pm
1 Skipped Deployment
Project Deployment Actions Updated (UTC)
documentation Skipped Skipped Jun 30, 2026 4:47pm

@coderabbitai

coderabbitai Bot commented Jun 30, 2026

Copy link
Copy Markdown
Contributor

Important

Review skipped

Auto reviews are disabled on this repository. Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration

Configuration used: Repository UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: d7f0646b-e73b-4c2d-907c-4b08654339d7

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch codex/desloppify-cleanup

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@unkey-deploy

unkey-deploy Bot commented Jun 30, 2026

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Unkey Deploy

Name Status Preview Inspect Updated (UTC)
api (preview) Ready Visit Preview Inspect Jun 30, 2026 4:47pm

@greptile-apps

greptile-apps Bot commented Jun 30, 2026

Copy link
Copy Markdown
Contributor

Greptile Summary

This PR is a type-safety refactor across three files, removing as unknown as forced casts in favour of satisfies checks and replacing the object-based LRU null sentinel with a Symbol.

  • usage-telemetry.ts: Inlines the lookupConfiguredModel wrapper and createSourceModel helper, and adds the missing name: id field to the synthesised SourceModel object (the old cast was silently omitting a required field). satisfies SourceModel now validates the shape at compile time.
  • redirect.ts: Replaces the Object.freeze({ __null: true }) as unknown as CachedLink sentinel with Symbol("null"), widens the LRU cache value type to CachedLink | typeof NULL_SENTINEL, and narrows at the call site — eliminating any risk of accidentally treating the sentinel as a real CachedLink.
  • context.tsx: Removes the intermediate VercelModelId alias and replaces the as unknown as SourceModel cast with satisfies SourceModel, mirroring the telemetry change.

Confidence Score: 5/5

Safe to merge — all three files make purely type-level improvements with no runtime logic changes, and the one implicit behavioural fix (adding the missing name field to the synthesised SourceModel) corrects a pre-existing gap rather than introducing new risk.

The redirect sentinel swap from a frozen object to a Symbol is handled correctly at every call site — the cache type is widened, the equality check is preserved, and TypeScript now prevents accidentally passing the sentinel where a real CachedLink is expected. The satisfies SourceModel replacements validate shape at compile time and were confirmed by the author's type-check run. The inlining of lookupConfiguredModel preserves the exact same lookup priority order. No new async paths, no new error surfaces, and no behavioural regressions were introduced.

No files require special attention.

Important Files Changed

Filename Overview
packages/ai/src/lib/usage-telemetry.ts Removes two small helper functions, inlines their logic, and switches from as unknown as SourceModel to satisfies SourceModel; also silently fixes a missing name field that was previously masked by the unsafe cast.
apps/links/src/routes/redirect.ts Replaces the frozen-object null sentinel with a Symbol, widens the LRU cache type to `CachedLink
apps/dashboard/components/ai-elements/context.tsx Drops the VercelModelId alias and replaces the as unknown as SourceModel cast with satisfies SourceModel; purely cosmetic/type-safety improvement with no runtime change.

Flowchart

%%{init: {'theme': 'neutral'}}%%
flowchart TD
    A["resolveCostModel(modelId)"] --> B{lookupAgentModelCost}
    B -- "found" --> C["createCostModel(id, cost)\n{ canonical_id, cost, id, name } satisfies SourceModel"]
    B -- "not found" --> D{lookupTokenlensModel}
    D -- "found & has cost" --> E["{ canonical_id, ...model } satisfies SourceModel"]
    D -- "not found" --> F["resolveAgentModelCost (fallback)\ncreateCostModel(fallback.id, fallback.cost, true)"]
    C --> G[computeTokenCostsForModel]
    E --> G
    F --> G

    subgraph "redirect.ts lookupLink(slug)"
    H["linkCache.get(slug)"] --> I{undefined?}
    I -- "yes" --> J[check Redis / DB]
    I -- "no" --> K{=== NULL_SENTINEL Symbol?}
    K -- "yes" --> L["return { link: null }"]
    K -- "no" --> M["return { link: CachedLink }"]
    J -- "DB miss" --> N["linkCache.set(slug, NULL_SENTINEL)"]
    J -- "DB hit" --> O["linkCache.set(slug, link)"]
    end
Loading
%%{init: {'theme': 'base', 'themeVariables': {"darkMode": true, "background": "#0d1117", "primaryColor": "#21262d", "primaryTextColor": "#e6edf3", "primaryBorderColor": "#8b949e", "lineColor": "#8b949e", "textColor": "#e6edf3", "edgeLabelBackground": "#161b22", "actorBkg": "#21262d", "actorBorder": "#8b949e", "actorTextColor": "#e6edf3", "actorLineColor": "#8b949e", "signalColor": "#8b949e", "signalTextColor": "#e6edf3", "noteBkgColor": "#373320", "noteBorderColor": "#d4a72c", "noteTextColor": "#f0e6c0", "labelBoxBkgColor": "#21262d", "labelBoxBorderColor": "#8b949e", "labelTextColor": "#e6edf3", "loopTextColor": "#e6edf3", "activationBkgColor": "#30363d", "activationBorderColor": "#8b949e"}}}%%
flowchart TD
    A["resolveCostModel(modelId)"] --> B{lookupAgentModelCost}
    B -- "found" --> C["createCostModel(id, cost)\n{ canonical_id, cost, id, name } satisfies SourceModel"]
    B -- "not found" --> D{lookupTokenlensModel}
    D -- "found & has cost" --> E["{ canonical_id, ...model } satisfies SourceModel"]
    D -- "not found" --> F["resolveAgentModelCost (fallback)\ncreateCostModel(fallback.id, fallback.cost, true)"]
    C --> G[computeTokenCostsForModel]
    E --> G
    F --> G

    subgraph "redirect.ts lookupLink(slug)"
    H["linkCache.get(slug)"] --> I{undefined?}
    I -- "yes" --> J[check Redis / DB]
    I -- "no" --> K{=== NULL_SENTINEL Symbol?}
    K -- "yes" --> L["return { link: null }"]
    K -- "no" --> M["return { link: CachedLink }"]
    J -- "DB miss" --> N["linkCache.set(slug, NULL_SENTINEL)"]
    J -- "DB hit" --> O["linkCache.set(slug, link)"]
    end
Loading

Reviews (1): Last reviewed commit: "refactor(types): remove forced tokenlens..." | Re-trigger Greptile

@cubic-dev-ai cubic-dev-ai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No issues found across 3 files

Confidence score: 5/5

  • Automated review surfaced no issues in the provided summaries.
  • No files require special attention.
Architecture diagram
sequenceDiagram
    participant UsageTelemetry as "Usage Telemetry"
    participant Config as "AgentModelCost Config"
    participant Tokenlens as "tokenlens / vercelModels"
    participant Dashboard as "Dashboard Context"
    participant LinkCache as "LRU Cache (linkCache)"
    participant LinksRedirect as "Links Redirect"

    Note over UsageTelemetry, Tokenlens: AI Usage – Cost Model Resolution
    UsageTelemetry->>UsageTelemetry: resolveCostModel(modelId)
    UsageTelemetry->>Config: lookupAgentModelCost(modelId)
    alt Configured cost found
        Config-->>UsageTelemetry: resolved cost + id
        UsageTelemetry->>UsageTelemetry: createCostModel(id, cost, fallback=false)
        Note right of UsageTelemetry: NEW: construct SourceModel\nwith satisfies (no cast)
    else No configured cost
        UsageTelemetry->>Tokenlens: vercelModels.models[id]
        Tokenlens-->>UsageTelemetry: model entry (or undefined)
        alt Tokenlens model exists
            UsageTelemetry->>UsageTelemetry: construct CostModel with satisfies
        else Tokenlens model not found
            UsageTelemetry->>UsageTelemetry: create fallback cost model
        end
    end
    UsageTelemetry-->>UsageTelemetry: return CostModel

    Note over Dashboard, Tokenlens: Dashboard – Model Lookup
    Dashboard->>Dashboard: lookupModel(modelId)
    Dashboard->>Tokenlens: vercelModels.models[id]
    Tokenlens-->>Dashboard: model entry
    alt Model found
        Dashboard->>Dashboard: return SourceModel with satisfies
    else Not found
        Dashboard-->>Dashboard: return undefined
    end

    Note over LinksRedirect, LinkCache: Redirect – Link Cache
    LinksRedirect->>LinkCache: get(linkKey)
    alt Cache hit
        LinkCache-->>LinksRedirect: CachedLink or NULL_SENTINEL
        Note right of LinksRedirect: CHANGED: sentinel is\nSymbol("null") instead of cast object
        alt Value is NULL_SENTINEL
            LinksRedirect->>LinksRedirect: treat as not found / expired
        else Real cached link
            LinksRedirect->>LinksRedirect: use cached link data
        end
    else Cache miss
        LinkCache-->>LinksRedirect: undefined
        LinksRedirect->>LinksRedirect: fetch link from DB / API
        LinksRedirect->>LinkCache: set(key, link) or set(key, NULL_SENTINEL) for miss
        LinkCache-->>LinksRedirect: stored
    end
    LinksRedirect-->>LinksRedirect: proceed with redirect logic
Loading

Shadow auto-approve: would auto-approve. Type-safety refactor: replace unsafe casts with satisfies and use Symbol sentinel for cache null. No behavior changes.

Re-trigger cubic

@izadoesdev
izadoesdev merged commit 7b6c683 into staging Jun 30, 2026
19 checks passed
@izadoesdev
izadoesdev deleted the codex/desloppify-cleanup branch June 30, 2026 16:50
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