Skip to content

Conversation

@analogrelay
Copy link
Member

This PR fixes two bugs, with the same root cause: We URL encode paths before signing the request, but we should not be doing that.

This PR fixes both by storing both the unencoded and encoded form of path segments in the ResourceLink, which get preserved as links are combined (to create sub-clients). In some SDKs, we "unencode" the string before generating the signature payload, but that's challenging because the current URL encoding library we're using (form_urlencoded) doesn't actually support decoding. We can improve this later, for now I just want to get something that fixes the immediate issue.

We don't have direct APIs for managing offers, so the easiest way to end-to-end test this was to produce a test that kept trying to create a database until it got one with an offer RID containing +. I did that, saw it fail, fixed this issue, and it passed. Since that test is inherently inconsistent, I haven't actually included it.

Closes #3394

@github-actions github-actions bot added the Cosmos The azure_cosmos crate label Dec 16, 2025
@analogrelay analogrelay changed the title Ashleyst/fix url encoding cosmos: Fix URL encoding for authentication signatures Dec 16, 2025
@analogrelay analogrelay marked this pull request as ready for review December 16, 2025 23:20
@analogrelay analogrelay requested a review from a team as a code owner December 16, 2025 23:20
Copilot AI review requested due to automatic review settings December 16, 2025 23:20
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

This PR fixes URL encoding issues in Cosmos DB authentication signatures. The core problem was that paths were URL-encoded before signing requests, but the Cosmos DB API expects unencoded paths in signatures. This caused authentication failures when resource IDs contained URL-unsafe characters like +, @, or /.

Key changes:

  • Introduced LinkSegment to store both encoded and unencoded forms of path segments
  • Added item_by_rid() method for RID-based links that should not be encoded
  • Renamed resource_link() to link_for_signing() to clarify its purpose
  • Added comprehensive tests for URL encoding edge cases

Reviewed changes

Copilot reviewed 7 out of 8 changed files in this pull request and generated 1 comment.

Show a summary per file
File Description
sdk/cosmos/azure_data_cosmos/src/resource_context.rs Core fix: Added LinkSegment struct to store both encoded/unencoded path forms; separated path() (encoded) from link_for_signing() (unencoded); added item_by_rid() for RIDs that shouldn't be encoded
sdk/cosmos/azure_data_cosmos/src/pipeline/signature_target.rs Updated to use link_for_signing() instead of resource_link(); added test for RID-based links
sdk/cosmos/azure_data_cosmos/src/pipeline/mod.rs Changed offers API to use item_by_rid() instead of item() since offer IDs are RIDs
sdk/cosmos/azure_data_cosmos/src/models/throughput_properties.rs Made offer_id field public to support RID-based link construction
sdk/cosmos/azure_data_cosmos/tests/cosmos_offers.rs New test file for throughput CRUD operations on databases and containers; moved from cosmos_containers.rs
sdk/cosmos/azure_data_cosmos/tests/cosmos_items.rs Added test coverage for IDs with @ character to verify URL-unsafe characters work correctly
sdk/cosmos/azure_data_cosmos/tests/cosmos_containers.rs Removed autoscale throughput test (moved to cosmos_offers.rs)
Cargo.lock Unrelated changes to azure_storage_blob_test dependencies

@github-actions
Copy link

github-actions bot commented Dec 16, 2025

API Change Check

APIView identified API level changes in this PR and created the following API reviews

azure_data_cosmos

Copy link
Member

@tvaron3 tvaron3 left a comment

Choose a reason for hiding this comment

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

LGTM

@analogrelay analogrelay merged commit 3c19762 into Azure:main Dec 19, 2025
17 checks passed
@simorenoh
Copy link
Member

Addresses #2994

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Cosmos The azure_cosmos crate

Projects

None yet

4 participants