SteNicholas opened a new pull request, #469:
URL: https://github.com/apache/paimon-cpp/pull/469
<!-- PR titles must follow Conventional Commits: <type>(<optional-scope>):
<description> -->
### Purpose
<!-- Linking this pull request to the issue -->
Linked issue: close #468
<!-- What is the purpose of the change -->
Paimon C++ only implemented the `default` and `openapi` DLF signers, so a
REST catalog
configured with `dlf.signing-algorithm=openapi-v4` failed at creation. Java
Paimon signs
requests to DlfNext endpoints with this opt-in algorithm (apache/paimon#9918,
apache/paimon#9937).
Add `DlfOpenApiV4Signer` to sign requests to DlfNext OpenAPI endpoints with
`ACS4-HMAC-SHA256`, aligned with Java `DLFOpenApiV4Signer`. It is opt-in:
only
`dlf.signing-algorithm=openapi-v4` selects it, and a `dlfnext` endpoint
without a
configured algorithm still selects `openapi`.
- Port Java `DLFOpenApiActions` as `DlfOpenApiActions`, which maps the
method and path of
a request to its POP action. The V4 signer signs that action in
`x-acs-action` and
sends it with the request; a request that matches no registered operation
is signed
without one.
- Pass the sign headers to `DlfRequestSigner::Authorization` by pointer so a
signer can
add headers to them. The default and openapi signers only read them.
- Spell the `Host` and `Content-Type` headers as `RestApi` and the openapi
signer do, so
merging them replaces a header of the same name instead of sending a
second copy that
differs only in case. The signature lowercases every header name, so it
still matches
Java.
- Share the signing key derivation between the default and V4 signers.
### Tests
<!-- List UT and IT cases to verify this change -->
Unit tests in `src/paimon/rest/dlf_auth_test.cpp`:
- `DlfOpenApiV4SignerTest`:
- `MatchesJavaGoldenSignatureForEncodedQueryValues` and
`MatchesJavaGoldenSignatureWithAction`: match the signatures pinned by
Java
`DLFOpenApiV4SignerTest`, covering query value encoding, header sorting
and the
signed action.
- `SignsHeadersWithBody` and `OmitsBodyAndSecurityTokenHeadersWhenAbsent`:
the headers
signed with and without a body.
- `SignsUtcDateInNonUtcTimezone`: the date in `x-acs-date` and in the
credential scope
stays UTC when the local timezone is ahead of UTC by a day.
- `SignatureDependsOnRegion`,
`SignsHeaderNamesInLowerCaseAndValuesTrimmed`,
`SignsUnregisteredPathWithoutAction` and `RequiresSigningDate`.
- `DlfAuthProviderTest.SignsWithOpenApiV4OnlyWhenConfigured`: only
`dlf.signing-algorithm=openapi-v4` signs with ACS4 and sends
`x-acs-action`, including
the STS token, and the merged request carries one `Host` and one
`Content-Type` header.
- `DlfOpenApiActionsTest`, ported from Java `DLFOpenApiActionsTest`: every
operation
resolves to its own unique action, every request `RestApi` sends resolves
to its
action, names match whole segments and methods ignore case, and
unregistered requests
have no action.
### API and Format
<!-- Does this change affect API in include dir or storage format or
protocol -->
No public API or storage format changes. `include/paimon/catalog_options.h`
only updates
the documentation of `DLF_SIGNING_ALGORITHM`. The internal
`DlfRequestSigner::Authorization`
in `src/paimon/rest/dlf_auth.h` now takes the sign headers by pointer.
On the wire, a request signed with `openapi-v4` carries an `ACS4-HMAC-SHA256`
authorization and, when it matches a registered operation, an `x-acs-action`
header, as
the Java client sends. Requests signed with `default` or `openapi` are
unchanged.
### Documentation
<!-- Does this change introduce a new feature -->
Yes. `docs/source/user_guide/catalog.rst` documents `openapi-v4` for
`dlf.signing-algorithm` and shows it in the DLF configuration example.
### Generative AI tooling
<!--
If generative AI tooling has been used in the process of authoring this
patch, please include the
phrase: 'Generated-by: ' followed by the name of the tool and its version.
If no, write 'No'.
Please refer to the [ASF Generative Tooling
Guidance](https://www.apache.org/legal/generative-tooling.html) for details.
-->
Generated-by: Claude Code 2.1.310 (Claude Opus 5.5)
🤖 Generated with [Claude Code](https://claude.com/claude-code)
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]