You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Found while fixing #12818 in the same function (buildAccumulator). Filed unassigned, not fixed — that dispatch scoped the work to the default arm, and this is a second accept-face narrowing with its own changeset and its own argument.
What was read
packages/drivers/driver-mongodb/src/mongodb-aggregation.ts, buildAccumulator, carries two arms for names the Query Protocol no longer declares:
case'array_agg':
return{$push: fieldRef??'$$ROOT'};case'string_agg':
// Collect into array; caller can post-process with $reducereturn{$push: fieldRef??''};
and postProcessAggregation carries the matching string_agg join.
AggregationFunction (packages/spec/src/data/query.zod.ts) declares six values — count, sum, avg, min, max, count_distinct. array_agg and string_agg were removed at #6188 under ADR-0049 enforce-or-remove, and the enum's own error map hands each a retirement prescription. packages/spec/src/data/query.test.ts pins the six.
The divergence
Both SQL faces already treat these two as class-1 undeclared names and refuse them with INVALID_QUERY / 400:
driver-turso's remote-transport.ts carries the same note verbatim.
driver-mongodb is the only face that still answers them. So one query gets a 400 on two backends and a $push array on the third — the local/remote fork #5907 exists to prevent, one vocabulary later.
Measured, without a server (mongodb-pipeline-evaluator.testkit.ts over AGGREGATION_ROWS): { function: 'array_agg', field: 'score' } answers [10, 20, 30, 40, 50, 60], and string_agg the same array before postProcessAggregation joins it. Both are pinned as current behaviour by mongodb-unrecognised-aggregate-function.test.ts (the "recorded, not fixed" block) so this divergence cannot be mistaken for an oversight in that file, and so whichever way it is decided, the pin moves deliberately.
Why it is worth a card rather than a silent cleanup
Reachability is the part that needs deciding rather than assuming. AggregationNodeSchema.function is the enum, so the protocol door rejects both spellings before they reach any driver; what can still reach buildAggregationPipeline is a direct caller of this exported builder, or the driver's own aggregate, which reads its aggregations through (query as any).aggregations. That is the same population #12818's refusal was written for.
Dispositions, for triage:
(a) delete both arms and let them fall to finding: driver-mongodb answers an unrecognised aggregate function as a silent SUM instead of refusing it #12818's class-1 refusal (400), matching both SQL faces. It also falsifies the converts string_agg arrays to joined strings case in mongodb-aggregation.test.ts, which would be INVERTED in place (asserting the refusal) rather than re-baselined, and postProcessAggregation's string_agg limb would go with them.
(b) keep them as a deliberate mongodb-only extension, and say so in the code — at which point the "one condition, one wording" parity note in driver-sql should record the exception.
(a) is the ADR-0049 direction and the one I would take, but it removes something a caller could be using today, so it is a vocabulary decision rather than a repair.
Whether any caller writes either spelling. Not swept across examples/, the dataset compiler, or service-analytics.
Not swept across the other faces for the reverse direction — whether driver-memory's analytics face also lowers more than the enum declares was not measured here.
Related: #12818 (the default arm, being fixed now), #6188 (the retirement), #7052 (the same interface's distinct?: boolean leftover after the same class of spec retirement — closed), #5907 (the two-class refusal these faces share).
Found while fixing #12818 in the same function (
buildAccumulator). Filed unassigned, not fixed — that dispatch scoped the work to thedefaultarm, and this is a second accept-face narrowing with its own changeset and its own argument.What was read
packages/drivers/driver-mongodb/src/mongodb-aggregation.ts,buildAccumulator, carries two arms for names the Query Protocol no longer declares:and
postProcessAggregationcarries the matchingstring_aggjoin.AggregationFunction(packages/spec/src/data/query.zod.ts) declares six values —count,sum,avg,min,max,count_distinct.array_aggandstring_aggwere removed at #6188 under ADR-0049 enforce-or-remove, and the enum's own error map hands each a retirement prescription.packages/spec/src/data/query.test.tspins the six.The divergence
Both SQL faces already treat these two as class-1 undeclared names and refuse them with
INVALID_QUERY/ 400:driver-sql:array_aggandstring_aggare in theUNDECLAREDroster ofsql-driver-out-of-contract-aggregate-function.test.ts, whose comment records that they moved there from class 2 at [spec] AggregationFunction 声明 8 个,SQL 族只实现 5 个 —— count_distinct / array_agg / string_agg 按 ADR-0049 enforce-or-remove 定去留 #6188;driver-turso'sremote-transport.tscarries the same note verbatim.driver-mongodbis the only face that still answers them. So one query gets a 400 on two backends and a$pusharray on the third — the local/remote fork #5907 exists to prevent, one vocabulary later.Measured, without a server (
mongodb-pipeline-evaluator.testkit.tsoverAGGREGATION_ROWS):{ function: 'array_agg', field: 'score' }answers[10, 20, 30, 40, 50, 60], andstring_aggthe same array beforepostProcessAggregationjoins it. Both are pinned as current behaviour bymongodb-unrecognised-aggregate-function.test.ts(the "recorded, not fixed" block) so this divergence cannot be mistaken for an oversight in that file, and so whichever way it is decided, the pin moves deliberately.Why it is worth a card rather than a silent cleanup
Reachability is the part that needs deciding rather than assuming.
AggregationNodeSchema.functionis the enum, so the protocol door rejects both spellings before they reach any driver; what can still reachbuildAggregationPipelineis a direct caller of this exported builder, or the driver's ownaggregate, which reads its aggregations through(query as any).aggregations. That is the same population #12818's refusal was written for.Dispositions, for triage:
converts string_agg arrays to joined stringscase inmongodb-aggregation.test.ts, which would be INVERTED in place (asserting the refusal) rather than re-baselined, andpostProcessAggregation'sstring_agglimb would go with them.driver-sqlshould record the exception.(a) is the ADR-0049 direction and the one I would take, but it removes something a caller could be using today, so it is a vocabulary decision rather than a repair.
What was NOT established
mongodb-memory-server's download is refused by the egress proxy — driver-mongodb 测试:两个套件并发下载 MongoDB 二进制,mongodb-memory-server 的 rename 竞态让全绿测试 exit 1(队列 flaky) #5517). Every value above comes from the in-process evaluator, which models the manual rather than observing a server.examples/, the dataset compiler, orservice-analytics.driver-memory's analytics face also lowers more than the enum declares was not measured here.Related: #12818 (the
defaultarm, being fixed now), #6188 (the retirement), #7052 (the same interface'sdistinct?: booleanleftover after the same class of spec retirement — closed), #5907 (the two-class refusal these faces share).