Skip to content

Both SDKs: PaginatedMarketsResult.total and PaginatedEventsResult.total are optional — core requires them #1409

Description

@realfishsam

Gap

Core defines PaginatedMarketsResult.total and PaginatedEventsResult.total as required number fields. Both SDKs model them as optional, which means consumers who write result.total without a null-check have different runtime semantics depending on whether they use core directly or go through an SDK.

Core

core/src/BaseExchange.ts lines 411–429:

export interface PaginatedMarketsResult {
    data: UnifiedMarket[];
    total: number;          // ← required
    nextCursor?: string;
}

export interface PaginatedEventsResult {
    data: UnifiedEvent[];
    total: number;          // ← required
    nextCursor?: string;
}

total carries no ? and is not | undefined — the core contract is that every paginated response includes the count.

TypeScript SDK

sdks/typescript/pmxt/models.ts lines 240–263:

export interface PaginatedMarketsResult {
    data: UnifiedMarket[];
    total?: number;          // ← optional (wrong)
    nextCursor?: string;
}

export interface PaginatedEventsResult {
    data: UnifiedEvent[];
    total?: number;          // ← optional (wrong)
    nextCursor?: string;
}

Python SDK

sdks/python/pmxt/models.py lines 411–436:

@dataclass
class PaginatedMarketsResult:
    data: List[UnifiedMarket]
    total: Optional[int] = None   # ← optional (wrong)
    next_cursor: Optional[str] = None

@dataclass
class PaginatedEventsResult:
    data: List[UnifiedEvent]
    total: Optional[int] = None   # ← optional (wrong)
    next_cursor: Optional[str] = None

Evidence

  • core/src/BaseExchange.ts:416: total: number — no ?, no | undefined
  • core/src/BaseExchange.ts:427: total: number — same
  • sdks/typescript/pmxt/models.ts:245: total?: number
  • sdks/typescript/pmxt/models.ts:259: total?: number
  • sdks/python/pmxt/models.py:418: total: Optional[int] = None
  • sdks/python/pmxt/models.py:432: total: Optional[int] = None

Impact

  • SDK consumers using result.total to render pagination controls (e.g. "page 2 of 47") must guard against undefined/None even though core always sends the count. This produces unnecessary defensive code.
  • TypeScript: result.total has type number | undefined; arithmetic like Math.ceil(result.total / pageSize) silently produces NaN when total is omitted despite core guaranteeing it.
  • Python: result.total typed as Optional[int]; code like range(0, result.total, page_size) requires an explicit not-None check that the core contract makes unnecessary.
  • Divergence from core weakens the SDK as a drop-in replacement for direct core usage.

Found by automated Core-to-SDK surface coverage audit

Metadata

Metadata

Assignees

No one assigned

    Labels

    core-sdk-gapCore engine capabilities not exposed in SDKs

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions