Skip to content

bug: piped's ListNotCompletedDeployments call ignores pagination and can miss deployments #6696

@veyron-kairo

Description

@veyron-kairo

What happened

In both piped (v0) and pipedv1, the deployment store's sync() loop calls ListNotCompletedDeployments exactly once per sync cycle and discards the cursor field on the response:

  • pkg/app/piped/apistore/deploymentstore/store.go:105-111
  • pkg/app/pipedv1/apistore/deploymentstore/store.go:105-111

Both files carry an explicit TODO that has been there since the RPC was introduced:

// TODO: Call ListNotCompletedDeployments itervally until all required deployments are fetched.
resp, err := s.apiClient.ListNotCompletedDeployments(ctx, &pipedservice.ListNotCompletedDeploymentsRequest{})

The server already returns a cursor on partial pages (pkg/app/server/service/pipedservice/service.proto:278-281), but the request message has no cursor / page_size fields, and the server (pkg/app/server/grpcapi/piped_api.go:350-386) does not accept one either — so there is currently no way for piped to request the next page.

Impact

If the controlplane's datastore returns a partial page of not-completed deployments (this depends on the backing datastore's default page size), piped will silently skip every deployment past the first page until the next sync tick — and since sync always starts from the beginning, the tail can be starved indefinitely under steady deployment pressure.

This is the classic "cursor returned but never followed" bug; it becomes user-visible as "some deployments appear stuck in PENDING/PLANNED until piped restarts or load decreases."

Proposed fix

  1. Add cursor (string) and page_size (int32) to ListNotCompletedDeploymentsRequest in service.proto, regenerate stubs.
  2. In PipedAPI.ListNotCompletedDeployments, forward req.Cursor and req.PageSize into datastore.ListOptions.
  3. In both piped stores, replace the single call with a loop that re-invokes the RPC with the returned cursor until it comes back empty, accumulating deployments across pages before classifying them into pendings / planneds / runnings.
  4. Add table-driven tests for both stores against a fake apiClient that returns multiple pages.

Happy to split this into a proto/server PR and a piped-client PR if maintainers would prefer smaller diffs. Will sign commits with DCO.

Environment

  • Branch: master at commit 78fdbeb7c
  • Affected components: piped, pipedv1, controlplane

If a maintainer is willing to assign this to me, I would like to pick it up.

Metadata

Metadata

Assignees

No one assigned

    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