What happened:
While reviewing the deployment store sync logic in pipedv1, the head-deployment selection in pkg/app/pipedv1/apistore/deploymentstore/store.go:125-134 looks inverted relative to the Lister interface's docstring.
The interface promises:
ListAppHeadDeployments returns the map from application ID to its head of deploying deployments.
Head deployment is same with the oldest uncompleted one.
But the implementation writes pendings → planneds → runnings into the same map[string]*model.Deployment, so for an application with both a pending and a running deployment, the running one wins by overwrite order:
for _, d := range pendings { headDeployments[d.ApplicationId] = d }
for _, d := range planneds { headDeployments[d.ApplicationId] = d }
for _, d := range runnings { headDeployments[d.ApplicationId] = d }
A PENDING deployment is logically newer than a RUNNING one for the same application (it was created later, after the running one started), so this code returns the newest uncompleted deployment, not the oldest.
The same inversion exists at the corresponding location in the v0 store (pkg/app/piped/apistore/deploymentstore/store.go).
What you expected to happen:
Either:
- The docstring is updated to match the implementation ("head = newest uncompleted"), or
- The implementation is corrected to match the docstring — either reverse the write order or pick the head explicitly by
created_at.
I don't know which side is correct, since I haven't traced where ListAppHeadDeployments is consumed downstream. Whichever way it ends up, the docstring and the code should agree.
How to reproduce it:
Unit test against the store with two *model.Deployment instances sharing one ApplicationId, one DEPLOYMENT_PENDING and one DEPLOYMENT_RUNNING. Lister.ListAppHeadDeployments()[appID] returns the running one — the opposite of what the docstring promises.
Environment:
What happened:
While reviewing the deployment store sync logic in
pipedv1, the head-deployment selection inpkg/app/pipedv1/apistore/deploymentstore/store.go:125-134looks inverted relative to theListerinterface's docstring.The interface promises:
But the implementation writes
pendings → planneds → runningsinto the samemap[string]*model.Deployment, so for an application with both a pending and a running deployment, the running one wins by overwrite order:A
PENDINGdeployment is logically newer than aRUNNINGone for the same application (it was created later, after the running one started), so this code returns the newest uncompleted deployment, not the oldest.The same inversion exists at the corresponding location in the v0 store (
pkg/app/piped/apistore/deploymentstore/store.go).What you expected to happen:
Either:
created_at.I don't know which side is correct, since I haven't traced where
ListAppHeadDeploymentsis consumed downstream. Whichever way it ends up, the docstring and the code should agree.How to reproduce it:
Unit test against the store with two
*model.Deploymentinstances sharing oneApplicationId, oneDEPLOYMENT_PENDINGand oneDEPLOYMENT_RUNNING.Lister.ListAppHeadDeployments()[appID]returns the running one — the opposite of what the docstring promises.Environment:
pipedversion: master @78fdbeb7c(both v0 and v1 affected)control-planeversion: sameListAppHeadDeployments