Skip to content

Conversation

@natsoman
Copy link
Contributor

What does this PR do?

Introduces CosmosDB module.

Why is it important?

ComsosDB container can be managed through Golang.

How to test this PR

It contains tests that run operations against the Cosmos DB container.

@netlify
Copy link

netlify bot commented Oct 23, 2025

Deploy Preview for testcontainers-go ready!

Name Link
🔨 Latest commit 2aaf95d
🔍 Latest deploy log https://app.netlify.com/projects/testcontainers-go/deploys/690b5b4ac9181b000802b3b3
😎 Deploy Preview https://deploy-preview-3452--testcontainers-go.netlify.app
📱 Preview on mobile
Toggle QR Code...

QR Code

Use your smartphone camera to open QR code link.

To edit notification comments on pull requests, go to your Netlify project configuration.

@coderabbitai
Copy link

coderabbitai bot commented Oct 23, 2025

Summary by CodeRabbit

  • New Features

    • Added Azure Cosmos DB emulator container provisioning to the Azure module, enabling local testing of Cosmos DB applications.
    • Automatically generates connection strings and manages container endpoints for seamless integration with Cosmos DB clients.
    • Includes example patterns demonstrating database and container creation workflows.
  • Documentation

    • Added comprehensive Cosmos DB module documentation with configuration options and usage examples.

Walkthrough

This PR introduces Azure CosmosDB module support to testcontainers-go. It adds a Container type, Run() function for container orchestration, a ConnectionString() method for emulator access, and a custom policy for HTTP request routing. Tests and documentation demonstrate integration with the Azure CosmosDB SDK.

Changes

Cohort / File(s) Summary
CosmosDB Container Implementation
modules/azure/cosmosdb/cosmosdb.go
New Container type wrapping testcontainers.Container; Run() function to create and configure CosmosDB containers with port 8081/tcp exposed and log-based wait strategy; ConnectionString() method to derive emulator endpoint and construct connection strings with predefined Cosmos DB Emulator key
CosmosDB Policy
modules/azure/cosmosdb/policy.go
New ContainerPolicy type for HTTP request routing; NewContainerPolicy() to initialize with container endpoint; Do() method to override request host; ClientOptions() to integrate policy into azcosmos retry pipeline
CosmosDB Tests & Examples
modules/azure/cosmosdb/cosmosdb_test.go, modules/azure/cosmosdb/examples_test.go
TestCosmosDB integration test demonstrating database and container creation with azcosmos client; ExampleRun() and ExampleRun_connect() example tests showing container startup and client integration patterns
Documentation
docs/modules/azure.md
Adds CosmosDB section documenting Run function signature, container options, ConnectionString method, usage examples, and link in Azure module index
Module Dependencies
modules/azure/go.mod
Upgrades azcore from v1.17.0 to v1.19.1; adds azcosmos v1.4.1, azblob v1.6.0, azqueue v1.0.0; updates azidentity and internal dependencies

Sequence Diagram(s)

sequenceDiagram
    participant User
    participant Run as cosmosdb.Run()
    participant Container as testcontainers
    participant Policy as ContainerPolicy
    participant Client as azcosmos.Client

    User->>Run: Run(ctx, img, opts...)
    activate Run
    Run->>Container: Create container with port 8081/tcp
    Run->>Container: Apply default + custom options
    Container-->>Run: Container started
    Run-->>User: *Container, nil
    deactivate Run

    User->>User: Create client from ConnectionString
    activate User
    User->>User: Call ConnectionString(ctx)
    User->>Policy: NewContainerPolicy(ctx, container)
    Policy-->>User: *ContainerPolicy with endpoint
    User->>Client: Create client with policy
    Client->>Client: Register policy in PerRetryPolicies
    User->>Policy: Policy.Do(request) on each API call
    activate Policy
    Policy->>Policy: Override request.Host
    Policy-->>Client: Forward to next policy
    deactivate Policy
    Client-->>User: Response
    deactivate User
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

  • Policy.Do() method: Verify HTTP request host override logic and error handling
  • Error wrapping: Check context wrapping consistency across Container, ConnectionString, and policy functions
  • azcosmos integration: Confirm ClientOptions embedding and PerRetryPolicies integration
  • Port and endpoint derivation: Validate ConnectionString construction using PortEndpoint and constant Cosmos DB Emulator key

Possibly related PRs

  • chore(azurite): use Run function #3318: Migrates other Azure modules (azurite, eventhubs, servicebus) to the same testcontainers.Run-style option composition pattern used in this CosmosDB implementation

Suggested reviewers

  • mdelapenya

Poem

🐰 Cosmos twinkles from the cloud,
Now in containers, spinning proud,
With endpoints mapped and policies true,
The emulator dances through and through!
Testcontainers blooms—another day,
Azure's cosmos here to stay! 🌟

Pre-merge checks and finishing touches

✅ Passed checks (2 passed)
Check name Status Explanation
Description check ✅ Passed The pull request description is directly related to the changeset, explaining what the PR does (introduces CosmosDB module), why it matters (enables Go management of Cosmos DB), and how to test it (includes test operations).
Title check ✅ Passed The title clearly and specifically describes the main change: adding a new CosmosDB module to the Azure functionality.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@natsoman natsoman marked this pull request as ready for review October 23, 2025 11:54
@natsoman natsoman requested a review from a team as a code owner October 23, 2025 11:54
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 4

🧹 Nitpick comments (5)
modules/cosmosdb/policy.go (3)

19-23: Use %w for error wrapping

Preserve the original error for callers.

-    return nil, fmt.Errorf("port endpoint: %v", err)
+    return nil, fmt.Errorf("port endpoint: %w", err)

30-35: Host rewrite vs scheme: confirm TLS path

You set Host and URL.Host but not URL.Scheme. This is fine if the connection string already has the correct scheme. Ensure callers use an HTTPS AccountEndpoint when the emulator serves TLS (typical), otherwise requests will fail during TLS negotiation.

Optionally store a scheme in the policy and set req.Raw().URL.Scheme to keep Host/Scheme consistent when needed.


37-44: Avoid overwriting caller options; offer an Apply/merge helper

ClientOptions() returns a fresh azcosmos.ClientOptions and can clobber caller-provided settings (transport, telemetry, retries, additional policies).

Example:

// Apply injects the policy into existing options without overwriting other fields.
func (p *ContainerPolicy) Apply(opts *azcosmos.ClientOptions) {
	opts.ClientOptions.PerRetryPolicies = append([]policy.Policy{p}, opts.ClientOptions.PerRetryPolicies...)
}

Keep ClientOptions() for convenience, but document that it overrides PerRetryPolicies.

modules/cosmosdb/cosmosdb.go (2)

48-56: Connection string key flagged by scanners; add allowlist note

The hard-coded key is the official Cosmos DB Emulator master key, safe for tests but triggers gitleaks.

Apply an inline allowlist to avoid CI noise, and keep the well-known value:

-    const testAccKey = "C2y6yDjf5/R+ob0N8A7Cgv30VRDJIWEHLM+4QDU5DE2nQ9nDuVTqobD4b8mGGyPMbIZnqyMsEcaGQy67XIw/Jw=="
+    // gitleaks:allow — official Cosmos DB Emulator key for local testing
+    const testAccKey = "C2y6yDjf5/R+ob0N8A7Cgv30VRDJIWEHLM+4QDU5DE2nQ9nDuVTqobD4b8mGGyPMbIZnqyMsEcaGQy67XIw/Jw=="

If TLS remains enabled (recommended), ensure the AccountEndpoint host matches the emulator certificate (commonly "localhost"); otherwise, set a transport with a custom root or an opt-in InsecureSkipVerify in client options used by azcosmos.


24-35: Option precedence: defaults first, then user is fine; document behavior

Appending user customizers after defaults lets callers extend or override. For flags like Cmd args, duplication may occur. Consider documenting precedence and whether "last write wins" applies for conflicting options.

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 32220d6 and de2ec73.

⛔ Files ignored due to path filters (1)
  • modules/cosmosdb/go.sum is excluded by !**/*.sum
📒 Files selected for processing (10)
  • .github/dependabot.yml (1 hunks)
  • .vscode/.testcontainers-go.code-workspace (1 hunks)
  • docs/modules/cosmosdb.md (1 hunks)
  • mkdocs.yml (1 hunks)
  • modules/cosmosdb/Makefile (1 hunks)
  • modules/cosmosdb/cosmosdb.go (1 hunks)
  • modules/cosmosdb/cosmosdb_test.go (1 hunks)
  • modules/cosmosdb/examples_test.go (1 hunks)
  • modules/cosmosdb/go.mod (1 hunks)
  • modules/cosmosdb/policy.go (1 hunks)
🧰 Additional context used
🧠 Learnings (1)
📚 Learning: 2025-09-18T08:24:27.479Z
Learnt from: mdelapenya
PR: testcontainers/testcontainers-go#3254
File: .github/dependabot.yml:21-21
Timestamp: 2025-09-18T08:24:27.479Z
Learning: In the testcontainers-go repository, submodules like atlaslocal that are part of a parent module (e.g., mongodb) share the same go.mod file and should not have separate Dependabot entries. They are already monitored through the parent module's Dependabot configuration entry.

Applied to files:

  • .github/dependabot.yml
  • modules/cosmosdb/go.mod
🧬 Code graph analysis (4)
modules/cosmosdb/policy.go (1)
modules/cosmosdb/cosmosdb.go (1)
  • Container (17-19)
modules/cosmosdb/cosmosdb_test.go (3)
modules/cosmosdb/cosmosdb.go (1)
  • Run (22-46)
testing.go (1)
  • CleanupContainer (91-97)
modules/cosmosdb/policy.go (1)
  • NewContainerPolicy (19-28)
modules/cosmosdb/examples_test.go (3)
modules/cosmosdb/cosmosdb.go (1)
  • Run (22-46)
cleanup.go (1)
  • TerminateContainer (97-108)
modules/cosmosdb/policy.go (1)
  • NewContainerPolicy (19-28)
modules/cosmosdb/cosmosdb.go (2)
options.go (4)
  • ContainerCustomizer (22-24)
  • WithExposedPorts (454-459)
  • WithCmdArgs (470-475)
  • WithWaitStrategy (366-368)
wait/log.go (1)
  • ForLog (118-120)
🪛 checkmake (0.2.2)
modules/cosmosdb/Makefile

[warning] 3-3: Missing required phony target "all"

(minphony)


[warning] 3-3: Missing required phony target "clean"

(minphony)

🪛 Gitleaks (8.28.0)
modules/cosmosdb/cosmosdb.go

[high] 54-54: Detected a Generic API Key, potentially exposing access to various services and sensitive operations.

(generic-api-key)

🪛 markdownlint-cli2 (0.18.1)
docs/modules/cosmosdb.md

13-13: Fenced code blocks should have a language specified

(MD040, fenced-code-language)

🔇 Additional comments (7)
.github/dependabot.yml (1)

29-29: LGTM!

The CosmosDB module entry is correctly added to the Dependabot configuration, alphabetically sorted between consul and couchbase, consistent with other standalone modules in the repository.

.vscode/.testcontainers-go.code-workspace (1)

56-59: LGTM!

The workspace configuration entry for the CosmosDB module is properly structured and alphabetically ordered.

mkdocs.yml (1)

80-80: LGTM!

The navigation entry for the CosmosDB module documentation is correctly added and properly ordered.

modules/cosmosdb/Makefile (1)

1-5: LGTM!

This minimal delegating Makefile follows the standard pattern for testcontainers-go modules. The static analysis warnings about missing "all" and "clean" phony targets are expected for this pattern and can be safely ignored.

modules/cosmosdb/go.mod (1)

1-73: LGTM!

The go.mod file follows the standard pattern for testcontainers-go modules with appropriate Azure Cosmos DB dependencies and the correct replace directive for local development.

modules/cosmosdb/cosmosdb_test.go (1)

15-77: LGTM!

The test comprehensively validates the CosmosDB module functionality, including container creation, client initialization, database and container operations, and item CRUD operations. The cleanup pattern with testcontainers.CleanupContainer is correctly implemented and handles edge cases gracefully.

modules/cosmosdb/examples_test.go (1)

14-84: LGTM!

Both example functions effectively demonstrate the CosmosDB module usage. ExampleRun shows basic container creation, while ExampleRun_connect demonstrates a complete workflow with client creation and database operations. The examples follow Go conventions with proper cleanup, error handling, and testable output.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (2)
modules/cosmosdb/policy.go (2)

13-17: Consider enhancing the doc comment for clarity.

The type definition is correct, but the doc comment could be more explicit about the intent. While it explains what is overridden, it could better explain why this is needed (i.e., to pin requests to the emulator endpoint).

Apply this diff to improve clarity:

-// ContainerPolicy ensures that the request always points to the container. It is required to
-// override globalEndpointManager of CosmosDB client, which dynamically updates the [http.Request.Host].
+// ContainerPolicy ensures that requests always target the CosmosDB emulator container endpoint.
+// It overrides the CosmosDB client's globalEndpointManager, which would otherwise dynamically
+// update [http.Request.Host] based on global endpoint discovery, pinning all requests to the container.
 type ContainerPolicy struct {
 	endpoint string
 }

19-28: Use %w for error wrapping to preserve error chain.

The constructor logic is correct, but line 22 uses %v which discards the original error chain. Use %w to enable proper error unwrapping.

Apply this diff:

 func NewContainerPolicy(ctx context.Context, c *Container) (*ContainerPolicy, error) {
 	endpoint, err := c.PortEndpoint(ctx, defaultPort, "")
 	if err != nil {
-		return nil, fmt.Errorf("port endpoint: %v", err)
+		return nil, fmt.Errorf("port endpoint: %w", err)
 	}
 
 	return &ContainerPolicy{
 		endpoint: endpoint,
 	}, nil
 }
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between de2ec73 and 4b17555.

📒 Files selected for processing (1)
  • modules/cosmosdb/policy.go (1 hunks)
🧰 Additional context used
🧬 Code graph analysis (1)
modules/cosmosdb/policy.go (1)
modules/cosmosdb/cosmosdb.go (1)
  • Container (17-19)
🔇 Additional comments (3)
modules/cosmosdb/policy.go (3)

1-11: LGTM!

Package declaration and imports are appropriate for the Azure CosmosDB policy implementation.


30-35: LGTM!

The Do method correctly implements the policy.Policy interface. Setting both Host and URL.Host ensures proper request routing to the container endpoint.


37-44: LGTM!

The ClientOptions method correctly integrates the policy into Azure CosmosDB client configuration by embedding it in PerRetryPolicies.

@mdelapenya
Copy link
Member

Hi @natsoman thanks for this contribution! Do you think this container can be part of the existing Azure module? We have specialized containers in there for some other Azure services.

We follow that pattern in the GCloud and MongoDB (for atlas) modules.

@natsoman
Copy link
Contributor Author

natsoman commented Oct 23, 2025

Hi @natsoman thanks for this contribution! Do you think this container can be part of the existing Azure module? We have specialized containers in there for some other Azure services.

We follow that pattern in the GCloud and MongoDB (for atlas) modules.

Hi @mdelapenya, sure! I had the same thought but wasn’t entirely sure about the best way to proceed. Should I update docs/modules/azure.md manually? 🤔

@mdelapenya
Copy link
Member

@natsoman yes please 🙏

I can help you out with that if you see it too cumbersome.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (1)
modules/azure/cosmosdb/cosmosdb.go (1)

48-56: Consider adding a comment about the well-known emulator key.

The hardcoded key is intentional and correct—it's the official Azure Cosmos DB Emulator key published by Microsoft for local development. However, the static analysis tool flagged it, and future readers might question it.

Consider adding a clarifying comment:

+	// Well-known key for Azure Cosmos DB Emulator
+	// See: https://learn.microsoft.com/azure/cosmos-db/emulator
 	const testAccKey = "C2y6yDjf5/R+ob0N8A7Cgv30VRDJIWEHLM+4QDU5DE2nQ9nDuVTqobD4b8mGGyPMbIZnqyMsEcaGQy67XIw/Jw=="
 	return fmt.Sprintf("AccountEndpoint=%s;AccountKey=%s;", endpoint, testAccKey), nil
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 4b17555 and 3c93dea.

⛔ Files ignored due to path filters (1)
  • modules/azure/go.sum is excluded by !**/*.sum
📒 Files selected for processing (7)
  • .vscode/.testcontainers-go.code-workspace (1 hunks)
  • docs/modules/azure.md (2 hunks)
  • modules/azure/cosmosdb/cosmosdb.go (1 hunks)
  • modules/azure/cosmosdb/cosmosdb_test.go (1 hunks)
  • modules/azure/cosmosdb/examples_test.go (1 hunks)
  • modules/azure/cosmosdb/policy.go (1 hunks)
  • modules/azure/go.mod (2 hunks)
✅ Files skipped from review due to trivial changes (1)
  • modules/azure/go.mod
🚧 Files skipped from review as they are similar to previous changes (1)
  • .vscode/.testcontainers-go.code-workspace
🧰 Additional context used
🧬 Code graph analysis (4)
modules/azure/cosmosdb/examples_test.go (3)
modules/azure/cosmosdb/cosmosdb.go (1)
  • Run (22-46)
cleanup.go (1)
  • TerminateContainer (97-108)
modules/azure/cosmosdb/policy.go (1)
  • NewContainerPolicy (19-28)
modules/azure/cosmosdb/cosmosdb.go (2)
options.go (4)
  • ContainerCustomizer (22-24)
  • WithExposedPorts (454-459)
  • WithCmdArgs (470-475)
  • WithWaitStrategy (366-368)
wait/log.go (1)
  • ForLog (118-120)
modules/azure/cosmosdb/cosmosdb_test.go (3)
modules/azure/cosmosdb/cosmosdb.go (1)
  • Run (22-46)
testing.go (1)
  • CleanupContainer (91-97)
modules/azure/cosmosdb/policy.go (1)
  • NewContainerPolicy (19-28)
modules/azure/cosmosdb/policy.go (1)
modules/azure/cosmosdb/cosmosdb.go (1)
  • Container (17-19)
🪛 Gitleaks (8.28.0)
modules/azure/cosmosdb/cosmosdb.go

[high] 54-54: Detected a Generic API Key, potentially exposing access to various services and sensitive operations.

(generic-api-key)

🔇 Additional comments (10)
docs/modules/azure.md (2)

26-26: LGTM! CosmosDB module properly added to the package list.

The documentation follows the established pattern for other Azure services in this module.


312-355: LGTM! Documentation structure is consistent and complete.

The CosmosDB section follows the same documentation pattern as other Azure services (Azurite, EventHubs, ServiceBus), including Run function signature, image usage, container options, container methods, and examples.

modules/azure/cosmosdb/cosmosdb_test.go (2)

15-20: LGTM! Proper test setup and cleanup pattern.

The test correctly calls CleanupContainer immediately after Run, which ensures cleanup even if the container creation fails. The testcontainers library handles nil containers gracefully.


22-77: LGTM! Comprehensive integration test.

The test thoroughly validates the CosmosDB emulator functionality by:

  • Creating a client with connection string and policy
  • Creating a database and container
  • Performing CRUD operations (create and read item)
  • Properly checking errors at each step

This provides good coverage for the module's core functionality.

modules/azure/cosmosdb/examples_test.go (2)

15-40: LGTM! Clear basic example.

The example demonstrates the simplest use case: starting the CosmosDB container and verifying it's running. Proper cleanup and error handling are in place.


42-85: LGTM! Comprehensive connection example.

This example effectively demonstrates:

  • Container startup
  • Connection string retrieval
  • Policy creation for request routing
  • Client initialization
  • Database creation with status verification

This will be helpful for users getting started with the module. The example code referenced in the documentation (line 354 of azure.md) correctly points to this function.

modules/azure/cosmosdb/cosmosdb.go (1)

16-46: LGTM! Well-structured container implementation.

The implementation follows the established testcontainers-go patterns:

  • Wraps the base Container type
  • Run function applies sensible defaults (exposed port, disabled explorer, wait strategy)
  • Allows user customization through variadic options
  • Proper error handling with context

The wait strategy on "Started" log message ensures the container is ready before returning.

modules/azure/cosmosdb/policy.go (3)

13-28: LGTM! Policy correctly overrides endpoint routing.

