Skip to content

feat(quota): add Cursor quota provider and fix null tasks encoding - #442

Open
davidfarah2003 wants to merge 1 commit into
Willxup:mainfrom
davidfarah2003:fix/cursor-quota-and-null-tasks
Open

feat(quota): add Cursor quota provider and fix null tasks encoding#442
davidfarah2003 wants to merge 1 commit into
Willxup:mainfrom
davidfarah2003:fix/cursor-quota-and-null-tasks

Conversation

@davidfarah2003

Copy link
Copy Markdown

Two changes:

Cursor quota provider. Adds Cursor to the quota refresh pipeline through the CPA management api-call endpoint, using the same aiserver.v1.DashboardService calls Cursor's own dashboard makes. The period read is required; plan info and weekly agent usage are optional enrichment. Includes provider registration, normalization, subscription state, and tests.

e.tasks is not iterable crash fix. The refresh endpoint encoded nil Go slices as "tasks": null, and the Auth Files frontend iterated response.tasks directly. Both sides are fixed: Tasks/Rejected initialize as empty slices so JSON encodes [], and the frontend guards with response.tasks ?? [].

Verification: Go quota tests and the full vitest suite (1011 tests) pass; the null-tasks fix was mutation-tested (reverting either half turns the suite red on the named assertions).

Add Cursor quota refresh through CPA api-call using the DashboardService
endpoints Cursor's own dashboard uses: aggregated usage events for the
per-model table plus plan/subscription state; period is required, plan
and weekly agent quotas optional.

Fix the Auth Files crash "e.tasks is not iterable": initialize Tasks and
Rejected as empty slices so JSON encodes [] instead of null, and guard
the frontend with response.tasks ?? [].

@chatgpt-codex-connector chatgpt-codex-connector 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.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 7c1d4e264e

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

}
return &CursorAgentPayload{
UsagePercent: floatPtrField(object, "usagePercent", "usage_percent"),
HasNonZeroIncludedLimit: boolPtrField(object, "hasNonZeroIncludedLimit", "has_non_zero_included_limit"),

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P2 Badge Parse Cursor's nonzero-limit field with its actual casing

Cursor's GetSandUsageStatus response uses hasNonzeroIncludedLimit (and the corresponding snake-case form is has_nonzero_included_limit), but this parser accepts only spellings that split “nonzero” into two words. As a result, an explicit false is parsed as nil, so cursorWeeklyQuotaRow cannot apply its suppression check and accounts without an included agent limit can be shown a misleading weekly quota row.

Useful? React with 👍 / 👎.

Comment thread internal/quota/cursor.go
agent = p.requestAgent(ctx, input)
}()
}
wg.Wait()

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P2 Badge Bound optional Cursor requests independently

When either optional plan or agent endpoint hangs, this unconditional wait blocks the otherwise usable period result until the shared 20-second refresh-task context expires; it even delays returning an already-known period error. Because these calls are explicitly optional and their errors are discarded, they should use shorter child deadlines or be canceled once the required request completes, otherwise Cursor refreshes can occupy the shared worker pool for the full timeout and delay unrelated quota refreshes.

Useful? React with 👍 / 👎.

BillingCycleStart: stringField(object, "billingCycleStart", "billing_cycle_start"),
BillingCycleEnd: stringField(object, "billingCycleEnd", "billing_cycle_end"),
}
if planUsage := objectField(object, "planUsage", "plan_usage"); planUsage != nil {

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

P2 Badge Preserve Cursor on-demand usage from the period response

Cursor's current-period response can include an onDemandUsage sibling containing its own spend, remaining amount, and cap, but this parser retains only planUsage. For accounts with pay-as-you-go enabled, normalization consequently marks the monthly plan as exhausted and sets Allowed to false as soon as included usage reaches its limit even when on-demand capacity remains, while also hiding that capacity entirely; the on-demand payload needs to be parsed and reflected in the billing rows or the monthly availability calculation.

Useful? React with 👍 / 👎.

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