Skip to content

Commit

Permalink
Simple grouping with untyped properties or open types (#2034)
Browse files Browse the repository at this point in the history
In the simple grouping algorithm, the last sub-bullet point of the
projection function says:
> Otherwise, if $p'$ is a prefix of a path in $G$, let $v[q]=s_G
(u[q],p')$

and the recursively called function $s_G$ assumes that its first
argument is a structured instance. But if $q$ is an untyped property or
a property of an open type, $u[q]$ can also be primitive<sup>1</sup>,
and then the first bullet point does not make sense:
> Let $v$ be an instance of the type of $u$ without properties and
without entity-id.

I suggest to rephrase the last sub-bullet point so that the recursive
call is omitted in such cases. This is the least invasive change and its
leads to $q$ being omitted from the projection.

<sup>1</sup> Of course $u[q]$ can also be primitive if $q$ declares a
primitive type, but the problem occurs only if $p'$ is a prefix of a
path in $G$, which means for a grouping criterion of the form $q/r$ or
$s/q/r$. And if $q$ declares a primitive type, $q/r$ does not make sense
at all.
  • Loading branch information
HeikoTheissen authored Jan 8, 2025
1 parent c94f424 commit 5bade31
Show file tree
Hide file tree
Showing 3 changed files with 3 additions and 3 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -1981,7 +1981,7 @@ <h4 id="3231-simple-grouping"><a id="SimpleGrouping" href="#SimpleGrouping">3.2.
<ul>
<li>If <span class="math inline">\(u\)</span> has a subtype of the type addressed by <span class="math inline">\(p\)</span> and <span class="math inline">\(q\)</span> is only declared on that subtype, let <span class="math inline">\(p&#39;=p/p&#39;&#39;/q\)</span> where <span class="math inline">\(p&#39;&#39;\)</span> is a type-cast to the subtype, otherwise let <span class="math inline">\(p&#39;=p/q\)</span>.</li>
<li>If <span class="math inline">\(p&#39;\)</span> occurs in <span class="math inline">\(G\)</span>, let <span class="math inline">\(v[q]=u[q]\)</span>.</li>
<li>Otherwise, if <span class="math inline">\(p&#39;\)</span> is a prefix of a path in <span class="math inline">\(G\)</span>, let <span class="math inline">\(v[q]=s_G(u[q],p&#39;)\)</span>.</li>
<li>Otherwise, if <span class="math inline">\(p&#39;\)</span> is a prefix of a path in <span class="math inline">\(G\)</span> and <span class="math inline">\(u[q]\)</span> has a structured type, let <span class="math inline">\(v[q]=s_G(u[q],p&#39;)\)</span>.</li>
</ul></li>
<li>Return <span class="math inline">\(v\)</span>.</li>
</ul></li>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1461,7 +1461,7 @@ The output set of the `groupby` transformation is constructed in five steps.
- For each structural or navigation property $q$ of $u$:
- If $u$ has a subtype of the type addressed by $p$ and $q$ is only declared on that subtype, let $p'=p/p''/q$ where $p''$ is a type-cast to the subtype, otherwise let $p'=p/q$.
- If $p'$ occurs in $G$, let $v[q]=u[q]$.
- Otherwise, if $p'$ is a prefix of a path in $G$, let $v[q]=s_G(u[q],p')$.
- Otherwise, if $p'$ is a prefix of a path in $G$ and $u[q]$ has a structured type, let $v[q]=s_G(u[q],p')$.
- Return $v$.
2. The input set is split into subsets where two instances are in the same subset if their projections are [the same](#SamenessandOrder). If [representations of the same non-transient entity](#SamenessandOrder) are encountered during the comparison of two projections, the service MUST assign them to one subset with the merged representation if they are complementary and MUST reject the request if they are contradictory.
3. The set transformations from the second parameter are applied to each subset, resulting in a new set of potentially different structure and cardinality. Associated with each resulting set is the common projection of the instances in the subset from which the resulting set was computed.
Expand Down
2 changes: 1 addition & 1 deletion odata-data-aggregation-ext/3.2 Basic Aggregation.md
Original file line number Diff line number Diff line change
Expand Up @@ -350,7 +350,7 @@ The output set of the `groupby` transformation is constructed in five steps.
- For each structural or navigation property $q$ of $u$:
- If $u$ has a subtype of the type addressed by $p$ and $q$ is only declared on that subtype, let $p'=p/p''/q$ where $p''$ is a type-cast to the subtype, otherwise let $p'=p/q$.
- If $p'$ occurs in $G$, let $v[q]=u[q]$.
- Otherwise, if $p'$ is a prefix of a path in $G$, let $v[q]=s_G(u[q],p')$.
- Otherwise, if $p'$ is a prefix of a path in $G$ and $u[q]$ has a structured type, let $v[q]=s_G(u[q],p')$.
- Return $v$.
2. The input set is split into subsets where two instances are in the same subset if their projections are [the same](#SamenessandOrder). If [representations of the same non-transient entity](#SamenessandOrder) are encountered during the comparison of two projections, the service MUST assign them to one subset with the merged representation if they are complementary and MUST reject the request if they are contradictory.
3. The set transformations from the second parameter are applied to each subset, resulting in a new set of potentially different structure and cardinality. Associated with each resulting set is the common projection of the instances in the subset from which the resulting set was computed.
Expand Down

0 comments on commit 5bade31

Please sign in to comment.