Skip to content

Conversation

@ykmr1224
Copy link
Collaborator

@ykmr1224 ykmr1224 commented Oct 28, 2025

This PR is for feature branch feature/permissive

Description

  • Introduce RelBuilderWrapper and RelFieldBuilder to abstract the field operations with dynamic fields.
  • RelBuilderWrapper uses delegation to RelBuilder so that it won't allow direct operation on fields without considering dynamic fields.
    • It uses delegation instead of inheritance since RelBuilder internally call field or fields methods and inheritance cannot prohibit access to some methods.
    • RelBuilderWrapper hide original field/fields operations, and provide some package private method to allow RelFieldBuilder to access raw operations.
  • It leaves fixes for several commands to later PR to avoid this PR becomes too big.

Related Issues

Permissive mode RFC: #4349
Dynamic fields RFC: #4433

Check List

  • New functionality includes testing.
  • New functionality has been documented.
  • New functionality has javadoc added.
  • New functionality has a user manual doc added.
  • New PPL command checklist all confirmed.
  • API changes companion pull request created.
  • Commits are signed per the DCO using --signoff or -s.
  • Public documentation issue/PR created.

By submitting this pull request, I confirm that my contribution is made under the terms of the Apache 2.0 license.
For more information on following Developer Certificate of Origin and signing off your commits, please check here.

@ykmr1224 ykmr1224 self-assigned this Oct 28, 2025
@ykmr1224 ykmr1224 added enhancement New feature or request PPL Piped processing language calcite calcite migration releated labels Oct 28, 2025
Signed-off-by: Tomoyuki Morita <[email protected]>
Signed-off-by: Tomoyuki Morita <[email protected]>
* direct field access methods to maintain consistency with dynamic fields handling.
*/
@RequiredArgsConstructor
public class RelBuilderWrapper {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

why not just leverage the OpenSearchRelBuilder directly?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you want a derived class of RexBuilder, we can create one as well in OpenSearchPrepareImpl.perform()

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

As I described in the PR description, inheritance didn't work well since there are some internal access within RelBuilder to the methods we want to prohibit.

Copy link
Member

@LantaoJin LantaoJin Oct 31, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Override all fields of raw RelBuilder in OpenSearchRelBuilder cannot work?

In CalciteRelNodeVisitor, all calling to context.relBuilder.fields/field are interrupted in OpenSearchRelBuilder.fields/field.
But in calcite.RelBuilder, all fields/field will access its raw fields/field method. <=== do you want to prohibit this?

Delegation might not work either. For example, RelBuilder.sort() calls RelBuilder.field(). How to prohibit this calling with delegation class?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In CalciteRelNodeVisitor, all calling to context.relBuilder.fields/field are interrupted in OpenSearchRelBuilder.fields/field.
But in calcite.RelBuilder, all fields/field will access its raw fields/field method. <=== do you want to prohibit this?

No, inheritance won't work like that. If we override fields/field in a subclass, even the call from calcite.RelBuilder will call the method in subclass.

Delegation might not work either. For example, RelBuilder.sort() calls RelBuilder.field(). How to prohibit this calling with delegation class?

The idea is that, if the method won't work as we expect, customize or prohibit (and provide alternative way) the usage in RelBuilderWrapper.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Overall, the simple approach is merging current RelFieldBuilder and OpenSearchRelBuilder. But It's okey that we keep the current RelBuilderWrapper.

Copy link
Member

@LantaoJin LantaoJin Nov 4, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Oh, I think we still need to use RelBuilder or its derived class OpenSearchRelBuilder because RelBuilder will be used in Calcite optimization rules. For example,

final RelBuilder relBuilder = call.builder();

we do have opportunity to get the OpenSearchRelBuilder from call.builder() but no way to get the wrapper.

How about just add dynamic methods in OpenSearchRelBuilder and keep the original field and fields as static field methods.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hi Lantao,
Can you revisit my comment?
I think you haven't understood why inheritance won't work.
If we inherit and override method with throwing exception, internal call from other methods in RelBuilder will also fail. And I don't have good idea to workaround this other than reimplementing the method and call super.field instead, which duplicates the implementation from Calcite and not maintainable.

Copy link
Member

@LantaoJin LantaoJin Nov 4, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, you are right, in inheritance, if the method calling chain is A() -> B() -> C(). The overridden method A'() will still call the overridden C'(): A'() -> B() -> C'() .

Can we just add @Deprecated and java doc on the override method to callout this method should not be used in the project?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just a suggestion @ykmr1224 . I am okey on the current POC, we can postpone the problem about how to restrict the usage of RelBuilder in optimize rules (Calcite internal).

return relBuilder.peek(n).getRowType().getFieldNames();
}

public RexInputRef staticField(String fieldName) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

how about simplify all staticField to field?

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I named it as staticField so it would be more explicit to access static field.
We want to avoid someone unintentionally omit the existence of dynamic fields.

* direct field access methods to maintain consistency with dynamic fields handling.
*/
@RequiredArgsConstructor
public class RelBuilderWrapper {
Copy link
Member

@LantaoJin LantaoJin Oct 31, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Override all fields of raw RelBuilder in OpenSearchRelBuilder cannot work?

In CalciteRelNodeVisitor, all calling to context.relBuilder.fields/field are interrupted in OpenSearchRelBuilder.fields/field.
But in calcite.RelBuilder, all fields/field will access its raw fields/field method. <=== do you want to prohibit this?

Delegation might not work either. For example, RelBuilder.sort() calls RelBuilder.field(). How to prohibit this calling with delegation class?

@ykmr1224 ykmr1224 merged commit 8fe17a0 into opensearch-project:feature/permissive Nov 4, 2025
50 of 51 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

calcite calcite migration releated enhancement New feature or request PPL Piped processing language

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants