Skip to content

limit is unvalidated, and the Shopify path does not clamp it at all #4

Description

@royalpinto007

What

The limit argument reaches both connectors without validation, and the two
paths disagree about what they do with it.

src/connectors.ts:12, the Shopify read, interpolates it raw:

const url = `https://${env.SHOPIFY_STORE}/admin/api/2024-07/orders.json?status=any&limit=${limit}`;

src/connectors.ts:65, the database read, clamps only the top:

`${env.SUPABASE_URL}/rest/v1/${table}?select=*&limit=${Math.min(limit, 50)}`

The tool schema says limit: { type: "number", description: "max rows (1-50)", default: 10 },
but nothing enforces that range, and the schema is advisory: the caller is an
agent, and an agent will eventually send something surprising.

What gets through today

input Shopify URL DB URL
1000 limit=1000, unbounded page limit=50, clamped
-5 limit=-5 limit=-5, Math.min only bounds above
NaN limit=NaN limit=NaN
1.5 limit=1.5 limit=1.5

None of these are a security hole, since the table allowlist and the write gate
still hold. It is a robustness and cost problem: an unbounded Shopify page is a
large upstream response an agent asked for by accident, and limit=NaN is a
confusing 4xx rather than a clear refusal.

Suggested fix

Validate once, where the arguments are parsed, rather than in each connector, so
the two paths cannot drift again:

  • coerce to an integer
  • reject or clamp outside 1 to 50
  • decide deliberately whether an out-of-range limit is a clamp or an error. An
    error is more honest for an agent, since a silent clamp makes it think it saw
    everything

Whichever you choose, add the case to the tests from #3.

Good first issue

Yes. It is a small, self-contained change with a clear right answer, and it
touches the argument-handling path which is a good way to learn the codebase.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions