Skip to content

Add Events for PolarisServiceImpl APIs #1904

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 4 commits into
base: main
Choose a base branch
from

Conversation

adnanhemani
Copy link
Collaborator

@adnanhemani adnanhemani commented Jun 16, 2025

Adding instrumentation for events for all events defined in PolarisServiceImpl.java. Not all events will be useful and/or necessary - but allow users to plug in with custom event listeners for any of these APIs. The default event listener is a no-op.

The main file to review here is PolarisServiceImpl. All new events are simply just a constructor and getter methods.

@adnanhemani adnanhemani reopened this Jun 16, 2025
@github-project-automation github-project-automation bot moved this from Done to PRs In Progress in Basic Kanban Board Jun 16, 2025
@@ -142,12 +211,24 @@ private PolarisAdminService newAdminService(
@Override
public Response createCatalog(
CreateCatalogRequest request, RealmContext realmContext, SecurityContext securityContext) {
String requestId = PolarisEvent.createRequestId();
Copy link
Contributor

Choose a reason for hiding this comment

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

A few remarks:

Injecting before/after event logic in every method looks like we are mixing concerns. I think the decorator pattern could make things look a lot nicer.

About the execution flow: how do we handle errors?

E.g. if the listener throws on a before event call, should the execution halt or continue?

Also: if the listener throws on an after event call, should the execution be aborted and the persisted changes rolled back, or should the business changes be kept? IOW, are we OK with weaker delivery guarantees for events (like "at most once")?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Re: execution flow

Personally, I'm okay if we do not give a successful execution back to the user if the event listeners throw an error. For the use case in which customers actually add perhaps additional authorization or validations to a call through an event listener, this is exactly what the customer would expect. This is how event listeners are currently instrumented today as well - and I don't see a solid reasoning to change this paradigm right now. (Event Listeners and their configuration are still the responsibility of the Polaris admin, as this is basically like a custom plugin; additionally, the sample events-to-persistence implementations in #1844 take this into account and purposefully will not throw errors during the execution of the event listener in-line code).


Re: decorator

I believe the pattern you are referring to includes defining a @decorator class which would also implement PolarisCatalogsApiService/PolarisPrincipalsApiService/PolarisPrincipalRolesApiService and then use the PolarisServiceImpl class as a delegator? If this is not correct, please do help provide some sample/hints that would make it clearer what you mean.

But going back - in the case of the decorator+delegator, sure this may make this particular file cleaner - but the same amount of code will exist as we will just be moving the event listener hooks to a different file and then calling PolarisServiceImpl from there. If you think that slight amount of cleanliness outweighs the redirection, I'm happy to take this as an action item. Wanted to confirm what you mean before going ahead with an implementation on this.

import org.apache.polaris.core.entity.PolarisPrivilege;

/** Event fired after a grant is added to a catalog role in Polaris. */
public class AfterAddGrantToCatalogRoleEvent implements PolarisEvent {
Copy link
Contributor

Choose a reason for hiding this comment

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

Couldn't all these event classes be records? We could even group them in one single file instead of having hundreds of similar files around.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Same response as: #1844 (comment)

@snazy
Copy link
Member

snazy commented Jun 18, 2025

I think this deserves a dev-ML discussions and consensus on the technical approach.
Alex and Eric already raised concerns about both the general and the specific technical approach

@adnanhemani
Copy link
Collaborator Author

@snazy - to be fair, Eric did not raise any concerns on this PR or approach (have verified offline with him as well). And I don't really see why this warrants a ML-thread. It seems that issues with this PR are implementation-specific, and I don't see a good reason to use ML threads for that (that is what PRs comments should be for).

But I will start a ML thread as per your suggestion - I hope there will be fruitful, outcome-driven conversation that will lead to a quick consensus.

@eric-maynard
Copy link
Contributor

I did have one or two comments on the related PR #1844, but that only to clarify the approach. I am OK with the direction of this PR and the other one; we need events for these operations. If we can reduce the amount of code needed to add the new events or otherwise break down or streamline the process that would be great but I have no blocking concerns at this time.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants