Skip to content
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

Correct the handling of access delegation mode #211

Merged
merged 5 commits into from
Sep 4, 2024

Conversation

dimas-b
Copy link
Contributor

@dimas-b dimas-b commented Aug 26, 2024

Description

Iceberg REST API spec defines two possible values for the X-Iceberg-Access-Delegation:

  • vended-credentials
  • remote-signing

This change fixes Polaris docs to use the vended-credentials value instead of previous (incorrect) value of true and makes the REST API service validate the X-Iceberg-Access-Delegation header submitted by the client against the spec.

Backward-compatibility with old clients using the value of true for access delegation is maintained.

Detailed changes:

  • Add AccessDelegationMode enum to parse and represent specified
    delegation modes in java.

  • Update IcebergCatalogAdapter to validate that if access
    delegation is supported by the client, that "vended-credentials"
    is accepted ("remote-signing" is not supported by the server).

  • Interpret the single header value of true as vended-credentials.

  • Remove unused method parameters.

  • Re-generate docs

Type of change

Please delete options that are not relevant.

  • Bug fix (non-breaking change which fixes an issue)
  • Documentation update
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to not work as expected)
  • This change requires a documentation update

How Has This Been Tested?

Existing and new unit tests

Checklist:

Please delete options that are not relevant.

  • I have performed a self-review of my code
  • I have commented my code, particularly in hard-to-understand areas
  • I have made corresponding changes to the documentation

private EnumSet<AccessDelegationMode> parseAccessDelegationModes(String accessDelegationMode) {
EnumSet<AccessDelegationMode> delegationModes =
AccessDelegationMode.fromProtocolValuesList(accessDelegationMode);
if (!delegationModes.isEmpty() && !delegationModes.contains(VENDED_CREDENTIALS)) {
Copy link
Contributor

Choose a reason for hiding this comment

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

For backward compatibility, can we support "true" for the time being?

Copy link
Contributor Author

@dimas-b dimas-b Aug 26, 2024

Choose a reason for hiding this comment

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

We could, but is it critical enough to justify carrying this baggage forward? Note that true is an invalid header value according to the Iceberg REST Catalog spec and Polaris is not released yet.

Copy link
Contributor

Choose a reason for hiding this comment

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

It seems like there will be some need to reconcile "strict intent" vs "hints" better in the future, since right now a lot of the Iceberg spec is open-ended about interpretation -- for example, the spec currently says:

The server may choose to supply access via any or none of the requested mechanisms.

This also relates to apache/iceberg#10359 in that some behaviors currently can only "guess" at the caller's intent.

I agree that any hard-coding of "true" is probably not good baggage to carry forward. I would say though that extrapolating from #77 and how the Tabular "demo REST docker image" provides hooks for directly returning the server-wide application credentials in credential-vending, maybe it's worth providing some extensibility here.

What if we extract a server-level configuration parameter or two:

  • SUPPORTED_ACCESS_DELEGATION_MODES=vended-credentials,...
  • ERROR_ON_FAILED_NEGOTIATION_FOR_ACCESS_DELEGATION_MODE=true

The first one would just be a set-intersection between the list of modes the client wants and the set that the server claims to accept. I suppose the later mapping of declared modes to access-delegation impl will be something to add in the future once we actually need to plumb it through to PolarisCatalogHandlerWrapper to do different things for different modes.

The second one will dictate whether the server should be in "strict" mode and return an error response, or instead be permissive and just log a warning (or if there was a way to return helpful warnings in Iceberg REST responses that'd be great).

To the last point I wonder if we should also think of proposing some standard scaffolding for "warning notices" in REST responses that client-libraries can start to support to display to a caller in whatever way is most natural for the client-library. I know cloud providers have gone through this exercise before so that individual service providers can have a standard way to start providing deprecation notices, etc.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

The server may choose to supply access via any or none of the requested mechanisms.

My reading of this is that if the client specifies some access modes via the header, the server must use zero, one or more of them. The server may not use a delegation mode that the client did not request (for the client may not be able to handle it).

In this PR, if the client does not request any delegation mode, the server will not use "vended credentials" (same as before). If the client sends "vended credentials" and something else, the server will use "vended credentials" (same as before).

If the client requests true - that will lead to an error response (change in behaviour).

If the client requests only remote signing - that will lead to an error response (change in behaviour). Previously, the server would still use "vended credentials", so this is a bug fix, IMHO.

I'm not against adding config for more lenient processing, but given that there's no released Polaris version that supported old values, I think we can use simpler and stricter validation logic. It is easier to relax conditions after a release than tighten them if we have to.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

After some offline thinking, I will add backward compatibility support for true presently.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

backward compatibility added

Copy link
Contributor

Choose a reason for hiding this comment

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

Makes sense, I think that's a decent tradeoff for now since "true" was unfortunately exposed through docs for awhile so this would facilitate migrating some initial proofs-of-concept for now.

I agree with having strict validation in general, and agree erroring on unsupported remote-signing or any other invalid values for now is a good idea since it's easier to relax such behaviors than tighten in the future.

snazy
snazy previously approved these changes Aug 27, 2024
Copy link
Member

@snazy snazy left a comment

Choose a reason for hiding this comment

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

Thanks @dimas-b !

Copy link
Contributor

@dennishuo dennishuo left a comment

Choose a reason for hiding this comment

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

LGTM

Comment on lines +57 to +59
if (protocolValues.trim().toLowerCase(Locale.ROOT).equals("true")) {
return EnumSet.of(VENDED_CREDENTIALS);
}
Copy link
Contributor

Choose a reason for hiding this comment

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

This isn't a blocker for this PR, but I think we need a plan to deprecate it.

RussellSpitzer
RussellSpitzer previously approved these changes Aug 28, 2024
@RussellSpitzer
Copy link
Member

@dimas-b Sorry about this but could you please rebase? Please ping me when you do so I can merge

* Add `AccessDelegationMode` enum to parse and represent specified
  delegation modes in java.

* Update `IcebergCatalogAdapter` to validate that if access
  delegation is supported by the client, that "vended-credentials"
  is accepted ("remote-signing" is not supported by the server).

* Remove unused method parameters.
@dimas-b
Copy link
Contributor Author

dimas-b commented Aug 29, 2024

@RussellSpitzer : rebased :)

  • Manually resolved conflicts in the first commit
  • Re-ran docs/build for the last commit

@RussellSpitzer RussellSpitzer enabled auto-merge (squash) September 3, 2024 21:10
@RussellSpitzer RussellSpitzer merged commit ed4c0cb into apache:main Sep 4, 2024
3 checks passed
@dimas-b dimas-b deleted the access-delegation-mode branch September 4, 2024 15:58
dimas-b added a commit to dimas-b/polaris-site that referenced this pull request Sep 6, 2024
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.

6 participants