The ContainerPolicy is well-designed to solve the specific problem of forcing Cosmos DB SDK requests to the emulator container. The comment clearly explains why this is needed (to override globalEndpointManager).

The constructor properly retrieves the endpoint from the container with appropriate error handling.


30-35: LGTM! Request override logic is correct.

The Do method properly implements the policy.Policy interface by:

  1. Overriding both Host and URL.Host to ensure the request targets the container
  2. Calling Next() to continue the policy chain

This ensures all Cosmos DB requests go to the emulator regardless of SDK's internal routing logic.


37-44: LGTM! Proper integration with Azure SDK client options.

The ClientOptions method correctly creates azcosmos.ClientOptions with the policy added to PerRetryPolicies, ensuring the endpoint override happens on every request attempt.

@natsoman
Copy link
Contributor Author

natsoman commented Oct 23, 2025

@natsoman yes please 🙏

I can help you out with that if you see it too cumbersome.

@mdelapenya no worries, I was just wondering if there’s any automation I might have missed.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

🧹 Nitpick comments (1)
modules/azure/cosmosdb/cosmosdb.go (1)

48-56: Add a comment documenting the well-known emulator key.

The implementation is correct, but the hardcoded account key on line 54 should include a comment explaining that this is the publicly documented, well-known key for the Azure CosmosDB Emulator (not a security issue). This will help clarify the static analysis warning and prevent confusion.

Apply this diff to add a clarifying comment:

 func (c *Container) ConnectionString(ctx context.Context) (string, error) {
 	endpoint, err := c.PortEndpoint(ctx, defaultPort, defaultProtocol)
 	if err != nil {
 		return "", fmt.Errorf("port endpoint: %w", err)
 	}
 
+	// Well-known, publicly documented account key for the Azure CosmosDB Emulator.
+	// See: https://learn.microsoft.com/en-us/azure/cosmos-db/how-to-develop-emulator
 	const testAccKey = "C2y6yDjf5/R+ob0N8A7Cgv30VRDJIWEHLM+4QDU5DE2nQ9nDuVTqobD4b8mGGyPMbIZnqyMsEcaGQy67XIw/Jw=="
 	return fmt.Sprintf("AccountEndpoint=%s;AccountKey=%s;", endpoint, testAccKey), nil
 }
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 3c93dea and c165e20.

⛔ Files ignored due to path filters (1)
  • modules/azure/go.sum is excluded by !**/*.sum
📒 Files selected for processing (7)
  • .vscode/.testcontainers-go.code-workspace (1 hunks)
  • docs/modules/azure.md (2 hunks)
  • modules/azure/cosmosdb/cosmosdb.go (1 hunks)
  • modules/azure/cosmosdb/cosmosdb_test.go (1 hunks)
  • modules/azure/cosmosdb/examples_test.go (1 hunks)
  • modules/azure/cosmosdb/policy.go (1 hunks)
  • modules/azure/go.mod (2 hunks)
✅ Files skipped from review due to trivial changes (1)
  • docs/modules/azure.md
🚧 Files skipped from review as they are similar to previous changes (2)
  • .vscode/.testcontainers-go.code-workspace
  • modules/azure/cosmosdb/cosmosdb_test.go
🧰 Additional context used
🧬 Code graph analysis (3)
modules/azure/cosmosdb/examples_test.go (3)
modules/azure/cosmosdb/cosmosdb.go (1)
  • Run (22-46)
cleanup.go (1)
  • TerminateContainer (97-108)
modules/azure/cosmosdb/policy.go (1)
  • NewContainerPolicy (19-28)
modules/azure/cosmosdb/policy.go (1)
modules/azure/cosmosdb/cosmosdb.go (1)
  • Container (17-19)
modules/azure/cosmosdb/cosmosdb.go (2)
options.go (4)
  • ContainerCustomizer (22-24)
  • WithExposedPorts (454-459)
  • WithCmdArgs (470-475)
  • WithWaitStrategy (366-368)
wait/log.go (1)
  • ForLog (118-120)
🪛 Gitleaks (8.28.0)
modules/azure/cosmosdb/cosmosdb.go

[high] 54-54: Detected a Generic API Key, potentially exposing access to various services and sensitive operations.

(generic-api-key)

🔇 Additional comments (7)
modules/azure/cosmosdb/policy.go (3)

13-28: LGTM!

The ContainerPolicy type and constructor are well-designed. The documentation clearly explains why this policy is needed (to override the globalEndpointManager), and error handling is appropriate.


30-35: LGTM!

The Do method correctly overrides both Host and URL.Host to ensure requests are routed to the container endpoint. This is the right approach for intercepting and redirecting CosmosDB client requests.


37-44: LGTM!

The ClientOptions method correctly embeds the policy in PerRetryPolicies, ensuring the endpoint override applies to all requests including retries. This provides a clean integration point with the azcosmos client.

modules/azure/cosmosdb/examples_test.go (2)

15-40: Clarify the purpose of the // } comment.

The example demonstrates proper container usage, but line 28 contains a // } comment that appears out of context. If this is a marker for documentation generation (e.g., to truncate code snippets), please add a clarifying comment. Otherwise, consider removing it.


42-85: Clarify the purpose of the // } comment; otherwise LGTM!

This example effectively demonstrates the complete workflow from container startup through database creation. However, line 79 contains the same // } comment as in the previous example. Please clarify its purpose or remove it if it's not needed.

modules/azure/cosmosdb/cosmosdb.go (2)

11-19: LGTM!

The constants and Container type definition follow standard patterns used throughout the testcontainers-go modules. Port 8081/tcp and HTTP protocol are correct defaults for the CosmosDB emulator.


21-46: LGTM!

The Run function follows the established testcontainers-go module pattern. The defaults are sensible for the CosmosDB emulator (exposed port, disabled explorer, appropriate wait strategy), and user options are correctly appended to allow overrides. Error handling is defensive and appropriate.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between f931f2f and e44e880.

⛔ Files ignored due to path filters (1)
  • modules/azure/go.sum is excluded by !**/*.sum
📒 Files selected for processing (3)
  • modules/azure/cosmosdb/cosmosdb.go (1 hunks)
  • modules/azure/cosmosdb/policy.go (1 hunks)
  • modules/azure/go.mod (2 hunks)
🧰 Additional context used
🧠 Learnings (3)
📓 Common learnings
Learnt from: mdelapenya
Repo: testcontainers/testcontainers-go PR: 3254
File: .github/dependabot.yml:21-21
Timestamp: 2025-09-18T08:24:27.479Z
Learning: In the testcontainers-go repository, submodules like atlaslocal that are part of a parent module (e.g., mongodb) share the same go.mod file and should not have separate Dependabot entries. They are already monitored through the parent module's Dependabot configuration entry.
Learnt from: natsoman
Repo: testcontainers/testcontainers-go PR: 3452
File: modules/cosmosdb/cosmosdb.go:11-14
Timestamp: 2025-11-05T11:57:09.216Z
Learning: In the testcontainers-go CosmosDB module (modules/azure/cosmosdb/), the defaultProtocol is intentionally set to "http" (not "https") to avoid requiring users to perform certificate setup steps (downloading and trusting the emulator's self-signed certificate). This design prioritizes ease of use for test containers over strict emulator fidelity.
📚 Learning: 2025-11-05T11:57:09.216Z
Learnt from: natsoman
Repo: testcontainers/testcontainers-go PR: 3452
File: modules/cosmosdb/cosmosdb.go:11-14
Timestamp: 2025-11-05T11:57:09.216Z
Learning: In the testcontainers-go CosmosDB module (modules/azure/cosmosdb/), the defaultProtocol is intentionally set to "http" (not "https") to avoid requiring users to perform certificate setup steps (downloading and trusting the emulator's self-signed certificate). This design prioritizes ease of use for test containers over strict emulator fidelity.

Applied to files:

  • modules/azure/cosmosdb/policy.go
  • modules/azure/cosmosdb/cosmosdb.go
📚 Learning: 2025-09-18T08:24:27.479Z
Learnt from: mdelapenya
Repo: testcontainers/testcontainers-go PR: 3254
File: .github/dependabot.yml:21-21
Timestamp: 2025-09-18T08:24:27.479Z
Learning: In the testcontainers-go repository, submodules like atlaslocal that are part of a parent module (e.g., mongodb) share the same go.mod file and should not have separate Dependabot entries. They are already monitored through the parent module's Dependabot configuration entry.

Applied to files:

  • modules/azure/cosmosdb/cosmosdb.go
🧬 Code graph analysis (2)
modules/azure/cosmosdb/policy.go (1)
modules/azure/cosmosdb/cosmosdb.go (1)
  • Container (19-21)
modules/azure/cosmosdb/cosmosdb.go (4)
options.go (4)
  • ContainerCustomizer (22-24)
  • WithExposedPorts (454-459)
  • WithCmdArgs (470-475)
  • WithWaitStrategy (366-368)
wait/all.go (1)
  • ForAll (46-50)
wait/log.go (1)
  • ForLog (118-120)
wait/host_port.go (1)
  • ForListeningPort (67-69)
🪛 Gitleaks (8.28.0)
modules/azure/cosmosdb/cosmosdb.go

[high] 61-61: Detected a Generic API Key, potentially exposing access to various services and sensitive operations.

(generic-api-key)

🔇 Additional comments (9)
modules/azure/go.mod (1)

8-9: Dependencies look good - previous concern addressed.

The Azure SDK dependencies have been appropriately updated. The azcore version is now v1.19.1 as previously recommended, and the azcosmos v1.4.1 dependency is properly added to support the new CosmosDB module functionality.

modules/azure/cosmosdb/policy.go (4)

13-18: Well-documented policy struct.

The ContainerPolicy struct is clearly documented with its purpose of overriding the CosmosDB client's globalEndpointManager to pin requests to the emulator container endpoint.


20-29: Constructor implementation is correct.

The NewContainerPolicy constructor properly retrieves the container endpoint and handles errors appropriately.


31-36: Request host override correctly implemented.

The Do method properly overrides both req.Raw().Host and req.Raw().URL.Host to ensure all requests target the container endpoint, then forwards the request to the next policy in the chain.


38-45: ClientOptions correctly configured.

The method properly constructs azcosmos.ClientOptions with the ContainerPolicy embedded in PerRetryPolicies, enabling the host override for all requests.

modules/azure/cosmosdb/cosmosdb.go (4)

13-16: Constants appropriately defined.

The defaultPort and defaultProtocol constants are correctly set. The HTTP protocol choice is intentional to simplify test container usage by avoiding certificate setup requirements.

Based on learnings.


18-21: Container struct follows testcontainers pattern.

The Container type correctly wraps testcontainers.Container, following the established pattern in the testcontainers-go repository.


40-50: Container creation and error handling correctly implemented.

The container creation logic properly applies module defaults followed by user options, handles container creation, wraps the result, and provides contextual error messages.


53-63: ConnectionString implementation is correct; static analysis warning is a false positive.

The method correctly constructs the connection string using the container endpoint and the well-known Azure Cosmos DB Emulator key. The static analysis tool flagged line 61 as containing a potential secret, but this is a documented public key specifically published by Microsoft for the emulator and is not a security concern.

@natsoman
Copy link
Contributor Author

natsoman commented Nov 5, 2025

hey @mdelapenya! I addressed CodeRabbit’s comments. Could you please take a look? 😄

mdelapenya
mdelapenya previously approved these changes Nov 5, 2025
Copy link
Member

@mdelapenya mdelapenya left a comment

Choose a reason for hiding this comment

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

I added just a nit comment, but I'm approving this PR as LGTM

Will run the CI and wait for it and for your follow-up, and then merge it.

Thank you so much for your work here 🙇

@mdelapenya
Copy link
Member

BTW, run make lint from the azure module 🙏

@natsoman natsoman requested a review from mdelapenya November 5, 2025 14:45
@mdelapenya mdelapenya self-assigned this Nov 5, 2025
@mdelapenya mdelapenya added the enhancement New feature or request label Nov 5, 2025
@mdelapenya mdelapenya changed the title feat: add cosmosdb module feat(azure): add cosmosdb module Nov 5, 2025
@mdelapenya mdelapenya merged commit f95900f into testcontainers:main Nov 5, 2025
18 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants